| ... | @@ -97,21 +97,20 @@ int main(int argc, char **argv) { | ... | @@ -97,21 +97,20 @@ int main(int argc, char **argv) { |
| 97 | "#include <stdint.h>\n" | 97 | "#include <stdint.h>\n" |
| 98 | "#include <stdlib.h>\n" | 98 | "#include <stdlib.h>\n" |
| 99 | "#include <string.h>\n" | 99 | "#include <string.h>\n" |
| | 100 | "\n" |
| | 101 | "static uint16_t i16_byteswap(uint16_t src) {\n" |
| | 102 | " return (uint16_t)(uint8_t)(src >> 0) << 8 |\n" |
| | 103 | " (uint16_t)(uint8_t)(src >> 8) << 0;\n" |
| | 104 | "}\n" |
| | 105 | "static uint32_t i32_byteswap(uint32_t src) {\n" |
| | 106 | " return (uint32_t)i16_byteswap(src >> 0) << 16 |\n" |
| | 107 | " (uint32_t)i16_byteswap(src >> 16) << 0;\n" |
| | 108 | "}\n" |
| | 109 | "static uint64_t i64_byteswap(uint64_t src) {\n" |
| | 110 | " return (uint64_t)i32_byteswap(src >> 0) << 32 |\n" |
| | 111 | " (uint64_t)i32_byteswap(src >> 32) << 0;\n" |
| | 112 | "}\n" |
| 100 | "\n", out); | 113 | "\n", out); |
| 101 | if (is_big_endian) | | |
| 102 | fputs("static uint16_t i16_byteswap(uint16_t src) {\n" | | |
| 103 | " return (uint16_t)(uint8_t)(src >> 0) << 8 |\n" | | |
| 104 | " (uint16_t)(uint8_t)(src >> 8) << 0;\n" | | |
| 105 | "}\n" | | |
| 106 | "static uint32_t i32_byteswap(uint32_t src) {\n" | | |
| 107 | " return (uint32_t)i16_byteswap(src >> 0) << 16 |\n" | | |
| 108 | " (uint32_t)i16_byteswap(src >> 16) << 0;\n" | | |
| 109 | "}\n" | | |
| 110 | "static uint64_t i64_byteswap(uint64_t src) {\n" | | |
| 111 | " return (uint64_t)i32_byteswap(src >> 0) << 32 |\n" | | |
| 112 | " (uint64_t)i32_byteswap(src >> 32) << 0;\n" | | |
| 113 | "}\n" | | |
| 114 | "\n", out); | | |
| 115 | fputs("static uint16_t load16_align0(const uint8_t *ptr) {\n" | 114 | fputs("static uint16_t load16_align0(const uint8_t *ptr) {\n" |
| 116 | " uint16_t val;\n" | 115 | " uint16_t val;\n" |
| 117 | " memcpy(&val, ptr, sizeof(val));\n", out); | 116 | " memcpy(&val, ptr, sizeof(val));\n", out); |
| ... | @@ -165,6 +164,39 @@ int main(int argc, char **argv) { | ... | @@ -165,6 +164,39 @@ int main(int argc, char **argv) { |
| 165 | " memcpy(&val, ptr, sizeof(val));\n", out); | 164 | " memcpy(&val, ptr, sizeof(val));\n", out); |
| 166 | if (is_big_endian) fputs(" val = i64_byteswap(val);", out); | 165 | if (is_big_endian) fputs(" val = i64_byteswap(val);", out); |
| 167 | fputs(" return val;\n" | 166 | fputs(" return val;\n" |
| | 167 | "}\n" |
| | 168 | "\n" |
| | 169 | "static uint32_t i32_popcnt(uint32_t lhs) {\n" |
| | 170 | " lhs = lhs - ((lhs >> 1) & UINT32_C(0x55555555));\n" |
| | 171 | " lhs = (lhs & UINT32_C(0x33333333)) + ((lhs >> 2) & UINT32_C(0x33333333));\n" |
| | 172 | " lhs = (lhs + (lhs >> 4)) & UINT32_C(0x0F0F0F0F);\n" |
| | 173 | " return (lhs * UINT32_C(0x01010101)) >> 24;\n" |
| | 174 | "}\n" |
| | 175 | "static uint32_t i32_ctz(uint32_t lhs) {\n" |
| | 176 | " return i32_popcnt(~lhs & (lhs - 1));\n" |
| | 177 | "}\n" |
| | 178 | "static uint32_t i32_clz(uint32_t lhs) {\n" |
| | 179 | " lhs = i32_byteswap(lhs);\n" |
| | 180 | " lhs = (lhs & UINT32_C(0x0F0F0F0F)) << 4 | (lhs & UINT32_C(0xF0F0F0F0)) >> 4;\n" |
| | 181 | " lhs = (lhs & UINT32_C(0x33333333)) << 2 | (lhs & UINT32_C(0xCCCCCCCC)) >> 2;\n" |
| | 182 | " lhs = (lhs & UINT32_C(0x55555555)) << 1 | (lhs & UINT32_C(0xAAAAAAAA)) >> 1;\n" |
| | 183 | " return i32_ctz(lhs);\n" |
| | 184 | "}\n" |
| | 185 | "static uint64_t i64_popcnt(uint64_t lhs) {\n" |
| | 186 | " lhs = lhs - ((lhs >> 1) & UINT64_C(0x5555555555555555));\n" |
| | 187 | " lhs = (lhs & UINT64_C(0x3333333333333333)) + ((lhs >> 2) & UINT64_C(0x3333333333333333));\n" |
| | 188 | " lhs = (lhs + (lhs >> 4)) & UINT64_C(0x0F0F0F0F0F0F0F0F);\n" |
| | 189 | " return (lhs * UINT64_C(0x0101010101010101)) >> 56;\n" |
| | 190 | "}\n" |
| | 191 | "static uint64_t i64_ctz(uint64_t lhs) {\n" |
| | 192 | " return i64_popcnt(~lhs & (lhs - 1));\n" |
| | 193 | "}\n" |
| | 194 | "static uint64_t i64_clz(uint64_t lhs) {\n" |
| | 195 | " lhs = i64_byteswap(lhs);\n" |
| | 196 | " lhs = (lhs & UINT64_C(0x0F0F0F0F0F0F0F0F)) << 4 | (lhs & UINT32_C(0xF0F0F0F0F0F0F0F0)) >> 4;\n" |
| | 197 | " lhs = (lhs & UINT64_C(0x3333333333333333)) << 2 | (lhs & UINT32_C(0xCCCCCCCCCCCCCCCC)) >> 2;\n" |
| | 198 | " lhs = (lhs & UINT64_C(0x5555555555555555)) << 1 | (lhs & UINT32_C(0xAAAAAAAAAAAAAAAA)) >> 1;\n" |
| | 199 | " return i64_ctz(lhs);\n" |
| 168 | "}\n" | 200 | "}\n" |
| 169 | "\n" | 201 | "\n" |
| 170 | "static void store16_align0(uint8_t *ptr, uint16_t val) {\n", out); | 202 | "static void store16_align0(uint8_t *ptr, uint16_t val) {\n", out); |
| ... | @@ -787,6 +819,7 @@ int main(int argc, char **argv) { | ... | @@ -787,6 +819,7 @@ int main(int argc, char **argv) { |
| 787 | } else unreachable_depth -= 1; | 819 | } else unreachable_depth -= 1; |
| 788 | switch (opcode) { | 820 | switch (opcode) { |
| 789 | case WasmOpcode_else: | 821 | case WasmOpcode_else: |
| | 822 | FuncGen_reuseReset(&fg); |
| 790 | FuncGen_outdent(&fg, out); | 823 | FuncGen_outdent(&fg, out); |
| 791 | fputs("} else {\n", out); | 824 | fputs("} else {\n", out); |
| 792 | break; | 825 | break; |
| ... | @@ -968,10 +1001,10 @@ int main(int argc, char **argv) { | ... | @@ -968,10 +1001,10 @@ int main(int argc, char **argv) { |
| 968 | if (unreachable_depth == 0) { | 1001 | if (unreachable_depth == 0) { |
| 969 | uint32_t cond = FuncGen_stackPop(&fg); | 1002 | uint32_t cond = FuncGen_stackPop(&fg); |
| 970 | uint32_t rhs = FuncGen_stackPop(&fg); | 1003 | uint32_t rhs = FuncGen_stackPop(&fg); |
| 971 | uint32_t lhs = FuncGen_stackPop(&fg); | 1004 | uint32_t lhs = FuncGen_stackAt(&fg, 0); |
| 972 | FuncGen_stackPush(&fg, out, FuncGen_localType(&fg, lhs)); | 1005 | FuncGen_indent(&fg, out); |
| 973 | fprintf(out, "l%" PRIu32 " ? l%" PRIu32 " : l%" PRIu32 ";\n", | 1006 | fprintf(out, "l%"PRIu32" = l%" PRIu32 " ? l%" PRIu32 " : l%" PRIu32 ";\n", |
| 974 | cond, lhs, rhs); | 1007 | lhs, cond, lhs, rhs); |
| 975 | } | 1008 | } |
| 976 | break; | 1009 | break; |
| 977 | | 1010 | |
| ... | @@ -1369,89 +1402,55 @@ int main(int argc, char **argv) { | ... | @@ -1369,89 +1402,55 @@ int main(int argc, char **argv) { |
| 1369 | | 1402 | |
| 1370 | case WasmOpcode_i32_eqz: | 1403 | case WasmOpcode_i32_eqz: |
| 1371 | if (unreachable_depth == 0) { | 1404 | if (unreachable_depth == 0) { |
| 1372 | uint32_t lhs = FuncGen_stackPop(&fg); | 1405 | uint32_t lhs = FuncGen_stackAt(&fg, 0); |
| 1373 | FuncGen_stackPush(&fg, out, WasmValType_i32); | 1406 | FuncGen_indent(&fg, out); |
| 1374 | fprintf(out, "!l%" PRIu32 ";\n", lhs); | 1407 | fprintf(out, "l%" PRIu32 " = !l%" PRIu32 ";\n", lhs, lhs); |
| 1375 | } | 1408 | } |
| 1376 | break; | 1409 | break; |
| 1377 | case WasmOpcode_i32_eq: | 1410 | case WasmOpcode_i32_eq: |
| 1378 | if (unreachable_depth == 0) { | | |
| 1379 | uint32_t rhs = FuncGen_stackPop(&fg); | | |
| 1380 | uint32_t lhs = FuncGen_stackPop(&fg); | | |
| 1381 | FuncGen_stackPush(&fg, out, WasmValType_i32); | | |
| 1382 | fprintf(out, "l%" PRIu32 " == l%" PRIu32 ";\n", lhs, rhs); | | |
| 1383 | } | | |
| 1384 | break; | | |
| 1385 | case WasmOpcode_i32_ne: | 1411 | case WasmOpcode_i32_ne: |
| 1386 | if (unreachable_depth == 0) { | | |
| 1387 | uint32_t rhs = FuncGen_stackPop(&fg); | | |
| 1388 | uint32_t lhs = FuncGen_stackPop(&fg); | | |
| 1389 | FuncGen_stackPush(&fg, out, WasmValType_i32); | | |
| 1390 | fprintf(out, "l%" PRIu32 " != l%" PRIu32 ";\n", lhs, rhs); | | |
| 1391 | } | | |
| 1392 | break; | | |
| 1393 | case WasmOpcode_i32_lt_s: | | |
| 1394 | if (unreachable_depth == 0) { | | |
| 1395 | uint32_t rhs = FuncGen_stackPop(&fg); | | |
| 1396 | uint32_t lhs = FuncGen_stackPop(&fg); | | |
| 1397 | FuncGen_stackPush(&fg, out, WasmValType_i32); | | |
| 1398 | fprintf(out, "(int32_t)l%" PRIu32 " < (int32_t)l%" PRIu32 ";\n", lhs, rhs); | | |
| 1399 | } | | |
| 1400 | break; | | |
| 1401 | case WasmOpcode_i32_lt_u: | 1412 | case WasmOpcode_i32_lt_u: |
| 1402 | if (unreachable_depth == 0) { | | |
| 1403 | uint32_t rhs = FuncGen_stackPop(&fg); | | |
| 1404 | uint32_t lhs = FuncGen_stackPop(&fg); | | |
| 1405 | FuncGen_stackPush(&fg, out, WasmValType_i32); | | |
| 1406 | fprintf(out, "l%" PRIu32 " < l%" PRIu32 ";\n", lhs, rhs); | | |
| 1407 | } | | |
| 1408 | break; | | |
| 1409 | case WasmOpcode_i32_gt_s: | | |
| 1410 | if (unreachable_depth == 0) { | | |
| 1411 | uint32_t rhs = FuncGen_stackPop(&fg); | | |
| 1412 | uint32_t lhs = FuncGen_stackPop(&fg); | | |
| 1413 | FuncGen_stackPush(&fg, out, WasmValType_i32); | | |
| 1414 | fprintf(out, "(int32_t)l%" PRIu32 " > (int32_t)l%" PRIu32 ";\n", lhs, rhs); | | |
| 1415 | } | | |
| 1416 | break; | | |
| 1417 | case WasmOpcode_i32_gt_u: | 1413 | case WasmOpcode_i32_gt_u: |
| 1418 | if (unreachable_depth == 0) { | | |
| 1419 | uint32_t rhs = FuncGen_stackPop(&fg); | | |
| 1420 | uint32_t lhs = FuncGen_stackPop(&fg); | | |
| 1421 | FuncGen_stackPush(&fg, out, WasmValType_i32); | | |
| 1422 | fprintf(out, "l%" PRIu32 " > l%" PRIu32 ";\n", lhs, rhs); | | |
| 1423 | } | | |
| 1424 | break; | | |
| 1425 | case WasmOpcode_i32_le_s: | | |
| 1426 | if (unreachable_depth == 0) { | | |
| 1427 | uint32_t rhs = FuncGen_stackPop(&fg); | | |
| 1428 | uint32_t lhs = FuncGen_stackPop(&fg); | | |
| 1429 | FuncGen_stackPush(&fg, out, WasmValType_i32); | | |
| 1430 | fprintf(out, "(int32_t)l%" PRIu32 " <= (int32_t)l%" PRIu32 ";\n", lhs, rhs); | | |
| 1431 | } | | |
| 1432 | break; | | |
| 1433 | case WasmOpcode_i32_le_u: | 1414 | case WasmOpcode_i32_le_u: |
| | 1415 | case WasmOpcode_i32_ge_u: |
| | 1416 | // i32 unsigned comparisons |
| 1434 | if (unreachable_depth == 0) { | 1417 | if (unreachable_depth == 0) { |
| 1435 | uint32_t rhs = FuncGen_stackPop(&fg); | 1418 | uint32_t rhs = FuncGen_stackPop(&fg); |
| 1436 | uint32_t lhs = FuncGen_stackPop(&fg); | 1419 | uint32_t lhs = FuncGen_stackAt(&fg, 0); |
| 1437 | FuncGen_stackPush(&fg, out, WasmValType_i32); | 1420 | const char *operator; |
| 1438 | fprintf(out, "l%" PRIu32 " <= l%" PRIu32 ";\n", lhs, rhs); | 1421 | switch (opcode) { |
| | 1422 | case WasmOpcode_i32_eq: operator = "=="; break; |
| | 1423 | case WasmOpcode_i32_ne: operator = "!="; break; |
| | 1424 | case WasmOpcode_i32_lt_u: operator = "<"; break; |
| | 1425 | case WasmOpcode_i32_gt_u: operator = ">"; break; |
| | 1426 | case WasmOpcode_i32_le_u: operator = "<="; break; |
| | 1427 | case WasmOpcode_i32_ge_u: operator = ">="; break; |
| | 1428 | default: panic("unreachable"); |
| | 1429 | } |
| | 1430 | FuncGen_indent(&fg, out); |
| | 1431 | fprintf(out, "l%" PRIu32 " = l%" PRIu32 " %s l%" PRIu32 ";\n", |
| | 1432 | lhs, lhs, operator, rhs); |
| 1439 | } | 1433 | } |
| 1440 | break; | 1434 | break; |
| | 1435 | case WasmOpcode_i32_lt_s: |
| | 1436 | case WasmOpcode_i32_gt_s: |
| | 1437 | case WasmOpcode_i32_le_s: |
| 1441 | case WasmOpcode_i32_ge_s: | 1438 | case WasmOpcode_i32_ge_s: |
| | 1439 | // i32 signed comparisons |
| 1442 | if (unreachable_depth == 0) { | 1440 | if (unreachable_depth == 0) { |
| 1443 | uint32_t rhs = FuncGen_stackPop(&fg); | 1441 | uint32_t rhs = FuncGen_stackPop(&fg); |
| 1444 | uint32_t lhs = FuncGen_stackPop(&fg); | 1442 | uint32_t lhs = FuncGen_stackAt(&fg, 0); |
| 1445 | FuncGen_stackPush(&fg, out, WasmValType_i32); | 1443 | const char *operator; |
| 1446 | fprintf(out, "(int32_t)l%" PRIu32 " >= (int32_t)l%" PRIu32 ";\n", lhs, rhs); | 1444 | switch (opcode) { |
| 1447 | } | 1445 | case WasmOpcode_i32_lt_s: operator = "<"; break; |
| 1448 | break; | 1446 | case WasmOpcode_i32_gt_s: operator = ">"; break; |
| 1449 | case WasmOpcode_i32_ge_u: | 1447 | case WasmOpcode_i32_le_s: operator = "<="; break; |
| 1450 | if (unreachable_depth == 0) { | 1448 | case WasmOpcode_i32_ge_s: operator = ">="; break; |
| 1451 | uint32_t rhs = FuncGen_stackPop(&fg); | 1449 | default: panic("unreachable"); |
| 1452 | uint32_t lhs = FuncGen_stackPop(&fg); | 1450 | } |
| 1453 | FuncGen_stackPush(&fg, out, WasmValType_i32); | 1451 | FuncGen_indent(&fg, out); |
| 1454 | fprintf(out, "l%" PRIu32 " >= l%" PRIu32 ";\n", lhs, rhs); | 1452 | fprintf(out, "l%" PRIu32 " = (int32_t)l%" PRIu32 " %s (int32_t)l%" PRIu32 |
| | 1453 | ";\n", lhs, lhs, operator, rhs); |
| 1455 | } | 1454 | } |
| 1456 | break; | 1455 | break; |
| 1457 | | 1456 | |
| ... | @@ -1463,685 +1462,385 @@ int main(int argc, char **argv) { | ... | @@ -1463,685 +1462,385 @@ int main(int argc, char **argv) { |
| 1463 | } | 1462 | } |
| 1464 | break; | 1463 | break; |
| 1465 | case WasmOpcode_i64_eq: | 1464 | case WasmOpcode_i64_eq: |
| 1466 | if (unreachable_depth == 0) { | | |
| 1467 | uint32_t rhs = FuncGen_stackPop(&fg); | | |
| 1468 | uint32_t lhs = FuncGen_stackPop(&fg); | | |
| 1469 | FuncGen_stackPush(&fg, out, WasmValType_i32); | | |
| 1470 | fprintf(out, "l%" PRIu32 " == l%" PRIu32 ";\n", lhs, rhs); | | |
| 1471 | } | | |
| 1472 | break; | | |
| 1473 | case WasmOpcode_i64_ne: | 1465 | case WasmOpcode_i64_ne: |
| | 1466 | case WasmOpcode_i64_lt_u: |
| | 1467 | case WasmOpcode_i64_gt_u: |
| | 1468 | case WasmOpcode_i64_le_u: |
| | 1469 | case WasmOpcode_i64_ge_u: |
| | 1470 | case WasmOpcode_f32_eq: |
| | 1471 | case WasmOpcode_f32_ne: |
| | 1472 | case WasmOpcode_f32_lt: |
| | 1473 | case WasmOpcode_f32_gt: |
| | 1474 | case WasmOpcode_f32_le: |
| | 1475 | case WasmOpcode_f32_ge: |
| | 1476 | case WasmOpcode_f64_eq: |
| | 1477 | case WasmOpcode_f64_ne: |
| | 1478 | case WasmOpcode_f64_lt: |
| | 1479 | case WasmOpcode_f64_gt: |
| | 1480 | case WasmOpcode_f64_le: |
| | 1481 | case WasmOpcode_f64_ge: |
| | 1482 | // non-i32 unsigned comparisons |
| 1474 | if (unreachable_depth == 0) { | 1483 | if (unreachable_depth == 0) { |
| 1475 | uint32_t rhs = FuncGen_stackPop(&fg); | 1484 | uint32_t rhs = FuncGen_stackPop(&fg); |
| 1476 | uint32_t lhs = FuncGen_stackPop(&fg); | 1485 | uint32_t lhs = FuncGen_stackPop(&fg); |
| | 1486 | const char *operator; |
| | 1487 | switch (opcode) { |
| | 1488 | case WasmOpcode_i64_eq: |
| | 1489 | case WasmOpcode_f32_eq: |
| | 1490 | case WasmOpcode_f64_eq: |
| | 1491 | operator = "=="; |
| | 1492 | break; |
| | 1493 | case WasmOpcode_i64_ne: |
| | 1494 | case WasmOpcode_f32_ne: |
| | 1495 | case WasmOpcode_f64_ne: |
| | 1496 | operator = "!="; |
| | 1497 | break; |
| | 1498 | case WasmOpcode_i64_lt_u: |
| | 1499 | case WasmOpcode_f32_lt: |
| | 1500 | case WasmOpcode_f64_lt: |
| | 1501 | operator = "<"; |
| | 1502 | break; |
| | 1503 | case WasmOpcode_i64_gt_u: |
| | 1504 | case WasmOpcode_f32_gt: |
| | 1505 | case WasmOpcode_f64_gt: |
| | 1506 | operator = ">"; |
| | 1507 | break; |
| | 1508 | case WasmOpcode_i64_le_u: |
| | 1509 | case WasmOpcode_f32_le: |
| | 1510 | case WasmOpcode_f64_le: |
| | 1511 | operator = "<="; |
| | 1512 | break; |
| | 1513 | case WasmOpcode_i64_ge_u: |
| | 1514 | case WasmOpcode_f32_ge: |
| | 1515 | case WasmOpcode_f64_ge: |
| | 1516 | operator = ">="; |
| | 1517 | break; |
| | 1518 | default: panic("unreachable"); |
| | 1519 | } |
| 1477 | FuncGen_stackPush(&fg, out, WasmValType_i32); | 1520 | FuncGen_stackPush(&fg, out, WasmValType_i32); |
| 1478 | fprintf(out, "l%" PRIu32 " != l%" PRIu32 ";\n", lhs, rhs); | 1521 | fprintf(out, "l%" PRIu32 " = l%" PRIu32 " %s l%" PRIu32 ";\n", |
| | 1522 | lhs, lhs, operator, rhs); |
| 1479 | } | 1523 | } |
| 1480 | break; | 1524 | break; |
| 1481 | case WasmOpcode_i64_lt_s: | 1525 | case WasmOpcode_i64_lt_s: |
| | 1526 | case WasmOpcode_i64_gt_s: |
| | 1527 | case WasmOpcode_i64_le_s: |
| | 1528 | case WasmOpcode_i64_ge_s: |
| | 1529 | // i64 signed comparisons |
| 1482 | if (unreachable_depth == 0) { | 1530 | if (unreachable_depth == 0) { |
| 1483 | uint32_t rhs = FuncGen_stackPop(&fg); | 1531 | uint32_t rhs = FuncGen_stackPop(&fg); |
| 1484 | uint32_t lhs = FuncGen_stackPop(&fg); | 1532 | uint32_t lhs = FuncGen_stackPop(&fg); |
| | 1533 | const char *operator; |
| | 1534 | switch (opcode) { |
| | 1535 | case WasmOpcode_i64_lt_s: operator = "<"; break; |
| | 1536 | case WasmOpcode_i64_gt_s: operator = ">"; break; |
| | 1537 | case WasmOpcode_i64_le_s: operator = "<="; break; |
| | 1538 | case WasmOpcode_i64_ge_s: operator = ">="; break; |
| | 1539 | default: panic("unreachable"); |
| | 1540 | } |
| 1485 | FuncGen_stackPush(&fg, out, WasmValType_i32); | 1541 | FuncGen_stackPush(&fg, out, WasmValType_i32); |
| 1486 | fprintf(out, "(int64_t)l%" PRIu32 " < (int64_t)l%" PRIu32 ";\n", lhs, rhs); | 1542 | fprintf(out, "l%" PRIu32 " = (int64_t)l%" PRIu32 " %s (int64_t)l%" PRIu32 |
| | 1543 | ";\n", lhs, lhs, operator, rhs); |
| 1487 | } | 1544 | } |
| 1488 | break; | 1545 | break; |
| 1489 | case WasmOpcode_i64_lt_u: | 1546 | |
| | 1547 | case WasmOpcode_i32_clz: |
| | 1548 | case WasmOpcode_i32_ctz: |
| | 1549 | case WasmOpcode_i32_popcnt: |
| | 1550 | case WasmOpcode_i64_clz: |
| | 1551 | case WasmOpcode_i64_ctz: |
| | 1552 | case WasmOpcode_i64_popcnt: |
| | 1553 | case WasmOpcode_f32_abs: |
| | 1554 | case WasmOpcode_f32_neg: |
| | 1555 | case WasmOpcode_f32_ceil: |
| | 1556 | case WasmOpcode_f32_floor: |
| | 1557 | case WasmOpcode_f32_trunc: |
| | 1558 | case WasmOpcode_f32_nearest: |
| | 1559 | case WasmOpcode_f32_sqrt: |
| | 1560 | case WasmOpcode_f64_abs: |
| | 1561 | case WasmOpcode_f64_neg: |
| | 1562 | case WasmOpcode_f64_ceil: |
| | 1563 | case WasmOpcode_f64_floor: |
| | 1564 | case WasmOpcode_f64_trunc: |
| | 1565 | case WasmOpcode_f64_nearest: |
| | 1566 | case WasmOpcode_f64_sqrt: |
| | 1567 | // unary functions |
| 1490 | if (unreachable_depth == 0) { | 1568 | if (unreachable_depth == 0) { |
| 1491 | uint32_t rhs = FuncGen_stackPop(&fg); | 1569 | uint32_t lhs = FuncGen_stackAt(&fg, 0); |
| 1492 | uint32_t lhs = FuncGen_stackPop(&fg); | 1570 | const char *function; |
| 1493 | FuncGen_stackPush(&fg, out, WasmValType_i32); | 1571 | switch (opcode) { |
| 1494 | fprintf(out, "l%" PRIu32 " < l%" PRIu32 ";\n", lhs, rhs); | 1572 | case WasmOpcode_i32_clz: function = "i32_clz"; break; |
| | 1573 | case WasmOpcode_i32_ctz: function = "i32_ctz"; break; |
| | 1574 | case WasmOpcode_i32_popcnt: function = "i32_popcnt"; break; |
| | 1575 | case WasmOpcode_i64_clz: function = "i64_clz"; break; |
| | 1576 | case WasmOpcode_i64_ctz: function = "i64_ctz"; break; |
| | 1577 | case WasmOpcode_i64_popcnt: function = "i64_popcnt"; break; |
| | 1578 | case WasmOpcode_f32_abs: function = "fabsf"; break; |
| | 1579 | case WasmOpcode_f32_neg: |
| | 1580 | case WasmOpcode_f64_neg: function = "-"; break; |
| | 1581 | case WasmOpcode_f32_ceil: function = "ceilf"; break; |
| | 1582 | case WasmOpcode_f32_floor: function = "floorf"; break; |
| | 1583 | case WasmOpcode_f32_trunc: function = "truncf"; break; |
| | 1584 | case WasmOpcode_f32_nearest: function = "roundf"; break; |
| | 1585 | case WasmOpcode_f32_sqrt: function = "sqrtf"; break; |
| | 1586 | case WasmOpcode_f64_abs: function = "fabs"; break; |
| | 1587 | case WasmOpcode_f64_ceil: function = "ceil"; break; |
| | 1588 | case WasmOpcode_f64_floor: function = "floor"; break; |
| | 1589 | case WasmOpcode_f64_trunc: function = "trunc"; break; |
| | 1590 | case WasmOpcode_f64_nearest: function = "round"; break; |
| | 1591 | case WasmOpcode_f64_sqrt: function = "sqrt"; break; |
| | 1592 | default: panic("unreachable"); |
| | 1593 | } |
| | 1594 | FuncGen_indent(&fg, out); |
| | 1595 | fprintf(out, "l%" PRIu32 " = %s(l%" PRIu32 ");\n", lhs, function, lhs); |
| 1495 | } | 1596 | } |
| 1496 | break; | 1597 | break; |
| 1497 | case WasmOpcode_i64_gt_s: | 1598 | case WasmOpcode_i32_add: |
| | 1599 | case WasmOpcode_i32_sub: |
| | 1600 | case WasmOpcode_i32_mul: |
| | 1601 | case WasmOpcode_i32_div_u: |
| | 1602 | case WasmOpcode_i32_rem_u: |
| | 1603 | case WasmOpcode_i32_and: |
| | 1604 | case WasmOpcode_i32_or: |
| | 1605 | case WasmOpcode_i32_xor: |
| | 1606 | case WasmOpcode_i64_add: |
| | 1607 | case WasmOpcode_i64_sub: |
| | 1608 | case WasmOpcode_i64_mul: |
| | 1609 | case WasmOpcode_i64_div_u: |
| | 1610 | case WasmOpcode_i64_rem_u: |
| | 1611 | case WasmOpcode_i64_and: |
| | 1612 | case WasmOpcode_i64_or: |
| | 1613 | case WasmOpcode_i64_xor: |
| | 1614 | case WasmOpcode_f32_add: |
| | 1615 | case WasmOpcode_f32_sub: |
| | 1616 | case WasmOpcode_f32_mul: |
| | 1617 | case WasmOpcode_f32_div: |
| | 1618 | case WasmOpcode_f64_add: |
| | 1619 | case WasmOpcode_f64_sub: |
| | 1620 | case WasmOpcode_f64_mul: |
| | 1621 | case WasmOpcode_f64_div: |
| | 1622 | // unsigned binary operators |
| 1498 | if (unreachable_depth == 0) { | 1623 | if (unreachable_depth == 0) { |
| 1499 | uint32_t rhs = FuncGen_stackPop(&fg); | 1624 | uint32_t rhs = FuncGen_stackPop(&fg); |
| 1500 | uint32_t lhs = FuncGen_stackPop(&fg); | 1625 | uint32_t lhs = FuncGen_stackAt(&fg, 0); |
| 1501 | FuncGen_stackPush(&fg, out, WasmValType_i32); | 1626 | char operator; |
| 1502 | fprintf(out, "(int64_t)l%" PRIu32 " > (int64_t)l%" PRIu32 ";\n", lhs, rhs); | 1627 | switch (opcode) { |
| | 1628 | case WasmOpcode_i32_add: |
| | 1629 | case WasmOpcode_i64_add: |
| | 1630 | case WasmOpcode_f32_add: |
| | 1631 | case WasmOpcode_f64_add: |
| | 1632 | operator = '+'; |
| | 1633 | break; |
| | 1634 | case WasmOpcode_i32_sub: |
| | 1635 | case WasmOpcode_i64_sub: |
| | 1636 | case WasmOpcode_f32_sub: |
| | 1637 | case WasmOpcode_f64_sub: |
| | 1638 | operator = '-'; |
| | 1639 | break; |
| | 1640 | case WasmOpcode_i32_mul: |
| | 1641 | case WasmOpcode_i64_mul: |
| | 1642 | case WasmOpcode_f32_mul: |
| | 1643 | case WasmOpcode_f64_mul: |
| | 1644 | operator = '*'; |
| | 1645 | break; |
| | 1646 | case WasmOpcode_i32_div_u: |
| | 1647 | case WasmOpcode_i64_div_u: |
| | 1648 | case WasmOpcode_f32_div: |
| | 1649 | case WasmOpcode_f64_div: |
| | 1650 | operator = '/'; |
| | 1651 | break; |
| | 1652 | case WasmOpcode_i32_rem_u: |
| | 1653 | case WasmOpcode_i64_rem_u: |
| | 1654 | operator = '%'; |
| | 1655 | break; |
| | 1656 | case WasmOpcode_i32_and: |
| | 1657 | case WasmOpcode_i64_and: |
| | 1658 | operator = '&'; |
| | 1659 | break; |
| | 1660 | case WasmOpcode_i32_or: |
| | 1661 | case WasmOpcode_i64_or: |
| | 1662 | operator = '|'; |
| | 1663 | break; |
| | 1664 | case WasmOpcode_i32_xor: |
| | 1665 | case WasmOpcode_i64_xor: |
| | 1666 | operator = '^'; |
| | 1667 | break; |
| | 1668 | default: panic("unreachable"); |
| | 1669 | } |
| | 1670 | FuncGen_indent(&fg, out); |
| | 1671 | fprintf(out, "l%" PRIu32 " %c= l%" PRIu32 ";\n", lhs, operator, rhs); |
| 1503 | } | 1672 | } |
| 1504 | break; | 1673 | break; |
| 1505 | case WasmOpcode_i64_gt_u: | 1674 | case WasmOpcode_i32_div_s: |
| | 1675 | case WasmOpcode_i32_rem_s: |
| | 1676 | case WasmOpcode_i64_div_s: |
| | 1677 | case WasmOpcode_i64_rem_s: |
| | 1678 | // signed binary operators |
| 1506 | if (unreachable_depth == 0) { | 1679 | if (unreachable_depth == 0) { |
| 1507 | uint32_t rhs = FuncGen_stackPop(&fg); | 1680 | uint32_t rhs = FuncGen_stackPop(&fg); |
| 1508 | uint32_t lhs = FuncGen_stackPop(&fg); | 1681 | uint32_t lhs = FuncGen_stackAt(&fg, 0); |
| 1509 | FuncGen_stackPush(&fg, out, WasmValType_i32); | 1682 | char operator; |
| 1510 | fprintf(out, "l%" PRIu32 " > l%" PRIu32 ";\n", lhs, rhs); | 1683 | unsigned width; |
| | 1684 | switch (opcode) { |
| | 1685 | case WasmOpcode_i32_div_s: |
| | 1686 | case WasmOpcode_i64_div_s: |
| | 1687 | operator = '/'; |
| | 1688 | break; |
| | 1689 | case WasmOpcode_i32_rem_s: |
| | 1690 | case WasmOpcode_i64_rem_s: |
| | 1691 | operator = '%'; |
| | 1692 | break; |
| | 1693 | default: panic("unreachable"); |
| | 1694 | } |
| | 1695 | switch (opcode) { |
| | 1696 | case WasmOpcode_i32_div_s: |
| | 1697 | case WasmOpcode_i32_rem_s: |
| | 1698 | width = 32; |
| | 1699 | break; |
| | 1700 | case WasmOpcode_i64_div_s: |
| | 1701 | case WasmOpcode_i64_rem_s: |
| | 1702 | width = 64; |
| | 1703 | break; |
| | 1704 | default: panic("unreachable"); |
| | 1705 | } |
| | 1706 | FuncGen_indent(&fg, out); |
| | 1707 | fprintf(out, "l%" PRIu32 " = (uint%u_t)((int%u_t)l%" PRIu32 " %c " |
| | 1708 | "(int%u_t)l%" PRIu32 ");\n", |
| | 1709 | lhs, width, width, lhs, operator, width, rhs); |
| 1511 | } | 1710 | } |
| 1512 | break; | 1711 | break; |
| 1513 | case WasmOpcode_i64_le_s: | 1712 | case WasmOpcode_i32_shl: |
| | 1713 | case WasmOpcode_i32_shr_u: |
| | 1714 | case WasmOpcode_i64_shl: |
| | 1715 | case WasmOpcode_i64_shr_u: |
| | 1716 | // unsigned shift operators |
| 1514 | if (unreachable_depth == 0) { | 1717 | if (unreachable_depth == 0) { |
| 1515 | uint32_t rhs = FuncGen_stackPop(&fg); | 1718 | uint32_t rhs = FuncGen_stackPop(&fg); |
| 1516 | uint32_t lhs = FuncGen_stackPop(&fg); | 1719 | uint32_t lhs = FuncGen_stackAt(&fg, 0); |
| 1517 | FuncGen_stackPush(&fg, out, WasmValType_i32); | 1720 | char operator; |
| 1518 | fprintf(out, "(int64_t)l%" PRIu32 " <= (int64_t)l%" PRIu32 ";\n", lhs, rhs); | 1721 | unsigned width; |
| | 1722 | switch (opcode) { |
| | 1723 | case WasmOpcode_i32_shl: |
| | 1724 | case WasmOpcode_i64_shl: |
| | 1725 | operator = '<'; |
| | 1726 | break; |
| | 1727 | case WasmOpcode_i32_shr_u: |
| | 1728 | case WasmOpcode_i64_shr_u: |
| | 1729 | operator = '>'; |
| | 1730 | break; |
| | 1731 | default: panic("unreachable"); |
| | 1732 | } |
| | 1733 | switch (opcode) { |
| | 1734 | case WasmOpcode_i32_shl: |
| | 1735 | case WasmOpcode_i32_shr_u: |
| | 1736 | width = 32; |
| | 1737 | break; |
| | 1738 | case WasmOpcode_i64_shl: |
| | 1739 | case WasmOpcode_i64_shr_u: |
| | 1740 | width = 64; |
| | 1741 | break; |
| | 1742 | default: panic("unreachable"); |
| | 1743 | } |
| | 1744 | FuncGen_indent(&fg, out); |
| | 1745 | fprintf(out, "l%" PRIu32 " %c%c= l%" PRIu32 " & 0x%X;\n", |
| | 1746 | lhs, operator, operator, rhs, width - 1); |
| 1519 | } | 1747 | } |
| 1520 | break; | 1748 | break; |
| 1521 | case WasmOpcode_i64_le_u: | 1749 | case WasmOpcode_i32_shr_s: |
| | 1750 | case WasmOpcode_i64_shr_s: |
| | 1751 | // signed shift operators |
| 1522 | if (unreachable_depth == 0) { | 1752 | if (unreachable_depth == 0) { |
| 1523 | uint32_t rhs = FuncGen_stackPop(&fg); | 1753 | uint32_t rhs = FuncGen_stackPop(&fg); |
| 1524 | uint32_t lhs = FuncGen_stackPop(&fg); | 1754 | uint32_t lhs = FuncGen_stackAt(&fg, 0); |
| 1525 | FuncGen_stackPush(&fg, out, WasmValType_i32); | 1755 | char operator; |
| 1526 | fprintf(out, "l%" PRIu32 " <= l%" PRIu32 ";\n", lhs, rhs); | 1756 | unsigned width; |
| | 1757 | switch (opcode) { |
| | 1758 | case WasmOpcode_i32_shr_s: |
| | 1759 | case WasmOpcode_i64_shr_s: |
| | 1760 | operator = '>'; |
| | 1761 | break; |
| | 1762 | default: panic("unreachable"); |
| | 1763 | } |
| | 1764 | switch (opcode) { |
| | 1765 | case WasmOpcode_i32_shr_s: |
| | 1766 | width = 32; |
| | 1767 | break; |
| | 1768 | case WasmOpcode_i64_shr_s: |
| | 1769 | width = 64; |
| | 1770 | break; |
| | 1771 | default: panic("unreachable"); |
| | 1772 | } |
| | 1773 | FuncGen_indent(&fg, out); |
| | 1774 | fprintf(out, "l%" PRIu32 " = (uint%u_t)((int%u_t)l%" PRIu32 " %c%c " |
| | 1775 | "(l%" PRIu32 " & 0x%X));\n", |
| | 1776 | lhs, width, width, lhs, operator, operator, rhs, width - 1); |
| 1527 | } | 1777 | } |
| 1528 | break; | 1778 | break; |
| 1529 | case WasmOpcode_i64_ge_s: | 1779 | case WasmOpcode_i32_rotl: |
| | 1780 | case WasmOpcode_i32_rotr: |
| | 1781 | case WasmOpcode_i64_rotl: |
| | 1782 | case WasmOpcode_i64_rotr: |
| | 1783 | // rotate operators |
| 1530 | if (unreachable_depth == 0) { | 1784 | if (unreachable_depth == 0) { |
| 1531 | uint32_t rhs = FuncGen_stackPop(&fg); | 1785 | uint32_t rhs = FuncGen_stackPop(&fg); |
| 1532 | uint32_t lhs = FuncGen_stackPop(&fg); | 1786 | uint32_t lhs = FuncGen_stackAt(&fg, 0); |
| 1533 | FuncGen_stackPush(&fg, out, WasmValType_i32); | 1787 | char forward_operator; |
| 1534 | fprintf(out, "(int64_t)l%" PRIu32 " >= (int64_t)l%" PRIu32 ";\n", lhs, rhs); | 1788 | char reverse_operator; |
| | 1789 | unsigned width; |
| | 1790 | switch (opcode) { |
| | 1791 | case WasmOpcode_i32_rotl: |
| | 1792 | case WasmOpcode_i64_rotl: |
| | 1793 | forward_operator = '<'; |
| | 1794 | reverse_operator = '>'; |
| | 1795 | break; |
| | 1796 | case WasmOpcode_i32_rotr: |
| | 1797 | case WasmOpcode_i64_rotr: |
| | 1798 | forward_operator = '>'; |
| | 1799 | reverse_operator = '<'; |
| | 1800 | break; |
| | 1801 | default: panic("unreachable"); |
| | 1802 | } |
| | 1803 | switch (opcode) { |
| | 1804 | case WasmOpcode_i32_rotl: |
| | 1805 | case WasmOpcode_i32_rotr: |
| | 1806 | width = 32; |
| | 1807 | break; |
| | 1808 | case WasmOpcode_i64_rotl: |
| | 1809 | case WasmOpcode_i64_rotr: |
| | 1810 | width = 64; |
| | 1811 | break; |
| | 1812 | default: panic("unreachable"); |
| | 1813 | } |
| | 1814 | FuncGen_indent(&fg, out); |
| | 1815 | fprintf(out, "l%" PRIu32" = l%" PRIu32 " %c%c (l%" PRIu32 " & 0x%X) | " |
| | 1816 | "l%" PRIu32 " %c%c (-l%" PRIu32" & 0x%X);\n", lhs, |
| | 1817 | lhs, forward_operator, forward_operator, rhs, width - 1, |
| | 1818 | lhs, reverse_operator, reverse_operator, rhs, width - 1); |
| 1535 | } | 1819 | } |
| 1536 | break; | 1820 | break; |
| 1537 | case WasmOpcode_i64_ge_u: | 1821 | case WasmOpcode_f32_min: |
| | 1822 | case WasmOpcode_f32_max: |
| | 1823 | case WasmOpcode_f32_copysign: |
| | 1824 | case WasmOpcode_f64_min: |
| | 1825 | case WasmOpcode_f64_max: |
| | 1826 | case WasmOpcode_f64_copysign: |
| | 1827 | // binary functions |
| 1538 | if (unreachable_depth == 0) { | 1828 | if (unreachable_depth == 0) { |
| 1539 | uint32_t rhs = FuncGen_stackPop(&fg); | 1829 | uint32_t rhs = FuncGen_stackPop(&fg); |
| 1540 | uint32_t lhs = FuncGen_stackPop(&fg); | 1830 | uint32_t lhs = FuncGen_stackAt(&fg, 0); |
| 1541 | FuncGen_stackPush(&fg, out, WasmValType_i32); | 1831 | const char *function; |
| 1542 | fprintf(out, "l%" PRIu32 " >= l%" PRIu32 ";\n", lhs, rhs); | 1832 | switch (opcode) { |
| 1543 | } | 1833 | case WasmOpcode_f32_min: function = "fminf"; break; |
| 1544 | break; | 1834 | case WasmOpcode_f32_max: function = "fmaxf"; break; |
| 1545 | | 1835 | case WasmOpcode_f32_copysign: function = "copysignf"; break; |
| 1546 | case WasmOpcode_f32_eq: | 1836 | case WasmOpcode_f64_min: function = "fmin"; break; |
| 1547 | if (unreachable_depth == 0) { | 1837 | case WasmOpcode_f64_max: function = "fmax"; break; |
| 1548 | uint32_t rhs = FuncGen_stackPop(&fg); | 1838 | case WasmOpcode_f64_copysign: function = "copysign"; break; |
| 1549 | uint32_t lhs = FuncGen_stackPop(&fg); | 1839 | default: panic("unreachable"); |
| 1550 | FuncGen_stackPush(&fg, out, WasmValType_i32); | 1840 | } |
| 1551 | fprintf(out, "l%" PRIu32 " == l%" PRIu32 ";\n", lhs, rhs); | 1841 | FuncGen_indent(&fg, out); |
| 1552 | } | 1842 | fprintf(out, "l%" PRIu32 " = %s(l%" PRIu32 ", l%" PRIu32 ");\n", |
| 1553 | break; | 1843 | lhs, function, lhs, rhs); |
| 1554 | case WasmOpcode_f32_ne: | | |
| 1555 | if (unreachable_depth == 0) { | | |
| 1556 | uint32_t rhs = FuncGen_stackPop(&fg); | | |
| 1557 | uint32_t lhs = FuncGen_stackPop(&fg); | | |
| 1558 | FuncGen_stackPush(&fg, out, WasmValType_i32); | | |
| 1559 | fprintf(out, "l%" PRIu32 " != l%" PRIu32 ";\n", lhs, rhs); | | |
| 1560 | } | | |
| 1561 | break; | | |
| 1562 | case WasmOpcode_f32_lt: | | |
| 1563 | if (unreachable_depth == 0) { | | |
| 1564 | uint32_t rhs = FuncGen_stackPop(&fg); | | |
| 1565 | uint32_t lhs = FuncGen_stackPop(&fg); | | |
| 1566 | FuncGen_stackPush(&fg, out, WasmValType_i32); | | |
| 1567 | fprintf(out, "l%" PRIu32 " < l%" PRIu32 ";\n", lhs, rhs); | | |
| 1568 | } | | |
| 1569 | break; | | |
| 1570 | case WasmOpcode_f32_gt: | | |
| 1571 | if (unreachable_depth == 0) { | | |
| 1572 | uint32_t rhs = FuncGen_stackPop(&fg); | | |
| 1573 | uint32_t lhs = FuncGen_stackPop(&fg); | | |
| 1574 | FuncGen_stackPush(&fg, out, WasmValType_i32); | | |
| 1575 | fprintf(out, "l%" PRIu32 " > l%" PRIu32 ";\n", lhs, rhs); | | |
| 1576 | } | | |
| 1577 | break; | | |
| 1578 | case WasmOpcode_f32_le: | | |
| 1579 | if (unreachable_depth == 0) { | | |
| 1580 | uint32_t rhs = FuncGen_stackPop(&fg); | | |
| 1581 | uint32_t lhs = FuncGen_stackPop(&fg); | | |
| 1582 | FuncGen_stackPush(&fg, out, WasmValType_i32); | | |
| 1583 | fprintf(out, "l%" PRIu32 " <= l%" PRIu32 ";\n", lhs, rhs); | | |
| 1584 | } | | |
| 1585 | break; | | |
| 1586 | case WasmOpcode_f32_ge: | | |
| 1587 | if (unreachable_depth == 0) { | | |
| 1588 | uint32_t rhs = FuncGen_stackPop(&fg); | | |
| 1589 | uint32_t lhs = FuncGen_stackPop(&fg); | | |
| 1590 | FuncGen_stackPush(&fg, out, WasmValType_i32); | | |
| 1591 | fprintf(out, "l%" PRIu32 " >= l%" PRIu32 ";\n", lhs, rhs); | | |
| 1592 | } | | |
| 1593 | break; | | |
| 1594 | | | |
| 1595 | case WasmOpcode_f64_eq: | | |
| 1596 | if (unreachable_depth == 0) { | | |
| 1597 | uint32_t rhs = FuncGen_stackPop(&fg); | | |
| 1598 | uint32_t lhs = FuncGen_stackPop(&fg); | | |
| 1599 | FuncGen_stackPush(&fg, out, WasmValType_i32); | | |
| 1600 | fprintf(out, "l%" PRIu32 " == l%" PRIu32 ";\n", lhs, rhs); | | |
| 1601 | } | | |
| 1602 | break; | | |
| 1603 | case WasmOpcode_f64_ne: | | |
| 1604 | if (unreachable_depth == 0) { | | |
| 1605 | uint32_t rhs = FuncGen_stackPop(&fg); | | |
| 1606 | uint32_t lhs = FuncGen_stackPop(&fg); | | |
| 1607 | FuncGen_stackPush(&fg, out, WasmValType_i32); | | |
| 1608 | fprintf(out, "l%" PRIu32 " != l%" PRIu32 ";\n", lhs, rhs); | | |
| 1609 | } | | |
| 1610 | break; | | |
| 1611 | case WasmOpcode_f64_lt: | | |
| 1612 | if (unreachable_depth == 0) { | | |
| 1613 | uint32_t rhs = FuncGen_stackPop(&fg); | | |
| 1614 | uint32_t lhs = FuncGen_stackPop(&fg); | | |
| 1615 | FuncGen_stackPush(&fg, out, WasmValType_i32); | | |
| 1616 | fprintf(out, "l%" PRIu32 " < l%" PRIu32 ";\n", lhs, rhs); | | |
| 1617 | } | | |
| 1618 | break; | | |
| 1619 | case WasmOpcode_f64_gt: | | |
| 1620 | if (unreachable_depth == 0) { | | |
| 1621 | uint32_t rhs = FuncGen_stackPop(&fg); | | |
| 1622 | uint32_t lhs = FuncGen_stackPop(&fg); | | |
| 1623 | FuncGen_stackPush(&fg, out, WasmValType_i32); | | |
| 1624 | fprintf(out, "l%" PRIu32 " > l%" PRIu32 ";\n", lhs, rhs); | | |
| 1625 | } | | |
| 1626 | break; | | |
| 1627 | case WasmOpcode_f64_le: | | |
| 1628 | if (unreachable_depth == 0) { | | |
| 1629 | uint32_t rhs = FuncGen_stackPop(&fg); | | |
| 1630 | uint32_t lhs = FuncGen_stackPop(&fg); | | |
| 1631 | FuncGen_stackPush(&fg, out, WasmValType_i32); | | |
| 1632 | fprintf(out, "l%" PRIu32 " <= l%" PRIu32 ";\n", lhs, rhs); | | |
| 1633 | } | | |
| 1634 | break; | | |
| 1635 | case WasmOpcode_f64_ge: | | |
| 1636 | if (unreachable_depth == 0) { | | |
| 1637 | uint32_t rhs = FuncGen_stackPop(&fg); | | |
| 1638 | uint32_t lhs = FuncGen_stackPop(&fg); | | |
| 1639 | FuncGen_stackPush(&fg, out, WasmValType_i32); | | |
| 1640 | fprintf(out, "l%" PRIu32 " >= l%" PRIu32 ";\n", lhs, rhs); | | |
| 1641 | } | | |
| 1642 | break; | | |
| 1643 | | | |
| 1644 | case WasmOpcode_i32_clz: | | |
| 1645 | if (unreachable_depth == 0) { | | |
| 1646 | uint32_t lhs = FuncGen_stackPop(&fg); | | |
| 1647 | FuncGen_stackPush(&fg, out, WasmValType_i32); | | |
| 1648 | fprintf(out, "l%" PRIu32 " != 0 ? __builtin_clz(l%" PRIu32 ") : 32;\n", | | |
| 1649 | lhs, lhs); | | |
| 1650 | } | | |
| 1651 | break; | | |
| 1652 | case WasmOpcode_i32_ctz: | | |
| 1653 | if (unreachable_depth == 0) { | | |
| 1654 | uint32_t lhs = FuncGen_stackPop(&fg); | | |
| 1655 | FuncGen_stackPush(&fg, out, WasmValType_i32); | | |
| 1656 | fprintf(out, "l%" PRIu32 " != 0 ? __builtin_ctz(l%" PRIu32 ") : 32;\n", | | |
| 1657 | lhs, lhs); | | |
| 1658 | } | | |
| 1659 | break; | | |
| 1660 | case WasmOpcode_i32_popcnt: | | |
| 1661 | if (unreachable_depth == 0) { | | |
| 1662 | uint32_t lhs = FuncGen_stackPop(&fg); | | |
| 1663 | FuncGen_stackPush(&fg, out, WasmValType_i32); | | |
| 1664 | fprintf(out, "__builtin_popcount(l%" PRIu32 ");\n", lhs); | | |
| 1665 | } | | |
| 1666 | break; | | |
| 1667 | case WasmOpcode_i32_add: | | |
| 1668 | if (unreachable_depth == 0) { | | |
| 1669 | uint32_t rhs = FuncGen_stackPop(&fg); | | |
| 1670 | uint32_t lhs = FuncGen_stackPop(&fg); | | |
| 1671 | FuncGen_stackPush(&fg, out, WasmValType_i32); | | |
| 1672 | fprintf(out, "l%" PRIu32 " + l%" PRIu32 ";\n", lhs, rhs); | | |
| 1673 | } | | |
| 1674 | break; | | |
| 1675 | case WasmOpcode_i32_sub: | | |
| 1676 | if (unreachable_depth == 0) { | | |
| 1677 | uint32_t rhs = FuncGen_stackPop(&fg); | | |
| 1678 | uint32_t lhs = FuncGen_stackPop(&fg); | | |
| 1679 | FuncGen_stackPush(&fg, out, WasmValType_i32); | | |
| 1680 | fprintf(out, "l%" PRIu32 " - l%" PRIu32 ";\n", lhs, rhs); | | |
| 1681 | } | | |
| 1682 | break; | | |
| 1683 | case WasmOpcode_i32_mul: | | |
| 1684 | if (unreachable_depth == 0) { | | |
| 1685 | uint32_t rhs = FuncGen_stackPop(&fg); | | |
| 1686 | uint32_t lhs = FuncGen_stackPop(&fg); | | |
| 1687 | FuncGen_stackPush(&fg, out, WasmValType_i32); | | |
| 1688 | fprintf(out, "l%" PRIu32 " * l%" PRIu32 ";\n", lhs, rhs); | | |
| 1689 | } | | |
| 1690 | break; | | |
| 1691 | case WasmOpcode_i32_div_s: | | |
| 1692 | if (unreachable_depth == 0) { | | |
| 1693 | uint32_t rhs = FuncGen_stackPop(&fg); | | |
| 1694 | uint32_t lhs = FuncGen_stackPop(&fg); | | |
| 1695 | FuncGen_stackPush(&fg, out, WasmValType_i32); | | |
| 1696 | fprintf(out, "(int32_t)l%" PRIu32 " / (int32_t)l%" PRIu32 ";\n", lhs, rhs); | | |
| 1697 | } | | |
| 1698 | break; | | |
| 1699 | case WasmOpcode_i32_div_u: | | |
| 1700 | if (unreachable_depth == 0) { | | |
| 1701 | uint32_t rhs = FuncGen_stackPop(&fg); | | |
| 1702 | uint32_t lhs = FuncGen_stackPop(&fg); | | |
| 1703 | FuncGen_stackPush(&fg, out, WasmValType_i32); | | |
| 1704 | fprintf(out, "l%" PRIu32 " / l%" PRIu32 ";\n", lhs, rhs); | | |
| 1705 | } | | |
| 1706 | break; | | |
| 1707 | case WasmOpcode_i32_rem_s: | | |
| 1708 | if (unreachable_depth == 0) { | | |
| 1709 | uint32_t rhs = FuncGen_stackPop(&fg); | | |
| 1710 | uint32_t lhs = FuncGen_stackPop(&fg); | | |
| 1711 | FuncGen_stackPush(&fg, out, WasmValType_i32); | | |
| 1712 | fprintf(out, "(int32_t)l%" PRIu32 " %% (int32_t)l%" PRIu32 ";\n", lhs, rhs); | | |
| 1713 | } | | |
| 1714 | break; | | |
| 1715 | case WasmOpcode_i32_rem_u: | | |
| 1716 | if (unreachable_depth == 0) { | | |
| 1717 | uint32_t rhs = FuncGen_stackPop(&fg); | | |
| 1718 | uint32_t lhs = FuncGen_stackPop(&fg); | | |
| 1719 | FuncGen_stackPush(&fg, out, WasmValType_i32); | | |
| 1720 | fprintf(out, "l%" PRIu32 " %% l%" PRIu32 ";\n", lhs, rhs); | | |
| 1721 | } | | |
| 1722 | break; | | |
| 1723 | case WasmOpcode_i32_and: | | |
| 1724 | if (unreachable_depth == 0) { | | |
| 1725 | uint32_t rhs = FuncGen_stackPop(&fg); | | |
| 1726 | uint32_t lhs = FuncGen_stackPop(&fg); | | |
| 1727 | FuncGen_stackPush(&fg, out, WasmValType_i32); | | |
| 1728 | fprintf(out, "l%" PRIu32 " & l%" PRIu32 ";\n", lhs, rhs); | | |
| 1729 | } | | |
| 1730 | break; | | |
| 1731 | case WasmOpcode_i32_or: | | |
| 1732 | if (unreachable_depth == 0) { | | |
| 1733 | uint32_t rhs = FuncGen_stackPop(&fg); | | |
| 1734 | uint32_t lhs = FuncGen_stackPop(&fg); | | |
| 1735 | FuncGen_stackPush(&fg, out, WasmValType_i32); | | |
| 1736 | fprintf(out, "l%" PRIu32 " | l%" PRIu32 ";\n", lhs, rhs); | | |
| 1737 | } | | |
| 1738 | break; | | |
| 1739 | case WasmOpcode_i32_xor: | | |
| 1740 | if (unreachable_depth == 0) { | | |
| 1741 | uint32_t rhs = FuncGen_stackPop(&fg); | | |
| 1742 | uint32_t lhs = FuncGen_stackPop(&fg); | | |
| 1743 | FuncGen_stackPush(&fg, out, WasmValType_i32); | | |
| 1744 | fprintf(out, "l%" PRIu32 " ^ l%" PRIu32 ";\n", lhs, rhs); | | |
| 1745 | } | | |
| 1746 | break; | | |
| 1747 | case WasmOpcode_i32_shl: | | |
| 1748 | if (unreachable_depth == 0) { | | |
| 1749 | uint32_t rhs = FuncGen_stackPop(&fg); | | |
| 1750 | uint32_t lhs = FuncGen_stackPop(&fg); | | |
| 1751 | FuncGen_stackPush(&fg, out, WasmValType_i32); | | |
| 1752 | fprintf(out, "l%" PRIu32 " << (l%" PRIu32 " & 0x1F);\n", lhs, rhs); | | |
| 1753 | } | | |
| 1754 | break; | | |
| 1755 | case WasmOpcode_i32_shr_s: | | |
| 1756 | if (unreachable_depth == 0) { | | |
| 1757 | uint32_t rhs = FuncGen_stackPop(&fg); | | |
| 1758 | uint32_t lhs = FuncGen_stackPop(&fg); | | |
| 1759 | FuncGen_stackPush(&fg, out, WasmValType_i32); | | |
| 1760 | fprintf(out, "(int32_t)l%" PRIu32 " >> (l%" PRIu32 " & 0x1F);\n", lhs, rhs); | | |
| 1761 | } | | |
| 1762 | break; | | |
| 1763 | case WasmOpcode_i32_shr_u: | | |
| 1764 | if (unreachable_depth == 0) { | | |
| 1765 | uint32_t rhs = FuncGen_stackPop(&fg); | | |
| 1766 | uint32_t lhs = FuncGen_stackPop(&fg); | | |
| 1767 | FuncGen_stackPush(&fg, out, WasmValType_i32); | | |
| 1768 | fprintf(out, "l%" PRIu32 " >> (l%" PRIu32 " & 0x1F);\n", lhs, rhs); | | |
| 1769 | } | | |
| 1770 | break; | | |
| 1771 | case WasmOpcode_i32_rotl: | | |
| 1772 | if (unreachable_depth == 0) { | | |
| 1773 | uint32_t rhs = FuncGen_stackPop(&fg); | | |
| 1774 | uint32_t lhs = FuncGen_stackPop(&fg); | | |
| 1775 | FuncGen_stackPush(&fg, out, WasmValType_i32); | | |
| 1776 | fprintf(out, "l%" PRIu32 " << (l%" PRIu32 " & 0x1F) | " | | |
| 1777 | "l%" PRIu32 " >> (-l%" PRIu32" & 0x1F);\n", lhs, rhs, lhs, rhs); | | |
| 1778 | } | | |
| 1779 | break; | | |
| 1780 | case WasmOpcode_i32_rotr: | | |
| 1781 | if (unreachable_depth == 0) { | | |
| 1782 | uint32_t rhs = FuncGen_stackPop(&fg); | | |
| 1783 | uint32_t lhs = FuncGen_stackPop(&fg); | | |
| 1784 | FuncGen_stackPush(&fg, out, WasmValType_i32); | | |
| 1785 | fprintf(out, "l%" PRIu32 " >> (l%" PRIu32 " & 0x1F) | " | | |
| 1786 | "l%" PRIu32 " << (-l%" PRIu32" & 0x1F);\n", lhs, rhs, lhs, rhs); | | |
| 1787 | } | | |
| 1788 | break; | | |
| 1789 | | | |
| 1790 | case WasmOpcode_i64_clz: | | |
| 1791 | if (unreachable_depth == 0) { | | |
| 1792 | uint32_t lhs = FuncGen_stackPop(&fg); | | |
| 1793 | FuncGen_stackPush(&fg, out, WasmValType_i64); | | |
| 1794 | fprintf(out, "l%" PRIu32 " != 0 ? __builtin_clzll(l%" PRIu32 ") : 64;\n", | | |
| 1795 | lhs, lhs); | | |
| 1796 | } | | |
| 1797 | break; | | |
| 1798 | case WasmOpcode_i64_ctz: | | |
| 1799 | if (unreachable_depth == 0) { | | |
| 1800 | uint32_t lhs = FuncGen_stackPop(&fg); | | |
| 1801 | FuncGen_stackPush(&fg, out, WasmValType_i64); | | |
| 1802 | fprintf(out, "l%" PRIu32 " != 0 ? __builtin_ctzll(l%" PRIu32 ") : 64;\n", | | |
| 1803 | lhs, lhs); | | |
| 1804 | } | | |
| 1805 | break; | | |
| 1806 | case WasmOpcode_i64_popcnt: | | |
| 1807 | if (unreachable_depth == 0) { | | |
| 1808 | uint32_t lhs = FuncGen_stackPop(&fg); | | |
| 1809 | FuncGen_stackPush(&fg, out, WasmValType_i64); | | |
| 1810 | fprintf(out, "__builtin_popcountll(l%" PRIu32 ");\n", lhs); | | |
| 1811 | } | | |
| 1812 | break; | | |
| 1813 | case WasmOpcode_i64_add: | | |
| 1814 | if (unreachable_depth == 0) { | | |
| 1815 | uint32_t rhs = FuncGen_stackPop(&fg); | | |
| 1816 | uint32_t lhs = FuncGen_stackPop(&fg); | | |
| 1817 | FuncGen_stackPush(&fg, out, WasmValType_i64); | | |
| 1818 | fprintf(out, "l%" PRIu32 " + l%" PRIu32 ";\n", lhs, rhs); | | |
| 1819 | } | | |
| 1820 | break; | | |
| 1821 | case WasmOpcode_i64_sub: | | |
| 1822 | if (unreachable_depth == 0) { | | |
| 1823 | uint32_t rhs = FuncGen_stackPop(&fg); | | |
| 1824 | uint32_t lhs = FuncGen_stackPop(&fg); | | |
| 1825 | FuncGen_stackPush(&fg, out, WasmValType_i64); | | |
| 1826 | fprintf(out, "l%" PRIu32 " - l%" PRIu32 ";\n", lhs, rhs); | | |
| 1827 | } | | |
| 1828 | break; | | |
| 1829 | case WasmOpcode_i64_mul: | | |
| 1830 | if (unreachable_depth == 0) { | | |
| 1831 | uint32_t rhs = FuncGen_stackPop(&fg); | | |
| 1832 | uint32_t lhs = FuncGen_stackPop(&fg); | | |
| 1833 | FuncGen_stackPush(&fg, out, WasmValType_i64); | | |
| 1834 | fprintf(out, "l%" PRIu32 " * l%" PRIu32 ";\n", lhs, rhs); | | |
| 1835 | } | | |
| 1836 | break; | | |
| 1837 | case WasmOpcode_i64_div_s: | | |
| 1838 | if (unreachable_depth == 0) { | | |
| 1839 | uint32_t rhs = FuncGen_stackPop(&fg); | | |
| 1840 | uint32_t lhs = FuncGen_stackPop(&fg); | | |
| 1841 | FuncGen_stackPush(&fg, out, WasmValType_i64); | | |
| 1842 | fprintf(out, "(int64_t)l%" PRIu32 " / (int64_t)l%" PRIu32 ";\n", lhs, rhs); | | |
| 1843 | } | | |
| 1844 | break; | | |
| 1845 | case WasmOpcode_i64_div_u: | | |
| 1846 | if (unreachable_depth == 0) { | | |
| 1847 | uint32_t rhs = FuncGen_stackPop(&fg); | | |
| 1848 | uint32_t lhs = FuncGen_stackPop(&fg); | | |
| 1849 | FuncGen_stackPush(&fg, out, WasmValType_i64); | | |
| 1850 | fprintf(out, "l%" PRIu32 " / l%" PRIu32 ";\n", lhs, rhs); | | |
| 1851 | } | | |
| 1852 | break; | | |
| 1853 | case WasmOpcode_i64_rem_s: | | |
| 1854 | if (unreachable_depth == 0) { | | |
| 1855 | uint32_t rhs = FuncGen_stackPop(&fg); | | |
| 1856 | uint32_t lhs = FuncGen_stackPop(&fg); | | |
| 1857 | FuncGen_stackPush(&fg, out, WasmValType_i64); | | |
| 1858 | fprintf(out, "(int64_t)l%" PRIu32 " %% (int64_t)l%" PRIu32 ";\n", lhs, rhs); | | |
| 1859 | } | | |
| 1860 | break; | | |
| 1861 | case WasmOpcode_i64_rem_u: | | |
| 1862 | if (unreachable_depth == 0) { | | |
| 1863 | uint32_t rhs = FuncGen_stackPop(&fg); | | |
| 1864 | uint32_t lhs = FuncGen_stackPop(&fg); | | |
| 1865 | FuncGen_stackPush(&fg, out, WasmValType_i64); | | |
| 1866 | fprintf(out, "l%" PRIu32 " %% l%" PRIu32 ";\n", lhs, rhs); | | |
| 1867 | } | | |
| 1868 | break; | | |
| 1869 | case WasmOpcode_i64_and: | | |
| 1870 | if (unreachable_depth == 0) { | | |
| 1871 | uint32_t rhs = FuncGen_stackPop(&fg); | | |
| 1872 | uint32_t lhs = FuncGen_stackPop(&fg); | | |
| 1873 | FuncGen_stackPush(&fg, out, WasmValType_i64); | | |
| 1874 | fprintf(out, "l%" PRIu32 " & l%" PRIu32 ";\n", lhs, rhs); | | |
| 1875 | } | | |
| 1876 | break; | | |
| 1877 | case WasmOpcode_i64_or: | | |
| 1878 | if (unreachable_depth == 0) { | | |
| 1879 | uint32_t rhs = FuncGen_stackPop(&fg); | | |
| 1880 | uint32_t lhs = FuncGen_stackPop(&fg); | | |
| 1881 | FuncGen_stackPush(&fg, out, WasmValType_i64); | | |
| 1882 | fprintf(out, "l%" PRIu32 " | l%" PRIu32 ";\n", lhs, rhs); | | |
| 1883 | } | | |
| 1884 | break; | | |
| 1885 | case WasmOpcode_i64_xor: | | |
| 1886 | if (unreachable_depth == 0) { | | |
| 1887 | uint32_t rhs = FuncGen_stackPop(&fg); | | |
| 1888 | uint32_t lhs = FuncGen_stackPop(&fg); | | |
| 1889 | FuncGen_stackPush(&fg, out, WasmValType_i64); | | |
| 1890 | fprintf(out, "l%" PRIu32 " ^ l%" PRIu32 ";\n", lhs, rhs); | | |
| 1891 | } | | |
| 1892 | break; | | |
| 1893 | case WasmOpcode_i64_shl: | | |
| 1894 | if (unreachable_depth == 0) { | | |
| 1895 | uint32_t rhs = FuncGen_stackPop(&fg); | | |
| 1896 | uint32_t lhs = FuncGen_stackPop(&fg); | | |
| 1897 | FuncGen_stackPush(&fg, out, WasmValType_i64); | | |
| 1898 | fprintf(out, "l%" PRIu32 " << (l%" PRIu32 " & 0x3F);\n", lhs, rhs); | | |
| 1899 | } | | |
| 1900 | break; | | |
| 1901 | case WasmOpcode_i64_shr_s: | | |
| 1902 | if (unreachable_depth == 0) { | | |
| 1903 | uint32_t rhs = FuncGen_stackPop(&fg); | | |
| 1904 | uint32_t lhs = FuncGen_stackPop(&fg); | | |
| 1905 | FuncGen_stackPush(&fg, out, WasmValType_i64); | | |
| 1906 | fprintf(out, "(int64_t)l%" PRIu32 " >> (l%" PRIu32 " & 0x3F);\n", lhs, rhs); | | |
| 1907 | } | | |
| 1908 | break; | | |
| 1909 | case WasmOpcode_i64_shr_u: | | |
| 1910 | if (unreachable_depth == 0) { | | |
| 1911 | uint32_t rhs = FuncGen_stackPop(&fg); | | |
| 1912 | uint32_t lhs = FuncGen_stackPop(&fg); | | |
| 1913 | FuncGen_stackPush(&fg, out, WasmValType_i64); | | |
| 1914 | fprintf(out, "l%" PRIu32 " >> (l%" PRIu32 " & 0x3F);\n", lhs, rhs); | | |
| 1915 | } | | |
| 1916 | break; | | |
| 1917 | case WasmOpcode_i64_rotl: | | |
| 1918 | if (unreachable_depth == 0) { | | |
| 1919 | uint32_t rhs = FuncGen_stackPop(&fg); | | |
| 1920 | uint32_t lhs = FuncGen_stackPop(&fg); | | |
| 1921 | FuncGen_stackPush(&fg, out, WasmValType_i64); | | |
| 1922 | fprintf(out, "l%" PRIu32 " << (l%" PRIu32 " & 0x3F) | " | | |
| 1923 | "l%" PRIu32 " >> (-l%" PRIu32" & 0x3F);\n", lhs, rhs, lhs, rhs); | | |
| 1924 | } | | |
| 1925 | break; | | |
| 1926 | case WasmOpcode_i64_rotr: | | |
| 1927 | if (unreachable_depth == 0) { | | |
| 1928 | uint32_t rhs = FuncGen_stackPop(&fg); | | |
| 1929 | uint32_t lhs = FuncGen_stackPop(&fg); | | |
| 1930 | FuncGen_stackPush(&fg, out, WasmValType_i64); | | |
| 1931 | fprintf(out, "l%" PRIu32 " >> (l%" PRIu32 " & 0x3F) | " | | |
| 1932 | "l%" PRIu32 " << (-l%" PRIu32" & 0x3F);\n", lhs, rhs, lhs, rhs); | | |
| 1933 | } | | |
| 1934 | break; | | |
| 1935 | | | |
| 1936 | case WasmOpcode_f32_abs: | | |
| 1937 | if (unreachable_depth == 0) { | | |
| 1938 | uint32_t lhs = FuncGen_stackPop(&fg); | | |
| 1939 | FuncGen_stackPush(&fg, out, WasmValType_f32); | | |
| 1940 | fprintf(out, "fabsf(l%" PRIu32 ");\n", lhs); | | |
| 1941 | } | | |
| 1942 | break; | | |
| 1943 | case WasmOpcode_f32_neg: | | |
| 1944 | if (unreachable_depth == 0) { | | |
| 1945 | uint32_t lhs = FuncGen_stackPop(&fg); | | |
| 1946 | FuncGen_stackPush(&fg, out, WasmValType_f32); | | |
| 1947 | fprintf(out, "-l%" PRIu32 ";\n", lhs); | | |
| 1948 | } | | |
| 1949 | break; | | |
| 1950 | case WasmOpcode_f32_ceil: | | |
| 1951 | if (unreachable_depth == 0) { | | |
| 1952 | uint32_t lhs = FuncGen_stackPop(&fg); | | |
| 1953 | FuncGen_stackPush(&fg, out, WasmValType_f32); | | |
| 1954 | fprintf(out, "ceilf(l%" PRIu32 ");\n", lhs); | | |
| 1955 | } | | |
| 1956 | break; | | |
| 1957 | case WasmOpcode_f32_floor: | | |
| 1958 | if (unreachable_depth == 0) { | | |
| 1959 | uint32_t lhs = FuncGen_stackPop(&fg); | | |
| 1960 | FuncGen_stackPush(&fg, out, WasmValType_f32); | | |
| 1961 | fprintf(out, "floorf(l%" PRIu32 ");\n", lhs); | | |
| 1962 | } | | |
| 1963 | break; | | |
| 1964 | case WasmOpcode_f32_trunc: | | |
| 1965 | if (unreachable_depth == 0) { | | |
| 1966 | uint32_t lhs = FuncGen_stackPop(&fg); | | |
| 1967 | FuncGen_stackPush(&fg, out, WasmValType_f32); | | |
| 1968 | fprintf(out, "truncf(l%" PRIu32 ");\n", lhs); | | |
| 1969 | } | | |
| 1970 | break; | | |
| 1971 | case WasmOpcode_f32_nearest: | | |
| 1972 | if (unreachable_depth == 0) { | | |
| 1973 | uint32_t lhs = FuncGen_stackPop(&fg); | | |
| 1974 | FuncGen_stackPush(&fg, out, WasmValType_f32); | | |
| 1975 | fprintf(out, "roundf(l%" PRIu32 ");\n", lhs); | | |
| 1976 | } | | |
| 1977 | break; | | |
| 1978 | case WasmOpcode_f32_sqrt: | | |
| 1979 | if (unreachable_depth == 0) { | | |
| 1980 | uint32_t lhs = FuncGen_stackPop(&fg); | | |
| 1981 | FuncGen_stackPush(&fg, out, WasmValType_f32); | | |
| 1982 | fprintf(out, "sqrtf(l%" PRIu32 ");\n", lhs); | | |
| 1983 | } | | |
| 1984 | break; | | |
| 1985 | case WasmOpcode_f32_add: | | |
| 1986 | if (unreachable_depth == 0) { | | |
| 1987 | uint32_t rhs = FuncGen_stackPop(&fg); | | |
| 1988 | uint32_t lhs = FuncGen_stackPop(&fg); | | |
| 1989 | FuncGen_stackPush(&fg, out, WasmValType_f32); | | |
| 1990 | fprintf(out, "l%" PRIu32 " + l%" PRIu32 ";\n", lhs, rhs); | | |
| 1991 | } | | |
| 1992 | break; | | |
| 1993 | case WasmOpcode_f32_sub: | | |
| 1994 | if (unreachable_depth == 0) { | | |
| 1995 | uint32_t rhs = FuncGen_stackPop(&fg); | | |
| 1996 | uint32_t lhs = FuncGen_stackPop(&fg); | | |
| 1997 | FuncGen_stackPush(&fg, out, WasmValType_f32); | | |
| 1998 | fprintf(out, "l%" PRIu32 " - l%" PRIu32 ";\n", lhs, rhs); | | |
| 1999 | } | | |
| 2000 | break; | | |
| 2001 | case WasmOpcode_f32_mul: | | |
| 2002 | if (unreachable_depth == 0) { | | |
| 2003 | uint32_t rhs = FuncGen_stackPop(&fg); | | |
| 2004 | uint32_t lhs = FuncGen_stackPop(&fg); | | |
| 2005 | FuncGen_stackPush(&fg, out, WasmValType_f32); | | |
| 2006 | fprintf(out, "l%" PRIu32 " * l%" PRIu32 ";\n", lhs, rhs); | | |
| 2007 | } | | |
| 2008 | break; | | |
| 2009 | case WasmOpcode_f32_div: | | |
| 2010 | if (unreachable_depth == 0) { | | |
| 2011 | uint32_t rhs = FuncGen_stackPop(&fg); | | |
| 2012 | uint32_t lhs = FuncGen_stackPop(&fg); | | |
| 2013 | FuncGen_stackPush(&fg, out, WasmValType_f32); | | |
| 2014 | fprintf(out, "l%" PRIu32 " / l%" PRIu32 ";\n", lhs, rhs); | | |
| 2015 | } | | |
| 2016 | break; | | |
| 2017 | case WasmOpcode_f32_min: | | |
| 2018 | if (unreachable_depth == 0) { | | |
| 2019 | uint32_t rhs = FuncGen_stackPop(&fg); | | |
| 2020 | uint32_t lhs = FuncGen_stackPop(&fg); | | |
| 2021 | FuncGen_stackPush(&fg, out, WasmValType_f32); | | |
| 2022 | fprintf(out, "fminf(l%" PRIu32 ", l%" PRIu32 ");\n", lhs, rhs); | | |
| 2023 | } | | |
| 2024 | break; | | |
| 2025 | case WasmOpcode_f32_max: | | |
| 2026 | if (unreachable_depth == 0) { | | |
| 2027 | uint32_t rhs = FuncGen_stackPop(&fg); | | |
| 2028 | uint32_t lhs = FuncGen_stackPop(&fg); | | |
| 2029 | FuncGen_stackPush(&fg, out, WasmValType_f32); | | |
| 2030 | fprintf(out, "fmaxf(l%" PRIu32 ", l%" PRIu32 ");\n", lhs, rhs); | | |
| 2031 | } | | |
| 2032 | break; | | |
| 2033 | case WasmOpcode_f32_copysign: | | |
| 2034 | if (unreachable_depth == 0) { | | |
| 2035 | uint32_t rhs = FuncGen_stackPop(&fg); | | |
| 2036 | uint32_t lhs = FuncGen_stackPop(&fg); | | |
| 2037 | FuncGen_stackPush(&fg, out, WasmValType_f32); | | |
| 2038 | fprintf(out, "copysignf(l%" PRIu32 ", l%" PRIu32 ");\n", lhs, rhs); | | |
| 2039 | } | | |
| 2040 | break; | | |
| 2041 | | | |
| 2042 | case WasmOpcode_f64_abs: | | |
| 2043 | if (unreachable_depth == 0) { | | |
| 2044 | uint32_t lhs = FuncGen_stackPop(&fg); | | |
| 2045 | FuncGen_stackPush(&fg, out, WasmValType_f64); | | |
| 2046 | fprintf(out, "fabs(l%" PRIu32 ");\n", lhs); | | |
| 2047 | } | | |
| 2048 | break; | | |
| 2049 | case WasmOpcode_f64_neg: | | |
| 2050 | if (unreachable_depth == 0) { | | |
| 2051 | uint32_t lhs = FuncGen_stackPop(&fg); | | |
| 2052 | FuncGen_stackPush(&fg, out, WasmValType_f64); | | |
| 2053 | fprintf(out, "-l%" PRIu32 ";\n", lhs); | | |
| 2054 | } | | |
| 2055 | break; | | |
| 2056 | case WasmOpcode_f64_ceil: | | |
| 2057 | if (unreachable_depth == 0) { | | |
| 2058 | uint32_t lhs = FuncGen_stackPop(&fg); | | |
| 2059 | FuncGen_stackPush(&fg, out, WasmValType_f64); | | |
| 2060 | fprintf(out, "ceil(l%" PRIu32 ");\n", lhs); | | |
| 2061 | } | | |
| 2062 | break; | | |
| 2063 | case WasmOpcode_f64_floor: | | |
| 2064 | if (unreachable_depth == 0) { | | |
| 2065 | uint32_t lhs = FuncGen_stackPop(&fg); | | |
| 2066 | FuncGen_stackPush(&fg, out, WasmValType_f64); | | |
| 2067 | fprintf(out, "floor(l%" PRIu32 ");\n", lhs); | | |
| 2068 | } | | |
| 2069 | break; | | |
| 2070 | case WasmOpcode_f64_trunc: | | |
| 2071 | if (unreachable_depth == 0) { | | |
| 2072 | uint32_t lhs = FuncGen_stackPop(&fg); | | |
| 2073 | FuncGen_stackPush(&fg, out, WasmValType_f64); | | |
| 2074 | fprintf(out, "trunc(l%" PRIu32 ");\n", lhs); | | |
| 2075 | } | | |
| 2076 | break; | | |
| 2077 | case WasmOpcode_f64_nearest: | | |
| 2078 | if (unreachable_depth == 0) { | | |
| 2079 | uint32_t lhs = FuncGen_stackPop(&fg); | | |
| 2080 | FuncGen_stackPush(&fg, out, WasmValType_f64); | | |
| 2081 | fprintf(out, "round(l%" PRIu32 ");\n", lhs); | | |
| 2082 | } | | |
| 2083 | break; | | |
| 2084 | case WasmOpcode_f64_sqrt: | | |
| 2085 | if (unreachable_depth == 0) { | | |
| 2086 | uint32_t lhs = FuncGen_stackPop(&fg); | | |
| 2087 | FuncGen_stackPush(&fg, out, WasmValType_f64); | | |
| 2088 | fprintf(out, "sqrt(l%" PRIu32 ");\n", lhs); | | |
| 2089 | } | | |
| 2090 | break; | | |
| 2091 | case WasmOpcode_f64_add: | | |
| 2092 | if (unreachable_depth == 0) { | | |
| 2093 | uint32_t rhs = FuncGen_stackPop(&fg); | | |
| 2094 | uint32_t lhs = FuncGen_stackPop(&fg); | | |
| 2095 | FuncGen_stackPush(&fg, out, WasmValType_f64); | | |
| 2096 | fprintf(out, "l%" PRIu32 " + l%" PRIu32 ";\n", lhs, rhs); | | |
| 2097 | } | | |
| 2098 | break; | | |
| 2099 | case WasmOpcode_f64_sub: | | |
| 2100 | if (unreachable_depth == 0) { | | |
| 2101 | uint32_t rhs = FuncGen_stackPop(&fg); | | |
| 2102 | uint32_t lhs = FuncGen_stackPop(&fg); | | |
| 2103 | FuncGen_stackPush(&fg, out, WasmValType_f64); | | |
| 2104 | fprintf(out, "l%" PRIu32 " - l%" PRIu32 ";\n", lhs, rhs); | | |
| 2105 | } | | |
| 2106 | break; | | |
| 2107 | case WasmOpcode_f64_mul: | | |
| 2108 | if (unreachable_depth == 0) { | | |
| 2109 | uint32_t rhs = FuncGen_stackPop(&fg); | | |
| 2110 | uint32_t lhs = FuncGen_stackPop(&fg); | | |
| 2111 | FuncGen_stackPush(&fg, out, WasmValType_f64); | | |
| 2112 | fprintf(out, "l%" PRIu32 " * l%" PRIu32 ";\n", lhs, rhs); | | |
| 2113 | } | | |
| 2114 | break; | | |
| 2115 | case WasmOpcode_f64_div: | | |
| 2116 | if (unreachable_depth == 0) { | | |
| 2117 | uint32_t rhs = FuncGen_stackPop(&fg); | | |
| 2118 | uint32_t lhs = FuncGen_stackPop(&fg); | | |
| 2119 | FuncGen_stackPush(&fg, out, WasmValType_f64); | | |
| 2120 | fprintf(out, "l%" PRIu32 " / l%" PRIu32 ";\n", lhs, rhs); | | |
| 2121 | } | | |
| 2122 | break; | | |
| 2123 | case WasmOpcode_f64_min: | | |
| 2124 | if (unreachable_depth == 0) { | | |
| 2125 | uint32_t rhs = FuncGen_stackPop(&fg); | | |
| 2126 | uint32_t lhs = FuncGen_stackPop(&fg); | | |
| 2127 | FuncGen_stackPush(&fg, out, WasmValType_f64); | | |
| 2128 | fprintf(out, "fmin(l%" PRIu32 ", l%" PRIu32 ");\n", lhs, rhs); | | |
| 2129 | } | | |
| 2130 | break; | | |
| 2131 | case WasmOpcode_f64_max: | | |
| 2132 | if (unreachable_depth == 0) { | | |
| 2133 | uint32_t rhs = FuncGen_stackPop(&fg); | | |
| 2134 | uint32_t lhs = FuncGen_stackPop(&fg); | | |
| 2135 | FuncGen_stackPush(&fg, out, WasmValType_f64); | | |
| 2136 | fprintf(out, "fmax(l%" PRIu32 ", l%" PRIu32 ");\n", lhs, rhs); | | |
| 2137 | } | | |
| 2138 | break; | | |
| 2139 | case WasmOpcode_f64_copysign: | | |
| 2140 | if (unreachable_depth == 0) { | | |
| 2141 | uint32_t rhs = FuncGen_stackPop(&fg); | | |
| 2142 | uint32_t lhs = FuncGen_stackPop(&fg); | | |
| 2143 | FuncGen_stackPush(&fg, out, WasmValType_f64); | | |
| 2144 | fprintf(out, "copysign(l%" PRIu32 ", l%" PRIu32 ");\n", lhs, rhs); | | |
| 2145 | } | 1844 | } |
| 2146 | break; | 1845 | break; |
| 2147 | | 1846 | |