From 9cbd4199f376fdccbf08bf2ac15b48c4310e36c4 Mon Sep 17 00:00:00 2001 From: Kartik Agaram Date: Wed, 29 Jul 2020 22:04:13 -0700 Subject: 6685 --- html/apps/mu.subx.html | 41594 ++++++++++++++++++++++--------------------- html/apps/mulisp.subx.html | 295 - 2 files changed, 20994 insertions(+), 20895 deletions(-) delete mode 100644 html/apps/mulisp.subx.html (limited to 'html/apps/*.subx.html') diff --git a/html/apps/mu.subx.html b/html/apps/mu.subx.html index 212787d5..ed09ba7c 100644 --- a/html/apps/mu.subx.html +++ b/html/apps/mu.subx.html @@ -469,13996 +469,13996 @@ if ('onhashchange' in window) { 407 # Not to be used directly, so we don't include a name here. 408 0/imm32 # 10 reserved for type parameters; value is (address array byte) in Type-tree-value2. 409 # Not to be used directly, so we don't include a name here. - 410 # Keep Primitive-type-ids in sync if you add types here. - 411 0/imm32 0/imm32 0/imm32 0/imm32 0/imm32 - 412 0/imm32 0/imm32 0/imm32 0/imm32 0/imm32 0/imm32 0/imm32 0/imm32 - 413 0/imm32 0/imm32 0/imm32 0/imm32 0/imm32 0/imm32 0/imm32 0/imm32 - 414 0/imm32 0/imm32 0/imm32 0/imm32 0/imm32 0/imm32 0/imm32 0/imm32 + 410 # some SubX types deliberately left undefined in Mu; they can only be operated on using SubX primitives + 411 "stream"/imm32 # 11 + 412 "slice"/imm32 # 12 + 413 # Keep Primitive-type-ids in sync if you add types here. + 414 0/imm32 0/imm32 0/imm32 415 0/imm32 0/imm32 0/imm32 0/imm32 0/imm32 0/imm32 0/imm32 0/imm32 416 0/imm32 0/imm32 0/imm32 0/imm32 0/imm32 0/imm32 0/imm32 0/imm32 417 0/imm32 0/imm32 0/imm32 0/imm32 0/imm32 0/imm32 0/imm32 0/imm32 - 418 - 419 Primitive-type-ids: # (addr int) - 420 0x2c + 418 0/imm32 0/imm32 0/imm32 0/imm32 0/imm32 0/imm32 0/imm32 0/imm32 + 419 0/imm32 0/imm32 0/imm32 0/imm32 0/imm32 0/imm32 0/imm32 0/imm32 + 420 0/imm32 0/imm32 0/imm32 0/imm32 0/imm32 0/imm32 0/imm32 0/imm32 421 - 422 # == Type definitions - 423 # Program->types contains some typeinfo for each type definition. - 424 # Types contain vars with types, but can't specify registers. - 425 Typeinfo-id: # type-id - 426 0/imm32 - 427 Typeinfo-fields: # (handle table (handle array byte) (handle typeinfo-entry)) - 428 4/imm32 - 429 # Total size must be >= 0 - 430 # During parsing it may take on two additional values: - 431 # -2: not yet initialized - 432 # -1: in process of being computed - 433 # See populate-mu-type-sizes for details. - 434 Typeinfo-total-size-in-bytes: # int - 435 0xc/imm32 - 436 Typeinfo-next: # (handle typeinfo) - 437 0x10/imm32 - 438 Typeinfo-size: # (addr int) - 439 0x18/imm32 - 440 - 441 # Each entry in the typeinfo->fields table has a pointer to a string and a - 442 # pointer to a typeinfo-entry. - 443 Typeinfo-fields-row-size: # (addr int) - 444 0x10/imm32 - 445 - 446 # typeinfo-entry objects have information about a field in a single record type - 447 # - 448 # each field of a type is represented using two var's: - 449 # 1. the input var: expected type of the field; convenient for creating using parse-var-with-type - 450 # 2. the output var: a constant containing the byte offset; convenient for code-generation - 451 # computing the output happens after parsing; in the meantime we preserve the - 452 # order of fields in the 'index' field. - 453 Typeinfo-entry-input-var: # (handle var) - 454 0/imm32 - 455 Typeinfo-entry-index: # int - 456 8/imm32 - 457 Typeinfo-entry-output-var: # (handle var) - 458 0xc/imm32 - 459 Typeinfo-entry-size: # (addr int) - 460 0x14/imm32 - 461 - 462 == code - 463 - 464 Entry: - 465 # . prologue - 466 89/<- %ebp 4/r32/esp - 467 (new-segment *Heap-size Heap) - 468 # if (argv[1] == "test') run-tests() - 469 { - 470 # if (argc <= 1) break - 471 81 7/subop/compare *ebp 1/imm32 - 472 7e/jump-if-<= break/disp8 - 473 # if (argv[1] != "test") break - 474 (kernel-string-equal? *(ebp+8) "test") # => eax - 475 3d/compare-eax-and 0/imm32/false - 476 74/jump-if-= break/disp8 - 477 # - 478 (run-tests) - 479 # syscall(exit, *Num-test-failures) - 480 8b/-> *Num-test-failures 3/r32/ebx - 481 eb/jump $mu-main:end/disp8 - 482 } - 483 # otherwise convert Stdin - 484 (convert-mu Stdin Stdout Stderr 0) - 485 (flush Stdout) - 486 # syscall(exit, 0) - 487 bb/copy-to-ebx 0/imm32 - 488 $mu-main:end: - 489 e8/call syscall_exit/disp32 - 490 - 491 convert-mu: # in: (addr buffered-file), out: (addr buffered-file), err: (addr buffered-file), ed: (addr exit-descriptor) - 492 # . prologue - 493 55/push-ebp - 494 89/<- %ebp 4/r32/esp - 495 # . save registers - 496 50/push-eax - 497 # initialize global data structures - 498 c7 0/subop/copy *Next-block-index 1/imm32 - 499 8b/-> *Primitive-type-ids 0/r32/eax - 500 89/<- *Type-id 0/r32/eax # stream-write - 501 c7 0/subop/copy *_Program-functions 0/imm32 - 502 c7 0/subop/copy *_Program-functions->payload 0/imm32 - 503 c7 0/subop/copy *_Program-types 0/imm32 - 504 c7 0/subop/copy *_Program-types->payload 0/imm32 - 505 c7 0/subop/copy *_Program-signatures 0/imm32 - 506 c7 0/subop/copy *_Program-signatures->payload 0/imm32 - 507 # - 508 (parse-mu *(ebp+8) *(ebp+0x10) *(ebp+0x14)) - 509 (populate-mu-type-sizes *(ebp+0x10) *(ebp+0x14)) - 510 #? (dump-typeinfos "=== typeinfos\n") - 511 (check-mu-types *(ebp+0x10) *(ebp+0x14)) - 512 (emit-subx *(ebp+0xc) *(ebp+0x10) *(ebp+0x14)) - 513 $convert-mu:end: - 514 # . restore registers - 515 58/pop-to-eax - 516 # . epilogue - 517 89/<- %esp 5/r32/ebp - 518 5d/pop-to-ebp - 519 c3/return - 520 - 521 test-convert-empty-input: - 522 # empty input => empty output - 523 # . prologue - 524 55/push-ebp - 525 89/<- %ebp 4/r32/esp - 526 # setup - 527 (clear-stream _test-input-stream) - 528 (clear-stream $_test-input-buffered-file->buffer) - 529 (clear-stream _test-output-stream) - 530 (clear-stream $_test-output-buffered-file->buffer) - 531 # - 532 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) - 533 (flush _test-output-buffered-file) - 534 (check-stream-equal _test-output-stream "" "F - test-convert-empty-input") - 535 # . epilogue - 536 89/<- %esp 5/r32/ebp - 537 5d/pop-to-ebp - 538 c3/return - 539 - 540 test-convert-function-skeleton: - 541 # . prologue - 542 55/push-ebp - 543 89/<- %ebp 4/r32/esp - 544 # setup - 545 (clear-stream _test-input-stream) - 546 (clear-stream $_test-input-buffered-file->buffer) - 547 (clear-stream _test-output-stream) - 548 (clear-stream $_test-output-buffered-file->buffer) - 549 # - 550 (write _test-input-stream "fn foo {\n") - 551 (write _test-input-stream "}\n") - 552 # convert - 553 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) - 554 (flush _test-output-buffered-file) - 555 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 561 # check output - 562 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-function-skeleton/0") - 563 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-function-skeleton/1") - 564 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-function-skeleton/2") - 565 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-function-skeleton/3") - 566 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-function-skeleton/4") - 567 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-function-skeleton/5") - 568 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-function-skeleton/6") - 569 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-function-skeleton/7") - 570 # . epilogue - 571 89/<- %esp 5/r32/ebp - 572 5d/pop-to-ebp - 573 c3/return - 574 - 575 test-convert-multiple-function-skeletons: - 576 # . prologue - 577 55/push-ebp - 578 89/<- %ebp 4/r32/esp - 579 # setup - 580 (clear-stream _test-input-stream) - 581 (clear-stream $_test-input-buffered-file->buffer) - 582 (clear-stream _test-output-stream) - 583 (clear-stream $_test-output-buffered-file->buffer) - 584 # - 585 (write _test-input-stream "fn foo {\n") - 586 (write _test-input-stream "}\n") - 587 (write _test-input-stream "fn bar {\n") - 588 (write _test-input-stream "}\n") - 589 # convert - 590 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) - 591 (flush _test-output-buffered-file) - 592 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 598 # check first function - 599 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-multiple-function-skeletons/0") - 600 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-multiple-function-skeletons/1") - 601 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-multiple-function-skeletons/2") - 602 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-multiple-function-skeletons/3") - 603 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-multiple-function-skeletons/4") - 604 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-multiple-function-skeletons/5") - 605 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-multiple-function-skeletons/6") - 606 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-multiple-function-skeletons/7") - 607 # check second function - 608 (check-next-stream-line-equal _test-output-stream "bar:" "F - test-convert-multiple-function-skeletons/10") - 609 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-multiple-function-skeletons/11") - 610 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-multiple-function-skeletons/12") - 611 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-multiple-function-skeletons/13") - 612 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-multiple-function-skeletons/14") - 613 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-multiple-function-skeletons/15") - 614 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-multiple-function-skeletons/16") - 615 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-multiple-function-skeletons/17") - 616 # . epilogue - 617 89/<- %esp 5/r32/ebp - 618 5d/pop-to-ebp - 619 c3/return - 620 - 621 test-convert-function-with-arg: - 622 # . prologue - 623 55/push-ebp - 624 89/<- %ebp 4/r32/esp - 625 # setup - 626 (clear-stream _test-input-stream) - 627 (clear-stream $_test-input-buffered-file->buffer) - 628 (clear-stream _test-output-stream) - 629 (clear-stream $_test-output-buffered-file->buffer) - 630 # - 631 (write _test-input-stream "fn foo n: int {\n") - 632 (write _test-input-stream "}\n") - 633 # convert - 634 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) - 635 (flush _test-output-buffered-file) - 636 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 642 # check output - 643 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-function-with-arg/0") - 644 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-function-with-arg/1") - 645 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-function-with-arg/2") - 646 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-function-with-arg/3") - 647 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-function-with-arg/4") - 648 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-function-with-arg/5") - 649 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-function-with-arg/6") - 650 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-function-with-arg/7") - 651 # . epilogue - 652 89/<- %esp 5/r32/ebp - 653 5d/pop-to-ebp - 654 c3/return - 655 - 656 test-convert-function-with-arg-and-body: - 657 # . prologue - 658 55/push-ebp - 659 89/<- %ebp 4/r32/esp - 660 # setup - 661 (clear-stream _test-input-stream) - 662 (clear-stream $_test-input-buffered-file->buffer) - 663 (clear-stream _test-output-stream) - 664 (clear-stream $_test-output-buffered-file->buffer) - 665 # - 666 (write _test-input-stream "fn foo n: int {\n") - 667 (write _test-input-stream " increment n\n") - 668 (write _test-input-stream "}\n") - 669 # convert - 670 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) - 671 (flush _test-output-buffered-file) - 672 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 678 # check output - 679 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-function-with-arg-and-body/0") - 680 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-function-with-arg-and-body/1") - 681 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-function-with-arg-and-body/2") - 682 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-function-with-arg-and-body/3") - 683 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-arg-and-body/4") - 684 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-function-with-arg-and-body/5") - 685 (check-next-stream-line-equal _test-output-stream " ff 0/subop/increment *(ebp+0x00000008)" "F - test-convert-function-with-arg-and-body/6") - 686 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-arg-and-body/7") - 687 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-function-with-arg-and-body/8") - 688 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-function-with-arg-and-body/9") - 689 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-function-with-arg-and-body/10") - 690 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-function-with-arg-and-body/11") - 691 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-function-with-arg-and-body/12") - 692 # . epilogue - 693 89/<- %esp 5/r32/ebp - 694 5d/pop-to-ebp - 695 c3/return - 696 - 697 test-convert-function-distinguishes-args: - 698 # . prologue - 699 55/push-ebp - 700 89/<- %ebp 4/r32/esp - 701 # setup - 702 (clear-stream _test-input-stream) - 703 (clear-stream $_test-input-buffered-file->buffer) - 704 (clear-stream _test-output-stream) - 705 (clear-stream $_test-output-buffered-file->buffer) - 706 # - 707 (write _test-input-stream "fn foo a: int, b: int {\n") - 708 (write _test-input-stream " increment b\n") - 709 (write _test-input-stream "}\n") - 710 # convert - 711 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) - 712 (flush _test-output-buffered-file) - 713 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 719 # check output - 720 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-function-distinguishes-args/0") - 721 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-function-distinguishes-args/1") - 722 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-function-distinguishes-args/2") - 723 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-function-distinguishes-args/3") - 724 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-distinguishes-args/4") - 725 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-function-distinguishes-args/5") - 726 (check-next-stream-line-equal _test-output-stream " ff 0/subop/increment *(ebp+0x0000000c)" "F - test-convert-function-distinguishes-args/6") - 727 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-distinguishes-args/7") - 728 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-function-distinguishes-args/8") - 729 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-function-distinguishes-args/9") - 730 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-function-distinguishes-args/10") - 731 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-function-distinguishes-args/11") - 732 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-function-distinguishes-args/12") - 733 # . epilogue - 734 89/<- %esp 5/r32/ebp - 735 5d/pop-to-ebp - 736 c3/return - 737 - 738 test-convert-function-returns-result: - 739 # . prologue - 740 55/push-ebp - 741 89/<- %ebp 4/r32/esp - 742 # setup - 743 (clear-stream _test-input-stream) - 744 (clear-stream $_test-input-buffered-file->buffer) - 745 (clear-stream _test-output-stream) - 746 (clear-stream $_test-output-buffered-file->buffer) - 747 # - 748 (write _test-input-stream "fn foo a: int, b: int -> result/eax: int {\n") - 749 (write _test-input-stream " result <- copy a\n") - 750 (write _test-input-stream " result <- increment\n") - 751 (write _test-input-stream "}\n") - 752 # convert - 753 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) - 754 (flush _test-output-buffered-file) - 755 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 761 # check output - 762 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-function-returns-result/0") - 763 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-function-returns-result/1") - 764 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-function-returns-result/2") - 765 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-function-returns-result/3") - 766 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-returns-result/4") - 767 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-function-returns-result/5") - 768 (check-next-stream-line-equal _test-output-stream " 8b/-> *(ebp+0x00000008) 0x00000000/r32" "F - test-convert-function-returns-result/6") - 769 (check-next-stream-line-equal _test-output-stream " 40/increment-eax" "F - test-convert-function-returns-result/7") - 770 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-returns-result/8") - 771 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-function-returns-result/9") - 772 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-function-returns-result/10") - 773 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-function-returns-result/11") - 774 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-function-returns-result/12") - 775 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-function-returns-result/13") - 776 # . epilogue - 777 89/<- %esp 5/r32/ebp - 778 5d/pop-to-ebp - 779 c3/return - 780 - 781 test-convert-function-with-literal-arg: - 782 # . prologue - 783 55/push-ebp - 784 89/<- %ebp 4/r32/esp - 785 # setup - 786 (clear-stream _test-input-stream) - 787 (clear-stream $_test-input-buffered-file->buffer) - 788 (clear-stream _test-output-stream) - 789 (clear-stream $_test-output-buffered-file->buffer) - 790 # - 791 (write _test-input-stream "fn foo a: int, b: int -> result/eax: int {\n") - 792 (write _test-input-stream " result <- copy a\n") - 793 (write _test-input-stream " result <- add 1\n") - 794 (write _test-input-stream "}\n") - 795 # convert - 796 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) - 797 (flush _test-output-buffered-file) - 798 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 804 # check output - 805 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-function-with-literal-arg/0") - 806 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-function-with-literal-arg/1") - 807 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-function-with-literal-arg/2") - 808 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-function-with-literal-arg/3") - 809 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-literal-arg/4") - 810 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-function-with-literal-arg/5") - 811 (check-next-stream-line-equal _test-output-stream " 8b/-> *(ebp+0x00000008) 0x00000000/r32" "F - test-convert-function-with-literal-arg/6") - 812 (check-next-stream-line-equal _test-output-stream " 05/add-to-eax 1/imm32" "F - test-convert-function-with-literal-arg/7") - 813 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-literal-arg/8") - 814 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-function-with-literal-arg/9") - 815 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-function-with-literal-arg/10") - 816 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-function-with-literal-arg/11") - 817 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-function-with-literal-arg/12") - 818 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-function-with-literal-arg/13") - 819 # . epilogue - 820 89/<- %esp 5/r32/ebp - 821 5d/pop-to-ebp - 822 c3/return - 823 - 824 test-convert-function-with-literal-arg-2: - 825 # . prologue - 826 55/push-ebp - 827 89/<- %ebp 4/r32/esp - 828 # setup - 829 (clear-stream _test-input-stream) - 830 (clear-stream $_test-input-buffered-file->buffer) - 831 (clear-stream _test-output-stream) - 832 (clear-stream $_test-output-buffered-file->buffer) - 833 # - 834 (write _test-input-stream "fn foo a: int, b: int -> result/ebx: int {\n") - 835 (write _test-input-stream " result <- copy a\n") - 836 (write _test-input-stream " result <- add 1\n") - 837 (write _test-input-stream "}\n") - 838 # convert - 839 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) - 840 (flush _test-output-buffered-file) - 841 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 847 # check output - 848 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-function-with-literal-arg-2/0") - 849 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-function-with-literal-arg-2/1") - 850 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-function-with-literal-arg-2/2") - 851 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-function-with-literal-arg-2/3") - 852 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-literal-arg-2/4") - 853 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-function-with-literal-arg-2/5") - 854 (check-next-stream-line-equal _test-output-stream " 8b/-> *(ebp+0x00000008) 0x00000003/r32" "F - test-convert-function-with-literal-arg-2/6") - 855 (check-next-stream-line-equal _test-output-stream " 81 0/subop/add %ebx 1/imm32" "F - test-convert-function-with-literal-arg-2/7") - 856 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-literal-arg-2/8") - 857 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-function-with-literal-arg-2/9") - 858 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-function-with-literal-arg-2/10") - 859 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-function-with-literal-arg-2/11") - 860 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-function-with-literal-arg-2/12") - 861 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-function-with-literal-arg-2/13") - 862 # . epilogue - 863 89/<- %esp 5/r32/ebp - 864 5d/pop-to-ebp - 865 c3/return - 866 - 867 test-convert-function-call-with-literal-arg: - 868 # . prologue - 869 55/push-ebp - 870 89/<- %ebp 4/r32/esp - 871 # setup - 872 (clear-stream _test-input-stream) - 873 (clear-stream $_test-input-buffered-file->buffer) - 874 (clear-stream _test-output-stream) - 875 (clear-stream $_test-output-buffered-file->buffer) - 876 # - 877 (write _test-input-stream "fn main -> result/ebx: int {\n") - 878 (write _test-input-stream " result <- do-add 3 4\n") - 879 (write _test-input-stream "}\n") - 880 (write _test-input-stream "fn do-add a: int, b: int -> result/ebx: int {\n") - 881 (write _test-input-stream " result <- copy a\n") - 882 (write _test-input-stream " result <- add b\n") - 883 (write _test-input-stream "}\n") - 884 # convert - 885 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) - 886 (flush _test-output-buffered-file) - 887 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 893 # check output - 894 (check-next-stream-line-equal _test-output-stream "main:" "F - test-convert-function-call-with-literal-arg/0") - 895 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-function-call-with-literal-arg/1") - 896 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-function-call-with-literal-arg/2") - 897 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-function-call-with-literal-arg/3") - 898 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-call-with-literal-arg/4") - 899 (check-next-stream-line-equal _test-output-stream "$main:0x00000001:loop:" "F - test-convert-function-call-with-literal-arg/5") - 900 (check-next-stream-line-equal _test-output-stream " (do-add 3 4)" "F - test-convert-function-call-with-literal-arg/6") - 901 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-call-with-literal-arg/7") - 902 (check-next-stream-line-equal _test-output-stream "$main:0x00000001:break:" "F - test-convert-function-call-with-literal-arg/8") - 903 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-function-call-with-literal-arg/9") - 904 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-function-call-with-literal-arg/10") - 905 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-function-call-with-literal-arg/11") - 906 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-function-call-with-literal-arg/12") - 907 (check-next-stream-line-equal _test-output-stream "do-add:" "F - test-convert-function-call-with-literal-arg/13") - 908 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-function-call-with-literal-arg/14") - 909 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-function-call-with-literal-arg/15") - 910 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-function-call-with-literal-arg/16") - 911 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-call-with-literal-arg/17") - 912 (check-next-stream-line-equal _test-output-stream "$do-add:0x00000002:loop:" "F - test-convert-function-call-with-literal-arg/18") - 913 (check-next-stream-line-equal _test-output-stream " 8b/-> *(ebp+0x00000008) 0x00000003/r32" "F - test-convert-function-call-with-literal-arg/19") - 914 (check-next-stream-line-equal _test-output-stream " 03/add *(ebp+0x0000000c) 0x00000003/r32" "F - test-convert-function-call-with-literal-arg/20") - 915 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-call-with-literal-arg/21") - 916 (check-next-stream-line-equal _test-output-stream "$do-add:0x00000002:break:" "F - test-convert-function-call-with-literal-arg/22") - 917 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-function-call-with-literal-arg/23") - 918 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-function-call-with-literal-arg/24") - 919 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-function-call-with-literal-arg/25") - 920 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-function-call-with-literal-arg/26") - 921 # . epilogue - 922 89/<- %esp 5/r32/ebp - 923 5d/pop-to-ebp - 924 c3/return - 925 - 926 test-convert-function-call-with-signature: - 927 # . prologue - 928 55/push-ebp - 929 89/<- %ebp 4/r32/esp - 930 # setup - 931 (clear-stream _test-input-stream) - 932 (clear-stream $_test-input-buffered-file->buffer) - 933 (clear-stream _test-output-stream) - 934 (clear-stream $_test-output-buffered-file->buffer) - 935 # - 936 (write _test-input-stream "fn main -> result/ebx: int {\n") - 937 (write _test-input-stream " result <- do-add 3 4\n") - 938 (write _test-input-stream "}\n") - 939 (write _test-input-stream "sig do-add a: int, b: int -> result/ebx: int\n") - 940 # convert - 941 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) - 942 (flush _test-output-buffered-file) - 943 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 949 # check output - 950 (check-next-stream-line-equal _test-output-stream "main:" "F - test-convert-function-call-with-signature/0") - 951 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-function-call-with-signature/1") - 952 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-function-call-with-signature/2") - 953 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-function-call-with-signature/3") - 954 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-call-with-signature/4") - 955 (check-next-stream-line-equal _test-output-stream "$main:0x00000001:loop:" "F - test-convert-function-call-with-signature/5") - 956 (check-next-stream-line-equal _test-output-stream " (do-add 3 4)" "F - test-convert-function-call-with-signature/6") - 957 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-call-with-signature/7") - 958 (check-next-stream-line-equal _test-output-stream "$main:0x00000001:break:" "F - test-convert-function-call-with-signature/8") - 959 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-function-call-with-signature/9") - 960 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-function-call-with-signature/10") - 961 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-function-call-with-signature/11") - 962 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-function-call-with-signature/12") - 963 # . epilogue - 964 89/<- %esp 5/r32/ebp - 965 5d/pop-to-ebp - 966 c3/return - 967 - 968 test-convert-function-with-local-var-in-mem: - 969 # . prologue - 970 55/push-ebp - 971 89/<- %ebp 4/r32/esp - 972 # setup - 973 (clear-stream _test-input-stream) - 974 (clear-stream $_test-input-buffered-file->buffer) - 975 (clear-stream _test-output-stream) - 976 (clear-stream $_test-output-buffered-file->buffer) - 977 # - 978 (write _test-input-stream "fn foo {\n") - 979 (write _test-input-stream " var x: int\n") - 980 (write _test-input-stream " increment x\n") - 981 (write _test-input-stream "}\n") - 982 # convert - 983 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) - 984 (flush _test-output-buffered-file) - 985 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 991 # check output - 992 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-function-with-local-var-in-mem/0") - 993 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-function-with-local-var-in-mem/1") - 994 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-function-with-local-var-in-mem/2") - 995 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-function-with-local-var-in-mem/3") - 996 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-local-var-in-mem/4") - 997 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-function-with-local-var-in-mem/5") - 998 (check-next-stream-line-equal _test-output-stream " 68/push 0/imm32" "F - test-convert-function-with-local-var-in-mem/6") - 999 (check-next-stream-line-equal _test-output-stream " ff 0/subop/increment *(ebp+0xfffffffc)" "F - test-convert-function-with-local-var-in-mem/7") - 1000 (check-next-stream-line-equal _test-output-stream " 81 0/subop/add %esp 0x00000004/imm32" "F - test-convert-function-with-local-var-in-mem/8") - 1001 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-local-var-in-mem/9") - 1002 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-function-with-local-var-in-mem/10") - 1003 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-function-with-local-var-in-mem/11") - 1004 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-function-with-local-var-in-mem/12") - 1005 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-function-with-local-var-in-mem/13") - 1006 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-function-with-local-var-in-mem/14") - 1007 # . epilogue - 1008 89/<- %esp 5/r32/ebp - 1009 5d/pop-to-ebp - 1010 c3/return - 1011 - 1012 test-convert-invalid-literal: - 1013 # . prologue - 1014 55/push-ebp - 1015 89/<- %ebp 4/r32/esp - 1016 # setup - 1017 (clear-stream _test-input-stream) - 1018 (clear-stream $_test-input-buffered-file->buffer) - 1019 (clear-stream _test-output-stream) - 1020 (clear-stream $_test-output-buffered-file->buffer) - 1021 (clear-stream _test-error-stream) - 1022 (clear-stream $_test-error-buffered-file->buffer) - 1023 # var ed/edx: exit-descriptor = tailor-exit-descriptor(16) - 1024 68/push 0/imm32 - 1025 68/push 0/imm32 - 1026 89/<- %edx 4/r32/esp - 1027 (tailor-exit-descriptor %edx 0x10) - 1028 # - 1029 (write _test-input-stream "fn foo {\n") - 1030 (write _test-input-stream " increment 1n\n") - 1031 (write _test-input-stream "}\n") - 1032 # convert - 1033 (convert-mu _test-input-buffered-file _test-output-buffered-file _test-error-buffered-file %edx) - 1034 # registers except esp clobbered at this point - 1035 # restore ed - 1036 89/<- %edx 4/r32/esp - 1037 (flush _test-output-buffered-file) - 1038 (flush _test-error-buffered-file) - 1039 +-- 6 lines: #? # dump _test-error-stream --------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 1045 # check output - 1046 (check-stream-equal _test-output-stream "" "F - test-convert-invalid-literal: output should be empty") - 1047 (check-next-stream-line-equal _test-error-stream "fn foo: variable '1n' cannot begin with a digit (or do you have a typo in a number?)" "F - test-convert-invalid-literal: error message") - 1048 # check that stop(1) was called - 1049 (check-ints-equal *(edx+4) 2 "F - test-convert-invalid-literal: exit status") - 1050 # don't restore from ebp - 1051 81 0/subop/add %esp 8/imm32 - 1052 # . epilogue - 1053 5d/pop-to-ebp - 1054 c3/return - 1055 - 1056 test-local-var-in-mem-has-no-initializer: - 1057 # . prologue - 1058 55/push-ebp - 1059 89/<- %ebp 4/r32/esp - 1060 # setup - 1061 (clear-stream _test-input-stream) - 1062 (clear-stream $_test-input-buffered-file->buffer) - 1063 (clear-stream _test-output-stream) - 1064 (clear-stream $_test-output-buffered-file->buffer) - 1065 (clear-stream _test-error-stream) - 1066 (clear-stream $_test-error-buffered-file->buffer) - 1067 # var ed/edx: exit-descriptor = tailor-exit-descriptor(16) - 1068 68/push 0/imm32 - 1069 68/push 0/imm32 - 1070 89/<- %edx 4/r32/esp - 1071 (tailor-exit-descriptor %edx 0x10) - 1072 # - 1073 (write _test-input-stream "fn foo {\n") - 1074 (write _test-input-stream " var x: int <- copy 0\n") - 1075 (write _test-input-stream " increment x\n") - 1076 (write _test-input-stream "}\n") - 1077 # convert - 1078 (convert-mu _test-input-buffered-file _test-output-buffered-file _test-error-buffered-file %edx) - 1079 # registers except esp clobbered at this point - 1080 # restore ed - 1081 89/<- %edx 4/r32/esp - 1082 (flush _test-output-buffered-file) - 1083 (flush _test-error-buffered-file) - 1084 +-- 6 lines: #? # dump _test-error-stream --------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 1090 # check output - 1091 (check-stream-equal _test-output-stream "" "F - test-var-in-mem-has-no-initializer: output should be empty") - 1092 (check-next-stream-line-equal _test-error-stream "fn foo: var x: variables on the stack can't take an initializer" "F - test-var-in-mem-has-no-initializer: error message") - 1093 # check that stop(1) was called - 1094 (check-ints-equal *(edx+4) 2 "F - test-var-in-mem-has-no-initializer: exit status") - 1095 # don't restore from ebp - 1096 81 0/subop/add %esp 8/imm32 - 1097 # . epilogue - 1098 5d/pop-to-ebp - 1099 c3/return - 1100 - 1101 test-convert-function-with-local-var-with-compound-type-in-mem: - 1102 # . prologue - 1103 55/push-ebp - 1104 89/<- %ebp 4/r32/esp - 1105 # setup - 1106 (clear-stream _test-input-stream) - 1107 (clear-stream $_test-input-buffered-file->buffer) - 1108 (clear-stream _test-output-stream) - 1109 (clear-stream $_test-output-buffered-file->buffer) - 1110 # - 1111 (write _test-input-stream "fn foo {\n") - 1112 (write _test-input-stream " var x: (addr int)\n") - 1113 (write _test-input-stream " copy-to x, 0\n") - 1114 (write _test-input-stream "}\n") - 1115 # convert - 1116 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) - 1117 (flush _test-output-buffered-file) - 1118 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 1124 # check output - 1125 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-function-with-local-var-with-compound-type-in-mem/0") - 1126 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-function-with-local-var-with-compound-type-in-mem/1") - 1127 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-function-with-local-var-with-compound-type-in-mem/2") - 1128 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-function-with-local-var-with-compound-type-in-mem/3") - 1129 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-local-var-with-compound-type-in-mem/4") - 1130 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-function-with-local-var-with-compound-type-in-mem/5") - 1131 (check-next-stream-line-equal _test-output-stream " 68/push 0/imm32" "F - test-convert-function-with-local-var-with-compound-type-in-mem/6") - 1132 (check-next-stream-line-equal _test-output-stream " c7 0/subop/copy *(ebp+0xfffffffc) 0/imm32" "F - test-convert-function-with-local-var-with-compound-type-in-mem/7") - 1133 (check-next-stream-line-equal _test-output-stream " 81 0/subop/add %esp 0x00000004/imm32" "F - test-convert-function-with-local-var-with-compound-type-in-mem/8") - 1134 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-local-var-with-compound-type-in-mem/9") - 1135 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-function-with-local-var-with-compound-type-in-mem/10") - 1136 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-function-with-local-var-with-compound-type-in-mem/11") - 1137 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-function-with-local-var-with-compound-type-in-mem/12") - 1138 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-function-with-local-var-with-compound-type-in-mem/13") - 1139 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-function-with-local-var-with-compound-type-in-mem/14") - 1140 # . epilogue - 1141 89/<- %esp 5/r32/ebp - 1142 5d/pop-to-ebp - 1143 c3/return - 1144 - 1145 test-convert-function-with-local-var-in-reg: - 1146 # . prologue - 1147 55/push-ebp - 1148 89/<- %ebp 4/r32/esp - 1149 # setup - 1150 (clear-stream _test-input-stream) - 1151 (clear-stream $_test-input-buffered-file->buffer) - 1152 (clear-stream _test-output-stream) - 1153 (clear-stream $_test-output-buffered-file->buffer) - 1154 # - 1155 (write _test-input-stream "fn foo {\n") - 1156 (write _test-input-stream " var x/ecx: int <- copy 3\n") - 1157 (write _test-input-stream " x <- increment\n") - 1158 (write _test-input-stream "}\n") - 1159 # convert - 1160 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) - 1161 (flush _test-output-buffered-file) - 1162 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 1168 # check output - 1169 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-function-with-local-var-in-reg/0") - 1170 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-function-with-local-var-in-reg/1") - 1171 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-function-with-local-var-in-reg/2") - 1172 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-function-with-local-var-in-reg/3") - 1173 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-local-var-in-reg/4") - 1174 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-function-with-local-var-in-reg/5") - 1175 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %ecx" "F - test-convert-function-with-local-var-in-reg/6") - 1176 (check-next-stream-line-equal _test-output-stream " b9/copy-to-ecx 3/imm32" "F - test-convert-function-with-local-var-in-reg/7") - 1177 (check-next-stream-line-equal _test-output-stream " 41/increment-ecx" "F - test-convert-function-with-local-var-in-reg/8") - 1178 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %ecx" "F - test-convert-function-with-local-var-in-reg/9") - 1179 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-local-var-in-reg/10") - 1180 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-function-with-local-var-in-reg/11") - 1181 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-function-with-local-var-in-reg/12") - 1182 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-function-with-local-var-in-reg/13") - 1183 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-function-with-local-var-in-reg/14") - 1184 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-function-with-local-var-in-reg/15") - 1185 # . epilogue - 1186 89/<- %esp 5/r32/ebp - 1187 5d/pop-to-ebp - 1188 c3/return - 1189 - 1190 test-convert-function-with-allocate: - 1191 # . prologue - 1192 55/push-ebp - 1193 89/<- %ebp 4/r32/esp - 1194 # setup - 1195 (clear-stream _test-input-stream) - 1196 (clear-stream $_test-input-buffered-file->buffer) - 1197 (clear-stream _test-output-stream) - 1198 (clear-stream $_test-output-buffered-file->buffer) - 1199 # - 1200 (write _test-input-stream "fn foo {\n") - 1201 (write _test-input-stream " var x/ecx: (addr handle int) <- copy 0\n") - 1202 (write _test-input-stream " allocate x\n") - 1203 (write _test-input-stream "}\n") - 1204 # convert - 1205 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) - 1206 (flush _test-output-buffered-file) - 1207 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 1213 # check output - 1214 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-function-with-allocate/0") - 1215 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-function-with-allocate/1") - 1216 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-function-with-allocate/2") - 1217 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-function-with-allocate/3") - 1218 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-allocate/4") - 1219 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-function-with-allocate/5") - 1220 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %ecx" "F - test-convert-function-with-allocate/6") - 1221 (check-next-stream-line-equal _test-output-stream " b9/copy-to-ecx 0/imm32" "F - test-convert-function-with-allocate/7") - 1222 (check-next-stream-line-equal _test-output-stream " (allocate Heap 0x00000004 %ecx)" "F - test-convert-function-with-allocate/8") # 4 = size-of(int) - 1223 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %ecx" "F - test-convert-function-with-allocate/9") - 1224 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-allocate/10") - 1225 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-function-with-allocate/11") - 1226 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-function-with-allocate/12") - 1227 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-function-with-allocate/13") - 1228 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-function-with-allocate/14") - 1229 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-function-with-allocate/15") - 1230 # . epilogue - 1231 89/<- %esp 5/r32/ebp - 1232 5d/pop-to-ebp - 1233 c3/return - 1234 - 1235 test-initializer-in-hex: - 1236 # . prologue - 1237 55/push-ebp - 1238 89/<- %ebp 4/r32/esp - 1239 # setup - 1240 (clear-stream _test-input-stream) - 1241 (clear-stream $_test-input-buffered-file->buffer) - 1242 (clear-stream _test-output-stream) - 1243 (clear-stream $_test-output-buffered-file->buffer) - 1244 (clear-stream _test-error-stream) - 1245 (clear-stream $_test-error-buffered-file->buffer) - 1246 # var ed/edx: exit-descriptor = tailor-exit-descriptor(16) - 1247 68/push 0/imm32 - 1248 68/push 0/imm32 - 1249 89/<- %edx 4/r32/esp - 1250 (tailor-exit-descriptor %edx 0x10) - 1251 # - 1252 (write _test-input-stream "fn foo {\n") - 1253 (write _test-input-stream " var x/ecx: int <- copy 10\n") - 1254 (write _test-input-stream "}\n") - 1255 # convert - 1256 (convert-mu _test-input-buffered-file _test-output-buffered-file _test-error-buffered-file %edx) - 1257 # registers except esp clobbered at this point - 1258 # restore ed - 1259 89/<- %edx 4/r32/esp - 1260 (flush _test-output-buffered-file) - 1261 (flush _test-error-buffered-file) - 1262 +-- 6 lines: #? # dump _test-error-stream --------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 1268 # check output - 1269 (check-stream-equal _test-output-stream "" "F - test-initializer-in-hex: output should be empty") - 1270 (check-next-stream-line-equal _test-error-stream "literal integers are always hex in Mu; either start '10' with a '0x' to be unambiguous, or convert it to decimal." "F - test-initializer-in-hex: error message") - 1271 # check that stop(1) was called - 1272 (check-ints-equal *(edx+4) 2 "F - test-initializer-in-hex: exit status") - 1273 # don't restore from ebp - 1274 81 0/subop/add %esp 8/imm32 - 1275 # . epilogue - 1276 5d/pop-to-ebp - 1277 c3/return - 1278 - 1279 test-convert-function-with-second-local-var-in-same-reg: - 1280 # . prologue - 1281 55/push-ebp - 1282 89/<- %ebp 4/r32/esp - 1283 # setup - 1284 (clear-stream _test-input-stream) - 1285 (clear-stream $_test-input-buffered-file->buffer) - 1286 (clear-stream _test-output-stream) - 1287 (clear-stream $_test-output-buffered-file->buffer) - 1288 # - 1289 (write _test-input-stream "fn foo {\n") - 1290 (write _test-input-stream " var x/ecx: int <- copy 3\n") - 1291 (write _test-input-stream " var y/ecx: int <- copy 4\n") - 1292 (write _test-input-stream " y <- increment\n") - 1293 (write _test-input-stream "}\n") - 1294 # convert - 1295 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) - 1296 (flush _test-output-buffered-file) - 1297 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 1303 # check output - 1304 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-function-with-second-local-var-in-same-reg/0") - 1305 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-function-with-second-local-var-in-same-reg/1") - 1306 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-function-with-second-local-var-in-same-reg/2") - 1307 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-function-with-second-local-var-in-same-reg/3") - 1308 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-second-local-var-in-same-reg/4") - 1309 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-function-with-second-local-var-in-same-reg/5") - 1310 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %ecx" "F - test-convert-function-with-second-local-var-in-same-reg/6") - 1311 (check-next-stream-line-equal _test-output-stream " b9/copy-to-ecx 3/imm32" "F - test-convert-function-with-second-local-var-in-same-reg/7") - 1312 (check-next-stream-line-equal _test-output-stream " b9/copy-to-ecx 4/imm32" "F - test-convert-function-with-second-local-var-in-same-reg/8") - 1313 (check-next-stream-line-equal _test-output-stream " 41/increment-ecx" "F - test-convert-function-with-second-local-var-in-same-reg/9") - 1314 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %ecx" "F - test-convert-function-with-second-local-var-in-same-reg/10") - 1315 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-second-local-var-in-same-reg/11") - 1316 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-function-with-second-local-var-in-same-reg/12") - 1317 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-function-with-second-local-var-in-same-reg/13") - 1318 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-function-with-second-local-var-in-same-reg/14") - 1319 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-function-with-second-local-var-in-same-reg/15") - 1320 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-function-with-second-local-var-in-same-reg/16") - 1321 # . epilogue - 1322 89/<- %esp 5/r32/ebp - 1323 5d/pop-to-ebp - 1324 c3/return - 1325 - 1326 test-read-clobbered-reg-var: - 1327 # . prologue - 1328 55/push-ebp - 1329 89/<- %ebp 4/r32/esp - 1330 # setup - 1331 (clear-stream _test-input-stream) - 1332 (clear-stream $_test-input-buffered-file->buffer) - 1333 (clear-stream _test-output-stream) - 1334 (clear-stream $_test-output-buffered-file->buffer) - 1335 (clear-stream _test-error-stream) - 1336 (clear-stream $_test-error-buffered-file->buffer) - 1337 # var ed/edx: exit-descriptor = tailor-exit-descriptor(16) # bytes of args in call to convert-mu - 1338 68/push 0/imm32 - 1339 68/push 0/imm32 - 1340 89/<- %edx 4/r32/esp - 1341 (tailor-exit-descriptor %edx 0x10) - 1342 # - 1343 (write _test-input-stream "fn foo {\n") - 1344 (write _test-input-stream " var x/ecx: int <- copy 3\n") - 1345 (write _test-input-stream " var y/ecx: int <- copy 4\n") - 1346 (write _test-input-stream " x <- increment\n") - 1347 (write _test-input-stream "}\n") - 1348 # convert - 1349 (convert-mu _test-input-buffered-file _test-output-buffered-file _test-error-buffered-file %edx) - 1350 # registers except esp clobbered at this point - 1351 # restore ed - 1352 89/<- %edx 4/r32/esp - 1353 (flush _test-output-buffered-file) - 1354 (flush _test-error-buffered-file) - 1355 +-- 6 lines: #? # dump _test-error-stream --------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 1361 # check output - 1362 (check-stream-equal _test-output-stream "" "F - test-read-clobbered-reg-var: output should be empty") - 1363 (check-next-stream-line-equal _test-error-stream "fn foo: register ecx reads var 'x' after writing var 'y'" "F - test-read-clobbered-reg-var: error message") - 1364 # check that stop(1) was called - 1365 (check-ints-equal *(edx+4) 2 "F - test-read-clobbered-reg-var: exit status") - 1366 # don't restore from ebp - 1367 81 0/subop/add %esp 8/imm32 - 1368 # . epilogue - 1369 5d/pop-to-ebp - 1370 c3/return - 1371 - 1372 test-convert-function-call: - 1373 # . prologue - 1374 55/push-ebp - 1375 89/<- %ebp 4/r32/esp - 1376 # setup - 1377 (clear-stream _test-input-stream) - 1378 (clear-stream $_test-input-buffered-file->buffer) - 1379 (clear-stream _test-output-stream) - 1380 (clear-stream $_test-output-buffered-file->buffer) - 1381 # - 1382 (write _test-input-stream "fn main -> result/ebx: int {\n") - 1383 (write _test-input-stream " result <- foo\n") - 1384 (write _test-input-stream "}\n") - 1385 (write _test-input-stream "fn foo -> result/ebx: int {\n") - 1386 (write _test-input-stream " result <- copy 3\n") + 422 Primitive-type-ids: # (addr int) + 423 0x34 + 424 + 425 # == Type definitions + 426 # Program->types contains some typeinfo for each type definition. + 427 # Types contain vars with types, but can't specify registers. + 428 Typeinfo-id: # type-id + 429 0/imm32 + 430 Typeinfo-fields: # (handle table (handle array byte) (handle typeinfo-entry)) + 431 4/imm32 + 432 # Total size must be >= 0 + 433 # During parsing it may take on two additional values: + 434 # -2: not yet initialized + 435 # -1: in process of being computed + 436 # See populate-mu-type-sizes for details. + 437 Typeinfo-total-size-in-bytes: # int + 438 0xc/imm32 + 439 Typeinfo-next: # (handle typeinfo) + 440 0x10/imm32 + 441 Typeinfo-size: # (addr int) + 442 0x18/imm32 + 443 + 444 # Each entry in the typeinfo->fields table has a pointer to a string and a + 445 # pointer to a typeinfo-entry. + 446 Typeinfo-fields-row-size: # (addr int) + 447 0x10/imm32 + 448 + 449 # typeinfo-entry objects have information about a field in a single record type + 450 # + 451 # each field of a type is represented using two var's: + 452 # 1. the input var: expected type of the field; convenient for creating using parse-var-with-type + 453 # 2. the output var: a constant containing the byte offset; convenient for code-generation + 454 # computing the output happens after parsing; in the meantime we preserve the + 455 # order of fields in the 'index' field. + 456 Typeinfo-entry-input-var: # (handle var) + 457 0/imm32 + 458 Typeinfo-entry-index: # int + 459 8/imm32 + 460 Typeinfo-entry-output-var: # (handle var) + 461 0xc/imm32 + 462 Typeinfo-entry-size: # (addr int) + 463 0x14/imm32 + 464 + 465 == code + 466 + 467 Entry: + 468 # . prologue + 469 89/<- %ebp 4/r32/esp + 470 (new-segment *Heap-size Heap) + 471 # if (argv[1] == "test') run-tests() + 472 { + 473 # if (argc <= 1) break + 474 81 7/subop/compare *ebp 1/imm32 + 475 7e/jump-if-<= break/disp8 + 476 # if (argv[1] != "test") break + 477 (kernel-string-equal? *(ebp+8) "test") # => eax + 478 3d/compare-eax-and 0/imm32/false + 479 74/jump-if-= break/disp8 + 480 # + 481 (run-tests) + 482 # syscall(exit, *Num-test-failures) + 483 8b/-> *Num-test-failures 3/r32/ebx + 484 eb/jump $mu-main:end/disp8 + 485 } + 486 # otherwise convert Stdin + 487 (convert-mu Stdin Stdout Stderr 0) + 488 (flush Stdout) + 489 # syscall(exit, 0) + 490 bb/copy-to-ebx 0/imm32 + 491 $mu-main:end: + 492 e8/call syscall_exit/disp32 + 493 + 494 convert-mu: # in: (addr buffered-file), out: (addr buffered-file), err: (addr buffered-file), ed: (addr exit-descriptor) + 495 # . prologue + 496 55/push-ebp + 497 89/<- %ebp 4/r32/esp + 498 # . save registers + 499 50/push-eax + 500 # initialize global data structures + 501 c7 0/subop/copy *Next-block-index 1/imm32 + 502 8b/-> *Primitive-type-ids 0/r32/eax + 503 89/<- *Type-id 0/r32/eax # stream-write + 504 c7 0/subop/copy *_Program-functions 0/imm32 + 505 c7 0/subop/copy *_Program-functions->payload 0/imm32 + 506 c7 0/subop/copy *_Program-types 0/imm32 + 507 c7 0/subop/copy *_Program-types->payload 0/imm32 + 508 c7 0/subop/copy *_Program-signatures 0/imm32 + 509 c7 0/subop/copy *_Program-signatures->payload 0/imm32 + 510 # + 511 (parse-mu *(ebp+8) *(ebp+0x10) *(ebp+0x14)) + 512 (populate-mu-type-sizes *(ebp+0x10) *(ebp+0x14)) + 513 #? (dump-typeinfos "=== typeinfos\n") + 514 (check-mu-types *(ebp+0x10) *(ebp+0x14)) + 515 (emit-subx *(ebp+0xc) *(ebp+0x10) *(ebp+0x14)) + 516 $convert-mu:end: + 517 # . restore registers + 518 58/pop-to-eax + 519 # . epilogue + 520 89/<- %esp 5/r32/ebp + 521 5d/pop-to-ebp + 522 c3/return + 523 + 524 test-convert-empty-input: + 525 # empty input => empty output + 526 # . prologue + 527 55/push-ebp + 528 89/<- %ebp 4/r32/esp + 529 # setup + 530 (clear-stream _test-input-stream) + 531 (clear-stream $_test-input-buffered-file->buffer) + 532 (clear-stream _test-output-stream) + 533 (clear-stream $_test-output-buffered-file->buffer) + 534 # + 535 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) + 536 (flush _test-output-buffered-file) + 537 (check-stream-equal _test-output-stream "" "F - test-convert-empty-input") + 538 # . epilogue + 539 89/<- %esp 5/r32/ebp + 540 5d/pop-to-ebp + 541 c3/return + 542 + 543 test-convert-function-skeleton: + 544 # . prologue + 545 55/push-ebp + 546 89/<- %ebp 4/r32/esp + 547 # setup + 548 (clear-stream _test-input-stream) + 549 (clear-stream $_test-input-buffered-file->buffer) + 550 (clear-stream _test-output-stream) + 551 (clear-stream $_test-output-buffered-file->buffer) + 552 # + 553 (write _test-input-stream "fn foo {\n") + 554 (write _test-input-stream "}\n") + 555 # convert + 556 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) + 557 (flush _test-output-buffered-file) + 558 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- + 564 # check output + 565 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-function-skeleton/0") + 566 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-function-skeleton/1") + 567 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-function-skeleton/2") + 568 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-function-skeleton/3") + 569 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-function-skeleton/4") + 570 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-function-skeleton/5") + 571 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-function-skeleton/6") + 572 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-function-skeleton/7") + 573 # . epilogue + 574 89/<- %esp 5/r32/ebp + 575 5d/pop-to-ebp + 576 c3/return + 577 + 578 test-convert-multiple-function-skeletons: + 579 # . prologue + 580 55/push-ebp + 581 89/<- %ebp 4/r32/esp + 582 # setup + 583 (clear-stream _test-input-stream) + 584 (clear-stream $_test-input-buffered-file->buffer) + 585 (clear-stream _test-output-stream) + 586 (clear-stream $_test-output-buffered-file->buffer) + 587 # + 588 (write _test-input-stream "fn foo {\n") + 589 (write _test-input-stream "}\n") + 590 (write _test-input-stream "fn bar {\n") + 591 (write _test-input-stream "}\n") + 592 # convert + 593 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) + 594 (flush _test-output-buffered-file) + 595 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- + 601 # check first function + 602 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-multiple-function-skeletons/0") + 603 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-multiple-function-skeletons/1") + 604 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-multiple-function-skeletons/2") + 605 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-multiple-function-skeletons/3") + 606 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-multiple-function-skeletons/4") + 607 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-multiple-function-skeletons/5") + 608 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-multiple-function-skeletons/6") + 609 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-multiple-function-skeletons/7") + 610 # check second function + 611 (check-next-stream-line-equal _test-output-stream "bar:" "F - test-convert-multiple-function-skeletons/10") + 612 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-multiple-function-skeletons/11") + 613 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-multiple-function-skeletons/12") + 614 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-multiple-function-skeletons/13") + 615 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-multiple-function-skeletons/14") + 616 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-multiple-function-skeletons/15") + 617 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-multiple-function-skeletons/16") + 618 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-multiple-function-skeletons/17") + 619 # . epilogue + 620 89/<- %esp 5/r32/ebp + 621 5d/pop-to-ebp + 622 c3/return + 623 + 624 test-convert-function-with-arg: + 625 # . prologue + 626 55/push-ebp + 627 89/<- %ebp 4/r32/esp + 628 # setup + 629 (clear-stream _test-input-stream) + 630 (clear-stream $_test-input-buffered-file->buffer) + 631 (clear-stream _test-output-stream) + 632 (clear-stream $_test-output-buffered-file->buffer) + 633 # + 634 (write _test-input-stream "fn foo n: int {\n") + 635 (write _test-input-stream "}\n") + 636 # convert + 637 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) + 638 (flush _test-output-buffered-file) + 639 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- + 645 # check output + 646 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-function-with-arg/0") + 647 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-function-with-arg/1") + 648 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-function-with-arg/2") + 649 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-function-with-arg/3") + 650 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-function-with-arg/4") + 651 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-function-with-arg/5") + 652 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-function-with-arg/6") + 653 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-function-with-arg/7") + 654 # . epilogue + 655 89/<- %esp 5/r32/ebp + 656 5d/pop-to-ebp + 657 c3/return + 658 + 659 test-convert-function-with-arg-and-body: + 660 # . prologue + 661 55/push-ebp + 662 89/<- %ebp 4/r32/esp + 663 # setup + 664 (clear-stream _test-input-stream) + 665 (clear-stream $_test-input-buffered-file->buffer) + 666 (clear-stream _test-output-stream) + 667 (clear-stream $_test-output-buffered-file->buffer) + 668 # + 669 (write _test-input-stream "fn foo n: int {\n") + 670 (write _test-input-stream " increment n\n") + 671 (write _test-input-stream "}\n") + 672 # convert + 673 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) + 674 (flush _test-output-buffered-file) + 675 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- + 681 # check output + 682 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-function-with-arg-and-body/0") + 683 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-function-with-arg-and-body/1") + 684 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-function-with-arg-and-body/2") + 685 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-function-with-arg-and-body/3") + 686 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-arg-and-body/4") + 687 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-function-with-arg-and-body/5") + 688 (check-next-stream-line-equal _test-output-stream " ff 0/subop/increment *(ebp+0x00000008)" "F - test-convert-function-with-arg-and-body/6") + 689 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-arg-and-body/7") + 690 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-function-with-arg-and-body/8") + 691 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-function-with-arg-and-body/9") + 692 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-function-with-arg-and-body/10") + 693 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-function-with-arg-and-body/11") + 694 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-function-with-arg-and-body/12") + 695 # . epilogue + 696 89/<- %esp 5/r32/ebp + 697 5d/pop-to-ebp + 698 c3/return + 699 + 700 test-convert-function-distinguishes-args: + 701 # . prologue + 702 55/push-ebp + 703 89/<- %ebp 4/r32/esp + 704 # setup + 705 (clear-stream _test-input-stream) + 706 (clear-stream $_test-input-buffered-file->buffer) + 707 (clear-stream _test-output-stream) + 708 (clear-stream $_test-output-buffered-file->buffer) + 709 # + 710 (write _test-input-stream "fn foo a: int, b: int {\n") + 711 (write _test-input-stream " increment b\n") + 712 (write _test-input-stream "}\n") + 713 # convert + 714 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) + 715 (flush _test-output-buffered-file) + 716 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- + 722 # check output + 723 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-function-distinguishes-args/0") + 724 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-function-distinguishes-args/1") + 725 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-function-distinguishes-args/2") + 726 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-function-distinguishes-args/3") + 727 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-distinguishes-args/4") + 728 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-function-distinguishes-args/5") + 729 (check-next-stream-line-equal _test-output-stream " ff 0/subop/increment *(ebp+0x0000000c)" "F - test-convert-function-distinguishes-args/6") + 730 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-distinguishes-args/7") + 731 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-function-distinguishes-args/8") + 732 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-function-distinguishes-args/9") + 733 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-function-distinguishes-args/10") + 734 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-function-distinguishes-args/11") + 735 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-function-distinguishes-args/12") + 736 # . epilogue + 737 89/<- %esp 5/r32/ebp + 738 5d/pop-to-ebp + 739 c3/return + 740 + 741 test-convert-function-returns-result: + 742 # . prologue + 743 55/push-ebp + 744 89/<- %ebp 4/r32/esp + 745 # setup + 746 (clear-stream _test-input-stream) + 747 (clear-stream $_test-input-buffered-file->buffer) + 748 (clear-stream _test-output-stream) + 749 (clear-stream $_test-output-buffered-file->buffer) + 750 # + 751 (write _test-input-stream "fn foo a: int, b: int -> result/eax: int {\n") + 752 (write _test-input-stream " result <- copy a\n") + 753 (write _test-input-stream " result <- increment\n") + 754 (write _test-input-stream "}\n") + 755 # convert + 756 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) + 757 (flush _test-output-buffered-file) + 758 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- + 764 # check output + 765 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-function-returns-result/0") + 766 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-function-returns-result/1") + 767 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-function-returns-result/2") + 768 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-function-returns-result/3") + 769 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-returns-result/4") + 770 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-function-returns-result/5") + 771 (check-next-stream-line-equal _test-output-stream " 8b/-> *(ebp+0x00000008) 0x00000000/r32" "F - test-convert-function-returns-result/6") + 772 (check-next-stream-line-equal _test-output-stream " 40/increment-eax" "F - test-convert-function-returns-result/7") + 773 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-returns-result/8") + 774 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-function-returns-result/9") + 775 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-function-returns-result/10") + 776 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-function-returns-result/11") + 777 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-function-returns-result/12") + 778 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-function-returns-result/13") + 779 # . epilogue + 780 89/<- %esp 5/r32/ebp + 781 5d/pop-to-ebp + 782 c3/return + 783 + 784 test-convert-function-with-literal-arg: + 785 # . prologue + 786 55/push-ebp + 787 89/<- %ebp 4/r32/esp + 788 # setup + 789 (clear-stream _test-input-stream) + 790 (clear-stream $_test-input-buffered-file->buffer) + 791 (clear-stream _test-output-stream) + 792 (clear-stream $_test-output-buffered-file->buffer) + 793 # + 794 (write _test-input-stream "fn foo a: int, b: int -> result/eax: int {\n") + 795 (write _test-input-stream " result <- copy a\n") + 796 (write _test-input-stream " result <- add 1\n") + 797 (write _test-input-stream "}\n") + 798 # convert + 799 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) + 800 (flush _test-output-buffered-file) + 801 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- + 807 # check output + 808 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-function-with-literal-arg/0") + 809 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-function-with-literal-arg/1") + 810 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-function-with-literal-arg/2") + 811 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-function-with-literal-arg/3") + 812 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-literal-arg/4") + 813 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-function-with-literal-arg/5") + 814 (check-next-stream-line-equal _test-output-stream " 8b/-> *(ebp+0x00000008) 0x00000000/r32" "F - test-convert-function-with-literal-arg/6") + 815 (check-next-stream-line-equal _test-output-stream " 05/add-to-eax 1/imm32" "F - test-convert-function-with-literal-arg/7") + 816 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-literal-arg/8") + 817 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-function-with-literal-arg/9") + 818 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-function-with-literal-arg/10") + 819 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-function-with-literal-arg/11") + 820 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-function-with-literal-arg/12") + 821 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-function-with-literal-arg/13") + 822 # . epilogue + 823 89/<- %esp 5/r32/ebp + 824 5d/pop-to-ebp + 825 c3/return + 826 + 827 test-convert-function-with-literal-arg-2: + 828 # . prologue + 829 55/push-ebp + 830 89/<- %ebp 4/r32/esp + 831 # setup + 832 (clear-stream _test-input-stream) + 833 (clear-stream $_test-input-buffered-file->buffer) + 834 (clear-stream _test-output-stream) + 835 (clear-stream $_test-output-buffered-file->buffer) + 836 # + 837 (write _test-input-stream "fn foo a: int, b: int -> result/ebx: int {\n") + 838 (write _test-input-stream " result <- copy a\n") + 839 (write _test-input-stream " result <- add 1\n") + 840 (write _test-input-stream "}\n") + 841 # convert + 842 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) + 843 (flush _test-output-buffered-file) + 844 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- + 850 # check output + 851 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-function-with-literal-arg-2/0") + 852 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-function-with-literal-arg-2/1") + 853 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-function-with-literal-arg-2/2") + 854 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-function-with-literal-arg-2/3") + 855 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-literal-arg-2/4") + 856 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-function-with-literal-arg-2/5") + 857 (check-next-stream-line-equal _test-output-stream " 8b/-> *(ebp+0x00000008) 0x00000003/r32" "F - test-convert-function-with-literal-arg-2/6") + 858 (check-next-stream-line-equal _test-output-stream " 81 0/subop/add %ebx 1/imm32" "F - test-convert-function-with-literal-arg-2/7") + 859 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-literal-arg-2/8") + 860 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-function-with-literal-arg-2/9") + 861 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-function-with-literal-arg-2/10") + 862 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-function-with-literal-arg-2/11") + 863 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-function-with-literal-arg-2/12") + 864 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-function-with-literal-arg-2/13") + 865 # . epilogue + 866 89/<- %esp 5/r32/ebp + 867 5d/pop-to-ebp + 868 c3/return + 869 + 870 test-convert-function-call-with-literal-arg: + 871 # . prologue + 872 55/push-ebp + 873 89/<- %ebp 4/r32/esp + 874 # setup + 875 (clear-stream _test-input-stream) + 876 (clear-stream $_test-input-buffered-file->buffer) + 877 (clear-stream _test-output-stream) + 878 (clear-stream $_test-output-buffered-file->buffer) + 879 # + 880 (write _test-input-stream "fn main -> result/ebx: int {\n") + 881 (write _test-input-stream " result <- do-add 3 4\n") + 882 (write _test-input-stream "}\n") + 883 (write _test-input-stream "fn do-add a: int, b: int -> result/ebx: int {\n") + 884 (write _test-input-stream " result <- copy a\n") + 885 (write _test-input-stream " result <- add b\n") + 886 (write _test-input-stream "}\n") + 887 # convert + 888 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) + 889 (flush _test-output-buffered-file) + 890 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- + 896 # check output + 897 (check-next-stream-line-equal _test-output-stream "main:" "F - test-convert-function-call-with-literal-arg/0") + 898 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-function-call-with-literal-arg/1") + 899 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-function-call-with-literal-arg/2") + 900 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-function-call-with-literal-arg/3") + 901 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-call-with-literal-arg/4") + 902 (check-next-stream-line-equal _test-output-stream "$main:0x00000001:loop:" "F - test-convert-function-call-with-literal-arg/5") + 903 (check-next-stream-line-equal _test-output-stream " (do-add 3 4)" "F - test-convert-function-call-with-literal-arg/6") + 904 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-call-with-literal-arg/7") + 905 (check-next-stream-line-equal _test-output-stream "$main:0x00000001:break:" "F - test-convert-function-call-with-literal-arg/8") + 906 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-function-call-with-literal-arg/9") + 907 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-function-call-with-literal-arg/10") + 908 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-function-call-with-literal-arg/11") + 909 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-function-call-with-literal-arg/12") + 910 (check-next-stream-line-equal _test-output-stream "do-add:" "F - test-convert-function-call-with-literal-arg/13") + 911 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-function-call-with-literal-arg/14") + 912 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-function-call-with-literal-arg/15") + 913 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-function-call-with-literal-arg/16") + 914 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-call-with-literal-arg/17") + 915 (check-next-stream-line-equal _test-output-stream "$do-add:0x00000002:loop:" "F - test-convert-function-call-with-literal-arg/18") + 916 (check-next-stream-line-equal _test-output-stream " 8b/-> *(ebp+0x00000008) 0x00000003/r32" "F - test-convert-function-call-with-literal-arg/19") + 917 (check-next-stream-line-equal _test-output-stream " 03/add *(ebp+0x0000000c) 0x00000003/r32" "F - test-convert-function-call-with-literal-arg/20") + 918 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-call-with-literal-arg/21") + 919 (check-next-stream-line-equal _test-output-stream "$do-add:0x00000002:break:" "F - test-convert-function-call-with-literal-arg/22") + 920 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-function-call-with-literal-arg/23") + 921 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-function-call-with-literal-arg/24") + 922 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-function-call-with-literal-arg/25") + 923 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-function-call-with-literal-arg/26") + 924 # . epilogue + 925 89/<- %esp 5/r32/ebp + 926 5d/pop-to-ebp + 927 c3/return + 928 + 929 test-convert-function-call-with-signature: + 930 # . prologue + 931 55/push-ebp + 932 89/<- %ebp 4/r32/esp + 933 # setup + 934 (clear-stream _test-input-stream) + 935 (clear-stream $_test-input-buffered-file->buffer) + 936 (clear-stream _test-output-stream) + 937 (clear-stream $_test-output-buffered-file->buffer) + 938 # + 939 (write _test-input-stream "fn main -> result/ebx: int {\n") + 940 (write _test-input-stream " result <- do-add 3 4\n") + 941 (write _test-input-stream "}\n") + 942 (write _test-input-stream "sig do-add a: int, b: int -> result/ebx: int\n") + 943 # convert + 944 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) + 945 (flush _test-output-buffered-file) + 946 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- + 952 # check output + 953 (check-next-stream-line-equal _test-output-stream "main:" "F - test-convert-function-call-with-signature/0") + 954 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-function-call-with-signature/1") + 955 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-function-call-with-signature/2") + 956 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-function-call-with-signature/3") + 957 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-call-with-signature/4") + 958 (check-next-stream-line-equal _test-output-stream "$main:0x00000001:loop:" "F - test-convert-function-call-with-signature/5") + 959 (check-next-stream-line-equal _test-output-stream " (do-add 3 4)" "F - test-convert-function-call-with-signature/6") + 960 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-call-with-signature/7") + 961 (check-next-stream-line-equal _test-output-stream "$main:0x00000001:break:" "F - test-convert-function-call-with-signature/8") + 962 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-function-call-with-signature/9") + 963 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-function-call-with-signature/10") + 964 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-function-call-with-signature/11") + 965 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-function-call-with-signature/12") + 966 # . epilogue + 967 89/<- %esp 5/r32/ebp + 968 5d/pop-to-ebp + 969 c3/return + 970 + 971 test-convert-function-with-local-var-in-mem: + 972 # . prologue + 973 55/push-ebp + 974 89/<- %ebp 4/r32/esp + 975 # setup + 976 (clear-stream _test-input-stream) + 977 (clear-stream $_test-input-buffered-file->buffer) + 978 (clear-stream _test-output-stream) + 979 (clear-stream $_test-output-buffered-file->buffer) + 980 # + 981 (write _test-input-stream "fn foo {\n") + 982 (write _test-input-stream " var x: int\n") + 983 (write _test-input-stream " increment x\n") + 984 (write _test-input-stream "}\n") + 985 # convert + 986 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) + 987 (flush _test-output-buffered-file) + 988 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- + 994 # check output + 995 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-function-with-local-var-in-mem/0") + 996 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-function-with-local-var-in-mem/1") + 997 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-function-with-local-var-in-mem/2") + 998 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-function-with-local-var-in-mem/3") + 999 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-local-var-in-mem/4") + 1000 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-function-with-local-var-in-mem/5") + 1001 (check-next-stream-line-equal _test-output-stream " 68/push 0/imm32" "F - test-convert-function-with-local-var-in-mem/6") + 1002 (check-next-stream-line-equal _test-output-stream " ff 0/subop/increment *(ebp+0xfffffffc)" "F - test-convert-function-with-local-var-in-mem/7") + 1003 (check-next-stream-line-equal _test-output-stream " 81 0/subop/add %esp 0x00000004/imm32" "F - test-convert-function-with-local-var-in-mem/8") + 1004 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-local-var-in-mem/9") + 1005 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-function-with-local-var-in-mem/10") + 1006 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-function-with-local-var-in-mem/11") + 1007 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-function-with-local-var-in-mem/12") + 1008 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-function-with-local-var-in-mem/13") + 1009 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-function-with-local-var-in-mem/14") + 1010 # . epilogue + 1011 89/<- %esp 5/r32/ebp + 1012 5d/pop-to-ebp + 1013 c3/return + 1014 + 1015 test-convert-invalid-literal: + 1016 # . prologue + 1017 55/push-ebp + 1018 89/<- %ebp 4/r32/esp + 1019 # setup + 1020 (clear-stream _test-input-stream) + 1021 (clear-stream $_test-input-buffered-file->buffer) + 1022 (clear-stream _test-output-stream) + 1023 (clear-stream $_test-output-buffered-file->buffer) + 1024 (clear-stream _test-error-stream) + 1025 (clear-stream $_test-error-buffered-file->buffer) + 1026 # var ed/edx: exit-descriptor = tailor-exit-descriptor(16) + 1027 68/push 0/imm32 + 1028 68/push 0/imm32 + 1029 89/<- %edx 4/r32/esp + 1030 (tailor-exit-descriptor %edx 0x10) + 1031 # + 1032 (write _test-input-stream "fn foo {\n") + 1033 (write _test-input-stream " increment 1n\n") + 1034 (write _test-input-stream "}\n") + 1035 # convert + 1036 (convert-mu _test-input-buffered-file _test-output-buffered-file _test-error-buffered-file %edx) + 1037 # registers except esp clobbered at this point + 1038 # restore ed + 1039 89/<- %edx 4/r32/esp + 1040 (flush _test-output-buffered-file) + 1041 (flush _test-error-buffered-file) + 1042 +-- 6 lines: #? # dump _test-error-stream ------------------------------------------------------------------------------------------------------------------------------------------ + 1048 # check output + 1049 (check-stream-equal _test-output-stream "" "F - test-convert-invalid-literal: output should be empty") + 1050 (check-next-stream-line-equal _test-error-stream "fn foo: variable '1n' cannot begin with a digit (or do you have a typo in a number?)" "F - test-convert-invalid-literal: error message") + 1051 # check that stop(1) was called + 1052 (check-ints-equal *(edx+4) 2 "F - test-convert-invalid-literal: exit status") + 1053 # don't restore from ebp + 1054 81 0/subop/add %esp 8/imm32 + 1055 # . epilogue + 1056 5d/pop-to-ebp + 1057 c3/return + 1058 + 1059 test-local-var-in-mem-has-no-initializer: + 1060 # . prologue + 1061 55/push-ebp + 1062 89/<- %ebp 4/r32/esp + 1063 # setup + 1064 (clear-stream _test-input-stream) + 1065 (clear-stream $_test-input-buffered-file->buffer) + 1066 (clear-stream _test-output-stream) + 1067 (clear-stream $_test-output-buffered-file->buffer) + 1068 (clear-stream _test-error-stream) + 1069 (clear-stream $_test-error-buffered-file->buffer) + 1070 # var ed/edx: exit-descriptor = tailor-exit-descriptor(16) + 1071 68/push 0/imm32 + 1072 68/push 0/imm32 + 1073 89/<- %edx 4/r32/esp + 1074 (tailor-exit-descriptor %edx 0x10) + 1075 # + 1076 (write _test-input-stream "fn foo {\n") + 1077 (write _test-input-stream " var x: int <- copy 0\n") + 1078 (write _test-input-stream " increment x\n") + 1079 (write _test-input-stream "}\n") + 1080 # convert + 1081 (convert-mu _test-input-buffered-file _test-output-buffered-file _test-error-buffered-file %edx) + 1082 # registers except esp clobbered at this point + 1083 # restore ed + 1084 89/<- %edx 4/r32/esp + 1085 (flush _test-output-buffered-file) + 1086 (flush _test-error-buffered-file) + 1087 +-- 6 lines: #? # dump _test-error-stream ------------------------------------------------------------------------------------------------------------------------------------------ + 1093 # check output + 1094 (check-stream-equal _test-output-stream "" "F - test-var-in-mem-has-no-initializer: output should be empty") + 1095 (check-next-stream-line-equal _test-error-stream "fn foo: var x: variables on the stack can't take an initializer" "F - test-var-in-mem-has-no-initializer: error message") + 1096 # check that stop(1) was called + 1097 (check-ints-equal *(edx+4) 2 "F - test-var-in-mem-has-no-initializer: exit status") + 1098 # don't restore from ebp + 1099 81 0/subop/add %esp 8/imm32 + 1100 # . epilogue + 1101 5d/pop-to-ebp + 1102 c3/return + 1103 + 1104 test-convert-function-with-local-var-with-compound-type-in-mem: + 1105 # . prologue + 1106 55/push-ebp + 1107 89/<- %ebp 4/r32/esp + 1108 # setup + 1109 (clear-stream _test-input-stream) + 1110 (clear-stream $_test-input-buffered-file->buffer) + 1111 (clear-stream _test-output-stream) + 1112 (clear-stream $_test-output-buffered-file->buffer) + 1113 # + 1114 (write _test-input-stream "fn foo {\n") + 1115 (write _test-input-stream " var x: (addr int)\n") + 1116 (write _test-input-stream " copy-to x, 0\n") + 1117 (write _test-input-stream "}\n") + 1118 # convert + 1119 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) + 1120 (flush _test-output-buffered-file) + 1121 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- + 1127 # check output + 1128 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-function-with-local-var-with-compound-type-in-mem/0") + 1129 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-function-with-local-var-with-compound-type-in-mem/1") + 1130 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-function-with-local-var-with-compound-type-in-mem/2") + 1131 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-function-with-local-var-with-compound-type-in-mem/3") + 1132 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-local-var-with-compound-type-in-mem/4") + 1133 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-function-with-local-var-with-compound-type-in-mem/5") + 1134 (check-next-stream-line-equal _test-output-stream " 68/push 0/imm32" "F - test-convert-function-with-local-var-with-compound-type-in-mem/6") + 1135 (check-next-stream-line-equal _test-output-stream " c7 0/subop/copy *(ebp+0xfffffffc) 0/imm32" "F - test-convert-function-with-local-var-with-compound-type-in-mem/7") + 1136 (check-next-stream-line-equal _test-output-stream " 81 0/subop/add %esp 0x00000004/imm32" "F - test-convert-function-with-local-var-with-compound-type-in-mem/8") + 1137 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-local-var-with-compound-type-in-mem/9") + 1138 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-function-with-local-var-with-compound-type-in-mem/10") + 1139 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-function-with-local-var-with-compound-type-in-mem/11") + 1140 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-function-with-local-var-with-compound-type-in-mem/12") + 1141 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-function-with-local-var-with-compound-type-in-mem/13") + 1142 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-function-with-local-var-with-compound-type-in-mem/14") + 1143 # . epilogue + 1144 89/<- %esp 5/r32/ebp + 1145 5d/pop-to-ebp + 1146 c3/return + 1147 + 1148 test-convert-function-with-local-var-in-reg: + 1149 # . prologue + 1150 55/push-ebp + 1151 89/<- %ebp 4/r32/esp + 1152 # setup + 1153 (clear-stream _test-input-stream) + 1154 (clear-stream $_test-input-buffered-file->buffer) + 1155 (clear-stream _test-output-stream) + 1156 (clear-stream $_test-output-buffered-file->buffer) + 1157 # + 1158 (write _test-input-stream "fn foo {\n") + 1159 (write _test-input-stream " var x/ecx: int <- copy 3\n") + 1160 (write _test-input-stream " x <- increment\n") + 1161 (write _test-input-stream "}\n") + 1162 # convert + 1163 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) + 1164 (flush _test-output-buffered-file) + 1165 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- + 1171 # check output + 1172 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-function-with-local-var-in-reg/0") + 1173 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-function-with-local-var-in-reg/1") + 1174 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-function-with-local-var-in-reg/2") + 1175 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-function-with-local-var-in-reg/3") + 1176 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-local-var-in-reg/4") + 1177 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-function-with-local-var-in-reg/5") + 1178 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %ecx" "F - test-convert-function-with-local-var-in-reg/6") + 1179 (check-next-stream-line-equal _test-output-stream " b9/copy-to-ecx 3/imm32" "F - test-convert-function-with-local-var-in-reg/7") + 1180 (check-next-stream-line-equal _test-output-stream " 41/increment-ecx" "F - test-convert-function-with-local-var-in-reg/8") + 1181 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %ecx" "F - test-convert-function-with-local-var-in-reg/9") + 1182 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-local-var-in-reg/10") + 1183 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-function-with-local-var-in-reg/11") + 1184 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-function-with-local-var-in-reg/12") + 1185 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-function-with-local-var-in-reg/13") + 1186 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-function-with-local-var-in-reg/14") + 1187 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-function-with-local-var-in-reg/15") + 1188 # . epilogue + 1189 89/<- %esp 5/r32/ebp + 1190 5d/pop-to-ebp + 1191 c3/return + 1192 + 1193 test-convert-function-with-allocate: + 1194 # . prologue + 1195 55/push-ebp + 1196 89/<- %ebp 4/r32/esp + 1197 # setup + 1198 (clear-stream _test-input-stream) + 1199 (clear-stream $_test-input-buffered-file->buffer) + 1200 (clear-stream _test-output-stream) + 1201 (clear-stream $_test-output-buffered-file->buffer) + 1202 # + 1203 (write _test-input-stream "fn foo {\n") + 1204 (write _test-input-stream " var x/ecx: (addr handle int) <- copy 0\n") + 1205 (write _test-input-stream " allocate x\n") + 1206 (write _test-input-stream "}\n") + 1207 # convert + 1208 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) + 1209 (flush _test-output-buffered-file) + 1210 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- + 1216 # check output + 1217 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-function-with-allocate/0") + 1218 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-function-with-allocate/1") + 1219 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-function-with-allocate/2") + 1220 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-function-with-allocate/3") + 1221 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-allocate/4") + 1222 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-function-with-allocate/5") + 1223 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %ecx" "F - test-convert-function-with-allocate/6") + 1224 (check-next-stream-line-equal _test-output-stream " b9/copy-to-ecx 0/imm32" "F - test-convert-function-with-allocate/7") + 1225 (check-next-stream-line-equal _test-output-stream " (allocate Heap 0x00000004 %ecx)" "F - test-convert-function-with-allocate/8") # 4 = size-of(int) + 1226 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %ecx" "F - test-convert-function-with-allocate/9") + 1227 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-allocate/10") + 1228 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-function-with-allocate/11") + 1229 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-function-with-allocate/12") + 1230 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-function-with-allocate/13") + 1231 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-function-with-allocate/14") + 1232 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-function-with-allocate/15") + 1233 # . epilogue + 1234 89/<- %esp 5/r32/ebp + 1235 5d/pop-to-ebp + 1236 c3/return + 1237 + 1238 test-initializer-in-hex: + 1239 # . prologue + 1240 55/push-ebp + 1241 89/<- %ebp 4/r32/esp + 1242 # setup + 1243 (clear-stream _test-input-stream) + 1244 (clear-stream $_test-input-buffered-file->buffer) + 1245 (clear-stream _test-output-stream) + 1246 (clear-stream $_test-output-buffered-file->buffer) + 1247 (clear-stream _test-error-stream) + 1248 (clear-stream $_test-error-buffered-file->buffer) + 1249 # var ed/edx: exit-descriptor = tailor-exit-descriptor(16) + 1250 68/push 0/imm32 + 1251 68/push 0/imm32 + 1252 89/<- %edx 4/r32/esp + 1253 (tailor-exit-descriptor %edx 0x10) + 1254 # + 1255 (write _test-input-stream "fn foo {\n") + 1256 (write _test-input-stream " var x/ecx: int <- copy 10\n") + 1257 (write _test-input-stream "}\n") + 1258 # convert + 1259 (convert-mu _test-input-buffered-file _test-output-buffered-file _test-error-buffered-file %edx) + 1260 # registers except esp clobbered at this point + 1261 # restore ed + 1262 89/<- %edx 4/r32/esp + 1263 (flush _test-output-buffered-file) + 1264 (flush _test-error-buffered-file) + 1265 +-- 6 lines: #? # dump _test-error-stream ------------------------------------------------------------------------------------------------------------------------------------------ + 1271 # check output + 1272 (check-stream-equal _test-output-stream "" "F - test-initializer-in-hex: output should be empty") + 1273 (check-next-stream-line-equal _test-error-stream "literal integers are always hex in Mu; either start '10' with a '0x' to be unambiguous, or convert it to decimal." "F - test-initializer-in-hex: error message") + 1274 # check that stop(1) was called + 1275 (check-ints-equal *(edx+4) 2 "F - test-initializer-in-hex: exit status") + 1276 # don't restore from ebp + 1277 81 0/subop/add %esp 8/imm32 + 1278 # . epilogue + 1279 5d/pop-to-ebp + 1280 c3/return + 1281 + 1282 test-convert-function-with-second-local-var-in-same-reg: + 1283 # . prologue + 1284 55/push-ebp + 1285 89/<- %ebp 4/r32/esp + 1286 # setup + 1287 (clear-stream _test-input-stream) + 1288 (clear-stream $_test-input-buffered-file->buffer) + 1289 (clear-stream _test-output-stream) + 1290 (clear-stream $_test-output-buffered-file->buffer) + 1291 # + 1292 (write _test-input-stream "fn foo {\n") + 1293 (write _test-input-stream " var x/ecx: int <- copy 3\n") + 1294 (write _test-input-stream " var y/ecx: int <- copy 4\n") + 1295 (write _test-input-stream " y <- increment\n") + 1296 (write _test-input-stream "}\n") + 1297 # convert + 1298 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) + 1299 (flush _test-output-buffered-file) + 1300 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- + 1306 # check output + 1307 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-function-with-second-local-var-in-same-reg/0") + 1308 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-function-with-second-local-var-in-same-reg/1") + 1309 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-function-with-second-local-var-in-same-reg/2") + 1310 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-function-with-second-local-var-in-same-reg/3") + 1311 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-second-local-var-in-same-reg/4") + 1312 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-function-with-second-local-var-in-same-reg/5") + 1313 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %ecx" "F - test-convert-function-with-second-local-var-in-same-reg/6") + 1314 (check-next-stream-line-equal _test-output-stream " b9/copy-to-ecx 3/imm32" "F - test-convert-function-with-second-local-var-in-same-reg/7") + 1315 (check-next-stream-line-equal _test-output-stream " b9/copy-to-ecx 4/imm32" "F - test-convert-function-with-second-local-var-in-same-reg/8") + 1316 (check-next-stream-line-equal _test-output-stream " 41/increment-ecx" "F - test-convert-function-with-second-local-var-in-same-reg/9") + 1317 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %ecx" "F - test-convert-function-with-second-local-var-in-same-reg/10") + 1318 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-second-local-var-in-same-reg/11") + 1319 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-function-with-second-local-var-in-same-reg/12") + 1320 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-function-with-second-local-var-in-same-reg/13") + 1321 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-function-with-second-local-var-in-same-reg/14") + 1322 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-function-with-second-local-var-in-same-reg/15") + 1323 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-function-with-second-local-var-in-same-reg/16") + 1324 # . epilogue + 1325 89/<- %esp 5/r32/ebp + 1326 5d/pop-to-ebp + 1327 c3/return + 1328 + 1329 test-read-clobbered-reg-var: + 1330 # . prologue + 1331 55/push-ebp + 1332 89/<- %ebp 4/r32/esp + 1333 # setup + 1334 (clear-stream _test-input-stream) + 1335 (clear-stream $_test-input-buffered-file->buffer) + 1336 (clear-stream _test-output-stream) + 1337 (clear-stream $_test-output-buffered-file->buffer) + 1338 (clear-stream _test-error-stream) + 1339 (clear-stream $_test-error-buffered-file->buffer) + 1340 # var ed/edx: exit-descriptor = tailor-exit-descriptor(16) # bytes of args in call to convert-mu + 1341 68/push 0/imm32 + 1342 68/push 0/imm32 + 1343 89/<- %edx 4/r32/esp + 1344 (tailor-exit-descriptor %edx 0x10) + 1345 # + 1346 (write _test-input-stream "fn foo {\n") + 1347 (write _test-input-stream " var x/ecx: int <- copy 3\n") + 1348 (write _test-input-stream " var y/ecx: int <- copy 4\n") + 1349 (write _test-input-stream " x <- increment\n") + 1350 (write _test-input-stream "}\n") + 1351 # convert + 1352 (convert-mu _test-input-buffered-file _test-output-buffered-file _test-error-buffered-file %edx) + 1353 # registers except esp clobbered at this point + 1354 # restore ed + 1355 89/<- %edx 4/r32/esp + 1356 (flush _test-output-buffered-file) + 1357 (flush _test-error-buffered-file) + 1358 +-- 6 lines: #? # dump _test-error-stream ------------------------------------------------------------------------------------------------------------------------------------------ + 1364 # check output + 1365 (check-stream-equal _test-output-stream "" "F - test-read-clobbered-reg-var: output should be empty") + 1366 (check-next-stream-line-equal _test-error-stream "fn foo: register ecx reads var 'x' after writing var 'y'" "F - test-read-clobbered-reg-var: error message") + 1367 # check that stop(1) was called + 1368 (check-ints-equal *(edx+4) 2 "F - test-read-clobbered-reg-var: exit status") + 1369 # don't restore from ebp + 1370 81 0/subop/add %esp 8/imm32 + 1371 # . epilogue + 1372 5d/pop-to-ebp + 1373 c3/return + 1374 + 1375 test-convert-function-call: + 1376 # . prologue + 1377 55/push-ebp + 1378 89/<- %ebp 4/r32/esp + 1379 # setup + 1380 (clear-stream _test-input-stream) + 1381 (clear-stream $_test-input-buffered-file->buffer) + 1382 (clear-stream _test-output-stream) + 1383 (clear-stream $_test-output-buffered-file->buffer) + 1384 # + 1385 (write _test-input-stream "fn main -> result/ebx: int {\n") + 1386 (write _test-input-stream " result <- foo\n") 1387 (write _test-input-stream "}\n") - 1388 # convert - 1389 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) - 1390 (flush _test-output-buffered-file) - 1391 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 1397 # check output - 1398 (check-next-stream-line-equal _test-output-stream "main:" "F - test-convert-function-call/0") - 1399 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-function-call/1") - 1400 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-function-call/2") - 1401 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-function-call/3") - 1402 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-call/4") - 1403 (check-next-stream-line-equal _test-output-stream "$main:0x00000001:loop:" "F - test-convert-function-call/5") - 1404 (check-next-stream-line-equal _test-output-stream " (foo)" "F - test-convert-function-call/6") - 1405 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-call/7") - 1406 (check-next-stream-line-equal _test-output-stream "$main:0x00000001:break:" "F - test-convert-function-call/8") - 1407 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-function-call/9") - 1408 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-function-call/10") - 1409 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-function-call/11") - 1410 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-function-call/12") - 1411 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-function-call/13") - 1412 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-function-call/14") - 1413 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-function-call/15") - 1414 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-function-call/16") - 1415 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-call/17") - 1416 (check-next-stream-line-equal _test-output-stream "$foo:0x00000002:loop:" "F - test-convert-function-call/18") - 1417 (check-next-stream-line-equal _test-output-stream " bb/copy-to-ebx 3/imm32" "F - test-convert-function-call/19") - 1418 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-call/20") - 1419 (check-next-stream-line-equal _test-output-stream "$foo:0x00000002:break:" "F - test-convert-function-call/21") - 1420 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-function-call/22") - 1421 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-function-call/23") - 1422 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-function-call/24") - 1423 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-function-call/25") - 1424 # . epilogue - 1425 89/<- %esp 5/r32/ebp - 1426 5d/pop-to-ebp - 1427 c3/return - 1428 - 1429 test-convert-function-call-with-inout-with-compound-type: - 1430 # . prologue - 1431 55/push-ebp - 1432 89/<- %ebp 4/r32/esp - 1433 # setup - 1434 (clear-stream _test-input-stream) - 1435 (clear-stream $_test-input-buffered-file->buffer) - 1436 (clear-stream _test-output-stream) - 1437 (clear-stream $_test-output-buffered-file->buffer) - 1438 # - 1439 (write _test-input-stream "fn f {\n") - 1440 (write _test-input-stream " var x: (addr int)\n") - 1441 (write _test-input-stream " g x\n") - 1442 (write _test-input-stream "}\n") - 1443 (write _test-input-stream "fn g a: (addr int) {\n") - 1444 (write _test-input-stream "}\n") - 1445 # convert - 1446 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) - 1447 (flush _test-output-buffered-file) - 1448 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 1454 # check output - 1455 (check-next-stream-line-equal _test-output-stream "f:" "F - test-convert-function-call-with-inout-with-compound-type/0") - 1456 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-function-call-with-inout-with-compound-type/1") - 1457 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-function-call-with-inout-with-compound-type/2") - 1458 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-function-call-with-inout-with-compound-type/3") - 1459 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-call-with-inout-with-compound-type/4") - 1460 (check-next-stream-line-equal _test-output-stream "$f:0x00000001:loop:" "F - test-convert-function-call-with-inout-with-compound-type/5") - 1461 (check-next-stream-line-equal _test-output-stream " 68/push 0/imm32" "F - test-convert-function-call-with-inout-with-compound-type/6") - 1462 (check-next-stream-line-equal _test-output-stream " (g *(ebp+0xfffffffc))" "F - test-convert-function-call-with-inout-with-compound-type/7") - 1463 (check-next-stream-line-equal _test-output-stream " 81 0/subop/add %esp 0x00000004/imm32" "F - test-convert-function-call-with-inout-with-compound-type/8") - 1464 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-call-with-inout-with-compound-type/9") - 1465 (check-next-stream-line-equal _test-output-stream "$f:0x00000001:break:" "F - test-convert-function-call-with-inout-with-compound-type/10") - 1466 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-function-call-with-inout-with-compound-type/11") - 1467 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-function-call-with-inout-with-compound-type/12") - 1468 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-function-call-with-inout-with-compound-type/13") - 1469 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-function-call-with-inout-with-compound-type/14") - 1470 (check-next-stream-line-equal _test-output-stream "g:" "F - test-convert-function-call-with-inout-with-compound-type/15") - 1471 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-function-call-with-inout-with-compound-type/16") - 1472 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-function-call-with-inout-with-compound-type/17") - 1473 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-function-call-with-inout-with-compound-type/18") - 1474 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-function-call-with-inout-with-compound-type/19") - 1475 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-function-call-with-inout-with-compound-type/20") - 1476 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-function-call-with-inout-with-compound-type/21") - 1477 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-function-call-with-inout-with-compound-type/22") - 1478 # . epilogue - 1479 89/<- %esp 5/r32/ebp - 1480 5d/pop-to-ebp - 1481 c3/return - 1482 - 1483 test-convert-function-call-with-inout-with-type-parameter: - 1484 # . prologue - 1485 55/push-ebp - 1486 89/<- %ebp 4/r32/esp - 1487 # setup - 1488 (clear-stream _test-input-stream) - 1489 (clear-stream $_test-input-buffered-file->buffer) - 1490 (clear-stream _test-output-stream) - 1491 (clear-stream $_test-output-buffered-file->buffer) - 1492 (clear-stream _test-error-stream) - 1493 (clear-stream $_test-error-buffered-file->buffer) - 1494 # var ed/edx: exit-descriptor = tailor-exit-descriptor(16) - 1495 68/push 0/imm32 - 1496 68/push 0/imm32 - 1497 89/<- %edx 4/r32/esp - 1498 (tailor-exit-descriptor %edx 0x10) - 1499 # - 1500 (write _test-input-stream "fn f {\n") - 1501 (write _test-input-stream " var x: (addr int)\n") - 1502 (write _test-input-stream " g x\n") - 1503 (write _test-input-stream "}\n") - 1504 (write _test-input-stream "fn g a: (addr _) {\n") - 1505 (write _test-input-stream "}\n") - 1506 # convert - 1507 (convert-mu _test-input-buffered-file _test-output-buffered-file _test-error-buffered-file %edx) - 1508 # registers except esp clobbered at this point - 1509 # restore ed - 1510 89/<- %edx 4/r32/esp - 1511 (flush _test-output-buffered-file) - 1512 (flush _test-error-buffered-file) - 1513 +-- 6 lines: #? # dump _test-error-stream --------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 1519 # no error; types matched - 1520 (check-stream-equal _test-error-stream "" "F - test-convert-function-call-with-inout-with-type-parameter: error stream should be empty") - 1521 # don't bother checking the generated code; that's in the test 'test-local-clobbered-by-fn-output' below - 1522 # don't restore from ebp - 1523 81 0/subop/add %esp 8/imm32 - 1524 # . epilogue - 1525 5d/pop-to-ebp - 1526 c3/return - 1527 - 1528 test-convert-function-call-with-incorrect-inout-type: - 1529 # . prologue - 1530 55/push-ebp - 1531 89/<- %ebp 4/r32/esp - 1532 # setup - 1533 (clear-stream _test-input-stream) - 1534 (clear-stream $_test-input-buffered-file->buffer) - 1535 (clear-stream _test-output-stream) - 1536 (clear-stream $_test-output-buffered-file->buffer) - 1537 (clear-stream _test-error-stream) - 1538 (clear-stream $_test-error-buffered-file->buffer) - 1539 # var ed/edx: exit-descriptor = tailor-exit-descriptor(16) - 1540 68/push 0/imm32 - 1541 68/push 0/imm32 - 1542 89/<- %edx 4/r32/esp - 1543 (tailor-exit-descriptor %edx 0x10) - 1544 # - 1545 (write _test-input-stream "fn f {\n") - 1546 (write _test-input-stream " var x: int\n") - 1547 (write _test-input-stream " g x\n") - 1548 (write _test-input-stream "}\n") - 1549 (write _test-input-stream "fn g a: foo {\n") - 1550 (write _test-input-stream "}\n") - 1551 # convert - 1552 (convert-mu _test-input-buffered-file _test-output-buffered-file _test-error-buffered-file %edx) - 1553 # registers except esp clobbered at this point - 1554 # restore ed - 1555 89/<- %edx 4/r32/esp - 1556 (flush _test-output-buffered-file) - 1557 (flush _test-error-buffered-file) - 1558 +-- 6 lines: #? # dump _test-error-stream --------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 1564 # check output - 1565 (check-stream-equal _test-output-stream "" "F - test-convert-function-call-with-incorrect-inout-type: output should be empty") - 1566 (check-next-stream-line-equal _test-error-stream "fn f: call g: type for inout 'x' is not right" "F - test-convert-function-call-with-incorrect-inout-type: error message") - 1567 # check that stop(1) was called - 1568 (check-ints-equal *(edx+4) 2 "F - test-convert-function-call-with-incorrect-inout-type: exit status") - 1569 # don't restore from ebp - 1570 81 0/subop/add %esp 8/imm32 - 1571 5d/pop-to-ebp - 1572 c3/return - 1573 - 1574 test-convert-function-call-with-inout-with-incorrect-compound-type: - 1575 # . prologue - 1576 55/push-ebp - 1577 89/<- %ebp 4/r32/esp - 1578 # setup - 1579 (clear-stream _test-input-stream) - 1580 (clear-stream $_test-input-buffered-file->buffer) - 1581 (clear-stream _test-output-stream) - 1582 (clear-stream $_test-output-buffered-file->buffer) - 1583 (clear-stream _test-error-stream) - 1584 (clear-stream $_test-error-buffered-file->buffer) - 1585 # var ed/edx: exit-descriptor = tailor-exit-descriptor(16) - 1586 68/push 0/imm32 - 1587 68/push 0/imm32 - 1588 89/<- %edx 4/r32/esp - 1589 (tailor-exit-descriptor %edx 0x10) - 1590 # - 1591 (write _test-input-stream "fn f {\n") - 1592 (write _test-input-stream " var x: (addr int)\n") - 1593 (write _test-input-stream " g x\n") - 1594 (write _test-input-stream "}\n") - 1595 (write _test-input-stream "fn g a: (addr bool) {\n") - 1596 (write _test-input-stream "}\n") - 1597 # convert - 1598 (convert-mu _test-input-buffered-file _test-output-buffered-file _test-error-buffered-file %edx) - 1599 # registers except esp clobbered at this point - 1600 # restore ed - 1601 89/<- %edx 4/r32/esp - 1602 (flush _test-output-buffered-file) - 1603 (flush _test-error-buffered-file) - 1604 +-- 6 lines: #? # dump _test-error-stream --------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 1610 # check output - 1611 (check-stream-equal _test-output-stream "" "F - test-convert-function-call-with-inout-with-incorrect-compound-type: output should be empty") - 1612 (check-next-stream-line-equal _test-error-stream "fn f: call g: type for inout 'x' is not right" "F - test-convert-function-call-with-inout-with-incorrect-compound-type: error message") - 1613 # don't restore from ebp - 1614 81 0/subop/add %esp 8/imm32 - 1615 # . epilogue - 1616 5d/pop-to-ebp - 1617 c3/return - 1618 - 1619 test-convert-function-call-with-inout-with-multiple-type-parameters: - 1620 # . prologue - 1621 55/push-ebp - 1622 89/<- %ebp 4/r32/esp - 1623 # setup - 1624 (clear-stream _test-input-stream) - 1625 (clear-stream $_test-input-buffered-file->buffer) - 1626 (clear-stream _test-output-stream) - 1627 (clear-stream $_test-output-buffered-file->buffer) - 1628 (clear-stream _test-error-stream) - 1629 (clear-stream $_test-error-buffered-file->buffer) - 1630 # var ed/edx: exit-descriptor = tailor-exit-descriptor(16) - 1631 68/push 0/imm32 - 1632 68/push 0/imm32 - 1633 89/<- %edx 4/r32/esp - 1634 (tailor-exit-descriptor %edx 0x10) - 1635 # - 1636 (write _test-input-stream "fn f {\n") - 1637 (write _test-input-stream " var x: (addr int)\n") - 1638 (write _test-input-stream " var y: (addr int)\n") - 1639 (write _test-input-stream " g x, y\n") - 1640 (write _test-input-stream "}\n") - 1641 (write _test-input-stream "fn g a: (addr _), b: (addr _) {\n") - 1642 (write _test-input-stream "}\n") - 1643 # convert - 1644 (convert-mu _test-input-buffered-file _test-output-buffered-file _test-error-buffered-file %edx) - 1645 # registers except esp clobbered at this point - 1646 # restore ed - 1647 89/<- %edx 4/r32/esp - 1648 (flush _test-output-buffered-file) - 1649 (flush _test-error-buffered-file) - 1650 +-- 6 lines: #? # dump _test-error-stream --------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 1656 # no errors - 1657 (check-stream-equal _test-error-stream "" "F - test-convert-function-call-with-inout-with-multiple-type-parameters: error stream should be empty") - 1658 # don't bother checking the generated code - 1659 # don't restore from ebp - 1660 81 0/subop/add %esp 8/imm32 - 1661 # . epilogue - 1662 5d/pop-to-ebp - 1663 c3/return - 1664 - 1665 test-convert-function-call-with-inout-with-incompatible-type-parameters: - 1666 # . prologue - 1667 55/push-ebp - 1668 89/<- %ebp 4/r32/esp - 1669 # setup - 1670 (clear-stream _test-input-stream) - 1671 (clear-stream $_test-input-buffered-file->buffer) - 1672 (clear-stream _test-output-stream) - 1673 (clear-stream $_test-output-buffered-file->buffer) - 1674 (clear-stream _test-error-stream) - 1675 (clear-stream $_test-error-buffered-file->buffer) - 1676 # var ed/edx: exit-descriptor = tailor-exit-descriptor(16) - 1677 68/push 0/imm32 - 1678 68/push 0/imm32 - 1679 89/<- %edx 4/r32/esp - 1680 (tailor-exit-descriptor %edx 0x10) - 1681 # - 1682 (write _test-input-stream "fn f {\n") - 1683 (write _test-input-stream " var x: (addr int)\n") - 1684 (write _test-input-stream " var y: (addr boolean)\n") - 1685 (write _test-input-stream " g x, y\n") - 1686 (write _test-input-stream "}\n") - 1687 (write _test-input-stream "fn g a: (addr _T), b: (addr _T) {\n") - 1688 (write _test-input-stream "}\n") - 1689 # convert - 1690 (convert-mu _test-input-buffered-file _test-output-buffered-file _test-error-buffered-file %edx) - 1691 # registers except esp clobbered at this point - 1692 # restore ed - 1693 89/<- %edx 4/r32/esp - 1694 (flush _test-output-buffered-file) - 1695 (flush _test-error-buffered-file) - 1696 +-- 6 lines: #? # dump _test-error-stream --------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 1702 # check output - 1703 (check-stream-equal _test-output-stream "" "F - test-convert-function-call-with-inout-with-incompatible-type-parameters: output should be empty") - 1704 (check-next-stream-line-equal _test-error-stream "fn f: call g: type for inout 'y' is not right" "F - test-convert-function-call-with-inout-with-incompatible-type-parameters: error message") - 1705 # don't restore from ebp - 1706 81 0/subop/add %esp 8/imm32 - 1707 # . epilogue - 1708 5d/pop-to-ebp - 1709 c3/return - 1710 - 1711 test-convert-function-call-with-too-few-inouts: - 1712 # . prologue - 1713 55/push-ebp - 1714 89/<- %ebp 4/r32/esp - 1715 # setup - 1716 (clear-stream _test-input-stream) - 1717 (clear-stream $_test-input-buffered-file->buffer) - 1718 (clear-stream _test-output-stream) - 1719 (clear-stream $_test-output-buffered-file->buffer) - 1720 (clear-stream _test-error-stream) - 1721 (clear-stream $_test-error-buffered-file->buffer) - 1722 # var ed/edx: exit-descriptor = tailor-exit-descriptor(16) - 1723 68/push 0/imm32 - 1724 68/push 0/imm32 - 1725 89/<- %edx 4/r32/esp - 1726 (tailor-exit-descriptor %edx 0x10) - 1727 # - 1728 (write _test-input-stream "fn f {\n") - 1729 (write _test-input-stream " g\n") - 1730 (write _test-input-stream "}\n") - 1731 (write _test-input-stream "fn g a: int {\n") - 1732 (write _test-input-stream "}\n") - 1733 # convert - 1734 (convert-mu _test-input-buffered-file _test-output-buffered-file _test-error-buffered-file %edx) - 1735 # registers except esp clobbered at this point - 1736 # restore ed - 1737 89/<- %edx 4/r32/esp - 1738 (flush _test-output-buffered-file) - 1739 (flush _test-error-buffered-file) - 1740 +-- 6 lines: #? # dump _test-error-stream --------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 1746 # check output - 1747 (check-stream-equal _test-output-stream "" "F - test-convert-function-call-with-too-few-inouts: output should be empty") - 1748 (check-next-stream-line-equal _test-error-stream "fn f: call g: too few inouts" "F - test-convert-function-call-with-too-few-inouts: error message") - 1749 # check that stop(1) was called - 1750 (check-ints-equal *(edx+4) 2 "F - test-convert-function-call-with-too-few-inouts: exit status") - 1751 # don't restore from ebp - 1752 81 0/subop/add %esp 8/imm32 - 1753 5d/pop-to-ebp - 1754 c3/return - 1755 - 1756 test-convert-function-call-with-too-many-inouts: - 1757 # . prologue - 1758 55/push-ebp - 1759 89/<- %ebp 4/r32/esp - 1760 # setup - 1761 (clear-stream _test-input-stream) - 1762 (clear-stream $_test-input-buffered-file->buffer) - 1763 (clear-stream _test-output-stream) - 1764 (clear-stream $_test-output-buffered-file->buffer) - 1765 (clear-stream _test-error-stream) - 1766 (clear-stream $_test-error-buffered-file->buffer) - 1767 # var ed/edx: exit-descriptor = tailor-exit-descriptor(16) - 1768 68/push 0/imm32 - 1769 68/push 0/imm32 - 1770 89/<- %edx 4/r32/esp - 1771 (tailor-exit-descriptor %edx 0x10) - 1772 # - 1773 (write _test-input-stream "fn f {\n") - 1774 (write _test-input-stream " var x: int\n") - 1775 (write _test-input-stream " g x\n") - 1776 (write _test-input-stream "}\n") - 1777 (write _test-input-stream "fn g {\n") - 1778 (write _test-input-stream "}\n") - 1779 # convert - 1780 (convert-mu _test-input-buffered-file _test-output-buffered-file _test-error-buffered-file %edx) - 1781 # registers except esp clobbered at this point - 1782 # restore ed - 1783 89/<- %edx 4/r32/esp - 1784 (flush _test-output-buffered-file) - 1785 (flush _test-error-buffered-file) - 1786 +-- 6 lines: #? # dump _test-error-stream --------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 1792 # check output - 1793 (check-stream-equal _test-output-stream "" "F - test-convert-function-call-with-too-many-inouts: output should be empty") - 1794 (check-next-stream-line-equal _test-error-stream "fn f: call g: too many inouts" "F - test-convert-function-call-with-too-many-inouts: error message") - 1795 # check that stop(1) was called - 1796 (check-ints-equal *(edx+4) 2 "F - test-convert-function-call-with-too-many-inouts: exit status") - 1797 # don't restore from ebp - 1798 81 0/subop/add %esp 8/imm32 - 1799 5d/pop-to-ebp - 1800 c3/return - 1801 - 1802 test-convert-function-call-with-incorrect-output-type: - 1803 # . prologue - 1804 55/push-ebp - 1805 89/<- %ebp 4/r32/esp - 1806 # setup - 1807 (clear-stream _test-input-stream) - 1808 (clear-stream $_test-input-buffered-file->buffer) - 1809 (clear-stream _test-output-stream) - 1810 (clear-stream $_test-output-buffered-file->buffer) - 1811 (clear-stream _test-error-stream) - 1812 (clear-stream $_test-error-buffered-file->buffer) - 1813 # var ed/edx: exit-descriptor = tailor-exit-descriptor(16) - 1814 68/push 0/imm32 - 1815 68/push 0/imm32 - 1816 89/<- %edx 4/r32/esp - 1817 (tailor-exit-descriptor %edx 0x10) - 1818 # - 1819 (write _test-input-stream "fn f {\n") - 1820 (write _test-input-stream " var x/eax: int <- g\n") - 1821 (write _test-input-stream "}\n") - 1822 (write _test-input-stream "fn g -> a/eax: foo {\n") - 1823 (write _test-input-stream "}\n") - 1824 # convert - 1825 (convert-mu _test-input-buffered-file _test-output-buffered-file _test-error-buffered-file %edx) - 1826 # registers except esp clobbered at this point - 1827 # restore ed - 1828 89/<- %edx 4/r32/esp - 1829 (flush _test-output-buffered-file) - 1830 (flush _test-error-buffered-file) - 1831 +-- 6 lines: #? # dump _test-error-stream --------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 1837 # check output - 1838 (check-stream-equal _test-output-stream "" "F - test-convert-function-call-with-incorrect-output-type: output should be empty") - 1839 (check-next-stream-line-equal _test-error-stream "fn f: call g: type for output 'x' is not right" "F - test-convert-function-call-with-incorrect-output-type: error message") - 1840 # check that stop(1) was called - 1841 (check-ints-equal *(edx+4) 2 "F - test-convert-function-call-with-incorrect-output-type: exit status") - 1842 # don't restore from ebp - 1843 81 0/subop/add %esp 8/imm32 - 1844 5d/pop-to-ebp - 1845 c3/return - 1846 - 1847 test-convert-function-call-with-too-few-outputs: - 1848 # . prologue - 1849 55/push-ebp - 1850 89/<- %ebp 4/r32/esp - 1851 # setup - 1852 (clear-stream _test-input-stream) - 1853 (clear-stream $_test-input-buffered-file->buffer) - 1854 (clear-stream _test-output-stream) - 1855 (clear-stream $_test-output-buffered-file->buffer) - 1856 (clear-stream _test-error-stream) - 1857 (clear-stream $_test-error-buffered-file->buffer) - 1858 # var ed/edx: exit-descriptor = tailor-exit-descriptor(16) - 1859 68/push 0/imm32 - 1860 68/push 0/imm32 - 1861 89/<- %edx 4/r32/esp - 1862 (tailor-exit-descriptor %edx 0x10) - 1863 # - 1864 (write _test-input-stream "fn f {\n") - 1865 (write _test-input-stream " g\n") - 1866 (write _test-input-stream "}\n") - 1867 (write _test-input-stream "fn g -> a/eax: int {\n") - 1868 (write _test-input-stream "}\n") - 1869 # convert - 1870 (convert-mu _test-input-buffered-file _test-output-buffered-file _test-error-buffered-file %edx) - 1871 # registers except esp clobbered at this point - 1872 # restore ed - 1873 89/<- %edx 4/r32/esp - 1874 (flush _test-output-buffered-file) - 1875 (flush _test-error-buffered-file) - 1876 +-- 6 lines: #? # dump _test-error-stream --------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 1882 # check output - 1883 (check-stream-equal _test-output-stream "" "F - test-convert-function-call-with-too-few-outputs: output should be empty") - 1884 (check-next-stream-line-equal _test-error-stream "fn f: call g: too few outputs" "F - test-convert-function-call-with-too-few-outputs: error message") - 1885 # check that stop(1) was called - 1886 (check-ints-equal *(edx+4) 2 "F - test-convert-function-call-with-too-few-outputs: exit status") - 1887 # don't restore from ebp - 1888 81 0/subop/add %esp 8/imm32 - 1889 5d/pop-to-ebp - 1890 c3/return - 1891 - 1892 test-convert-function-call-with-too-many-outputs: - 1893 # . prologue - 1894 55/push-ebp - 1895 89/<- %ebp 4/r32/esp - 1896 # setup - 1897 (clear-stream _test-input-stream) - 1898 (clear-stream $_test-input-buffered-file->buffer) - 1899 (clear-stream _test-output-stream) - 1900 (clear-stream $_test-output-buffered-file->buffer) - 1901 (clear-stream _test-error-stream) - 1902 (clear-stream $_test-error-buffered-file->buffer) - 1903 # var ed/edx: exit-descriptor = tailor-exit-descriptor(16) - 1904 68/push 0/imm32 - 1905 68/push 0/imm32 - 1906 89/<- %edx 4/r32/esp - 1907 (tailor-exit-descriptor %edx 0x10) - 1908 # - 1909 (write _test-input-stream "fn f {\n") - 1910 (write _test-input-stream " var x/eax: int <- g\n") - 1911 (write _test-input-stream "}\n") - 1912 (write _test-input-stream "fn g {\n") - 1913 (write _test-input-stream "}\n") - 1914 # convert - 1915 (convert-mu _test-input-buffered-file _test-output-buffered-file _test-error-buffered-file %edx) - 1916 # registers except esp clobbered at this point - 1917 # restore ed - 1918 89/<- %edx 4/r32/esp - 1919 (flush _test-output-buffered-file) - 1920 (flush _test-error-buffered-file) - 1921 +-- 6 lines: #? # dump _test-error-stream --------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 1927 # check output - 1928 (check-stream-equal _test-output-stream "" "F - test-convert-function-call-with-too-many-outputs: output should be empty") - 1929 (check-next-stream-line-equal _test-error-stream "fn f: call g: too many outputs" "F - test-convert-function-call-with-too-many-outputs: error message") - 1930 # check that stop(1) was called - 1931 (check-ints-equal *(edx+4) 2 "F - test-convert-function-call-with-too-many-outputs: exit status") - 1932 # don't restore from ebp - 1933 81 0/subop/add %esp 8/imm32 - 1934 5d/pop-to-ebp - 1935 c3/return - 1936 - 1937 test-convert-function-call-with-incorrect-output-register: - 1938 # . prologue - 1939 55/push-ebp - 1940 89/<- %ebp 4/r32/esp - 1941 # setup - 1942 (clear-stream _test-input-stream) - 1943 (clear-stream $_test-input-buffered-file->buffer) - 1944 (clear-stream _test-output-stream) - 1945 (clear-stream $_test-output-buffered-file->buffer) - 1946 (clear-stream _test-error-stream) - 1947 (clear-stream $_test-error-buffered-file->buffer) - 1948 # var ed/edx: exit-descriptor = tailor-exit-descriptor(16) - 1949 68/push 0/imm32 - 1950 68/push 0/imm32 - 1951 89/<- %edx 4/r32/esp - 1952 (tailor-exit-descriptor %edx 0x10) - 1953 # - 1954 (write _test-input-stream "fn f {\n") - 1955 (write _test-input-stream " var x/ecx: int <- g\n") - 1956 (write _test-input-stream "}\n") - 1957 (write _test-input-stream "fn g -> a/eax: int {\n") - 1958 (write _test-input-stream "}\n") - 1959 # convert - 1960 (convert-mu _test-input-buffered-file _test-output-buffered-file _test-error-buffered-file %edx) - 1961 # registers except esp clobbered at this point - 1962 # restore ed - 1963 89/<- %edx 4/r32/esp - 1964 (flush _test-output-buffered-file) - 1965 (flush _test-error-buffered-file) - 1966 +-- 6 lines: #? # dump _test-error-stream --------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 1972 # check output - 1973 (check-stream-equal _test-output-stream "" "F - test-convert-function-call-with-incorrect-output-register: output should be empty") - 1974 (check-next-stream-line-equal _test-error-stream "fn f: call g: register for output 'x' is not right" "F - test-convert-function-call-with-incorrect-output-register: error message") - 1975 # check that stop(1) was called - 1976 (check-ints-equal *(edx+4) 2 "F - test-convert-function-call-with-incorrect-output-register: exit status") - 1977 # don't restore from ebp - 1978 81 0/subop/add %esp 8/imm32 - 1979 5d/pop-to-ebp - 1980 c3/return - 1981 - 1982 test-convert-function-with-local-var-dereferenced: - 1983 # . prologue - 1984 55/push-ebp - 1985 89/<- %ebp 4/r32/esp - 1986 # setup - 1987 (clear-stream _test-input-stream) - 1988 (clear-stream $_test-input-buffered-file->buffer) - 1989 (clear-stream _test-output-stream) - 1990 (clear-stream $_test-output-buffered-file->buffer) - 1991 # - 1992 (write _test-input-stream "fn foo {\n") - 1993 (write _test-input-stream " var x/ecx: (addr int) <- copy 0\n") - 1994 (write _test-input-stream " increment *x\n") - 1995 (write _test-input-stream "}\n") - 1996 # convert - 1997 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) - 1998 (flush _test-output-buffered-file) - 1999 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 2005 # check output - 2006 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-function-with-local-var-dereferenced/0") - 2007 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-function-with-local-var-dereferenced/1") - 2008 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-function-with-local-var-dereferenced/2") - 2009 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-function-with-local-var-dereferenced/3") - 2010 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-local-var-dereferenced/4") - 2011 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-function-with-local-var-dereferenced/5") - 2012 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %ecx" "F - test-convert-function-with-local-var-dereferenced/6") - 2013 (check-next-stream-line-equal _test-output-stream " b9/copy-to-ecx 0/imm32" "F - test-convert-function-with-local-var-dereferenced/7") - 2014 (check-next-stream-line-equal _test-output-stream " ff 0/subop/increment *ecx" "F - test-convert-function-with-local-var-dereferenced/8") - 2015 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %ecx" "F - test-convert-function-with-local-var-dereferenced/9") - 2016 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-local-var-dereferenced/10") - 2017 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-function-with-local-var-dereferenced/11") - 2018 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-function-with-local-var-dereferenced/12") - 2019 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-function-with-local-var-dereferenced/13") - 2020 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-function-with-local-var-dereferenced/14") - 2021 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-function-with-local-var-dereferenced/15") - 2022 # . epilogue - 2023 89/<- %esp 5/r32/ebp - 2024 5d/pop-to-ebp - 2025 c3/return - 2026 - 2027 # variables of type 'byte' are not allowed on the stack - 2028 test-convert-function-with-byte-operations: - 2029 # . prologue - 2030 55/push-ebp - 2031 89/<- %ebp 4/r32/esp - 2032 # setup - 2033 (clear-stream _test-input-stream) - 2034 (clear-stream $_test-input-buffered-file->buffer) - 2035 (clear-stream _test-output-stream) - 2036 (clear-stream $_test-output-buffered-file->buffer) - 2037 # - 2038 (write _test-input-stream "fn foo {\n") - 2039 (write _test-input-stream " var x/eax: byte <- copy 0\n") - 2040 (write _test-input-stream " var y/ecx: byte <- copy 0\n") - 2041 (write _test-input-stream " y <- copy-byte x\n") - 2042 (write _test-input-stream " var z/edx: (addr byte) <- copy 0\n") - 2043 (write _test-input-stream " y <- copy-byte *z\n") - 2044 (write _test-input-stream " copy-byte-to *z, x\n") - 2045 (write _test-input-stream "}\n") - 2046 # convert - 2047 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) - 2048 (flush _test-output-buffered-file) - 2049 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 2055 # check output - 2056 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-function-with-byte-operations/0") - 2057 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-function-with-byte-operations/1") - 2058 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-function-with-byte-operations/2") - 2059 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-function-with-byte-operations/3") - 2060 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-byte-operations/4") - 2061 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-function-with-byte-operations/5") - 2062 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %eax" "F - test-convert-function-with-byte-operations/6") - 2063 (check-next-stream-line-equal _test-output-stream " b8/copy-to-eax 0/imm32" "F - test-convert-function-with-byte-operations/7") - 2064 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %ecx" "F - test-convert-function-with-byte-operations/8") - 2065 (check-next-stream-line-equal _test-output-stream " b9/copy-to-ecx 0/imm32" "F - test-convert-function-with-byte-operations/9") - 2066 (check-next-stream-line-equal _test-output-stream " 8a/byte-> %eax 0x00000001/r32" "F - test-convert-function-with-byte-operations/10") - 2067 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %edx" "F - test-convert-function-with-byte-operations/11") - 2068 (check-next-stream-line-equal _test-output-stream " ba/copy-to-edx 0/imm32" "F - test-convert-function-with-byte-operations/12") - 2069 (check-next-stream-line-equal _test-output-stream " 8a/byte-> *edx 0x00000001/r32" "F - test-convert-function-with-byte-operations/13") - 2070 (check-next-stream-line-equal _test-output-stream " 88/byte<- *edx 0x00000000/r32" "F - test-convert-function-with-byte-operations/14") - 2071 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %edx" "F - test-convert-function-with-byte-operations/15") - 2072 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %ecx" "F - test-convert-function-with-byte-operations/16") - 2073 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %eax" "F - test-convert-function-with-byte-operations/17") - 2074 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-byte-operations/18") - 2075 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-function-with-byte-operations/19") - 2076 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-function-with-byte-operations/20") - 2077 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-function-with-byte-operations/21") - 2078 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-function-with-byte-operations/22") - 2079 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-function-with-byte-operations/23") - 2080 # . epilogue - 2081 89/<- %esp 5/r32/ebp - 2082 5d/pop-to-ebp - 2083 c3/return - 2084 - 2085 # variables of type 'byte' _can_ be function args. They then occupy 4 bytes. - 2086 test-copy-byte-var-from-fn-arg: - 2087 # . prologue - 2088 55/push-ebp - 2089 89/<- %ebp 4/r32/esp - 2090 # setup - 2091 (clear-stream _test-input-stream) - 2092 (clear-stream $_test-input-buffered-file->buffer) - 2093 (clear-stream _test-output-stream) - 2094 (clear-stream $_test-output-buffered-file->buffer) - 2095 # - 2096 (write _test-input-stream "fn foo x: byte, y: int {\n") - 2097 (write _test-input-stream " var a/eax: byte <- copy x\n") - 2098 (write _test-input-stream " var b/eax: int <- copy y\n") - 2099 (write _test-input-stream "}\n") - 2100 # convert - 2101 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) - 2102 (flush _test-output-buffered-file) - 2103 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 2109 # check output - 2110 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-copy-byte-from-fn-arg/0") - 2111 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-copy-byte-from-fn-arg/1") - 2112 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-copy-byte-from-fn-arg/2") - 2113 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-copy-byte-from-fn-arg/3") - 2114 (check-next-stream-line-equal _test-output-stream " {" "F - test-copy-byte-from-fn-arg/4") - 2115 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-copy-byte-from-fn-arg/5") - 2116 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %eax" "F - test-copy-byte-from-fn-arg/6") - 2117 (check-next-stream-line-equal _test-output-stream " 8b/-> *(ebp+0x00000008) 0x00000000/r32" "F - test-copy-byte-from-fn-arg/7") - 2118 (check-next-stream-line-equal _test-output-stream " 8b/-> *(ebp+0x0000000c) 0x00000000/r32" "F - test-copy-byte-from-fn-arg/8") - 2119 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %eax" "F - test-copy-byte-from-fn-arg/9") - 2120 (check-next-stream-line-equal _test-output-stream " }" "F - test-copy-byte-from-fn-arg/10") - 2121 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-copy-byte-from-fn-arg/11") - 2122 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-copy-byte-from-fn-arg/12") - 2123 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-copy-byte-from-fn-arg/13") - 2124 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-copy-byte-from-fn-arg/14") - 2125 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-copy-byte-from-fn-arg/15") - 2126 # . epilogue - 2127 89/<- %esp 5/r32/ebp - 2128 5d/pop-to-ebp - 2129 c3/return - 2130 - 2131 test-convert-compare-register-with-literal: - 2132 # . prologue - 2133 55/push-ebp - 2134 89/<- %ebp 4/r32/esp - 2135 # setup - 2136 (clear-stream _test-input-stream) - 2137 (clear-stream $_test-input-buffered-file->buffer) - 2138 (clear-stream _test-output-stream) - 2139 (clear-stream $_test-output-buffered-file->buffer) - 2140 # - 2141 (write _test-input-stream "fn foo {\n") - 2142 (write _test-input-stream " var x/ecx: int <- copy 0\n") - 2143 (write _test-input-stream " compare x, 0\n") - 2144 (write _test-input-stream "}\n") - 2145 # convert - 2146 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) - 2147 (flush _test-output-buffered-file) - 2148 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 2154 # check output - 2155 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-compare-register-with-literal/0") - 2156 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-compare-register-with-literal/1") - 2157 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-compare-register-with-literal/2") - 2158 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-compare-register-with-literal/3") - 2159 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-compare-register-with-literal/4") - 2160 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-compare-register-with-literal/5") - 2161 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %ecx" "F - test-convert-compare-register-with-literal/6") - 2162 (check-next-stream-line-equal _test-output-stream " b9/copy-to-ecx 0/imm32" "F - test-convert-compare-register-with-literal/7") - 2163 (check-next-stream-line-equal _test-output-stream " 81 7/subop/compare %ecx 0/imm32" "F - test-convert-compare-register-with-literal/8") - 2164 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %ecx" "F - test-convert-compare-register-with-literal/9") - 2165 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-compare-register-with-literal/10") - 2166 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-compare-register-with-literal/11") - 2167 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-compare-register-with-literal/12") - 2168 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-compare-register-with-literal/13") - 2169 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-compare-register-with-literal/14") - 2170 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-compare-register-with-literal/15") - 2171 # . epilogue - 2172 89/<- %esp 5/r32/ebp - 2173 5d/pop-to-ebp - 2174 c3/return - 2175 - 2176 test-unknown-variable: - 2177 # . prologue - 2178 55/push-ebp - 2179 89/<- %ebp 4/r32/esp - 2180 # setup - 2181 (clear-stream _test-input-stream) - 2182 (clear-stream $_test-input-buffered-file->buffer) - 2183 (clear-stream _test-output-stream) - 2184 (clear-stream $_test-output-buffered-file->buffer) - 2185 (clear-stream _test-error-stream) - 2186 (clear-stream $_test-error-buffered-file->buffer) - 2187 # var ed/edx: exit-descriptor = tailor-exit-descriptor(16) - 2188 68/push 0/imm32 - 2189 68/push 0/imm32 - 2190 89/<- %edx 4/r32/esp - 2191 (tailor-exit-descriptor %edx 0x10) - 2192 # - 2193 (write _test-input-stream "fn foo {\n") - 2194 (write _test-input-stream " compare x, 0\n") - 2195 (write _test-input-stream "}\n") - 2196 # convert - 2197 (convert-mu _test-input-buffered-file _test-output-buffered-file _test-error-buffered-file %edx) - 2198 # registers except esp clobbered at this point - 2199 # restore ed - 2200 89/<- %edx 4/r32/esp - 2201 (flush _test-output-buffered-file) - 2202 (flush _test-error-buffered-file) - 2203 +-- 6 lines: #? # dump _test-error-stream --------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 2209 # check output - 2210 (check-stream-equal _test-output-stream "" "F - test-unknown-variable: output should be empty") - 2211 (check-next-stream-line-equal _test-error-stream "fn foo: unknown variable 'x'" "F - test-unknown-variable: error message") - 2212 # check that stop(1) was called - 2213 (check-ints-equal *(edx+4) 2 "F - test-unknown-variable: exit status") - 2214 # don't restore from ebp - 2215 81 0/subop/add %esp 8/imm32 - 2216 # . epilogue - 2217 5d/pop-to-ebp - 2218 c3/return - 2219 - 2220 test-convert-function-with-local-var-in-block: - 2221 # . prologue - 2222 55/push-ebp - 2223 89/<- %ebp 4/r32/esp - 2224 # setup - 2225 (clear-stream _test-input-stream) - 2226 (clear-stream $_test-input-buffered-file->buffer) - 2227 (clear-stream _test-output-stream) - 2228 (clear-stream $_test-output-buffered-file->buffer) - 2229 # - 2230 (write _test-input-stream "fn foo {\n") - 2231 (write _test-input-stream " {\n") - 2232 (write _test-input-stream " var x: int\n") - 2233 (write _test-input-stream " increment x\n") - 2234 (write _test-input-stream " }\n") - 2235 (write _test-input-stream "}\n") - 2236 # convert - 2237 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) - 2238 (flush _test-output-buffered-file) - 2239 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 2245 # check output - 2246 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-function-with-local-var-in-block/0") - 2247 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-function-with-local-var-in-block/1") - 2248 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-function-with-local-var-in-block/2") - 2249 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-function-with-local-var-in-block/3") - 2250 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-local-var-in-block/4") - 2251 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-function-with-local-var-in-block/5") - 2252 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-local-var-in-block/6") - 2253 (check-next-stream-line-equal _test-output-stream "$foo:0x00000002:loop:" "F - test-convert-function-with-local-var-in-block/7") - 2254 (check-next-stream-line-equal _test-output-stream " 68/push 0/imm32" "F - test-convert-function-with-local-var-in-block/8") - 2255 (check-next-stream-line-equal _test-output-stream " ff 0/subop/increment *(ebp+0xfffffffc)" "F - test-convert-function-with-local-var-in-block/9") - 2256 (check-next-stream-line-equal _test-output-stream " 81 0/subop/add %esp 0x00000004/imm32" "F - test-convert-function-with-local-var-in-block/10") - 2257 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-local-var-in-block/11") - 2258 (check-next-stream-line-equal _test-output-stream "$foo:0x00000002:break:" "F - test-convert-function-with-local-var-in-block/12") - 2259 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-local-var-in-block/13") - 2260 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-function-with-local-var-in-block/14") - 2261 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-function-with-local-var-in-block/15") - 2262 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-function-with-local-var-in-block/16") - 2263 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-function-with-local-var-in-block/17") - 2264 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-function-with-local-var-in-block/18") - 2265 # . epilogue - 2266 89/<- %esp 5/r32/ebp - 2267 5d/pop-to-ebp - 2268 c3/return - 2269 - 2270 test-convert-function-with-local-var-in-named-block: - 2271 # . prologue - 2272 55/push-ebp - 2273 89/<- %ebp 4/r32/esp - 2274 # setup - 2275 (clear-stream _test-input-stream) - 2276 (clear-stream $_test-input-buffered-file->buffer) - 2277 (clear-stream _test-output-stream) - 2278 (clear-stream $_test-output-buffered-file->buffer) - 2279 # - 2280 (write _test-input-stream "fn foo {\n") - 2281 (write _test-input-stream " $bar: {\n") - 2282 (write _test-input-stream " var x: int\n") - 2283 (write _test-input-stream " increment x\n") - 2284 (write _test-input-stream " }\n") - 2285 (write _test-input-stream "}\n") - 2286 # convert - 2287 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) - 2288 (flush _test-output-buffered-file) - 2289 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 2295 # check output - 2296 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-function-with-local-var-in-named-block/0") - 2297 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-function-with-local-var-in-named-block/1") - 2298 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-function-with-local-var-in-named-block/2") - 2299 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-function-with-local-var-in-named-block/3") - 2300 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-local-var-in-named-block/4") - 2301 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-function-with-local-var-in-named-block/5") - 2302 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-local-var-in-named-block/6") - 2303 (check-next-stream-line-equal _test-output-stream "$bar:loop:" "F - test-convert-function-with-local-var-in-named-block/7") - 2304 (check-next-stream-line-equal _test-output-stream " 68/push 0/imm32" "F - test-convert-function-with-local-var-in-named-block/8") - 2305 (check-next-stream-line-equal _test-output-stream " ff 0/subop/increment *(ebp+0xfffffffc)" "F - test-convert-function-with-local-var-in-named-block/9") - 2306 (check-next-stream-line-equal _test-output-stream " 81 0/subop/add %esp 0x00000004/imm32" "F - test-convert-function-with-local-var-in-named-block/10") - 2307 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-local-var-in-named-block/11") - 2308 (check-next-stream-line-equal _test-output-stream "$bar:break:" "F - test-convert-function-with-local-var-in-named-block/12") - 2309 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-local-var-in-named-block/13") - 2310 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-function-with-local-var-in-named-block/14") - 2311 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-function-with-local-var-in-named-block/15") - 2312 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-function-with-local-var-in-named-block/16") - 2313 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-function-with-local-var-in-named-block/17") - 2314 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-function-with-local-var-in-named-block/18") - 2315 # . epilogue - 2316 89/<- %esp 5/r32/ebp - 2317 5d/pop-to-ebp - 2318 c3/return - 2319 - 2320 test-unknown-variable-in-named-block: - 2321 # . prologue - 2322 55/push-ebp - 2323 89/<- %ebp 4/r32/esp - 2324 # setup - 2325 (clear-stream _test-input-stream) - 2326 (clear-stream $_test-input-buffered-file->buffer) - 2327 (clear-stream _test-output-stream) - 2328 (clear-stream $_test-output-buffered-file->buffer) - 2329 (clear-stream _test-error-stream) - 2330 (clear-stream $_test-error-buffered-file->buffer) - 2331 # var ed/edx: exit-descriptor = tailor-exit-descriptor(16) - 2332 68/push 0/imm32 - 2333 68/push 0/imm32 - 2334 89/<- %edx 4/r32/esp - 2335 (tailor-exit-descriptor %edx 0x10) - 2336 # - 2337 (write _test-input-stream "fn foo {\n") - 2338 (write _test-input-stream " $a: {\n") - 2339 (write _test-input-stream " compare x, 0\n") - 2340 (write _test-input-stream " }\n") - 2341 (write _test-input-stream "}\n") - 2342 # convert - 2343 (convert-mu _test-input-buffered-file _test-output-buffered-file _test-error-buffered-file %edx) - 2344 # registers except esp clobbered at this point - 2345 # restore ed - 2346 89/<- %edx 4/r32/esp - 2347 (flush _test-output-buffered-file) - 2348 (flush _test-error-buffered-file) - 2349 +-- 6 lines: #? # dump _test-error-stream --------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 2355 # check output - 2356 (check-stream-equal _test-output-stream "" "F - test-unknown-variable-in-named-block: output should be empty") - 2357 (check-next-stream-line-equal _test-error-stream "fn foo: unknown variable 'x'" "F - test-unknown-variable-in-named-block: error message") - 2358 # check that stop(1) was called - 2359 (check-ints-equal *(edx+4) 2 "F - test-unknown-variable-in-named-block: exit status") - 2360 # don't restore from ebp - 2361 81 0/subop/add %esp 8/imm32 - 2362 # . epilogue - 2363 5d/pop-to-ebp - 2364 c3/return - 2365 - 2366 test-always-shadow-outermost-reg-vars-in-function: - 2367 # . prologue - 2368 55/push-ebp - 2369 89/<- %ebp 4/r32/esp - 2370 # setup - 2371 (clear-stream _test-input-stream) - 2372 (clear-stream $_test-input-buffered-file->buffer) - 2373 (clear-stream _test-output-stream) - 2374 (clear-stream $_test-output-buffered-file->buffer) - 2375 # - 2376 (write _test-input-stream "fn foo {\n") - 2377 (write _test-input-stream " var x/ecx: int <- copy 3\n") - 2378 (write _test-input-stream "}\n") - 2379 # convert - 2380 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) - 2381 (flush _test-output-buffered-file) - 2382 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 2388 # check output - 2389 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-always-shadow-outermost-reg-vars-in-function/0") - 2390 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-always-shadow-outermost-reg-vars-in-function/1") - 2391 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-always-shadow-outermost-reg-vars-in-function/2") - 2392 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-always-shadow-outermost-reg-vars-in-function/3") - 2393 (check-next-stream-line-equal _test-output-stream " {" "F - test-always-shadow-outermost-reg-vars-in-function/4") - 2394 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-always-shadow-outermost-reg-vars-in-function/5") - 2395 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %ecx" "F - test-convert-compare-register-with-literal/6") - 2396 (check-next-stream-line-equal _test-output-stream " b9/copy-to-ecx 3/imm32" "F - test-always-shadow-outermost-reg-vars-in-function/8") - 2397 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %ecx" "F - test-convert-compare-register-with-literal/9") - 2398 (check-next-stream-line-equal _test-output-stream " }" "F - test-always-shadow-outermost-reg-vars-in-function/12") - 2399 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-always-shadow-outermost-reg-vars-in-function/13") - 2400 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-always-shadow-outermost-reg-vars-in-function/14") - 2401 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-always-shadow-outermost-reg-vars-in-function/15") - 2402 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-always-shadow-outermost-reg-vars-in-function/16") - 2403 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-always-shadow-outermost-reg-vars-in-function/17") - 2404 # . epilogue - 2405 89/<- %esp 5/r32/ebp - 2406 5d/pop-to-ebp - 2407 c3/return - 2408 - 2409 _pending-test-clobber-dead-local: - 2410 # . prologue - 2411 55/push-ebp - 2412 89/<- %ebp 4/r32/esp - 2413 # setup - 2414 (clear-stream _test-input-stream) - 2415 (clear-stream $_test-input-buffered-file->buffer) - 2416 (clear-stream _test-output-stream) - 2417 (clear-stream $_test-output-buffered-file->buffer) - 2418 # - 2419 (write _test-input-stream "fn foo {\n") - 2420 (write _test-input-stream " var x/ecx: int <- copy 3\n") - 2421 (write _test-input-stream " {\n") - 2422 (write _test-input-stream " var y/ecx: int <- copy 4\n") - 2423 (write _test-input-stream " }\n") - 2424 (write _test-input-stream "}\n") - 2425 # convert - 2426 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) - 2427 (flush _test-output-buffered-file) - 2428 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 2434 # check output - 2435 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-clobber-dead-local/0") - 2436 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-clobber-dead-local/1") - 2437 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-clobber-dead-local/2") - 2438 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-clobber-dead-local/3") - 2439 (check-next-stream-line-equal _test-output-stream " {" "F - test-clobber-dead-local/4") - 2440 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-clobber-dead-local/5") - 2441 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %ecx" "F - test-clobber-dead-local/6") - 2442 (check-next-stream-line-equal _test-output-stream " b9/copy-to-ecx 3/imm32" "F - test-clobber-dead-local/7") - 2443 (check-next-stream-line-equal _test-output-stream " {" "F - test-clobber-dead-local/8") - 2444 (check-next-stream-line-equal _test-output-stream "$foo:0x00000002:loop:" "F - test-clobber-dead-local/9") - 2445 (check-next-stream-line-equal _test-output-stream " b9/copy-to-ecx 4/imm32" "F - test-clobber-dead-local/10") # no push/pop here - 2446 (check-next-stream-line-equal _test-output-stream " }" "F - test-clobber-dead-local/11") - 2447 (check-next-stream-line-equal _test-output-stream "$foo:0x00000002:break:" "F - test-clobber-dead-local/12") - 2448 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %ecx" "F - test-clobber-dead-local/13") - 2449 (check-next-stream-line-equal _test-output-stream " }" "F - test-clobber-dead-local/14") - 2450 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-clobber-dead-local/15") - 2451 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-clobber-dead-local/16") - 2452 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-clobber-dead-local/17") - 2453 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-clobber-dead-local/18") - 2454 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-clobber-dead-local/19") - 2455 # . epilogue - 2456 89/<- %esp 5/r32/ebp - 2457 5d/pop-to-ebp - 2458 c3/return - 2459 - 2460 test-shadow-live-local: - 2461 # . prologue - 2462 55/push-ebp - 2463 89/<- %ebp 4/r32/esp - 2464 # setup - 2465 (clear-stream _test-input-stream) - 2466 (clear-stream $_test-input-buffered-file->buffer) - 2467 (clear-stream _test-output-stream) - 2468 (clear-stream $_test-output-buffered-file->buffer) - 2469 # - 2470 (write _test-input-stream "fn foo {\n") - 2471 (write _test-input-stream " var x/ecx: int <- copy 3\n") - 2472 (write _test-input-stream " {\n") - 2473 (write _test-input-stream " var y/ecx: int <- copy 4\n") - 2474 (write _test-input-stream " }\n") - 2475 (write _test-input-stream " x <- increment\n") - 2476 (write _test-input-stream "}\n") - 2477 # convert - 2478 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) - 2479 (flush _test-output-buffered-file) - 2480 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 2486 # check output - 2487 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-shadow-live-local/0") - 2488 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-shadow-live-local/1") - 2489 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-shadow-live-local/2") - 2490 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-shadow-live-local/3") - 2491 (check-next-stream-line-equal _test-output-stream " {" "F - test-shadow-live-local/4") - 2492 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-shadow-live-local/5") - 2493 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %ecx" "F - test-shadow-live-local/6") - 2494 (check-next-stream-line-equal _test-output-stream " b9/copy-to-ecx 3/imm32" "F - test-shadow-live-local/7") - 2495 (check-next-stream-line-equal _test-output-stream " {" "F - test-shadow-live-local/8") - 2496 (check-next-stream-line-equal _test-output-stream "$foo:0x00000002:loop:" "F - test-shadow-live-local/9") - 2497 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %ecx" "F - test-shadow-live-local/10") - 2498 (check-next-stream-line-equal _test-output-stream " b9/copy-to-ecx 4/imm32" "F - test-shadow-live-local/11") - 2499 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %ecx" "F - test-shadow-live-local/12") - 2500 (check-next-stream-line-equal _test-output-stream " }" "F - test-shadow-live-local/13") - 2501 (check-next-stream-line-equal _test-output-stream "$foo:0x00000002:break:" "F - test-shadow-live-local/14") - 2502 (check-next-stream-line-equal _test-output-stream " 41/increment-ecx" "F - test-shadow-live-local/15") - 2503 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %ecx" "F - test-shadow-live-local/16") - 2504 (check-next-stream-line-equal _test-output-stream " }" "F - test-shadow-live-local/17") - 2505 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-shadow-live-local/18") - 2506 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-shadow-live-local/19") - 2507 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-shadow-live-local/20") - 2508 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-shadow-live-local/21") - 2509 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-shadow-live-local/22") - 2510 # . epilogue - 2511 89/<- %esp 5/r32/ebp - 2512 5d/pop-to-ebp - 2513 c3/return - 2514 - 2515 test-shadow-name: - 2516 # . prologue - 2517 55/push-ebp - 2518 89/<- %ebp 4/r32/esp - 2519 # setup - 2520 (clear-stream _test-input-stream) - 2521 (clear-stream $_test-input-buffered-file->buffer) - 2522 (clear-stream _test-output-stream) - 2523 (clear-stream $_test-output-buffered-file->buffer) - 2524 # - 2525 (write _test-input-stream "fn foo {\n") - 2526 (write _test-input-stream " var x/ecx: int <- copy 3\n") - 2527 (write _test-input-stream " {\n") - 2528 (write _test-input-stream " var x/edx: int <- copy 4\n") - 2529 (write _test-input-stream " }\n") - 2530 (write _test-input-stream " x <- increment\n") - 2531 (write _test-input-stream "}\n") - 2532 # convert - 2533 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) - 2534 (flush _test-output-buffered-file) - 2535 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 2541 # check output - 2542 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-shadow-name/0") - 2543 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-shadow-name/1") - 2544 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-shadow-name/2") - 2545 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-shadow-name/3") - 2546 (check-next-stream-line-equal _test-output-stream " {" "F - test-shadow-name/4") - 2547 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-shadow-name/5") - 2548 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %ecx" "F - test-shadow-name/6") - 2549 (check-next-stream-line-equal _test-output-stream " b9/copy-to-ecx 3/imm32" "F - test-shadow-name/7") - 2550 (check-next-stream-line-equal _test-output-stream " {" "F - test-shadow-name/8") - 2551 (check-next-stream-line-equal _test-output-stream "$foo:0x00000002:loop:" "F - test-shadow-name/9") - 2552 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %edx" "F - test-shadow-name/10") - 2553 (check-next-stream-line-equal _test-output-stream " ba/copy-to-edx 4/imm32" "F - test-shadow-name/11") - 2554 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %edx" "F - test-shadow-name/12") - 2555 (check-next-stream-line-equal _test-output-stream " }" "F - test-shadow-name/13") - 2556 (check-next-stream-line-equal _test-output-stream "$foo:0x00000002:break:" "F - test-shadow-name/14") - 2557 (check-next-stream-line-equal _test-output-stream " 41/increment-ecx" "F - test-shadow-name/15") - 2558 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %ecx" "F - test-shadow-name/16") - 2559 (check-next-stream-line-equal _test-output-stream " }" "F - test-shadow-name/17") - 2560 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-shadow-name/18") - 2561 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-shadow-name/19") - 2562 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-shadow-name/20") - 2563 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-shadow-name/21") - 2564 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-shadow-name/22") - 2565 # . epilogue - 2566 89/<- %esp 5/r32/ebp - 2567 5d/pop-to-ebp - 2568 c3/return - 2569 - 2570 test-shadow-name-2: - 2571 # . prologue - 2572 55/push-ebp - 2573 89/<- %ebp 4/r32/esp - 2574 # setup - 2575 (clear-stream _test-input-stream) - 2576 (clear-stream $_test-input-buffered-file->buffer) - 2577 (clear-stream _test-output-stream) - 2578 (clear-stream $_test-output-buffered-file->buffer) - 2579 # - 2580 (write _test-input-stream "fn foo {\n") - 2581 (write _test-input-stream " var x/ecx: int <- copy 3\n") - 2582 (write _test-input-stream " {\n") - 2583 (write _test-input-stream " var x/edx: int <- copy 4\n") - 2584 (write _test-input-stream " var y/ecx: int <- copy 5\n") - 2585 (write _test-input-stream " }\n") - 2586 (write _test-input-stream " x <- increment\n") - 2587 (write _test-input-stream "}\n") - 2588 # convert - 2589 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) - 2590 (flush _test-output-buffered-file) - 2591 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 2597 # check output - 2598 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-shadow-name-2/0") - 2599 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-shadow-name-2/1") - 2600 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-shadow-name-2/2") - 2601 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-shadow-name-2/3") - 2602 (check-next-stream-line-equal _test-output-stream " {" "F - test-shadow-name-2/4") - 2603 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-shadow-name-2/5") - 2604 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %ecx" "F - test-shadow-name-2/6") - 2605 (check-next-stream-line-equal _test-output-stream " b9/copy-to-ecx 3/imm32" "F - test-shadow-name-2/7") - 2606 (check-next-stream-line-equal _test-output-stream " {" "F - test-shadow-name-2/8") - 2607 (check-next-stream-line-equal _test-output-stream "$foo:0x00000002:loop:" "F - test-shadow-name-2/9") - 2608 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %edx" "F - test-shadow-name-2/10") - 2609 (check-next-stream-line-equal _test-output-stream " ba/copy-to-edx 4/imm32" "F - test-shadow-name-2/11") - 2610 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %ecx" "F - test-shadow-name-2/12") - 2611 (check-next-stream-line-equal _test-output-stream " b9/copy-to-ecx 5/imm32" "F - test-shadow-name-2/13") - 2612 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %ecx" "F - test-shadow-name-2/14") - 2613 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %edx" "F - test-shadow-name-2/15") - 2614 (check-next-stream-line-equal _test-output-stream " }" "F - test-shadow-name-2/16") - 2615 (check-next-stream-line-equal _test-output-stream "$foo:0x00000002:break:" "F - test-shadow-name-2/17") - 2616 (check-next-stream-line-equal _test-output-stream " 41/increment-ecx" "F - test-shadow-name-2/18") - 2617 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %ecx" "F - test-shadow-name-2/19") - 2618 (check-next-stream-line-equal _test-output-stream " }" "F - test-shadow-name-2/20") - 2619 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-shadow-name-2/21") - 2620 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-shadow-name-2/22") - 2621 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-shadow-name-2/23") - 2622 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-shadow-name-2/24") - 2623 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-shadow-name-2/25") - 2624 # . epilogue - 2625 89/<- %esp 5/r32/ebp - 2626 5d/pop-to-ebp - 2627 c3/return - 2628 - 2629 test-do-not-spill-same-register-in-block: - 2630 # . prologue - 2631 55/push-ebp - 2632 89/<- %ebp 4/r32/esp - 2633 # setup - 2634 (clear-stream _test-input-stream) - 2635 (clear-stream $_test-input-buffered-file->buffer) - 2636 (clear-stream _test-output-stream) - 2637 (clear-stream $_test-output-buffered-file->buffer) - 2638 # - 2639 (write _test-input-stream "fn foo {\n") - 2640 (write _test-input-stream " var x/ecx: int <- copy 3\n") - 2641 (write _test-input-stream " var y/ecx: int <- copy 4\n") - 2642 (write _test-input-stream " y <- increment\n") - 2643 (write _test-input-stream "}\n") - 2644 # convert - 2645 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) - 2646 (flush _test-output-buffered-file) - 2647 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 2653 # check output - 2654 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-do-not-spill-same-register-in-block/0") - 2655 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-do-not-spill-same-register-in-block/1") - 2656 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-do-not-spill-same-register-in-block/2") - 2657 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-do-not-spill-same-register-in-block/3") - 2658 (check-next-stream-line-equal _test-output-stream " {" "F - test-do-not-spill-same-register-in-block/4") - 2659 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-do-not-spill-same-register-in-block/5") - 2660 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %ecx" "F - test-do-not-spill-same-register-in-block/6") - 2661 (check-next-stream-line-equal _test-output-stream " b9/copy-to-ecx 3/imm32" "F - test-do-not-spill-same-register-in-block/7") - 2662 (check-next-stream-line-equal _test-output-stream " b9/copy-to-ecx 4/imm32" "F - test-do-not-spill-same-register-in-block/8") - 2663 (check-next-stream-line-equal _test-output-stream " 41/increment-ecx" "F - test-do-not-spill-same-register-in-block/9") - 2664 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %ecx" "F - test-do-not-spill-same-register-in-block/10") - 2665 (check-next-stream-line-equal _test-output-stream " }" "F - test-do-not-spill-same-register-in-block/11") - 2666 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-do-not-spill-same-register-in-block/12") - 2667 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-do-not-spill-same-register-in-block/13") - 2668 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-do-not-spill-same-register-in-block/14") - 2669 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-do-not-spill-same-register-in-block/15") - 2670 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-do-not-spill-same-register-in-block/16") - 2671 # . epilogue - 2672 89/<- %esp 5/r32/ebp - 2673 5d/pop-to-ebp - 2674 c3/return - 2675 - 2676 test-spill-different-register-in-block: - 2677 # . prologue - 2678 55/push-ebp - 2679 89/<- %ebp 4/r32/esp - 2680 # setup - 2681 (clear-stream _test-input-stream) - 2682 (clear-stream $_test-input-buffered-file->buffer) - 2683 (clear-stream _test-output-stream) - 2684 (clear-stream $_test-output-buffered-file->buffer) - 2685 # - 2686 (write _test-input-stream "fn foo {\n") - 2687 (write _test-input-stream " var x/eax: int <- copy 3\n") - 2688 (write _test-input-stream " var y/ecx: int <- copy 4\n") - 2689 (write _test-input-stream " y <- increment\n") - 2690 (write _test-input-stream "}\n") - 2691 # convert - 2692 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) - 2693 (flush _test-output-buffered-file) - 2694 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 2700 # check output - 2701 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-spill-different-register-in-block/0") - 2702 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-spill-different-register-in-block/1") - 2703 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-spill-different-register-in-block/2") - 2704 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-spill-different-register-in-block/3") - 2705 (check-next-stream-line-equal _test-output-stream " {" "F - test-spill-different-register-in-block/4") - 2706 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-spill-different-register-in-block/5") - 2707 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %eax" "F - test-spill-different-register-in-block/6") - 2708 (check-next-stream-line-equal _test-output-stream " b8/copy-to-eax 3/imm32" "F - test-spill-different-register-in-block/7") - 2709 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %ecx" "F - test-spill-different-register-in-block/8") - 2710 (check-next-stream-line-equal _test-output-stream " b9/copy-to-ecx 4/imm32" "F - test-spill-different-register-in-block/9") - 2711 (check-next-stream-line-equal _test-output-stream " 41/increment-ecx" "F - test-spill-different-register-in-block/10") - 2712 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %ecx" "F - test-spill-different-register-in-block/11") - 2713 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %eax" "F - test-spill-different-register-in-block/12") - 2714 (check-next-stream-line-equal _test-output-stream " }" "F - test-spill-different-register-in-block/13") - 2715 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-spill-different-register-in-block/14") - 2716 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-spill-different-register-in-block/15") - 2717 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-spill-different-register-in-block/16") - 2718 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-spill-different-register-in-block/17") - 2719 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-spill-different-register-in-block/18") - 2720 # . epilogue - 2721 89/<- %esp 5/r32/ebp - 2722 5d/pop-to-ebp - 2723 c3/return - 2724 - 2725 test-shadow-live-output: - 2726 # . prologue - 2727 55/push-ebp - 2728 89/<- %ebp 4/r32/esp - 2729 # setup - 2730 (clear-stream _test-input-stream) - 2731 (clear-stream $_test-input-buffered-file->buffer) - 2732 (clear-stream _test-output-stream) - 2733 (clear-stream $_test-output-buffered-file->buffer) - 2734 # - 2735 (write _test-input-stream "fn foo -> x/ecx: int {\n") - 2736 (write _test-input-stream " x <- copy 3\n") - 2737 (write _test-input-stream " {\n") - 2738 (write _test-input-stream " var y/ecx: int <- copy 4\n") - 2739 (write _test-input-stream " }\n") - 2740 (write _test-input-stream " x <- increment\n") - 2741 (write _test-input-stream "}\n") - 2742 # convert - 2743 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) - 2744 (flush _test-output-buffered-file) - 2745 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 2751 # check output - 2752 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-shadow-live-output/0") - 2753 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-shadow-live-output/1") - 2754 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-shadow-live-output/2") - 2755 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-shadow-live-output/3") - 2756 (check-next-stream-line-equal _test-output-stream " {" "F - test-shadow-live-output/4") - 2757 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-shadow-live-output/5") - 2758 (check-next-stream-line-equal _test-output-stream " b9/copy-to-ecx 3/imm32" "F - test-shadow-live-output/7") # no push because it's an output reg - 2759 (check-next-stream-line-equal _test-output-stream " {" "F - test-shadow-live-output/8") - 2760 (check-next-stream-line-equal _test-output-stream "$foo:0x00000002:loop:" "F - test-shadow-live-output/9") - 2761 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %ecx" "F - test-shadow-live-output/10") - 2762 (check-next-stream-line-equal _test-output-stream " b9/copy-to-ecx 4/imm32" "F - test-shadow-live-output/11") - 2763 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %ecx" "F - test-shadow-live-output/12") - 2764 (check-next-stream-line-equal _test-output-stream " }" "F - test-shadow-live-output/13") - 2765 (check-next-stream-line-equal _test-output-stream "$foo:0x00000002:break:" "F - test-shadow-live-output/14") - 2766 (check-next-stream-line-equal _test-output-stream " 41/increment-ecx" "F - test-shadow-live-output/15") - 2767 (check-next-stream-line-equal _test-output-stream " }" "F - test-shadow-live-output/17") - 2768 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-shadow-live-output/18") - 2769 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-shadow-live-output/19") - 2770 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-shadow-live-output/20") - 2771 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-shadow-live-output/21") - 2772 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-shadow-live-output/21") - 2773 # . epilogue - 2774 89/<- %esp 5/r32/ebp - 2775 5d/pop-to-ebp - 2776 c3/return - 2777 - 2778 test-stmt-defines-output-in-same-register-as-inout: - 2779 # . prologue - 2780 55/push-ebp - 2781 89/<- %ebp 4/r32/esp - 2782 # setup - 2783 (clear-stream _test-input-stream) - 2784 (clear-stream $_test-input-buffered-file->buffer) - 2785 (clear-stream _test-output-stream) - 2786 (clear-stream $_test-output-buffered-file->buffer) - 2787 (clear-stream _test-error-stream) - 2788 (clear-stream $_test-error-buffered-file->buffer) - 2789 # var ed/edx: exit-descriptor = tailor-exit-descriptor(16) - 2790 68/push 0/imm32 - 2791 68/push 0/imm32 - 2792 89/<- %edx 4/r32/esp - 2793 (tailor-exit-descriptor %edx 0x10) - 2794 # - 2795 (write _test-input-stream "fn foo -> x/ecx: int {\n") - 2796 (write _test-input-stream " var y/ecx: int <- copy 4\n") - 2797 (write _test-input-stream " x <- copy y\n") # writing to a fn output is currently the only way for a statement to define a new var - 2798 (write _test-input-stream "}\n") - 2799 # convert - 2800 (convert-mu _test-input-buffered-file _test-output-buffered-file _test-error-buffered-file %edx) - 2801 # registers except esp clobbered at this point - 2802 # restore ed - 2803 89/<- %edx 4/r32/esp - 2804 (flush _test-output-buffered-file) - 2805 (flush _test-error-buffered-file) - 2806 +-- 6 lines: #? # dump _test-error-stream --------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 2812 # no error; we looked up 'y' correctly before pushing the binding for 'x' - 2813 (check-stream-equal _test-error-stream "" "F - test-stmt-defines-output-in-same-register-as-inout: error stream should be empty") - 2814 # don't bother checking the generated code; that's in the test 'test-local-clobbered-by-fn-output' below - 2815 # don't restore from ebp - 2816 81 0/subop/add %esp 8/imm32 - 2817 # . epilogue - 2818 5d/pop-to-ebp - 2819 c3/return - 2820 - 2821 test-local-clobbered-by-fn-output: - 2822 # . prologue - 2823 55/push-ebp - 2824 89/<- %ebp 4/r32/esp - 2825 # setup - 2826 (clear-stream _test-input-stream) - 2827 (clear-stream $_test-input-buffered-file->buffer) - 2828 (clear-stream _test-output-stream) - 2829 (clear-stream $_test-output-buffered-file->buffer) - 2830 # - 2831 (write _test-input-stream "fn foo -> x/ecx: int {\n") - 2832 (write _test-input-stream " var y/ecx: int <- copy 4\n") - 2833 (write _test-input-stream " x <- copy y\n") - 2834 (write _test-input-stream "}\n") - 2835 # convert - 2836 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) - 2837 (flush _test-output-buffered-file) - 2838 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 2844 # check output - 2845 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-local-clobbered-by-fn-output/0") - 2846 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-local-clobbered-by-fn-output/1") - 2847 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-local-clobbered-by-fn-output/2") - 2848 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-local-clobbered-by-fn-output/3") - 2849 (check-next-stream-line-equal _test-output-stream " {" "F - test-local-clobbered-by-fn-output/4") - 2850 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-local-clobbered-by-fn-output/5") - 2851 (check-next-stream-line-equal _test-output-stream " b9/copy-to-ecx 4/imm32" "F - test-local-clobbered-by-fn-output/6") # no push because it's an output reg - 2852 (check-next-stream-line-equal _test-output-stream " 89/<- %ecx 0x00000001/r32" "F - test-local-clobbered-by-fn-output/7") - 2853 (check-next-stream-line-equal _test-output-stream " }" "F - test-local-clobbered-by-fn-output/8") - 2854 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-local-clobbered-by-fn-output/9") - 2855 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-local-clobbered-by-fn-output/10") - 2856 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-local-clobbered-by-fn-output/11") - 2857 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-local-clobbered-by-fn-output/12") - 2858 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-local-clobbered-by-fn-output/13") - 2859 # . epilogue - 2860 89/<- %esp 5/r32/ebp - 2861 5d/pop-to-ebp - 2862 c3/return - 2863 - 2864 test-read-output: - 2865 # . prologue - 2866 55/push-ebp - 2867 89/<- %ebp 4/r32/esp - 2868 # setup - 2869 (clear-stream _test-input-stream) - 2870 (clear-stream $_test-input-buffered-file->buffer) - 2871 (clear-stream _test-output-stream) - 2872 (clear-stream $_test-output-buffered-file->buffer) - 2873 # - 2874 (write _test-input-stream "fn foo -> x/ecx: int {\n") - 2875 (write _test-input-stream " x <- copy 0x34\n") - 2876 (write _test-input-stream " compare x, 0x35\n") - 2877 (write _test-input-stream "}\n") - 2878 # convert - 2879 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) - 2880 (flush _test-output-buffered-file) - 2881 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 2887 # check output - 2888 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-read-output/0") - 2889 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-read-output/1") - 2890 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-read-output/2") - 2891 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-read-output/3") - 2892 (check-next-stream-line-equal _test-output-stream " {" "F - test-read-output/4") - 2893 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-read-output/5") - 2894 (check-next-stream-line-equal _test-output-stream " b9/copy-to-ecx 0x34/imm32" "F - test-read-output/6") - 2895 (check-next-stream-line-equal _test-output-stream " 81 7/subop/compare %ecx 0x35/imm32" "F - test-read-output/7") - 2896 (check-next-stream-line-equal _test-output-stream " }" "F - test-read-output/8") - 2897 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-read-output/9") - 2898 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-read-output/10") - 2899 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-read-output/11") - 2900 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-read-output/12") - 2901 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-read-output/13") - 2902 # . epilogue - 2903 89/<- %esp 5/r32/ebp - 2904 5d/pop-to-ebp - 2905 c3/return - 2906 - 2907 test-fn-output-written-in-inner-block: - 2908 # . prologue - 2909 55/push-ebp - 2910 89/<- %ebp 4/r32/esp - 2911 # setup - 2912 (clear-stream _test-input-stream) - 2913 (clear-stream $_test-input-buffered-file->buffer) - 2914 (clear-stream _test-output-stream) - 2915 (clear-stream $_test-output-buffered-file->buffer) - 2916 # - 2917 (write _test-input-stream "fn foo -> out/edi: int {\n") - 2918 (write _test-input-stream " var a/eax: int <- copy 3\n") # define outer local - 2919 (write _test-input-stream " {\n") - 2920 (write _test-input-stream " var a/ecx: int <- copy 4\n") # shadow outer local - 2921 (write _test-input-stream " out <- copy a\n") # write to fn output - 2922 (write _test-input-stream " }\n") - 2923 (write _test-input-stream " compare a, 0\n") # use outer local - 2924 (write _test-input-stream "}\n") - 2925 # convert - 2926 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) - 2927 (flush _test-output-buffered-file) - 2928 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 2934 # no error; defining 'out' didn't interfere with the reclamation of 'b' - 2935 # check output - 2936 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-fn-output-written-in-inner-block/0") - 2937 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-fn-output-written-in-inner-block/1") - 2938 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-fn-output-written-in-inner-block/2") - 2939 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-fn-output-written-in-inner-block/3") - 2940 (check-next-stream-line-equal _test-output-stream " {" "F - test-fn-output-written-in-inner-block/4") - 2941 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-fn-output-written-in-inner-block/5") - 2942 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %eax" "F - test-fn-output-written-in-inner-block/6") - 2943 (check-next-stream-line-equal _test-output-stream " b8/copy-to-eax 3/imm32" "F - test-fn-output-written-in-inner-block/7") - 2944 (check-next-stream-line-equal _test-output-stream " {" "F - test-fn-output-written-in-inner-block/8") - 2945 (check-next-stream-line-equal _test-output-stream "$foo:0x00000002:loop:" "F - test-fn-output-written-in-inner-block/9") - 2946 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %ecx" "F - test-fn-output-written-in-inner-block/10") - 2947 (check-next-stream-line-equal _test-output-stream " b9/copy-to-ecx 4/imm32" "F - test-fn-output-written-in-inner-block/10") - 2948 (check-next-stream-line-equal _test-output-stream " 89/<- %edi 0x00000001/r32" "F - test-fn-output-written-in-inner-block/11") - 2949 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %ecx" "F - test-fn-output-written-in-inner-block/12") - 2950 (check-next-stream-line-equal _test-output-stream " }" "F - test-fn-output-written-in-inner-block/13") - 2951 (check-next-stream-line-equal _test-output-stream "$foo:0x00000002:break:" "F - test-fn-output-written-in-inner-block/14") - 2952 (check-next-stream-line-equal _test-output-stream " 3d/compare-eax-with 0/imm32" "F - test-fn-output-written-in-inner-block/15") - 2953 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %eax" "F - test-fn-output-written-in-inner-block/16") - 2954 (check-next-stream-line-equal _test-output-stream " }" "F - test-fn-output-written-in-inner-block/17") - 2955 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-fn-output-written-in-inner-block/18") - 2956 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-fn-output-written-in-inner-block/19") - 2957 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-fn-output-written-in-inner-block/20") - 2958 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-fn-output-written-in-inner-block/21") - 2959 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-fn-output-written-in-inner-block/22") - 2960 # . epilogue - 2961 89/<- %esp 5/r32/ebp - 2962 5d/pop-to-ebp - 2963 c3/return - 2964 - 2965 test-convert-function-with-branches-in-block: - 2966 # . prologue - 2967 55/push-ebp - 2968 89/<- %ebp 4/r32/esp - 2969 # setup - 2970 (clear-stream _test-input-stream) - 2971 (clear-stream $_test-input-buffered-file->buffer) - 2972 (clear-stream _test-output-stream) - 2973 (clear-stream $_test-output-buffered-file->buffer) - 2974 # - 2975 (write _test-input-stream "fn foo x: int {\n") - 2976 (write _test-input-stream " {\n") - 2977 (write _test-input-stream " break-if->=\n") - 2978 (write _test-input-stream " loop-if-addr<\n") - 2979 (write _test-input-stream " increment x\n") - 2980 (write _test-input-stream " loop\n") - 2981 (write _test-input-stream " }\n") - 2982 (write _test-input-stream "}\n") - 2983 # convert - 2984 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) - 2985 (flush _test-output-buffered-file) - 2986 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 2992 # check output - 2993 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-function-with-branches-in-block/0") - 2994 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-function-with-branches-in-block/1") - 2995 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-function-with-branches-in-block/2") - 2996 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-function-with-branches-in-block/3") - 2997 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-branches-in-block/4") - 2998 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-function-with-branches-in-block/5") - 2999 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-branches-in-block/6") - 3000 (check-next-stream-line-equal _test-output-stream "$foo:0x00000002:loop:" "F - test-convert-function-with-branches-in-block/7") - 3001 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-branches-in-block/8") - 3002 (check-next-stream-line-equal _test-output-stream " 0f 8c/jump-if-< break/disp32" "F - test-convert-function-with-branches-in-block/9") - 3003 (check-next-stream-line-equal _test-output-stream " e9/jump $foo:0x00000002:break/disp32" "F - test-convert-function-with-branches-in-block/10") - 3004 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-branches-in-block/11") - 3005 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-branches-in-block/12") - 3006 (check-next-stream-line-equal _test-output-stream " 0f 83/jump-if-addr>= break/disp32" "F - test-convert-function-with-branches-in-block/13") - 3007 (check-next-stream-line-equal _test-output-stream " e9/jump $foo:0x00000002:loop/disp32" "F - test-convert-function-with-branches-in-block/14") - 3008 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-branches-in-block/15") - 3009 (check-next-stream-line-equal _test-output-stream " ff 0/subop/increment *(ebp+0x00000008)" "F - test-convert-function-with-branches-in-block/16") - 3010 (check-next-stream-line-equal _test-output-stream " e9/jump loop/disp32" "F - test-convert-function-with-branches-in-block/17") - 3011 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-branches-in-block/18") - 3012 (check-next-stream-line-equal _test-output-stream "$foo:0x00000002:break:" "F - test-convert-function-with-branches-in-block/19") - 3013 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-branches-in-block/20") - 3014 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-function-with-branches-in-block/21") - 3015 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-function-with-branches-in-block/22") - 3016 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-function-with-branches-in-block/23") - 3017 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-function-with-branches-in-block/24") - 3018 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-function-with-branches-in-block/25") - 3019 # . epilogue - 3020 89/<- %esp 5/r32/ebp - 3021 5d/pop-to-ebp - 3022 c3/return - 3023 - 3024 test-convert-function-with-branches-in-named-block: - 3025 # . prologue - 3026 55/push-ebp - 3027 89/<- %ebp 4/r32/esp - 3028 # setup - 3029 (clear-stream _test-input-stream) - 3030 (clear-stream $_test-input-buffered-file->buffer) - 3031 (clear-stream _test-output-stream) - 3032 (clear-stream $_test-output-buffered-file->buffer) - 3033 # - 3034 (write _test-input-stream "fn foo x: int {\n") - 3035 (write _test-input-stream " $bar: {\n") - 3036 (write _test-input-stream " break-if->= $bar\n") - 3037 (write _test-input-stream " loop-if-addr< $bar\n") - 3038 (write _test-input-stream " increment x\n") - 3039 (write _test-input-stream " loop\n") - 3040 (write _test-input-stream " }\n") - 3041 (write _test-input-stream "}\n") - 3042 # convert - 3043 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) - 3044 (flush _test-output-buffered-file) - 3045 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 3051 # check output - 3052 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-function-with-branches-in-named-block/0") - 3053 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-function-with-branches-in-named-block/1") - 3054 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-function-with-branches-in-named-block/2") - 3055 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-function-with-branches-in-named-block/3") - 3056 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-branches-in-named-block/4") - 3057 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-function-with-branches-in-named-block/5") - 3058 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-branches-in-named-block/6") - 3059 (check-next-stream-line-equal _test-output-stream "$bar:loop:" "F - test-convert-function-with-branches-in-named-block/7") - 3060 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-branches-in-named-block/8") - 3061 (check-next-stream-line-equal _test-output-stream " 0f 8c/jump-if-< break/disp32" "F - test-convert-function-with-branches-in-named-block/9") - 3062 (check-next-stream-line-equal _test-output-stream " e9/jump $bar:break/disp32" "F - test-convert-function-with-branches-in-named-block/10") - 3063 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-branches-in-named-block/11") - 3064 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-branches-in-named-block/12") - 3065 (check-next-stream-line-equal _test-output-stream " 0f 83/jump-if-addr>= break/disp32" "F - test-convert-function-with-branches-in-named-block/13") - 3066 (check-next-stream-line-equal _test-output-stream " e9/jump $bar:loop/disp32" "F - test-convert-function-with-branches-in-named-block/14") - 3067 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-branches-in-named-block/15") - 3068 (check-next-stream-line-equal _test-output-stream " ff 0/subop/increment *(ebp+0x00000008)" "F - test-convert-function-with-branches-in-named-block/16") - 3069 (check-next-stream-line-equal _test-output-stream " e9/jump loop/disp32" "F - test-convert-function-with-branches-in-named-block/17") - 3070 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-branches-in-named-block/18") - 3071 (check-next-stream-line-equal _test-output-stream "$bar:break:" "F - test-convert-function-with-branches-in-named-block/19") - 3072 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-branches-in-named-block/20") - 3073 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-function-with-branches-in-named-block/21") - 3074 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-function-with-branches-in-named-block/22") - 3075 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-function-with-branches-in-named-block/23") - 3076 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-function-with-branches-in-named-block/24") - 3077 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-function-with-branches-in-named-block/25") - 3078 # . epilogue - 3079 89/<- %esp 5/r32/ebp - 3080 5d/pop-to-ebp - 3081 c3/return - 3082 - 3083 test-convert-function-with-var-in-nested-block: - 3084 # . prologue - 3085 55/push-ebp - 3086 89/<- %ebp 4/r32/esp - 3087 # setup - 3088 (clear-stream _test-input-stream) - 3089 (clear-stream $_test-input-buffered-file->buffer) - 3090 (clear-stream _test-output-stream) - 3091 (clear-stream $_test-output-buffered-file->buffer) - 3092 # - 3093 (write _test-input-stream "fn foo x: int {\n") - 3094 (write _test-input-stream " {\n") - 3095 (write _test-input-stream " {\n") - 3096 (write _test-input-stream " var x: int\n") - 3097 (write _test-input-stream " increment x\n") - 3098 (write _test-input-stream " }\n") - 3099 (write _test-input-stream " }\n") - 3100 (write _test-input-stream "}\n") - 3101 # convert - 3102 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) - 3103 (flush _test-output-buffered-file) - 3104 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 3110 # check output - 3111 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-function-with-var-in-nested-block/0") - 3112 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-function-with-var-in-nested-block/1") - 3113 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-function-with-var-in-nested-block/2") - 3114 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-function-with-var-in-nested-block/3") - 3115 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-var-in-nested-block/4") - 3116 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-function-with-var-in-nested-block/5") - 3117 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-var-in-nested-block/6") - 3118 (check-next-stream-line-equal _test-output-stream "$foo:0x00000002:loop:" "F - test-convert-function-with-var-in-nested-block/7") - 3119 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-var-in-nested-block/8") - 3120 (check-next-stream-line-equal _test-output-stream "$foo:0x00000003:loop:" "F - test-convert-function-with-var-in-nested-block/9") - 3121 (check-next-stream-line-equal _test-output-stream " 68/push 0/imm32" "F - test-convert-function-with-var-in-nested-block/10") - 3122 (check-next-stream-line-equal _test-output-stream " ff 0/subop/increment *(ebp+0xfffffffc)" "F - test-convert-function-with-var-in-nested-block/11") - 3123 (check-next-stream-line-equal _test-output-stream " 81 0/subop/add %esp 0x00000004/imm32" "F - test-convert-function-with-var-in-nested-block/12") - 3124 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-var-in-nested-block/13") - 3125 (check-next-stream-line-equal _test-output-stream "$foo:0x00000003:break:" "F - test-convert-function-with-var-in-nested-block/14") - 3126 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-var-in-nested-block/15") - 3127 (check-next-stream-line-equal _test-output-stream "$foo:0x00000002:break:" "F - test-convert-function-with-var-in-nested-block/16") - 3128 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-var-in-nested-block/17") - 3129 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-function-with-var-in-nested-block/18") - 3130 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-function-with-var-in-nested-block/19") - 3131 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-function-with-var-in-nested-block/20") - 3132 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-function-with-var-in-nested-block/21") - 3133 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-function-with-var-in-nested-block/22") - 3134 # . epilogue - 3135 89/<- %esp 5/r32/ebp - 3136 5d/pop-to-ebp - 3137 c3/return - 3138 - 3139 test-convert-function-with-multiple-vars-in-nested-blocks: - 3140 # . prologue - 3141 55/push-ebp - 3142 89/<- %ebp 4/r32/esp - 3143 # setup - 3144 (clear-stream _test-input-stream) - 3145 (clear-stream $_test-input-buffered-file->buffer) - 3146 (clear-stream _test-output-stream) - 3147 (clear-stream $_test-output-buffered-file->buffer) - 3148 # - 3149 (write _test-input-stream "fn foo x: int {\n") - 3150 (write _test-input-stream " {\n") - 3151 (write _test-input-stream " var x/eax: int <- copy 0\n") - 3152 (write _test-input-stream " {\n") - 3153 (write _test-input-stream " var y: int\n") - 3154 (write _test-input-stream " x <- add y\n") - 3155 (write _test-input-stream " }\n") - 3156 (write _test-input-stream " }\n") - 3157 (write _test-input-stream "}\n") - 3158 # convert - 3159 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) - 3160 (flush _test-output-buffered-file) - 3161 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 3167 # check output - 3168 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-function-with-multiple-vars-in-nested-blocks/0") - 3169 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-function-with-multiple-vars-in-nested-blocks/1") - 3170 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-function-with-multiple-vars-in-nested-blocks/2") - 3171 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-function-with-multiple-vars-in-nested-blocks/3") - 3172 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-multiple-vars-in-nested-blocks/4") - 3173 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-function-with-multiple-vars-in-nested-blocks/5") - 3174 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-multiple-vars-in-nested-blocks/6") - 3175 (check-next-stream-line-equal _test-output-stream "$foo:0x00000002:loop:" "F - test-convert-function-with-multiple-vars-in-nested-blocks/7") - 3176 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %eax" "F - test-convert-function-with-multiple-vars-in-nested-blocks/8") - 3177 (check-next-stream-line-equal _test-output-stream " b8/copy-to-eax 0/imm32" "F - test-convert-function-with-multiple-vars-in-nested-blocks/9") - 3178 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-multiple-vars-in-nested-blocks/10") - 3179 (check-next-stream-line-equal _test-output-stream "$foo:0x00000003:loop:" "F - test-convert-function-with-multiple-vars-in-nested-blocks/11") - 3180 (check-next-stream-line-equal _test-output-stream " 68/push 0/imm32" "F - test-convert-function-with-multiple-vars-in-nested-blocks/12") - 3181 (check-next-stream-line-equal _test-output-stream " 03/add *(ebp+0xfffffff8) 0x00000000/r32" "F - test-convert-function-with-multiple-vars-in-nested-blocks/13") - 3182 (check-next-stream-line-equal _test-output-stream " 81 0/subop/add %esp 0x00000004/imm32" "F - test-convert-function-with-multiple-vars-in-nested-blocks/14") - 3183 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-multiple-vars-in-nested-blocks/15") - 3184 (check-next-stream-line-equal _test-output-stream "$foo:0x00000003:break:" "F - test-convert-function-with-multiple-vars-in-nested-blocks/16") - 3185 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %eax" "F - test-convert-function-with-multiple-vars-in-nested-blocks/17") - 3186 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-multiple-vars-in-nested-blocks/18") - 3187 (check-next-stream-line-equal _test-output-stream "$foo:0x00000002:break:" "F - test-convert-function-with-multiple-vars-in-nested-blocks/19") - 3188 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-multiple-vars-in-nested-blocks/20") - 3189 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-function-with-multiple-vars-in-nested-blocks/21") - 3190 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-function-with-multiple-vars-in-nested-blocks/22") - 3191 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-function-with-multiple-vars-in-nested-blocks/23") - 3192 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-function-with-multiple-vars-in-nested-blocks/24") - 3193 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-function-with-multiple-vars-in-nested-blocks/25") - 3194 # . epilogue - 3195 89/<- %esp 5/r32/ebp - 3196 5d/pop-to-ebp - 3197 c3/return - 3198 - 3199 test-convert-function-with-branches-and-local-vars: - 3200 # A conditional 'break' after a 'var' in a block is converted into a - 3201 # nested block that performs all necessary cleanup before jumping. This - 3202 # results in some ugly code duplication. - 3203 # . prologue - 3204 55/push-ebp - 3205 89/<- %ebp 4/r32/esp - 3206 # setup - 3207 (clear-stream _test-input-stream) - 3208 (clear-stream $_test-input-buffered-file->buffer) - 3209 (clear-stream _test-output-stream) - 3210 (clear-stream $_test-output-buffered-file->buffer) - 3211 # - 3212 (write _test-input-stream "fn foo {\n") - 3213 (write _test-input-stream " {\n") - 3214 (write _test-input-stream " var x: int\n") - 3215 (write _test-input-stream " break-if->=\n") - 3216 (write _test-input-stream " increment x\n") - 3217 (write _test-input-stream " }\n") - 3218 (write _test-input-stream "}\n") - 3219 # convert - 3220 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) - 3221 (flush _test-output-buffered-file) - 3222 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 3228 # check output - 3229 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-function-with-branches-and-local-vars/0") - 3230 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-function-with-branches-and-local-vars/1") - 3231 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-function-with-branches-and-local-vars/2") - 3232 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-function-with-branches-and-local-vars/3") - 3233 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-branches-and-local-vars/4") - 3234 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-function-with-branches-and-local-vars/5") - 3235 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-branches-and-local-vars/6") - 3236 (check-next-stream-line-equal _test-output-stream "$foo:0x00000002:loop:" "F - test-convert-function-with-branches-and-local-vars/7") - 3237 (check-next-stream-line-equal _test-output-stream " 68/push 0/imm32" "F - test-convert-function-with-branches-and-local-vars/8") - 3238 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-branches-and-local-vars/9") - 3239 (check-next-stream-line-equal _test-output-stream " 0f 8c/jump-if-< break/disp32" "F - test-convert-function-with-branches-and-local-vars/10") - 3240 (check-next-stream-line-equal _test-output-stream " 81 0/subop/add %esp 0x00000004/imm32" "F - test-convert-function-with-branches-and-local-vars/11") - 3241 (check-next-stream-line-equal _test-output-stream " e9/jump $foo:0x00000002:break/disp32" "F - test-convert-function-with-branches-and-local-vars/12") - 3242 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-branches-and-local-vars/13") - 3243 (check-next-stream-line-equal _test-output-stream " ff 0/subop/increment *(ebp+0xfffffffc)" "F - test-convert-function-with-branches-and-local-vars/14") - 3244 (check-next-stream-line-equal _test-output-stream " 81 0/subop/add %esp 0x00000004/imm32" "F - test-convert-function-with-branches-and-local-vars/15") - 3245 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-branches-and-local-vars/16") - 3246 (check-next-stream-line-equal _test-output-stream "$foo:0x00000002:break:" "F - test-convert-function-with-branches-and-local-vars/17") - 3247 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-branches-and-local-vars/18") - 3248 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-function-with-branches-and-local-vars/19") - 3249 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-function-with-branches-and-local-vars/20") - 3250 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-function-with-branches-and-local-vars/21") - 3251 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-function-with-branches-and-local-vars/22") - 3252 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-function-with-branches-and-local-vars/23") - 3253 # . epilogue - 3254 89/<- %esp 5/r32/ebp - 3255 5d/pop-to-ebp - 3256 c3/return - 3257 - 3258 test-convert-function-with-conditional-loops-and-local-vars: - 3259 # A conditional 'loop' after a 'var' in a block is converted into a nested - 3260 # block that performs all necessary cleanup before jumping. This results - 3261 # in some ugly code duplication. - 3262 # . prologue - 3263 55/push-ebp - 3264 89/<- %ebp 4/r32/esp - 3265 # setup - 3266 (clear-stream _test-input-stream) - 3267 (clear-stream $_test-input-buffered-file->buffer) - 3268 (clear-stream _test-output-stream) - 3269 (clear-stream $_test-output-buffered-file->buffer) - 3270 # - 3271 (write _test-input-stream "fn foo {\n") - 3272 (write _test-input-stream " {\n") - 3273 (write _test-input-stream " var x: int\n") - 3274 (write _test-input-stream " loop-if->=\n") - 3275 (write _test-input-stream " increment x\n") - 3276 (write _test-input-stream " }\n") - 3277 (write _test-input-stream "}\n") - 3278 # convert - 3279 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) - 3280 (flush _test-output-buffered-file) - 3281 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 3287 # check output - 3288 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-function-with-conditional-loops-and-local-vars/0") - 3289 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-function-with-conditional-loops-and-local-vars/1") - 3290 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-function-with-conditional-loops-and-local-vars/2") - 3291 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-function-with-conditional-loops-and-local-vars/3") - 3292 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-conditional-loops-and-local-vars/4") - 3293 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-function-with-conditional-loops-and-local-vars/5") - 3294 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-conditional-loops-and-local-vars/6") - 3295 (check-next-stream-line-equal _test-output-stream "$foo:0x00000002:loop:" "F - test-convert-function-with-conditional-loops-and-local-vars/7") - 3296 (check-next-stream-line-equal _test-output-stream " 68/push 0/imm32" "F - test-convert-function-with-conditional-loops-and-local-vars/8") - 3297 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-conditional-loops-and-local-vars/9") - 3298 (check-next-stream-line-equal _test-output-stream " 0f 8c/jump-if-< break/disp32" "F - test-convert-function-with-conditional-loops-and-local-vars/10") - 3299 (check-next-stream-line-equal _test-output-stream " 81 0/subop/add %esp 0x00000004/imm32" "F - test-convert-function-with-conditional-loops-and-local-vars/11") - 3300 (check-next-stream-line-equal _test-output-stream " e9/jump $foo:0x00000002:loop/disp32" "F - test-convert-function-with-conditional-loops-and-local-vars/12") - 3301 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-conditional-loops-and-local-vars/13") - 3302 (check-next-stream-line-equal _test-output-stream " ff 0/subop/increment *(ebp+0xfffffffc)" "F - test-convert-function-with-conditional-loops-and-local-vars/14") - 3303 (check-next-stream-line-equal _test-output-stream " 81 0/subop/add %esp 0x00000004/imm32" "F - test-convert-function-with-conditional-loops-and-local-vars/15") - 3304 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-conditional-loops-and-local-vars/16") - 3305 (check-next-stream-line-equal _test-output-stream "$foo:0x00000002:break:" "F - test-convert-function-with-conditional-loops-and-local-vars/17") - 3306 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-conditional-loops-and-local-vars/18") - 3307 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-function-with-conditional-loops-and-local-vars/19") - 3308 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-function-with-conditional-loops-and-local-vars/20") - 3309 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-function-with-conditional-loops-and-local-vars/21") - 3310 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-function-with-conditional-loops-and-local-vars/22") - 3311 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-function-with-conditional-loops-and-local-vars/23") - 3312 # . epilogue - 3313 89/<- %esp 5/r32/ebp - 3314 5d/pop-to-ebp - 3315 c3/return - 3316 - 3317 test-convert-function-with-unconditional-loops-and-local-vars: - 3318 # An unconditional 'loop' after a 'var' in a block is emitted _after_ the - 3319 # regular block cleanup. Any instructions after 'loop' are dead and - 3320 # therefore skipped. - 3321 # . prologue - 3322 55/push-ebp - 3323 89/<- %ebp 4/r32/esp - 3324 # setup - 3325 (clear-stream _test-input-stream) - 3326 (clear-stream $_test-input-buffered-file->buffer) - 3327 (clear-stream _test-output-stream) - 3328 (clear-stream $_test-output-buffered-file->buffer) - 3329 # - 3330 (write _test-input-stream "fn foo {\n") - 3331 (write _test-input-stream " {\n") - 3332 (write _test-input-stream " var x: int\n") - 3333 (write _test-input-stream " loop\n") - 3334 (write _test-input-stream " increment x\n") - 3335 (write _test-input-stream " }\n") - 3336 (write _test-input-stream "}\n") - 3337 # convert - 3338 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) - 3339 (flush _test-output-buffered-file) - 3340 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 3346 # check output - 3347 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-function-with-unconditional-loops-and-local-vars/0") - 3348 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-function-with-unconditional-loops-and-local-vars/1") - 3349 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-function-with-unconditional-loops-and-local-vars/2") - 3350 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-function-with-unconditional-loops-and-local-vars/3") - 3351 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-unconditional-loops-and-local-vars/4") - 3352 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-function-with-unconditional-loops-and-local-vars/5") - 3353 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-unconditional-loops-and-local-vars/6") - 3354 (check-next-stream-line-equal _test-output-stream "$foo:0x00000002:loop:" "F - test-convert-function-with-unconditional-loops-and-local-vars/7") - 3355 (check-next-stream-line-equal _test-output-stream " 68/push 0/imm32" "F - test-convert-function-with-unconditional-loops-and-local-vars/8") - 3356 (check-next-stream-line-equal _test-output-stream " 81 0/subop/add %esp 0x00000004/imm32" "F - test-convert-function-with-unconditional-loops-and-local-vars/9") - 3357 (check-next-stream-line-equal _test-output-stream " e9/jump loop/disp32" "F - test-convert-function-with-unconditional-loops-and-local-vars/10") - 3358 # not emitted: ff 0/subop/increment *(ebp+0xfffffffc) - 3359 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-unconditional-loops-and-local-vars/11") - 3360 (check-next-stream-line-equal _test-output-stream "$foo:0x00000002:break:" "F - test-convert-function-with-unconditional-loops-and-local-vars/12") - 3361 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-unconditional-loops-and-local-vars/13") - 3362 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-function-with-unconditional-loops-and-local-vars/14") - 3363 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-function-with-unconditional-loops-and-local-vars/15") - 3364 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-function-with-unconditional-loops-and-local-vars/16") - 3365 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-function-with-unconditional-loops-and-local-vars/17") - 3366 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-function-with-unconditional-loops-and-local-vars/18") - 3367 # . epilogue - 3368 89/<- %esp 5/r32/ebp - 3369 5d/pop-to-ebp - 3370 c3/return - 3371 - 3372 test-convert-function-with-branches-and-loops-and-local-vars: - 3373 # . prologue - 3374 55/push-ebp - 3375 89/<- %ebp 4/r32/esp - 3376 # setup - 3377 (clear-stream _test-input-stream) - 3378 (clear-stream $_test-input-buffered-file->buffer) - 3379 (clear-stream _test-output-stream) - 3380 (clear-stream $_test-output-buffered-file->buffer) - 3381 # - 3382 (write _test-input-stream "fn foo {\n") - 3383 (write _test-input-stream " {\n") - 3384 (write _test-input-stream " var x: int\n") - 3385 (write _test-input-stream " break-if->=\n") - 3386 (write _test-input-stream " increment x\n") - 3387 (write _test-input-stream " loop\n") - 3388 (write _test-input-stream " }\n") - 3389 (write _test-input-stream "}\n") - 3390 # convert - 3391 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) - 3392 (flush _test-output-buffered-file) - 3393 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 3399 # check output - 3400 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-function-with-branches-and-loops-and-local-vars/0") - 3401 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-function-with-branches-and-loops-and-local-vars/1") - 3402 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-function-with-branches-and-loops-and-local-vars/2") - 3403 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-function-with-branches-and-loops-and-local-vars/3") - 3404 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-branches-and-loops-and-local-vars/4") - 3405 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-function-with-branches-and-loops-and-local-vars/5") - 3406 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-branches-and-loops-and-local-vars/6") - 3407 (check-next-stream-line-equal _test-output-stream "$foo:0x00000002:loop:" "F - test-convert-function-with-branches-and-loops-and-local-vars/7") - 3408 (check-next-stream-line-equal _test-output-stream " 68/push 0/imm32" "F - test-convert-function-with-branches-and-loops-and-local-vars/8") - 3409 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-branches-and-loops-and-local-vars/9") - 3410 (check-next-stream-line-equal _test-output-stream " 0f 8c/jump-if-< break/disp32" "F - test-convert-function-with-branches-and-loops-and-local-vars/10") - 3411 (check-next-stream-line-equal _test-output-stream " 81 0/subop/add %esp 0x00000004/imm32" "F - test-convert-function-with-branches-and-loops-and-local-vars/11") - 3412 (check-next-stream-line-equal _test-output-stream " e9/jump $foo:0x00000002:break/disp32" "F - test-convert-function-with-branches-and-loops-and-local-vars/12") - 3413 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-branches-and-loops-and-local-vars/13") - 3414 (check-next-stream-line-equal _test-output-stream " ff 0/subop/increment *(ebp+0xfffffffc)" "F - test-convert-function-with-branches-and-loops-and-local-vars/14") - 3415 (check-next-stream-line-equal _test-output-stream " 81 0/subop/add %esp 0x00000004/imm32" "F - test-convert-function-with-branches-and-loops-and-local-vars/15") - 3416 (check-next-stream-line-equal _test-output-stream " e9/jump loop/disp32" "F - test-convert-function-with-branches-and-loops-and-local-vars/16") - 3417 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-branches-and-loops-and-local-vars/17") - 3418 (check-next-stream-line-equal _test-output-stream "$foo:0x00000002:break:" "F - test-convert-function-with-branches-and-loops-and-local-vars/18") - 3419 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-branches-and-loops-and-local-vars/19") - 3420 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-function-with-branches-and-loops-and-local-vars/20") - 3421 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-function-with-branches-and-loops-and-local-vars/21") - 3422 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-function-with-branches-and-loops-and-local-vars/22") - 3423 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-function-with-branches-and-loops-and-local-vars/23") - 3424 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-function-with-branches-and-loops-and-local-vars/24") - 3425 # . epilogue - 3426 89/<- %esp 5/r32/ebp - 3427 5d/pop-to-ebp - 3428 c3/return - 3429 - 3430 test-convert-function-with-nonlocal-branches-and-loops-and-local-vars: - 3431 # . prologue - 3432 55/push-ebp - 3433 89/<- %ebp 4/r32/esp - 3434 # setup - 3435 (clear-stream _test-input-stream) - 3436 (clear-stream $_test-input-buffered-file->buffer) - 3437 (clear-stream _test-output-stream) - 3438 (clear-stream $_test-output-buffered-file->buffer) - 3439 # - 3440 (write _test-input-stream "fn foo {\n") - 3441 (write _test-input-stream " a: {\n") - 3442 (write _test-input-stream " var x: int\n") - 3443 (write _test-input-stream " {\n") - 3444 (write _test-input-stream " var y: int\n") - 3445 (write _test-input-stream " break-if->= a\n") - 3446 (write _test-input-stream " increment x\n") - 3447 (write _test-input-stream " loop\n") - 3448 (write _test-input-stream " }\n") - 3449 (write _test-input-stream " }\n") - 3450 (write _test-input-stream "}\n") - 3451 # convert - 3452 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) - 3453 (flush _test-output-buffered-file) - 3454 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 3460 # check output - 3461 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars/0") - 3462 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars/1") - 3463 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars/2") - 3464 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars/3") - 3465 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars/4") - 3466 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars/5") - 3467 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars/6") - 3468 (check-next-stream-line-equal _test-output-stream "a:loop:" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars/7") - 3469 (check-next-stream-line-equal _test-output-stream " 68/push 0/imm32" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars/8") - 3470 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars/9") - 3471 (check-next-stream-line-equal _test-output-stream "$foo:0x00000003:loop:" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars/10") - 3472 (check-next-stream-line-equal _test-output-stream " 68/push 0/imm32" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars/11") - 3473 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars/12") - 3474 (check-next-stream-line-equal _test-output-stream " 0f 8c/jump-if-< break/disp32" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars/13") - 3475 (check-next-stream-line-equal _test-output-stream " 81 0/subop/add %esp 0x00000004/imm32" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars/14") - 3476 (check-next-stream-line-equal _test-output-stream " 81 0/subop/add %esp 0x00000004/imm32" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars/15") - 3477 (check-next-stream-line-equal _test-output-stream " e9/jump a:break/disp32" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars/16") - 3478 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars/17") - 3479 (check-next-stream-line-equal _test-output-stream " ff 0/subop/increment *(ebp+0xfffffffc)" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars/18") - 3480 (check-next-stream-line-equal _test-output-stream " 81 0/subop/add %esp 0x00000004/imm32" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars/19") - 3481 (check-next-stream-line-equal _test-output-stream " e9/jump loop/disp32" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars/20") - 3482 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars/21") - 3483 (check-next-stream-line-equal _test-output-stream "$foo:0x00000003:break:" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars/22") - 3484 (check-next-stream-line-equal _test-output-stream " 81 0/subop/add %esp 0x00000004/imm32" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars/23") - 3485 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars/24") - 3486 (check-next-stream-line-equal _test-output-stream "a:break:" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars/25") - 3487 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars/26") - 3488 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars/27") - 3489 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars/28") - 3490 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars/29") - 3491 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars/30") - 3492 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars/31") - 3493 # . epilogue - 3494 89/<- %esp 5/r32/ebp - 3495 5d/pop-to-ebp - 3496 c3/return - 3497 - 3498 test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-2: - 3499 # . prologue - 3500 55/push-ebp - 3501 89/<- %ebp 4/r32/esp - 3502 # setup - 3503 (clear-stream _test-input-stream) - 3504 (clear-stream $_test-input-buffered-file->buffer) - 3505 (clear-stream _test-output-stream) - 3506 (clear-stream $_test-output-buffered-file->buffer) - 3507 # non-local conditional branch from a block without a local variable, - 3508 # unwinding a local on the stack - 3509 (write _test-input-stream "fn foo {\n") - 3510 (write _test-input-stream " a: {\n") - 3511 (write _test-input-stream " var x: int\n") - 3512 (write _test-input-stream " {\n") - 3513 (write _test-input-stream " break-if->= a\n") - 3514 (write _test-input-stream " }\n") - 3515 (write _test-input-stream " }\n") - 3516 (write _test-input-stream "}\n") - 3517 # convert - 3518 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) - 3519 (flush _test-output-buffered-file) - 3520 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 3526 # check output - 3527 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-2/0") - 3528 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-2/1") - 3529 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-2/2") - 3530 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-2/3") - 3531 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-2/4") - 3532 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-2/5") - 3533 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-2/6") - 3534 (check-next-stream-line-equal _test-output-stream "a:loop:" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-2/7") - 3535 (check-next-stream-line-equal _test-output-stream " 68/push 0/imm32" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-2/8") - 3536 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-2/9") - 3537 (check-next-stream-line-equal _test-output-stream "$foo:0x00000003:loop:" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-2/10") - 3538 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-2/11") - 3539 (check-next-stream-line-equal _test-output-stream " 0f 8c/jump-if-< break/disp32" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-2/12") - 3540 (check-next-stream-line-equal _test-output-stream " 81 0/subop/add %esp 0x00000004/imm32" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-2/13") - 3541 (check-next-stream-line-equal _test-output-stream " e9/jump a:break/disp32" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-2/14") - 3542 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-2/15") - 3543 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-2/16") - 3544 (check-next-stream-line-equal _test-output-stream "$foo:0x00000003:break:" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-2/17") - 3545 (check-next-stream-line-equal _test-output-stream " 81 0/subop/add %esp 0x00000004/imm32" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-2/18") - 3546 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-2/19") - 3547 (check-next-stream-line-equal _test-output-stream "a:break:" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-2/20") - 3548 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-2/21") - 3549 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-2/22") - 3550 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-2/23") - 3551 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-2/24") - 3552 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-2/25") - 3553 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-2/26") - 3554 # . epilogue - 3555 89/<- %esp 5/r32/ebp - 3556 5d/pop-to-ebp - 3557 c3/return - 3558 - 3559 test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-3: - 3560 # . prologue - 3561 55/push-ebp - 3562 89/<- %ebp 4/r32/esp - 3563 # setup - 3564 (clear-stream _test-input-stream) - 3565 (clear-stream $_test-input-buffered-file->buffer) - 3566 (clear-stream _test-output-stream) - 3567 (clear-stream $_test-output-buffered-file->buffer) - 3568 # non-local unconditional branch from a block without a local variable, - 3569 # unwinding a local on the stack - 3570 (write _test-input-stream "fn foo {\n") - 3571 (write _test-input-stream " a: {\n") - 3572 (write _test-input-stream " var x: int\n") - 3573 (write _test-input-stream " {\n") - 3574 (write _test-input-stream " break a\n") - 3575 (write _test-input-stream " }\n") - 3576 (write _test-input-stream " }\n") - 3577 (write _test-input-stream "}\n") - 3578 # convert - 3579 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) - 3580 (flush _test-output-buffered-file) - 3581 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 3587 # check output - 3588 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-3/0") - 3589 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-3/1") - 3590 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-3/2") - 3591 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-3/3") - 3592 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-3/4") - 3593 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-3/5") - 3594 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-3/6") - 3595 (check-next-stream-line-equal _test-output-stream "a:loop:" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-3/7") - 3596 (check-next-stream-line-equal _test-output-stream " 68/push 0/imm32" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-3/8") - 3597 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-3/9") - 3598 (check-next-stream-line-equal _test-output-stream "$foo:0x00000003:loop:" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-3/10") - 3599 (check-next-stream-line-equal _test-output-stream " 81 0/subop/add %esp 0x00000004/imm32" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-3/11") - 3600 (check-next-stream-line-equal _test-output-stream " e9/jump a:break/disp32" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-3/12") - 3601 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-3/14") - 3602 (check-next-stream-line-equal _test-output-stream "$foo:0x00000003:break:" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-3/15") - 3603 (check-next-stream-line-equal _test-output-stream " 81 0/subop/add %esp 0x00000004/imm32" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-3/16") - 3604 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-3/17") - 3605 (check-next-stream-line-equal _test-output-stream "a:break:" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-3/18") - 3606 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-3/19") - 3607 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-3/20") - 3608 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-3/21") - 3609 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-3/22") - 3610 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-3/23") - 3611 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-3/24") - 3612 # . epilogue - 3613 89/<- %esp 5/r32/ebp - 3614 5d/pop-to-ebp - 3615 c3/return - 3616 - 3617 test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-4: - 3618 # . prologue - 3619 55/push-ebp - 3620 89/<- %ebp 4/r32/esp - 3621 # setup - 3622 (clear-stream _test-input-stream) - 3623 (clear-stream $_test-input-buffered-file->buffer) - 3624 (clear-stream _test-output-stream) - 3625 (clear-stream $_test-output-buffered-file->buffer) - 3626 # - 3627 (write _test-input-stream "fn foo {\n") - 3628 (write _test-input-stream " a: {\n") - 3629 (write _test-input-stream " var x/esi: int <- copy 0\n") - 3630 (write _test-input-stream " {\n") - 3631 (write _test-input-stream " break a\n") - 3632 (write _test-input-stream " }\n") - 3633 (write _test-input-stream " }\n") - 3634 (write _test-input-stream "}\n") - 3635 # convert - 3636 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) - 3637 (flush _test-output-buffered-file) - 3638 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 3644 # check output - 3645 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-4/0") - 3646 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-4/1") - 3647 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-4/2") - 3648 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-4/3") - 3649 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-4/4") - 3650 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-4/5") - 3651 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-4/6") - 3652 (check-next-stream-line-equal _test-output-stream "a:loop:" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-4/7") - 3653 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %esi" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-4/8") - 3654 (check-next-stream-line-equal _test-output-stream " be/copy-to-esi 0/imm32" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-4/9") - 3655 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-4/10") - 3656 (check-next-stream-line-equal _test-output-stream "$foo:0x00000003:loop:" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-4/11") - 3657 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %esi" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-4/12") - 3658 (check-next-stream-line-equal _test-output-stream " e9/jump a:break/disp32" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-4/13") - 3659 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-4/14") - 3660 (check-next-stream-line-equal _test-output-stream "$foo:0x00000003:break:" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-4/15") - 3661 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %esi" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-4/16") - 3662 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-4/17") - 3663 (check-next-stream-line-equal _test-output-stream "a:break:" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-4/18") - 3664 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-4/19") - 3665 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-4/20") - 3666 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-4/21") - 3667 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-4/22") - 3668 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-4/23") - 3669 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-4/24") - 3670 # . epilogue - 3671 89/<- %esp 5/r32/ebp - 3672 5d/pop-to-ebp - 3673 c3/return - 3674 - 3675 test-convert-function-with-nonlocal-unconditional-break-and-local-vars: - 3676 # . prologue - 3677 55/push-ebp - 3678 89/<- %ebp 4/r32/esp - 3679 # setup - 3680 (clear-stream _test-input-stream) - 3681 (clear-stream $_test-input-buffered-file->buffer) - 3682 (clear-stream _test-output-stream) - 3683 (clear-stream $_test-output-buffered-file->buffer) - 3684 # - 3685 (write _test-input-stream "fn foo {\n") - 3686 (write _test-input-stream " a: {\n") - 3687 (write _test-input-stream " var x: int\n") - 3688 (write _test-input-stream " {\n") - 3689 (write _test-input-stream " var y: int\n") - 3690 (write _test-input-stream " break a\n") - 3691 (write _test-input-stream " increment x\n") - 3692 (write _test-input-stream " }\n") - 3693 (write _test-input-stream " }\n") - 3694 (write _test-input-stream "}\n") - 3695 # convert - 3696 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) - 3697 (flush _test-output-buffered-file) - 3698 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 3704 # check output - 3705 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-function-with-nonlocal-unconditional-break-and-local-vars/0") - 3706 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-function-with-nonlocal-unconditional-break-and-local-vars/1") - 3707 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-function-with-nonlocal-unconditional-break-and-local-vars/2") - 3708 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-function-with-nonlocal-unconditional-break-and-local-vars/3") - 3709 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-nonlocal-unconditional-break-and-local-vars/4") - 3710 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-function-with-nonlocal-unconditional-break-and-local-vars/5") - 3711 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-nonlocal-unconditional-break-and-local-vars/6") - 3712 (check-next-stream-line-equal _test-output-stream "a:loop:" "F - test-convert-function-with-nonlocal-unconditional-break-and-local-vars/7") - 3713 (check-next-stream-line-equal _test-output-stream " 68/push 0/imm32" "F - test-convert-function-with-nonlocal-unconditional-break-and-local-vars/8") - 3714 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-nonlocal-unconditional-break-and-local-vars/9") - 3715 (check-next-stream-line-equal _test-output-stream "$foo:0x00000003:loop:" "F - test-convert-function-with-nonlocal-unconditional-break-and-local-vars/10") - 3716 (check-next-stream-line-equal _test-output-stream " 68/push 0/imm32" "F - test-convert-function-with-nonlocal-unconditional-break-and-local-vars/11") - 3717 (check-next-stream-line-equal _test-output-stream " 81 0/subop/add %esp 0x00000004/imm32" "F - test-convert-function-with-nonlocal-unconditional-break-and-local-vars/12") - 3718 (check-next-stream-line-equal _test-output-stream " 81 0/subop/add %esp 0x00000004/imm32" "F - test-convert-function-with-nonlocal-unconditional-break-and-local-vars/13") - 3719 (check-next-stream-line-equal _test-output-stream " e9/jump a:break/disp32" "F - test-convert-function-with-nonlocal-unconditional-break-and-local-vars/14") - 3720 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-nonlocal-unconditional-break-and-local-vars/15") - 3721 (check-next-stream-line-equal _test-output-stream "$foo:0x00000003:break:" "F - test-convert-function-with-nonlocal-unconditional-break-and-local-vars/16") - 3722 (check-next-stream-line-equal _test-output-stream " 81 0/subop/add %esp 0x00000004/imm32" "F - test-convert-function-with-nonlocal-unconditional-break-and-local-vars/17") - 3723 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-nonlocal-unconditional-break-and-local-vars/18") - 3724 (check-next-stream-line-equal _test-output-stream "a:break:" "F - test-convert-function-with-nonlocal-unconditional-break-and-local-vars/19") - 3725 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-nonlocal-unconditional-break-and-local-vars/20") - 3726 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-function-with-nonlocal-unconditional-break-and-local-vars/21") - 3727 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-function-with-nonlocal-unconditional-break-and-local-vars/22") - 3728 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-function-with-nonlocal-unconditional-break-and-local-vars/23") - 3729 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-function-with-nonlocal-unconditional-break-and-local-vars/24") - 3730 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-function-with-nonlocal-unconditional-break-and-local-vars/25") - 3731 # . epilogue - 3732 89/<- %esp 5/r32/ebp - 3733 5d/pop-to-ebp - 3734 c3/return - 3735 - 3736 test-convert-function-with-unconditional-break-and-local-vars: - 3737 # . prologue - 3738 55/push-ebp - 3739 89/<- %ebp 4/r32/esp - 3740 # setup - 3741 (clear-stream _test-input-stream) - 3742 (clear-stream $_test-input-buffered-file->buffer) - 3743 (clear-stream _test-output-stream) - 3744 (clear-stream $_test-output-buffered-file->buffer) - 3745 # - 3746 (write _test-input-stream "fn foo {\n") - 3747 (write _test-input-stream " {\n") - 3748 (write _test-input-stream " var x: int\n") - 3749 (write _test-input-stream " {\n") - 3750 (write _test-input-stream " var y: int\n") - 3751 (write _test-input-stream " break\n") - 3752 (write _test-input-stream " increment x\n") - 3753 (write _test-input-stream " }\n") - 3754 (write _test-input-stream " }\n") - 3755 (write _test-input-stream "}\n") - 3756 # convert - 3757 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) - 3758 (flush _test-output-buffered-file) - 3759 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 3765 # check output - 3766 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-function-with-unconditional-break-and-local-vars/0") - 3767 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-function-with-unconditional-break-and-local-vars/1") - 3768 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-function-with-unconditional-break-and-local-vars/2") - 3769 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-function-with-unconditional-break-and-local-vars/3") - 3770 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-unconditional-break-and-local-vars/4") - 3771 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-function-with-unconditional-break-and-local-vars/5") - 3772 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-unconditional-break-and-local-vars/6") - 3773 (check-next-stream-line-equal _test-output-stream "$foo:0x00000002:loop:" "F - test-convert-function-with-unconditional-break-and-local-vars/7") - 3774 (check-next-stream-line-equal _test-output-stream " 68/push 0/imm32" "F - test-convert-function-with-unconditional-break-and-local-vars/8") - 3775 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-unconditional-break-and-local-vars/9") - 3776 (check-next-stream-line-equal _test-output-stream "$foo:0x00000003:loop:" "F - test-convert-function-with-unconditional-break-and-local-vars/10") - 3777 (check-next-stream-line-equal _test-output-stream " 68/push 0/imm32" "F - test-convert-function-with-unconditional-break-and-local-vars/11") - 3778 (check-next-stream-line-equal _test-output-stream " 81 0/subop/add %esp 0x00000004/imm32" "F - test-convert-function-with-unconditional-break-and-local-vars/12") - 3779 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-unconditional-break-and-local-vars/13") - 3780 (check-next-stream-line-equal _test-output-stream "$foo:0x00000003:break:" "F - test-convert-function-with-unconditional-break-and-local-vars/14") - 3781 (check-next-stream-line-equal _test-output-stream " 81 0/subop/add %esp 0x00000004/imm32" "F - test-convert-function-with-unconditional-break-and-local-vars/15") - 3782 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-unconditional-break-and-local-vars/16") - 3783 (check-next-stream-line-equal _test-output-stream "$foo:0x00000002:break:" "F - test-convert-function-with-unconditional-break-and-local-vars/17") - 3784 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-unconditional-break-and-local-vars/18") - 3785 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-function-with-unconditional-break-and-local-vars/19") - 3786 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-function-with-unconditional-break-and-local-vars/20") - 3787 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-function-with-unconditional-break-and-local-vars/21") - 3788 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-function-with-unconditional-break-and-local-vars/22") - 3789 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-function-with-unconditional-break-and-local-vars/23") - 3790 # . epilogue - 3791 89/<- %esp 5/r32/ebp - 3792 5d/pop-to-ebp - 3793 c3/return - 3794 - 3795 test-convert-function-with-nonlocal-unconditional-loop-and-local-vars: - 3796 # . prologue - 3797 55/push-ebp - 3798 89/<- %ebp 4/r32/esp - 3799 # setup - 3800 (clear-stream _test-input-stream) - 3801 (clear-stream $_test-input-buffered-file->buffer) - 3802 (clear-stream _test-output-stream) - 3803 (clear-stream $_test-output-buffered-file->buffer) - 3804 # - 3805 (write _test-input-stream "fn foo {\n") - 3806 (write _test-input-stream " a: {\n") - 3807 (write _test-input-stream " var x: int\n") - 3808 (write _test-input-stream " {\n") - 3809 (write _test-input-stream " var y: int\n") - 3810 (write _test-input-stream " loop a\n") - 3811 (write _test-input-stream " increment x\n") - 3812 (write _test-input-stream " }\n") - 3813 (write _test-input-stream " }\n") - 3814 (write _test-input-stream "}\n") - 3815 # convert - 3816 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) - 3817 (flush _test-output-buffered-file) - 3818 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 3824 # check output - 3825 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-function-with-nonlocal-unconditional-loop-and-local-vars/0") - 3826 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-function-with-nonlocal-unconditional-loop-and-local-vars/1") - 3827 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-function-with-nonlocal-unconditional-loop-and-local-vars/2") - 3828 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-function-with-nonlocal-unconditional-loop-and-local-vars/3") - 3829 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-nonlocal-unconditional-loop-and-local-vars/4") - 3830 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-function-with-nonlocal-unconditional-loop-and-local-vars/5") - 3831 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-nonlocal-unconditional-loop-and-local-vars/6") - 3832 (check-next-stream-line-equal _test-output-stream "a:loop:" "F - test-convert-function-with-nonlocal-unconditional-loop-and-local-vars/7") - 3833 (check-next-stream-line-equal _test-output-stream " 68/push 0/imm32" "F - test-convert-function-with-nonlocal-unconditional-loop-and-local-vars/8") - 3834 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-nonlocal-unconditional-loop-and-local-vars/9") - 3835 (check-next-stream-line-equal _test-output-stream "$foo:0x00000003:loop:" "F - test-convert-function-with-nonlocal-unconditional-loop-and-local-vars/10") - 3836 (check-next-stream-line-equal _test-output-stream " 68/push 0/imm32" "F - test-convert-function-with-nonlocal-unconditional-loop-and-local-vars/11") - 3837 (check-next-stream-line-equal _test-output-stream " 81 0/subop/add %esp 0x00000004/imm32" "F - test-convert-function-with-nonlocal-unconditional-loop-and-local-vars/12") - 3838 (check-next-stream-line-equal _test-output-stream " 81 0/subop/add %esp 0x00000004/imm32" "F - test-convert-function-with-nonlocal-unconditional-loop-and-local-vars/13") - 3839 (check-next-stream-line-equal _test-output-stream " e9/jump a:loop/disp32" "F - test-convert-function-with-nonlocal-unconditional-loop-and-local-vars/14") - 3840 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-nonlocal-unconditional-loop-and-local-vars/15") - 3841 (check-next-stream-line-equal _test-output-stream "$foo:0x00000003:break:" "F - test-convert-function-with-nonlocal-unconditional-loop-and-local-vars/16") - 3842 (check-next-stream-line-equal _test-output-stream " 81 0/subop/add %esp 0x00000004/imm32" "F - test-convert-function-with-nonlocal-unconditional-loop-and-local-vars/17") - 3843 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-nonlocal-unconditional-loop-and-local-vars/18") - 3844 (check-next-stream-line-equal _test-output-stream "a:break:" "F - test-convert-function-with-nonlocal-unconditional-loop-and-local-vars/19") - 3845 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-nonlocal-unconditional-loop-and-local-vars/20") - 3846 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-function-with-nonlocal-unconditional-loop-and-local-vars/21") - 3847 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-function-with-nonlocal-unconditional-loop-and-local-vars/22") - 3848 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-function-with-nonlocal-unconditional-loop-and-local-vars/23") - 3849 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-function-with-nonlocal-unconditional-loop-and-local-vars/24") - 3850 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-function-with-nonlocal-unconditional-loop-and-local-vars/25") - 3851 # . epilogue - 3852 89/<- %esp 5/r32/ebp - 3853 5d/pop-to-ebp - 3854 c3/return - 3855 - 3856 test-convert-function-with-local-array-var-in-mem: - 3857 # . prologue - 3858 55/push-ebp - 3859 89/<- %ebp 4/r32/esp - 3860 # setup - 3861 (clear-stream _test-input-stream) - 3862 (clear-stream $_test-input-buffered-file->buffer) - 3863 (clear-stream _test-output-stream) - 3864 (clear-stream $_test-output-buffered-file->buffer) - 3865 # - 3866 (write _test-input-stream "fn foo {\n") - 3867 (write _test-input-stream " var x: (array int 3)\n") - 3868 (write _test-input-stream "}\n") - 3869 # convert - 3870 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) - 3871 (flush _test-output-buffered-file) - 3872 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 3878 # check output - 3879 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-function-with-local-array-var-in-mem/0") - 3880 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-function-with-local-array-var-in-mem/1") - 3881 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-function-with-local-array-var-in-mem/2") - 3882 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-function-with-local-array-var-in-mem/3") - 3883 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-local-array-var-in-mem/4") - 3884 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-function-with-local-array-var-in-mem/5") - 3885 # define x - 3886 (check-next-stream-line-equal _test-output-stream " (push-n-zero-bytes 0x0000000c)" "F - test-convert-function-with-local-array-var-in-mem/7") - 3887 (check-next-stream-line-equal _test-output-stream " 68/push 0x0000000c/imm32" "F - test-convert-function-with-local-array-var-in-mem/8") - 3888 # reclaim x - 3889 (check-next-stream-line-equal _test-output-stream " 81 0/subop/add %esp 0x00000010/imm32" "F - test-convert-function-with-local-array-var-in-mem/9") - 3890 # - 3891 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-local-array-var-in-mem/10") - 3892 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-function-with-local-array-var-in-mem/11") - 3893 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-function-with-local-array-var-in-mem/12") - 3894 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-function-with-local-array-var-in-mem/13") - 3895 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-function-with-local-array-var-in-mem/14") - 3896 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-function-with-local-array-var-in-mem/15") - 3897 # . epilogue - 3898 89/<- %esp 5/r32/ebp - 3899 5d/pop-to-ebp - 3900 c3/return - 3901 - 3902 test-array-size-in-hex: - 3903 # . prologue - 3904 55/push-ebp - 3905 89/<- %ebp 4/r32/esp - 3906 # setup - 3907 (clear-stream _test-input-stream) - 3908 (clear-stream $_test-input-buffered-file->buffer) - 3909 (clear-stream _test-output-stream) - 3910 (clear-stream $_test-output-buffered-file->buffer) - 3911 (clear-stream _test-error-stream) - 3912 (clear-stream $_test-error-buffered-file->buffer) - 3913 # var ed/edx: exit-descriptor = tailor-exit-descriptor(16) - 3914 68/push 0/imm32 - 3915 68/push 0/imm32 - 3916 89/<- %edx 4/r32/esp - 3917 (tailor-exit-descriptor %edx 0x10) - 3918 # - 3919 (write _test-input-stream "fn foo {\n") - 3920 (write _test-input-stream " var x: (array int 10)\n") - 3921 (write _test-input-stream "}\n") - 3922 # convert - 3923 (convert-mu _test-input-buffered-file _test-output-buffered-file _test-error-buffered-file %edx) - 3924 # registers except esp clobbered at this point - 3925 # restore ed - 3926 89/<- %edx 4/r32/esp - 3927 (flush _test-output-buffered-file) - 3928 (flush _test-error-buffered-file) - 3929 +-- 6 lines: #? # dump _test-error-stream --------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 3935 # check output - 3936 (check-stream-equal _test-output-stream "" "F - test-array-size-in-hex: output should be empty") - 3937 (check-next-stream-line-equal _test-error-stream "literal integers are always hex in Mu; either start '10' with a '0x' to be unambiguous, or convert it to decimal." "F - test-array-size-in-hex: error message") - 3938 # check that stop(1) was called - 3939 (check-ints-equal *(edx+4) 2 "F - test-array-size-in-hex: exit status") - 3940 # don't restore from ebp - 3941 81 0/subop/add %esp 8/imm32 - 3942 # . epilogue - 3943 5d/pop-to-ebp - 3944 c3/return - 3945 - 3946 test-convert-function-with-populate: - 3947 # . prologue - 3948 55/push-ebp - 3949 89/<- %ebp 4/r32/esp - 3950 # setup - 3951 (clear-stream _test-input-stream) - 3952 (clear-stream $_test-input-buffered-file->buffer) - 3953 (clear-stream _test-output-stream) - 3954 (clear-stream $_test-output-buffered-file->buffer) - 3955 # - 3956 (write _test-input-stream "fn foo {\n") - 3957 (write _test-input-stream " var x/ecx: (addr handle array int) <- copy 0\n") - 3958 (write _test-input-stream " populate x, 7\n") - 3959 (write _test-input-stream "}\n") - 3960 # convert - 3961 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) - 3962 (flush _test-output-buffered-file) - 3963 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 3969 # check output - 3970 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-function-with-populate/0") - 3971 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-function-with-populate/1") - 3972 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-function-with-populate/2") - 3973 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-function-with-populate/3") - 3974 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-populate/4") - 3975 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-function-with-populate/5") - 3976 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %ecx" "F - test-convert-function-with-populate/6") - 3977 (check-next-stream-line-equal _test-output-stream " b9/copy-to-ecx 0/imm32" "F - test-convert-function-with-populate/7") - 3978 (check-next-stream-line-equal _test-output-stream " (allocate-array2 Heap 0x00000004 7 %ecx)" "F - test-convert-function-with-populate/8") # 4 = size-of(int) - 3979 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %ecx" "F - test-convert-function-with-populate/9") - 3980 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-populate/10") - 3981 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-function-with-populate/11") - 3982 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-function-with-populate/12") - 3983 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-function-with-populate/13") - 3984 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-function-with-populate/14") - 3985 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-function-with-populate/15") - 3986 # . epilogue - 3987 89/<- %esp 5/r32/ebp - 3988 5d/pop-to-ebp - 3989 c3/return - 3990 - 3991 # special-case for size(byte) when allocating array - 3992 test-convert-function-with-local-array-of-bytes-in-mem: - 3993 # . prologue - 3994 55/push-ebp - 3995 89/<- %ebp 4/r32/esp - 3996 # setup - 3997 (clear-stream _test-input-stream) - 3998 (clear-stream $_test-input-buffered-file->buffer) - 3999 (clear-stream _test-output-stream) - 4000 (clear-stream $_test-output-buffered-file->buffer) - 4001 # - 4002 (write _test-input-stream "fn foo {\n") - 4003 (write _test-input-stream " var x: (array byte 3)\n") - 4004 (write _test-input-stream "}\n") - 4005 # convert - 4006 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) - 4007 (flush _test-output-buffered-file) - 4008 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 4014 # check output - 4015 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-function-with-local-array-of-bytes-in-mem/0") - 4016 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-function-with-local-array-of-bytes-in-mem/1") - 4017 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-function-with-local-array-of-bytes-in-mem/2") - 4018 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-function-with-local-array-of-bytes-in-mem/3") - 4019 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-local-array-of-bytes-in-mem/4") - 4020 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-function-with-local-array-of-bytes-in-mem/5") - 4021 # define x - 4022 (check-next-stream-line-equal _test-output-stream " (push-n-zero-bytes 0x00000003)" "F - test-convert-function-with-local-array-of-bytes-in-mem/7") - 4023 (check-next-stream-line-equal _test-output-stream " 68/push 0x00000003/imm32" "F - test-convert-function-with-local-array-of-bytes-in-mem/8") - 4024 # reclaim x - 4025 (check-next-stream-line-equal _test-output-stream " 81 0/subop/add %esp 0x00000007/imm32" "F - test-convert-function-with-local-array-of-bytes-in-mem/9") - 4026 # - 4027 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-local-array-of-bytes-in-mem/10") - 4028 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-function-with-local-array-of-bytes-in-mem/11") - 4029 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-function-with-local-array-of-bytes-in-mem/12") - 4030 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-function-with-local-array-of-bytes-in-mem/13") - 4031 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-function-with-local-array-of-bytes-in-mem/14") - 4032 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-function-with-local-array-of-bytes-in-mem/15") - 4033 # . epilogue - 4034 89/<- %esp 5/r32/ebp - 4035 5d/pop-to-ebp - 4036 c3/return - 4037 - 4038 test-convert-address: - 4039 # . prologue - 4040 55/push-ebp - 4041 89/<- %ebp 4/r32/esp - 4042 # setup - 4043 (clear-stream _test-input-stream) - 4044 (clear-stream $_test-input-buffered-file->buffer) - 4045 (clear-stream _test-output-stream) - 4046 (clear-stream $_test-output-buffered-file->buffer) - 4047 # - 4048 (write _test-input-stream "fn foo {\n") - 4049 (write _test-input-stream " var a: int\n") - 4050 (write _test-input-stream " var b/eax: (addr int) <- address a\n") - 4051 (write _test-input-stream "}\n") - 4052 # convert - 4053 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) - 4054 (flush _test-output-buffered-file) - 4055 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 4061 # check output - 4062 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-address/0") - 4063 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-address/1") - 4064 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-address/2") - 4065 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-address/3") - 4066 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-address/4") - 4067 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-address/5") - 4068 (check-next-stream-line-equal _test-output-stream " 68/push 0/imm32" "F - test-convert-address/6") - 4069 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %eax" "F - test-convert-address/7") - 4070 (check-next-stream-line-equal _test-output-stream " 8d/copy-address *(ebp+0xfffffffc) 0x00000000/r32" "F - test-convert-address/8") - 4071 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %eax" "F - test-convert-address/9") - 4072 (check-next-stream-line-equal _test-output-stream " 81 0/subop/add %esp 0x00000004/imm32" "F - test-convert-address/10") - 4073 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-address/11") - 4074 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-address/12") - 4075 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-address/13") - 4076 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-address/14") - 4077 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-address/15") - 4078 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-address/16") - 4079 # . epilogue - 4080 89/<- %esp 5/r32/ebp - 4081 5d/pop-to-ebp - 4082 c3/return - 4083 - 4084 test-convert-length-of-array: - 4085 # . prologue - 4086 55/push-ebp - 4087 89/<- %ebp 4/r32/esp - 4088 # setup - 4089 (clear-stream _test-input-stream) - 4090 (clear-stream $_test-input-buffered-file->buffer) - 4091 (clear-stream _test-output-stream) - 4092 (clear-stream $_test-output-buffered-file->buffer) - 4093 # - 4094 (write _test-input-stream "fn foo a: (addr array int) {\n") - 4095 (write _test-input-stream " var b/eax: (addr array int) <- copy a\n") - 4096 (write _test-input-stream " var c/eax: int <- length b\n") - 4097 (write _test-input-stream "}\n") - 4098 # convert - 4099 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) - 4100 (flush _test-output-buffered-file) - 4101 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 4107 # check output - 4108 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-length-of-array/0") - 4109 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-length-of-array/1") - 4110 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-length-of-array/2") - 4111 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-length-of-array/3") - 4112 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-length-of-array/4") - 4113 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-length-of-array/5") - 4114 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %eax" "F - test-convert-length-of-array/6") - 4115 (check-next-stream-line-equal _test-output-stream " 8b/-> *(ebp+0x00000008) 0x00000000/r32" "F - test-convert-length-of-array/7") - 4116 (check-next-stream-line-equal _test-output-stream " 8b/-> *eax 0x00000000/r32" "F - test-convert-length-of-array/8") - 4117 (check-next-stream-line-equal _test-output-stream " c1/shift 5/subop/>> %eax 0x00000002/imm8" "F - test-convert-length-of-array/9") - 4118 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %eax" "F - test-convert-length-of-array/10") - 4119 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-length-of-array/11") - 4120 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-length-of-array/12") - 4121 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-length-of-array/13") - 4122 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-length-of-array/14") - 4123 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-length-of-array/15") - 4124 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-length-of-array/16") - 4125 # . epilogue - 4126 89/<- %esp 5/r32/ebp - 4127 5d/pop-to-ebp - 4128 c3/return - 4129 - 4130 # special-case for size(byte) when computing array length - 4131 test-convert-length-of-array-of-bytes: - 4132 # . prologue - 4133 55/push-ebp - 4134 89/<- %ebp 4/r32/esp - 4135 # setup - 4136 (clear-stream _test-input-stream) - 4137 (clear-stream $_test-input-buffered-file->buffer) - 4138 (clear-stream _test-output-stream) - 4139 (clear-stream $_test-output-buffered-file->buffer) - 4140 # - 4141 (write _test-input-stream "fn foo a: (addr array byte) {\n") - 4142 (write _test-input-stream " var b/eax: (addr array byte) <- copy a\n") - 4143 (write _test-input-stream " var c/eax: int <- length b\n") - 4144 (write _test-input-stream "}\n") - 4145 # convert - 4146 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) - 4147 (flush _test-output-buffered-file) - 4148 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 4154 # check output - 4155 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-length-of-array-of-bytes/0") - 4156 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-length-of-array-of-bytes/1") - 4157 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-length-of-array-of-bytes/2") - 4158 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-length-of-array-of-bytes/3") - 4159 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-length-of-array-of-bytes/4") - 4160 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-length-of-array-of-bytes/5") - 4161 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %eax" "F - test-convert-length-of-array-of-bytes/6") - 4162 (check-next-stream-line-equal _test-output-stream " 8b/-> *(ebp+0x00000008) 0x00000000/r32" "F - test-convert-length-of-array-of-bytes/7") - 4163 (check-next-stream-line-equal _test-output-stream " 8b/-> *eax 0x00000000/r32" "F - test-convert-length-of-array-of-bytes/8") - 4164 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %eax" "F - test-convert-length-of-array-of-bytes/9") - 4165 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-length-of-array-of-bytes/10") - 4166 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-length-of-array-of-bytes/11") - 4167 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-length-of-array-of-bytes/12") - 4168 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-length-of-array-of-bytes/13") - 4169 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-length-of-array-of-bytes/14") - 4170 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-length-of-array-of-bytes/15") - 4171 # . epilogue - 4172 89/<- %esp 5/r32/ebp - 4173 5d/pop-to-ebp - 4174 c3/return - 4175 - 4176 test-convert-length-of-array-on-stack: - 4177 # . prologue - 4178 55/push-ebp - 4179 89/<- %ebp 4/r32/esp - 4180 # setup - 4181 (clear-stream _test-input-stream) - 4182 (clear-stream $_test-input-buffered-file->buffer) - 4183 (clear-stream _test-output-stream) - 4184 (clear-stream $_test-output-buffered-file->buffer) - 4185 # - 4186 (write _test-input-stream "fn foo {\n") - 4187 (write _test-input-stream " var a: (array int 3)\n") - 4188 (write _test-input-stream " var b/eax: int <- length a\n") - 4189 (write _test-input-stream "}\n") - 4190 # convert - 4191 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) - 4192 (flush _test-output-buffered-file) - 4193 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 4199 # check output - 4200 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-length-of-array-on-stack/0") - 4201 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-length-of-array-on-stack/1") - 4202 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-length-of-array-on-stack/2") - 4203 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-length-of-array-on-stack/3") - 4204 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-length-of-array-on-stack/4") - 4205 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-length-of-array-on-stack/5") - 4206 # define x - 4207 (check-next-stream-line-equal _test-output-stream " (push-n-zero-bytes 0x0000000c)" "F - test-convert-length-of-array-on-stack/6") - 4208 (check-next-stream-line-equal _test-output-stream " 68/push 0x0000000c/imm32" "F - test-convert-length-of-array-on-stack/7") - 4209 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %eax" "F - test-convert-length-of-array-on-stack/8") - 4210 (check-next-stream-line-equal _test-output-stream " 8b/-> *(ebp+0xfffffff0) 0x00000000/r32" "F - test-convert-length-of-array-on-stack/9") - 4211 (check-next-stream-line-equal _test-output-stream " c1/shift 5/subop/>> %eax 0x00000002/imm8" "F - test-convert-length-of-array-on-stack/10") - 4212 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %eax" "F - test-convert-length-of-array-on-stack/11") - 4213 (check-next-stream-line-equal _test-output-stream " 81 0/subop/add %esp 0x00000010/imm32" "F - test-convert-length-of-array-on-stack/12") - 4214 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-length-of-array-on-stack/13") - 4215 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-length-of-array-on-stack/14") - 4216 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-length-of-array-on-stack/15") - 4217 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-length-of-array-on-stack/16") - 4218 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-length-of-array-on-stack/17") - 4219 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-length-of-array-on-stack/18") - 4220 # . epilogue - 4221 89/<- %esp 5/r32/ebp - 4222 5d/pop-to-ebp - 4223 c3/return - 4224 - 4225 test-reg-var-def-with-read-of-same-register: - 4226 # . prologue - 4227 55/push-ebp - 4228 89/<- %ebp 4/r32/esp - 4229 # setup - 4230 (clear-stream _test-input-stream) - 4231 (clear-stream $_test-input-buffered-file->buffer) - 4232 (clear-stream _test-output-stream) - 4233 (clear-stream $_test-output-buffered-file->buffer) - 4234 (clear-stream _test-error-stream) - 4235 (clear-stream $_test-error-buffered-file->buffer) - 4236 # var ed/edx: exit-descriptor = tailor-exit-descriptor(16) # bytes of args in call to convert-mu - 4237 68/push 0/imm32 - 4238 68/push 0/imm32 - 4239 89/<- %edx 4/r32/esp - 4240 (tailor-exit-descriptor %edx 0x10) - 4241 # - 4242 (write _test-input-stream "fn foo {\n") - 4243 (write _test-input-stream " var arr/eax: (addr array int) <- copy 0\n") - 4244 (write _test-input-stream " var idx/ecx: int <- copy 3\n") - 4245 (write _test-input-stream " var x/eax: (addr int) <- index arr, idx\n") - 4246 (write _test-input-stream "}\n") - 4247 # convert - 4248 (convert-mu _test-input-buffered-file _test-output-buffered-file _test-error-buffered-file %edx) - 4249 # registers except esp could be clobbered at this point (though they shouldn't be) - 4250 # restore ed - 4251 89/<- %edx 4/r32/esp - 4252 (flush _test-output-buffered-file) - 4253 (flush _test-error-buffered-file) - 4254 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 4260 (check-stream-equal _test-error-stream "" "F - test-reg-var-def-with-read-of-same-register: error stream should be empty") - 4261 # check output - 4262 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-reg-var-def-with-read-of-same-register/0") - 4263 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-reg-var-def-with-read-of-same-register/1") - 4264 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-reg-var-def-with-read-of-same-register/2") - 4265 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-reg-var-def-with-read-of-same-register/3") - 4266 (check-next-stream-line-equal _test-output-stream " {" "F - test-reg-var-def-with-read-of-same-register/4") - 4267 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-reg-var-def-with-read-of-same-register/5") - 4268 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %eax" "F - test-reg-var-def-with-read-of-same-register/6") - 4269 (check-next-stream-line-equal _test-output-stream " b8/copy-to-eax 0/imm32" "F - test-reg-var-def-with-read-of-same-register/7") - 4270 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %ecx" "F - test-reg-var-def-with-read-of-same-register/8") - 4271 (check-next-stream-line-equal _test-output-stream " b9/copy-to-ecx 3/imm32" "F - test-reg-var-def-with-read-of-same-register/9") - 4272 (check-next-stream-line-equal _test-output-stream " 8d/copy-address *(eax + ecx<<0x00000002 + 4) 0x00000000/r32" "F - test-reg-var-def-with-read-of-same-register/11") - 4273 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %ecx" "F - test-reg-var-def-with-read-of-same-register/13") - 4274 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %eax" "F - test-reg-var-def-with-read-of-same-register/14") - 4275 (check-next-stream-line-equal _test-output-stream " }" "F - test-reg-var-def-with-read-of-same-register/15") - 4276 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-reg-var-def-with-read-of-same-register/16") - 4277 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-reg-var-def-with-read-of-same-register/17") - 4278 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-reg-var-def-with-read-of-same-register/18") - 4279 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-reg-var-def-with-read-of-same-register/19") - 4280 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-reg-var-def-with-read-of-same-register/20") - 4281 # don't restore from ebp - 4282 81 0/subop/add %esp 8/imm32 - 4283 # . epilogue - 4284 5d/pop-to-ebp - 4285 c3/return - 4286 - 4287 test-convert-index-into-array: - 4288 # . prologue - 4289 55/push-ebp - 4290 89/<- %ebp 4/r32/esp - 4291 # setup - 4292 (clear-stream _test-input-stream) - 4293 (clear-stream $_test-input-buffered-file->buffer) - 4294 (clear-stream _test-output-stream) - 4295 (clear-stream $_test-output-buffered-file->buffer) - 4296 # - 4297 (write _test-input-stream "fn foo {\n") - 4298 (write _test-input-stream " var arr/eax: (addr array int) <- copy 0\n") - 4299 (write _test-input-stream " var idx/ecx: int <- copy 3\n") - 4300 (write _test-input-stream " var x/eax: (addr int) <- index arr, idx\n") - 4301 (write _test-input-stream "}\n") - 4302 # convert - 4303 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) - 4304 (flush _test-output-buffered-file) - 4305 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 4311 # check output - 4312 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-index-into-array/0") - 4313 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-index-into-array/1") - 4314 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-index-into-array/2") - 4315 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-index-into-array/3") - 4316 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-index-into-array/4") - 4317 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-index-into-array/5") - 4318 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %eax" "F - test-convert-index-into-array/6") - 4319 (check-next-stream-line-equal _test-output-stream " b8/copy-to-eax 0/imm32" "F - test-convert-index-into-array/7") - 4320 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %ecx" "F - test-convert-index-into-array/8") - 4321 (check-next-stream-line-equal _test-output-stream " b9/copy-to-ecx 3/imm32" "F - test-convert-index-into-array/9") - 4322 (check-next-stream-line-equal _test-output-stream " 8d/copy-address *(eax + ecx<<0x00000002 + 4) 0x00000000/r32" "F - test-convert-index-into-array/10") - 4323 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %ecx" "F - test-convert-index-into-array/11") - 4324 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %eax" "F - test-convert-index-into-array/12") - 4325 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-index-into-array/13") - 4326 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-index-into-array/14") - 4327 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-index-into-array/15") - 4328 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-index-into-array/16") - 4329 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-index-into-array/17") - 4330 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-index-into-array/18") - 4331 # . epilogue - 4332 89/<- %esp 5/r32/ebp - 4333 5d/pop-to-ebp - 4334 c3/return - 4335 - 4336 test-convert-index-into-array-of-bytes: - 4337 # . prologue - 4338 55/push-ebp - 4339 89/<- %ebp 4/r32/esp - 4340 # setup - 4341 (clear-stream _test-input-stream) - 4342 (clear-stream $_test-input-buffered-file->buffer) - 4343 (clear-stream _test-output-stream) - 4344 (clear-stream $_test-output-buffered-file->buffer) - 4345 # - 4346 (write _test-input-stream "fn foo {\n") - 4347 (write _test-input-stream " var arr/eax: (addr array byte) <- copy 0\n") - 4348 (write _test-input-stream " var idx/ecx: int <- copy 3\n") - 4349 (write _test-input-stream " var x/eax: (addr byte) <- index arr, idx\n") - 4350 (write _test-input-stream "}\n") - 4351 # convert - 4352 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) - 4353 (flush _test-output-buffered-file) - 4354 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 4360 # check output - 4361 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-index-into-array-of-bytes/0") - 4362 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-index-into-array-of-bytes/1") - 4363 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-index-into-array-of-bytes/2") - 4364 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-index-into-array-of-bytes/3") - 4365 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-index-into-array-of-bytes/4") - 4366 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-index-into-array-of-bytes/5") - 4367 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %eax" "F - test-convert-index-into-array-of-bytes/6") - 4368 (check-next-stream-line-equal _test-output-stream " b8/copy-to-eax 0/imm32" "F - test-convert-index-into-array-of-bytes/7") - 4369 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %ecx" "F - test-convert-index-into-array-of-bytes/8") - 4370 (check-next-stream-line-equal _test-output-stream " b9/copy-to-ecx 3/imm32" "F - test-convert-index-into-array-of-bytes/9") - 4371 (check-next-stream-line-equal _test-output-stream " 8d/copy-address *(eax + ecx<<0x00000000 + 4) 0x00000000/r32" "F - test-convert-index-into-array-of-bytes/11") - 4372 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %ecx" "F - test-convert-index-into-array-of-bytes/13") - 4373 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %eax" "F - test-convert-index-into-array-of-bytes/14") - 4374 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-index-into-array-of-bytes/15") - 4375 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-index-into-array-of-bytes/16") - 4376 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-index-into-array-of-bytes/17") - 4377 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-index-into-array-of-bytes/18") - 4378 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-index-into-array-of-bytes/19") - 4379 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-index-into-array-of-bytes/20") - 4380 # . epilogue - 4381 89/<- %esp 5/r32/ebp - 4382 5d/pop-to-ebp - 4383 c3/return - 4384 - 4385 test-convert-index-into-array-with-literal: - 4386 # . prologue - 4387 55/push-ebp - 4388 89/<- %ebp 4/r32/esp - 4389 # setup - 4390 (clear-stream _test-input-stream) - 4391 (clear-stream $_test-input-buffered-file->buffer) - 4392 (clear-stream _test-output-stream) - 4393 (clear-stream $_test-output-buffered-file->buffer) - 4394 # - 4395 (write _test-input-stream "fn foo {\n") - 4396 (write _test-input-stream " var arr/eax: (addr array int) <- copy 0\n") - 4397 (write _test-input-stream " var x/eax: (addr int) <- index arr, 2\n") - 4398 (write _test-input-stream "}\n") - 4399 # convert - 4400 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) - 4401 (flush _test-output-buffered-file) - 4402 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 4408 # check output - 4409 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-index-into-array-with-literal/0") - 4410 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-index-into-array-with-literal/1") - 4411 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-index-into-array-with-literal/2") - 4412 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-index-into-array-with-literal/3") - 4413 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-index-into-array-with-literal/4") - 4414 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-index-into-array-with-literal/5") - 4415 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %eax" "F - test-convert-index-into-array-with-literal/6") - 4416 (check-next-stream-line-equal _test-output-stream " b8/copy-to-eax 0/imm32" "F - test-convert-index-into-array-with-literal/7") - 4417 # 2 * 4 bytes/elem + 4 bytes for size = offset 12 - 4418 (check-next-stream-line-equal _test-output-stream " 8d/copy-address *(eax + 0x0000000c) 0x00000000/r32" "F - test-convert-index-into-array-with-literal/8") - 4419 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %eax" "F - test-convert-index-into-array-with-literal/9") - 4420 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-index-into-array-with-literal/10") - 4421 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-index-into-array-with-literal/11") - 4422 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-index-into-array-with-literal/12") - 4423 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-index-into-array-with-literal/13") - 4424 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-index-into-array-with-literal/14") - 4425 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-index-into-array-with-literal/15") - 4426 # . epilogue - 4427 89/<- %esp 5/r32/ebp - 4428 5d/pop-to-ebp - 4429 c3/return - 4430 - 4431 test-convert-index-into-array-of-bytes-with-literal: - 4432 # . prologue - 4433 55/push-ebp - 4434 89/<- %ebp 4/r32/esp - 4435 # setup - 4436 (clear-stream _test-input-stream) - 4437 (clear-stream $_test-input-buffered-file->buffer) - 4438 (clear-stream _test-output-stream) - 4439 (clear-stream $_test-output-buffered-file->buffer) - 4440 # - 4441 (write _test-input-stream "fn foo {\n") - 4442 (write _test-input-stream " var arr/eax: (addr array byte) <- copy 0\n") - 4443 (write _test-input-stream " var x/eax: (addr byte) <- index arr, 2\n") - 4444 (write _test-input-stream "}\n") - 4445 # convert - 4446 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) - 4447 (flush _test-output-buffered-file) - 4448 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 4454 # check output - 4455 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-index-into-array-of-bytes-with-literal/0") - 4456 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-index-into-array-of-bytes-with-literal/1") - 4457 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-index-into-array-of-bytes-with-literal/2") - 4458 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-index-into-array-of-bytes-with-literal/3") - 4459 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-index-into-array-of-bytes-with-literal/4") - 4460 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-index-into-array-of-bytes-with-literal/5") - 4461 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %eax" "F - test-convert-index-into-array-of-bytes-with-literal/6") - 4462 (check-next-stream-line-equal _test-output-stream " b8/copy-to-eax 0/imm32" "F - test-convert-index-into-array-of-bytes-with-literal/7") - 4463 # 2 * 1 byte/elem + 4 bytes for size = offset 6 - 4464 (check-next-stream-line-equal _test-output-stream " 8d/copy-address *(eax + 0x00000006) 0x00000000/r32" "F - test-convert-index-into-array-of-bytes-with-literal/8") - 4465 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %eax" "F - test-convert-index-into-array-of-bytes-with-literal/9") - 4466 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-index-into-array-of-bytes-with-literal/10") - 4467 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-index-into-array-of-bytes-with-literal/11") - 4468 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-index-into-array-of-bytes-with-literal/12") - 4469 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-index-into-array-of-bytes-with-literal/13") - 4470 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-index-into-array-of-bytes-with-literal/14") - 4471 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-index-into-array-of-bytes-with-literal/15") - 4472 # . epilogue - 4473 89/<- %esp 5/r32/ebp - 4474 5d/pop-to-ebp - 4475 c3/return - 4476 - 4477 test-convert-index-into-array-on-stack: - 4478 # . prologue - 4479 55/push-ebp - 4480 89/<- %ebp 4/r32/esp - 4481 # setup - 4482 (clear-stream _test-input-stream) - 4483 (clear-stream $_test-input-buffered-file->buffer) - 4484 (clear-stream _test-output-stream) - 4485 (clear-stream $_test-output-buffered-file->buffer) - 4486 # - 4487 (write _test-input-stream "fn foo {\n") - 4488 (write _test-input-stream " var arr: (array int 3)\n") - 4489 (write _test-input-stream " var idx/eax: int <- copy 2\n") - 4490 (write _test-input-stream " var x/eax: (addr int) <- index arr, idx\n") - 4491 (write _test-input-stream "}\n") - 4492 # convert - 4493 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) - 4494 (flush _test-output-buffered-file) - 4495 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 4501 # check output - 4502 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-index-into-array-on-stack/0") - 4503 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-index-into-array-on-stack/1") - 4504 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-index-into-array-on-stack/2") - 4505 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-index-into-array-on-stack/3") - 4506 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-index-into-array-on-stack/4") - 4507 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-index-into-array-on-stack/5") - 4508 # var arr - 4509 (check-next-stream-line-equal _test-output-stream " (push-n-zero-bytes 0x0000000c)" "F - test-convert-index-into-array-on-stack/6") - 4510 (check-next-stream-line-equal _test-output-stream " 68/push 0x0000000c/imm32" "F - test-convert-index-into-array-on-stack/7") - 4511 # var idx - 4512 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %eax" "F - test-convert-index-into-array-on-stack/8") - 4513 (check-next-stream-line-equal _test-output-stream " b8/copy-to-eax 2/imm32" "F - test-convert-index-into-array-on-stack/9") - 4514 # var x is at (ebp-0x10) + idx<<2 + 4 = ebp + idx<<2 - 0xc - 4515 (check-next-stream-line-equal _test-output-stream " 8d/copy-address *(ebp + eax<<0x00000002 + 0xfffffff4) 0x00000000/r32" "F - test-convert-index-into-array-on-stack/10") - 4516 # reclaim idx - 4517 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %eax" "F - test-convert-index-into-array-on-stack/11") - 4518 # reclaim arr - 4519 (check-next-stream-line-equal _test-output-stream " 81 0/subop/add %esp 0x00000010/imm32" "F - test-convert-index-into-array-on-stack/12") - 4520 # - 4521 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-index-into-array-on-stack/13") - 4522 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-index-into-array-on-stack/14") - 4523 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-index-into-array-on-stack/15") - 4524 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-index-into-array-on-stack/16") - 4525 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-index-into-array-on-stack/17") - 4526 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-index-into-array-on-stack/18") - 4527 # . epilogue - 4528 89/<- %esp 5/r32/ebp - 4529 5d/pop-to-ebp - 4530 c3/return - 4531 - 4532 test-convert-index-into-array-on-stack-with-literal: - 4533 # . prologue - 4534 55/push-ebp - 4535 89/<- %ebp 4/r32/esp - 4536 # setup - 4537 (clear-stream _test-input-stream) - 4538 (clear-stream $_test-input-buffered-file->buffer) - 4539 (clear-stream _test-output-stream) - 4540 (clear-stream $_test-output-buffered-file->buffer) - 4541 # - 4542 (write _test-input-stream "fn foo {\n") - 4543 (write _test-input-stream " var arr: (array int 3)\n") - 4544 (write _test-input-stream " var x/eax: (addr int) <- index arr, 2\n") - 4545 (write _test-input-stream "}\n") - 4546 # convert - 4547 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) - 4548 (flush _test-output-buffered-file) - 4549 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 4555 # check output - 4556 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-index-into-array-on-stack-with-literal/0") - 4557 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-index-into-array-on-stack-with-literal/1") - 4558 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-index-into-array-on-stack-with-literal/2") - 4559 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-index-into-array-on-stack-with-literal/3") - 4560 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-index-into-array-on-stack-with-literal/4") - 4561 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-index-into-array-on-stack-with-literal/5") - 4562 # var arr - 4563 (check-next-stream-line-equal _test-output-stream " (push-n-zero-bytes 0x0000000c)" "F - test-convert-index-into-array-on-stack-with-literal/6") - 4564 (check-next-stream-line-equal _test-output-stream " 68/push 0x0000000c/imm32" "F - test-convert-index-into-array-on-stack-with-literal/7") - 4565 # var x - 4566 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %eax" "F - test-convert-index-into-array-on-stack-with-literal/8") - 4567 # x is at (ebp-0x10) + 4 + 2*4 = ebp-4 - 4568 (check-next-stream-line-equal _test-output-stream " 8d/copy-address *(ebp + 0xfffffffc) 0x00000000/r32" "F - test-convert-index-into-array-on-stack-with-literal/9") - 4569 # reclaim x - 4570 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %eax" "F - test-convert-index-into-array-on-stack-with-literal/10") - 4571 # reclaim arr - 4572 (check-next-stream-line-equal _test-output-stream " 81 0/subop/add %esp 0x00000010/imm32" "F - test-convert-index-into-array-on-stack-with-literal/11") - 4573 # - 4574 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-index-into-array-on-stack-with-literal/12") - 4575 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-index-into-array-on-stack-with-literal/13") - 4576 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-index-into-array-on-stack-with-literal/14") - 4577 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-index-into-array-on-stack-with-literal/15") - 4578 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-index-into-array-on-stack-with-literal/16") - 4579 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-index-into-array-on-stack-with-literal/17") - 4580 # . epilogue - 4581 89/<- %esp 5/r32/ebp - 4582 5d/pop-to-ebp - 4583 c3/return - 4584 - 4585 test-convert-index-into-array-of-bytes-on-stack-with-literal: - 4586 # . prologue - 4587 55/push-ebp - 4588 89/<- %ebp 4/r32/esp - 4589 # setup - 4590 (clear-stream _test-input-stream) - 4591 (clear-stream $_test-input-buffered-file->buffer) - 4592 (clear-stream _test-output-stream) - 4593 (clear-stream $_test-output-buffered-file->buffer) - 4594 # - 4595 (write _test-input-stream "fn foo {\n") - 4596 (write _test-input-stream " var arr: (array byte 3)\n") - 4597 (write _test-input-stream " var x/eax: (addr byte) <- index arr, 2\n") - 4598 (write _test-input-stream "}\n") - 4599 # convert - 4600 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) - 4601 (flush _test-output-buffered-file) - 4602 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 4608 # check output - 4609 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-index-into-array-of-bytes-on-stack-with-literal/0") - 4610 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-index-into-array-of-bytes-on-stack-with-literal/1") - 4611 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-index-into-array-of-bytes-on-stack-with-literal/2") - 4612 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-index-into-array-of-bytes-on-stack-with-literal/3") - 4613 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-index-into-array-of-bytes-on-stack-with-literal/4") - 4614 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-index-into-array-of-bytes-on-stack-with-literal/5") - 4615 # var arr - 4616 (check-next-stream-line-equal _test-output-stream " (push-n-zero-bytes 0x00000003)" "F - test-convert-index-into-array-of-bytes-on-stack-with-literal/6") - 4617 (check-next-stream-line-equal _test-output-stream " 68/push 0x00000003/imm32" "F - test-convert-index-into-array-of-bytes-on-stack-with-literal/7") - 4618 # var x - 4619 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %eax" "F - test-convert-index-into-array-of-bytes-on-stack-with-literal/8") - 4620 # x is at (ebp-7) + 4 + 2 = ebp-1 - 4621 (check-next-stream-line-equal _test-output-stream " 8d/copy-address *(ebp + 0xffffffff) 0x00000000/r32" "F - test-convert-index-into-array-of-bytes-on-stack-with-literal/9") - 4622 # reclaim x - 4623 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %eax" "F - test-convert-index-into-array-of-bytes-on-stack-with-literal/10") - 4624 # reclaim arr - 4625 (check-next-stream-line-equal _test-output-stream " 81 0/subop/add %esp 0x00000007/imm32" "F - test-convert-index-into-array-of-bytes-on-stack-with-literal/11") - 4626 # - 4627 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-index-into-array-of-bytes-on-stack-with-literal/12") - 4628 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-index-into-array-of-bytes-on-stack-with-literal/13") - 4629 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-index-into-array-of-bytes-on-stack-with-literal/14") - 4630 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-index-into-array-of-bytes-on-stack-with-literal/15") - 4631 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-index-into-array-of-bytes-on-stack-with-literal/16") - 4632 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-index-into-array-of-bytes-on-stack-with-literal/17") - 4633 # . epilogue - 4634 89/<- %esp 5/r32/ebp - 4635 5d/pop-to-ebp - 4636 c3/return - 4637 - 4638 test-convert-index-into-array-using-offset: - 4639 # . prologue - 4640 55/push-ebp - 4641 89/<- %ebp 4/r32/esp - 4642 # setup - 4643 (clear-stream _test-input-stream) - 4644 (clear-stream $_test-input-buffered-file->buffer) - 4645 (clear-stream _test-output-stream) - 4646 (clear-stream $_test-output-buffered-file->buffer) - 4647 # - 4648 (write _test-input-stream "fn foo {\n") - 4649 (write _test-input-stream " var arr/eax: (addr array int) <- copy 0\n") - 4650 (write _test-input-stream " var idx/ecx: int <- copy 3\n") - 4651 (write _test-input-stream " var off/ecx: (offset int) <- compute-offset arr, idx\n") - 4652 (write _test-input-stream " var x/eax: (addr int) <- index arr, off\n") - 4653 (write _test-input-stream "}\n") - 4654 # convert - 4655 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) - 4656 (flush _test-output-buffered-file) - 4657 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 4663 # check output - 4664 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-index-into-array-using-offset/0") - 4665 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-index-into-array-using-offset/1") - 4666 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-index-into-array-using-offset/2") - 4667 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-index-into-array-using-offset/3") - 4668 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-index-into-array-using-offset/4") - 4669 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-index-into-array-using-offset/5") - 4670 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %eax" "F - test-convert-index-into-array-using-offset/6") - 4671 (check-next-stream-line-equal _test-output-stream " b8/copy-to-eax 0/imm32" "F - test-convert-index-into-array-using-offset/7") - 4672 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %ecx" "F - test-convert-index-into-array-using-offset/8") - 4673 (check-next-stream-line-equal _test-output-stream " b9/copy-to-ecx 3/imm32" "F - test-convert-index-into-array-using-offset/9") - 4674 (check-next-stream-line-equal _test-output-stream " 69/multiply %ecx 0x00000004/imm32 0x00000001/r32" "F - test-convert-index-into-array-using-offset/10") - 4675 (check-next-stream-line-equal _test-output-stream " 8d/copy-address *(eax + ecx + 4) 0x00000000/r32" "F - test-convert-index-into-array-using-offset/11") - 4676 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %ecx" "F - test-convert-index-into-array-using-offset/12") - 4677 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %eax" "F - test-convert-index-into-array-using-offset/13") - 4678 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-index-into-array-using-offset/14") - 4679 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-index-into-array-using-offset/15") - 4680 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-index-into-array-using-offset/16") - 4681 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-index-into-array-using-offset/17") - 4682 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-index-into-array-using-offset/18") - 4683 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-index-into-array-using-offset/19") - 4684 # . epilogue - 4685 89/<- %esp 5/r32/ebp - 4686 5d/pop-to-ebp - 4687 c3/return - 4688 - 4689 test-convert-index-into-array-of-bytes-using-offset: - 4690 # . prologue - 4691 55/push-ebp - 4692 89/<- %ebp 4/r32/esp - 4693 # setup - 4694 (clear-stream _test-input-stream) - 4695 (clear-stream $_test-input-buffered-file->buffer) - 4696 (clear-stream _test-output-stream) - 4697 (clear-stream $_test-output-buffered-file->buffer) - 4698 # - 4699 (write _test-input-stream "fn foo {\n") - 4700 (write _test-input-stream " var arr/eax: (addr array byte) <- copy 0\n") - 4701 (write _test-input-stream " var idx/ecx: int <- copy 3\n") - 4702 (write _test-input-stream " var off/ecx: (offset byte) <- compute-offset arr, idx\n") - 4703 (write _test-input-stream " var x/eax: (addr byte) <- index arr, off\n") - 4704 (write _test-input-stream "}\n") - 4705 # convert - 4706 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) - 4707 (flush _test-output-buffered-file) - 4708 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 4714 # check output - 4715 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-index-into-array-of-bytes-using-offset/0") - 4716 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-index-into-array-of-bytes-using-offset/1") - 4717 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-index-into-array-of-bytes-using-offset/2") - 4718 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-index-into-array-of-bytes-using-offset/3") - 4719 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-index-into-array-of-bytes-using-offset/4") - 4720 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-index-into-array-of-bytes-using-offset/5") - 4721 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %eax" "F - test-convert-index-into-array-of-bytes-using-offset/6") - 4722 (check-next-stream-line-equal _test-output-stream " b8/copy-to-eax 0/imm32" "F - test-convert-index-into-array-of-bytes-using-offset/7") - 4723 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %ecx" "F - test-convert-index-into-array-of-bytes-using-offset/8") - 4724 (check-next-stream-line-equal _test-output-stream " b9/copy-to-ecx 3/imm32" "F - test-convert-index-into-array-of-bytes-using-offset/9") - 4725 (check-next-stream-line-equal _test-output-stream " 69/multiply %ecx 0x00000001/imm32 0x00000001/r32" "F - test-convert-index-into-array-of-bytes-using-offset/10") - 4726 (check-next-stream-line-equal _test-output-stream " 8d/copy-address *(eax + ecx + 4) 0x00000000/r32" "F - test-convert-index-into-array-of-bytes-using-offset/11") - 4727 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %ecx" "F - test-convert-index-into-array-of-bytes-using-offset/12") - 4728 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %eax" "F - test-convert-index-into-array-of-bytes-using-offset/13") - 4729 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-index-into-array-of-bytes-using-offset/14") - 4730 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-index-into-array-of-bytes-using-offset/15") - 4731 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-index-into-array-of-bytes-using-offset/16") - 4732 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-index-into-array-of-bytes-using-offset/17") - 4733 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-index-into-array-of-bytes-using-offset/18") - 4734 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-index-into-array-of-bytes-using-offset/19") - 4735 # . epilogue - 4736 89/<- %esp 5/r32/ebp - 4737 5d/pop-to-ebp - 4738 c3/return - 4739 - 4740 test-convert-index-into-array-using-offset-on-stack: - 4741 # . prologue - 4742 55/push-ebp - 4743 89/<- %ebp 4/r32/esp - 4744 # setup - 4745 (clear-stream _test-input-stream) - 4746 (clear-stream $_test-input-buffered-file->buffer) - 4747 (clear-stream _test-output-stream) - 4748 (clear-stream $_test-output-buffered-file->buffer) - 4749 # - 4750 (write _test-input-stream "fn foo {\n") - 4751 (write _test-input-stream " var arr/eax: (addr array int) <- copy 0\n") - 4752 (write _test-input-stream " var idx: int\n") - 4753 (write _test-input-stream " var off/ecx: (offset int) <- compute-offset arr, idx\n") - 4754 (write _test-input-stream " var x/eax: (addr int) <- index arr, off\n") - 4755 (write _test-input-stream "}\n") - 4756 # convert - 4757 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) - 4758 (flush _test-output-buffered-file) - 4759 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 4765 # check output - 4766 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-index-into-array-using-offset-on-stack/0") - 4767 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-index-into-array-using-offset-on-stack/1") - 4768 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-index-into-array-using-offset-on-stack/2") - 4769 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-index-into-array-using-offset-on-stack/3") - 4770 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-index-into-array-using-offset-on-stack/4") - 4771 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-index-into-array-using-offset-on-stack/5") - 4772 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %eax" "F - test-convert-index-into-array-using-offset-on-stack/6") - 4773 (check-next-stream-line-equal _test-output-stream " b8/copy-to-eax 0/imm32" "F - test-convert-index-into-array-using-offset-on-stack/7") - 4774 (check-next-stream-line-equal _test-output-stream " 68/push 0/imm32" "F - test-convert-index-into-array-using-offset-on-stack/8") - 4775 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %ecx" "F - test-convert-index-into-array-using-offset-on-stack/9") - 4776 (check-next-stream-line-equal _test-output-stream " 69/multiply *(ebp+0xfffffff8) 0x00000004/imm32 0x00000001/r32" "F - test-convert-index-into-array-using-offset-on-stack/10") - 4777 (check-next-stream-line-equal _test-output-stream " 8d/copy-address *(eax + ecx + 4) 0x00000000/r32" "F - test-convert-index-into-array-using-offset-on-stack/11") - 4778 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %ecx" "F - test-convert-index-into-array-using-offset-on-stack/12") - 4779 (check-next-stream-line-equal _test-output-stream " 81 0/subop/add %esp 0x00000004/imm32" "F - test-convert-index-into-array-using-offset-on-stack/13") - 4780 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %eax" "F - test-convert-index-into-array-using-offset-on-stack/14") - 4781 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-index-into-array-using-offset-on-stack/15") - 4782 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-index-into-array-using-offset-on-stack/16") - 4783 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-index-into-array-using-offset-on-stack/17") - 4784 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-index-into-array-using-offset-on-stack/18") - 4785 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-index-into-array-using-offset-on-stack/19") - 4786 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-index-into-array-using-offset-on-stack/20") - 4787 # . epilogue - 4788 89/<- %esp 5/r32/ebp - 4789 5d/pop-to-ebp - 4790 c3/return - 4791 - 4792 test-convert-index-into-array-of-bytes-using-offset-on-stack: - 4793 # . prologue - 4794 55/push-ebp - 4795 89/<- %ebp 4/r32/esp - 4796 # setup - 4797 (clear-stream _test-input-stream) - 4798 (clear-stream $_test-input-buffered-file->buffer) - 4799 (clear-stream _test-output-stream) - 4800 (clear-stream $_test-output-buffered-file->buffer) - 4801 # - 4802 (write _test-input-stream "fn foo {\n") - 4803 (write _test-input-stream " var arr/eax: (addr array byte) <- copy 0\n") - 4804 (write _test-input-stream " var idx: int\n") - 4805 (write _test-input-stream " var off/ecx: (offset byte) <- compute-offset arr, idx\n") - 4806 (write _test-input-stream " var x/eax: (addr byte) <- index arr, off\n") - 4807 (write _test-input-stream "}\n") - 4808 # convert - 4809 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) - 4810 (flush _test-output-buffered-file) - 4811 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 4817 # check output - 4818 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-index-into-array-of-bytes-using-offset-on-stack/0") - 4819 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-index-into-array-of-bytes-using-offset-on-stack/1") - 4820 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-index-into-array-of-bytes-using-offset-on-stack/2") - 4821 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-index-into-array-of-bytes-using-offset-on-stack/3") - 4822 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-index-into-array-of-bytes-using-offset-on-stack/4") - 4823 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-index-into-array-of-bytes-using-offset-on-stack/5") - 4824 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %eax" "F - test-convert-index-into-array-of-bytes-using-offset-on-stack/6") - 4825 (check-next-stream-line-equal _test-output-stream " b8/copy-to-eax 0/imm32" "F - test-convert-index-into-array-of-bytes-using-offset-on-stack/7") - 4826 (check-next-stream-line-equal _test-output-stream " 68/push 0/imm32" "F - test-convert-index-into-array-of-bytes-using-offset-on-stack/8") - 4827 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %ecx" "F - test-convert-index-into-array-of-bytes-using-offset-on-stack/9") - 4828 (check-next-stream-line-equal _test-output-stream " 69/multiply *(ebp+0xfffffff8) 0x00000001/imm32 0x00000001/r32" "F - test-convert-index-into-array-of-bytes-using-offset-on-stack/10") - 4829 (check-next-stream-line-equal _test-output-stream " 8d/copy-address *(eax + ecx + 4) 0x00000000/r32" "F - test-convert-index-into-array-of-bytes-using-offset-on-stack/11") - 4830 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %ecx" "F - test-convert-index-into-array-of-bytes-using-offset-on-stack/12") - 4831 (check-next-stream-line-equal _test-output-stream " 81 0/subop/add %esp 0x00000004/imm32" "F - test-convert-index-into-array-of-bytes-using-offset-on-stack/13") - 4832 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %eax" "F - test-convert-index-into-array-of-bytes-using-offset-on-stack/14") - 4833 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-index-into-array-of-bytes-using-offset-on-stack/15") - 4834 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-index-into-array-of-bytes-using-offset-on-stack/16") - 4835 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-index-into-array-of-bytes-using-offset-on-stack/17") - 4836 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-index-into-array-of-bytes-using-offset-on-stack/18") - 4837 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-index-into-array-of-bytes-using-offset-on-stack/19") - 4838 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-index-into-array-of-bytes-using-offset-on-stack/20") - 4839 # . epilogue - 4840 89/<- %esp 5/r32/ebp - 4841 5d/pop-to-ebp - 4842 c3/return - 4843 - 4844 test-convert-function-and-type-definition: - 4845 # . prologue - 4846 55/push-ebp - 4847 89/<- %ebp 4/r32/esp - 4848 # setup - 4849 (clear-stream _test-input-stream) - 4850 (clear-stream $_test-input-buffered-file->buffer) - 4851 (clear-stream _test-output-stream) - 4852 (clear-stream $_test-output-buffered-file->buffer) - 4853 # - 4854 (write _test-input-stream "fn foo a: (addr t) {\n") - 4855 (write _test-input-stream " var _a/eax: (addr t) <- copy a\n") - 4856 (write _test-input-stream " var b/ecx: (addr int) <- get _a, x\n") - 4857 (write _test-input-stream " var c/ecx: (addr int) <- get _a, y\n") - 4858 (write _test-input-stream "}\n") - 4859 (write _test-input-stream "type t {\n") - 4860 (write _test-input-stream " x: int\n") - 4861 (write _test-input-stream " y: int\n") - 4862 (write _test-input-stream "}\n") - 4863 # convert - 4864 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) - 4865 (flush _test-output-buffered-file) - 4866 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 4872 # check output - 4873 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-function-and-type-definition/0") - 4874 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-function-and-type-definition/1") - 4875 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-function-and-type-definition/2") - 4876 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-function-and-type-definition/3") - 4877 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-and-type-definition/4") - 4878 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-function-and-type-definition/5") - 4879 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %eax" "F - test-convert-function-and-type-definition/6") - 4880 (check-next-stream-line-equal _test-output-stream " 8b/-> *(ebp+0x00000008) 0x00000000/r32" "F - test-convert-function-and-type-definition/7") - 4881 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %ecx" "F - test-convert-function-and-type-definition/8") - 4882 (check-next-stream-line-equal _test-output-stream " 8d/copy-address *(eax + 0x00000000) 0x00000001/r32" "F - test-convert-function-and-type-definition/9") - 4883 (check-next-stream-line-equal _test-output-stream " 8d/copy-address *(eax + 0x00000004) 0x00000001/r32" "F - test-convert-function-and-type-definition/11") - 4884 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %ecx" "F - test-convert-function-and-type-definition/13") - 4885 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %eax" "F - test-convert-function-and-type-definition/14") - 4886 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-and-type-definition/15") - 4887 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-function-and-type-definition/16") - 4888 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-function-and-type-definition/17") - 4889 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-function-and-type-definition/18") - 4890 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-function-and-type-definition/19") - 4891 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-function-and-type-definition/20") - 4892 # . epilogue - 4893 89/<- %esp 5/r32/ebp - 4894 5d/pop-to-ebp - 4895 c3/return - 4896 - 4897 test-type-definition-with-array: - 4898 # . prologue - 4899 55/push-ebp - 4900 89/<- %ebp 4/r32/esp - 4901 # setup - 4902 (clear-stream _test-input-stream) - 4903 (clear-stream $_test-input-buffered-file->buffer) - 4904 (clear-stream _test-output-stream) - 4905 (clear-stream $_test-output-buffered-file->buffer) - 4906 (clear-stream _test-error-stream) - 4907 (clear-stream $_test-error-buffered-file->buffer) - 4908 # var ed/edx: exit-descriptor = tailor-exit-descriptor(16) - 4909 68/push 0/imm32 - 4910 68/push 0/imm32 - 4911 89/<- %edx 4/r32/esp - 4912 (tailor-exit-descriptor %edx 0x10) - 4913 # - 4914 (write _test-input-stream "type t {\n") - 4915 (write _test-input-stream " a: (array int 3)\n") - 4916 (write _test-input-stream "}\n") - 4917 # convert - 4918 (convert-mu _test-input-buffered-file _test-output-buffered-file _test-error-buffered-file %edx) - 4919 # registers except esp clobbered at this point - 4920 # restore ed - 4921 89/<- %edx 4/r32/esp - 4922 (flush _test-output-buffered-file) - 4923 (flush _test-error-buffered-file) - 4924 +-- 6 lines: #? # dump _test-error-stream --------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 4930 # check output - 4931 (check-stream-equal _test-output-stream "" "F - test-type-definition-with-array: output should be empty") - 4932 (check-next-stream-line-equal _test-error-stream "type t: invalid type 'array'" "F - test-type-definition-with-array: error message") - 4933 # check that stop(1) was called - 4934 (check-ints-equal *(edx+4) 2 "F - test-type-definition-with-array: exit status") - 4935 # don't restore from ebp - 4936 81 0/subop/add %esp 8/imm32 - 4937 # . epilogue - 4938 5d/pop-to-ebp - 4939 c3/return - 4940 - 4941 test-type-definition-with-addr: - 4942 # . prologue - 4943 55/push-ebp - 4944 89/<- %ebp 4/r32/esp - 4945 # setup - 4946 (clear-stream _test-input-stream) - 4947 (clear-stream $_test-input-buffered-file->buffer) - 4948 (clear-stream _test-output-stream) - 4949 (clear-stream $_test-output-buffered-file->buffer) - 4950 (clear-stream _test-error-stream) - 4951 (clear-stream $_test-error-buffered-file->buffer) - 4952 # var ed/edx: exit-descriptor = tailor-exit-descriptor(16) - 4953 68/push 0/imm32 - 4954 68/push 0/imm32 - 4955 89/<- %edx 4/r32/esp - 4956 (tailor-exit-descriptor %edx 0x10) - 4957 # - 4958 (write _test-input-stream "type t {\n") - 4959 (write _test-input-stream " a: (addr int)\n") - 4960 (write _test-input-stream "}\n") - 4961 # convert - 4962 (convert-mu _test-input-buffered-file _test-output-buffered-file _test-error-buffered-file %edx) - 4963 # registers except esp clobbered at this point - 4964 # restore ed - 4965 89/<- %edx 4/r32/esp - 4966 (flush _test-output-buffered-file) - 4967 (flush _test-error-buffered-file) - 4968 +-- 6 lines: #? # dump _test-error-stream --------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 4974 # check output - 4975 (check-stream-equal _test-output-stream "" "F - test-type-definition-with-addr: output should be empty") - 4976 (check-next-stream-line-equal _test-error-stream "type t: invalid type 'addr'" "F - test-type-definition-with-addr: error message") - 4977 # check that stop(1) was called - 4978 (check-ints-equal *(edx+4) 2 "F - test-type-definition-with-addr: exit status") - 4979 # don't restore from ebp - 4980 81 0/subop/add %esp 8/imm32 - 4981 # . epilogue - 4982 5d/pop-to-ebp - 4983 c3/return - 4984 - 4985 test-convert-function-with-local-var-with-user-defined-type: - 4986 # . prologue - 4987 55/push-ebp - 4988 89/<- %ebp 4/r32/esp - 4989 # setup - 4990 (clear-stream _test-input-stream) - 4991 (clear-stream $_test-input-buffered-file->buffer) - 4992 (clear-stream _test-output-stream) - 4993 (clear-stream $_test-output-buffered-file->buffer) - 4994 # - 4995 (write _test-input-stream "fn foo {\n") - 4996 (write _test-input-stream " var a: t\n") - 4997 (write _test-input-stream "}\n") - 4998 (write _test-input-stream "type t {\n") - 4999 (write _test-input-stream " x: int\n") - 5000 (write _test-input-stream " y: int\n") - 5001 (write _test-input-stream "}\n") - 5002 # convert - 5003 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) - 5004 (flush _test-output-buffered-file) - 5005 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 5011 # check output - 5012 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-function-with-local-var-with-user-defined-type/0") - 5013 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-function-with-local-var-with-user-defined-type/1") - 5014 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-function-with-local-var-with-user-defined-type/2") - 5015 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-function-with-local-var-with-user-defined-type/3") - 5016 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-local-var-with-user-defined-type/4") - 5017 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-function-with-local-var-with-user-defined-type/5") - 5018 (check-next-stream-line-equal _test-output-stream " 68/push 0/imm32" "F - test-convert-function-with-local-var-with-user-defined-type/6") - 5019 (check-next-stream-line-equal _test-output-stream " 68/push 0/imm32" "F - test-convert-function-with-local-var-with-user-defined-type/7") - 5020 (check-next-stream-line-equal _test-output-stream " 81 0/subop/add %esp 0x00000008/imm32" "F - test-convert-function-with-local-var-with-user-defined-type/8") - 5021 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-local-var-with-user-defined-type/9") - 5022 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-function-with-local-var-with-user-defined-type/10") - 5023 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-function-with-local-var-with-user-defined-type/11") - 5024 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-function-with-local-var-with-user-defined-type/12") - 5025 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-function-with-local-var-with-user-defined-type/13") - 5026 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-function-with-local-var-with-user-defined-type/14") - 5027 # . epilogue - 5028 89/<- %esp 5/r32/ebp - 5029 5d/pop-to-ebp - 5030 c3/return - 5031 - 5032 test-convert-function-call-with-arg-of-user-defined-type: - 5033 # . prologue - 5034 55/push-ebp - 5035 89/<- %ebp 4/r32/esp - 5036 # setup - 5037 (clear-stream _test-input-stream) - 5038 (clear-stream $_test-input-buffered-file->buffer) - 5039 (clear-stream _test-output-stream) - 5040 (clear-stream $_test-output-buffered-file->buffer) - 5041 # - 5042 (write _test-input-stream "fn f {\n") - 5043 (write _test-input-stream " var a: t\n") - 5044 (write _test-input-stream " foo a\n") - 5045 (write _test-input-stream "}\n") - 5046 (write _test-input-stream "fn foo x: t {\n") - 5047 (write _test-input-stream "}\n") - 5048 (write _test-input-stream "type t {\n") - 5049 (write _test-input-stream " x: int\n") - 5050 (write _test-input-stream " y: int\n") - 5051 (write _test-input-stream "}\n") - 5052 # convert - 5053 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) - 5054 (flush _test-output-buffered-file) - 5055 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 5061 # check output - 5062 (check-next-stream-line-equal _test-output-stream "f:" "F - test-convert-function-call-with-arg-of-user-defined-type/0") - 5063 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-function-call-with-arg-of-user-defined-type/1") - 5064 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-function-call-with-arg-of-user-defined-type/2") - 5065 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-function-call-with-arg-of-user-defined-type/3") - 5066 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-call-with-arg-of-user-defined-type/4") - 5067 (check-next-stream-line-equal _test-output-stream "$f:0x00000001:loop:" "F - test-convert-function-call-with-arg-of-user-defined-type/5") - 5068 # var a: t - 5069 (check-next-stream-line-equal _test-output-stream " 68/push 0/imm32" "F - test-convert-function-call-with-arg-of-user-defined-type/6") - 5070 (check-next-stream-line-equal _test-output-stream " 68/push 0/imm32" "F - test-convert-function-call-with-arg-of-user-defined-type/7") - 5071 # foo a - 5072 (check-next-stream-line-equal _test-output-stream " (foo *(ebp+0xfffffff8) *(ebp+0xfffffffc))" "F - test-convert-function-call-with-arg-of-user-defined-type/8") - 5073 # - 5074 (check-next-stream-line-equal _test-output-stream " 81 0/subop/add %esp 0x00000008/imm32" "F - test-convert-function-call-with-arg-of-user-defined-type/9") - 5075 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-call-with-arg-of-user-defined-type/10") - 5076 (check-next-stream-line-equal _test-output-stream "$f:0x00000001:break:" "F - test-convert-function-call-with-arg-of-user-defined-type/11") - 5077 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-function-call-with-arg-of-user-defined-type/12") - 5078 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-function-call-with-arg-of-user-defined-type/13") - 5079 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-function-call-with-arg-of-user-defined-type/14") - 5080 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-function-call-with-arg-of-user-defined-type/15") - 5081 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-function-call-with-arg-of-user-defined-type/16") - 5082 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-function-call-with-arg-of-user-defined-type/17") - 5083 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-function-call-with-arg-of-user-defined-type/18") - 5084 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-function-call-with-arg-of-user-defined-type/19") - 5085 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-function-call-with-arg-of-user-defined-type/20") - 5086 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-function-call-with-arg-of-user-defined-type/21") - 5087 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-function-call-with-arg-of-user-defined-type/22") - 5088 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-function-call-with-arg-of-user-defined-type/23") - 5089 # . epilogue - 5090 89/<- %esp 5/r32/ebp - 5091 5d/pop-to-ebp - 5092 c3/return - 5093 - 5094 test-convert-function-call-with-arg-of-user-defined-type-register-indirect: - 5095 # . prologue - 5096 55/push-ebp - 5097 89/<- %ebp 4/r32/esp - 5098 # setup - 5099 (clear-stream _test-input-stream) - 5100 (clear-stream $_test-input-buffered-file->buffer) - 5101 (clear-stream _test-output-stream) - 5102 (clear-stream $_test-output-buffered-file->buffer) - 5103 # - 5104 (write _test-input-stream "fn f {\n") - 5105 (write _test-input-stream " var a/eax: (addr t) <- copy 0\n") - 5106 (write _test-input-stream " foo *a\n") - 5107 (write _test-input-stream "}\n") - 5108 (write _test-input-stream "fn foo x: t {\n") - 5109 (write _test-input-stream "}\n") - 5110 (write _test-input-stream "type t {\n") - 5111 (write _test-input-stream " x: int\n") - 5112 (write _test-input-stream " y: int\n") - 5113 (write _test-input-stream "}\n") - 5114 # convert - 5115 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) - 5116 (flush _test-output-buffered-file) - 5117 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 5123 # check output - 5124 (check-next-stream-line-equal _test-output-stream "f:" "F - test-convert-function-call-with-arg-of-user-defined-type/0") - 5125 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-function-call-with-arg-of-user-defined-type/1") - 5126 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-function-call-with-arg-of-user-defined-type/2") - 5127 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-function-call-with-arg-of-user-defined-type/3") - 5128 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-call-with-arg-of-user-defined-type/4") - 5129 (check-next-stream-line-equal _test-output-stream "$f:0x00000001:loop:" "F - test-convert-function-call-with-arg-of-user-defined-type/5") - 5130 # var a - 5131 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %eax" "F - test-convert-function-call-with-arg-of-user-defined-type/6") - 5132 (check-next-stream-line-equal _test-output-stream " b8/copy-to-eax 0/imm32" "F - test-convert-function-call-with-arg-of-user-defined-type/7") - 5133 # foo a - 5134 (check-next-stream-line-equal _test-output-stream " (foo *(eax+0x00000000) *(eax+0x00000004))" "F - test-convert-function-call-with-arg-of-user-defined-type/8") - 5135 # - 5136 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %eax" "F - test-convert-function-call-with-arg-of-user-defined-type/9") - 5137 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-call-with-arg-of-user-defined-type/10") - 5138 (check-next-stream-line-equal _test-output-stream "$f:0x00000001:break:" "F - test-convert-function-call-with-arg-of-user-defined-type/11") - 5139 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-function-call-with-arg-of-user-defined-type/12") - 5140 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-function-call-with-arg-of-user-defined-type/13") - 5141 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-function-call-with-arg-of-user-defined-type/14") - 5142 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-function-call-with-arg-of-user-defined-type/15") - 5143 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-function-call-with-arg-of-user-defined-type/16") - 5144 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-function-call-with-arg-of-user-defined-type/17") - 5145 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-function-call-with-arg-of-user-defined-type/18") - 5146 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-function-call-with-arg-of-user-defined-type/19") - 5147 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-function-call-with-arg-of-user-defined-type/20") - 5148 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-function-call-with-arg-of-user-defined-type/21") - 5149 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-function-call-with-arg-of-user-defined-type/22") - 5150 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-function-call-with-arg-of-user-defined-type/23") - 5151 # . epilogue - 5152 89/<- %esp 5/r32/ebp - 5153 5d/pop-to-ebp - 5154 c3/return - 5155 - 5156 # we don't have special support for call-by-reference; just explicitly create - 5157 # a new variable with the address of the arg - 5158 test-convert-function-call-with-arg-of-user-defined-type-by-reference: - 5159 # . prologue - 5160 55/push-ebp - 5161 89/<- %ebp 4/r32/esp - 5162 # setup - 5163 (clear-stream _test-input-stream) - 5164 (clear-stream $_test-input-buffered-file->buffer) - 5165 (clear-stream _test-output-stream) - 5166 (clear-stream $_test-output-buffered-file->buffer) - 5167 # - 5168 (write _test-input-stream "fn f {\n") - 5169 (write _test-input-stream " var a: t\n") - 5170 (write _test-input-stream " var b/eax: (addr t) <- address a\n") - 5171 (write _test-input-stream " foo b\n") - 5172 (write _test-input-stream "}\n") - 5173 (write _test-input-stream "fn foo x: (addr t) {\n") - 5174 (write _test-input-stream " var x/ecx: (addr int) <- copy x\n") - 5175 (write _test-input-stream " increment *x\n") - 5176 (write _test-input-stream "}\n") - 5177 (write _test-input-stream "type t {\n") - 5178 (write _test-input-stream " x: int\n") - 5179 (write _test-input-stream " y: int\n") - 5180 (write _test-input-stream "}\n") - 5181 # convert - 5182 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) - 5183 (flush _test-output-buffered-file) - 5184 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 5190 # check output - 5191 (check-next-stream-line-equal _test-output-stream "f:" "F - test-convert-function-call-with-arg-of-user-defined-type-by-reference/0") - 5192 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-function-call-with-arg-of-user-defined-type-by-reference/1") - 5193 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-function-call-with-arg-of-user-defined-type-by-reference/2") - 5194 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-function-call-with-arg-of-user-defined-type-by-reference/3") - 5195 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-call-with-arg-of-user-defined-type-by-reference/4") - 5196 (check-next-stream-line-equal _test-output-stream "$f:0x00000001:loop:" "F - test-convert-function-call-with-arg-of-user-defined-type-by-reference/5") - 5197 # var a: t - 5198 (check-next-stream-line-equal _test-output-stream " 68/push 0/imm32" "F - test-convert-function-call-with-arg-of-user-defined-type-by-reference/6") - 5199 (check-next-stream-line-equal _test-output-stream " 68/push 0/imm32" "F - test-convert-function-call-with-arg-of-user-defined-type-by-reference/7") - 5200 # var b/eax: (addr t) - 5201 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %eax" "F - test-convert-function-call-with-arg-of-user-defined-type-by-reference/8") - 5202 (check-next-stream-line-equal _test-output-stream " 8d/copy-address *(ebp+0xfffffff8) 0x00000000/r32" "F - test-convert-function-call-with-arg-of-user-defined-type-by-reference/9") - 5203 # foo a - 5204 (check-next-stream-line-equal _test-output-stream " (foo %eax)" "F - test-convert-function-call-with-arg-of-user-defined-type-by-reference/10") - 5205 # - 5206 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %eax" "F - test-convert-function-call-with-arg-of-user-defined-type-by-reference/11") - 5207 (check-next-stream-line-equal _test-output-stream " 81 0/subop/add %esp 0x00000008/imm32" "F - test-convert-function-call-with-arg-of-user-defined-type-by-reference/12") - 5208 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-call-with-arg-of-user-defined-type-by-reference/13") - 5209 (check-next-stream-line-equal _test-output-stream "$f:0x00000001:break:" "F - test-convert-function-call-with-arg-of-user-defined-type-by-reference/14") - 5210 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-function-call-with-arg-of-user-defined-type-by-reference/15") - 5211 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-function-call-with-arg-of-user-defined-type-by-reference/16") - 5212 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-function-call-with-arg-of-user-defined-type-by-reference/17") - 5213 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-function-call-with-arg-of-user-defined-type-by-reference/18") - 5214 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-function-call-with-arg-of-user-defined-type-by-reference/19") - 5215 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-function-call-with-arg-of-user-defined-type-by-reference/20") - 5216 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-function-call-with-arg-of-user-defined-type-by-reference/21") - 5217 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-function-call-with-arg-of-user-defined-type-by-reference/22") - 5218 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-call-with-arg-of-user-defined-type-by-reference/23") - 5219 (check-next-stream-line-equal _test-output-stream "$foo:0x00000002:loop:" "F - test-convert-function-call-with-arg-of-user-defined-type-by-reference/24") - 5220 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %ecx" "F - test-convert-function-call-with-arg-of-user-defined-type-by-reference/25") - 5221 (check-next-stream-line-equal _test-output-stream " 8b/-> *(ebp+0x00000008) 0x00000001/r32" "F - test-convert-function-call-with-arg-of-user-defined-type-by-reference/26") - 5222 (check-next-stream-line-equal _test-output-stream " ff 0/subop/increment *ecx" "F - test-convert-function-call-with-arg-of-user-defined-type-by-reference/27") - 5223 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %ecx" "F - test-convert-function-call-with-arg-of-user-defined-type-by-reference/28") - 5224 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-call-with-arg-of-user-defined-type-by-reference/29") - 5225 (check-next-stream-line-equal _test-output-stream "$foo:0x00000002:break:" "F - test-convert-function-call-with-arg-of-user-defined-type-by-reference/30") - 5226 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-function-call-with-arg-of-user-defined-type-by-reference/31") - 5227 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-function-call-with-arg-of-user-defined-type-by-reference/32") - 5228 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-function-call-with-arg-of-user-defined-type-by-reference/33") - 5229 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-function-call-with-arg-of-user-defined-type-by-reference/34") - 5230 # . epilogue - 5231 89/<- %esp 5/r32/ebp - 5232 5d/pop-to-ebp - 5233 c3/return - 5234 - 5235 test-convert-get-on-local-variable: - 5236 # . prologue - 5237 55/push-ebp - 5238 89/<- %ebp 4/r32/esp - 5239 # setup - 5240 (clear-stream _test-input-stream) - 5241 (clear-stream $_test-input-buffered-file->buffer) - 5242 (clear-stream _test-output-stream) - 5243 (clear-stream $_test-output-buffered-file->buffer) - 5244 # - 5245 (write _test-input-stream "fn foo {\n") - 5246 (write _test-input-stream " var a: t\n") - 5247 (write _test-input-stream " var c/ecx: (addr int) <- get a, y\n") - 5248 (write _test-input-stream "}\n") - 5249 (write _test-input-stream "type t {\n") - 5250 (write _test-input-stream " x: int\n") - 5251 (write _test-input-stream " y: int\n") - 5252 (write _test-input-stream "}\n") - 5253 # convert - 5254 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) - 5255 (flush _test-output-buffered-file) - 5256 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 5262 # check output - 5263 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-get-on-local-variable/0") - 5264 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-get-on-local-variable/1") - 5265 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-get-on-local-variable/2") - 5266 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-get-on-local-variable/3") - 5267 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-get-on-local-variable/4") - 5268 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-get-on-local-variable/5") - 5269 # var a - 5270 (check-next-stream-line-equal _test-output-stream " 68/push 0/imm32" "F - test-convert-get-on-local-variable/6") - 5271 (check-next-stream-line-equal _test-output-stream " 68/push 0/imm32" "F - test-convert-get-on-local-variable/7") - 5272 # var c - 5273 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %ecx" "F - test-convert-get-on-local-variable/8") - 5274 # get - 5275 (check-next-stream-line-equal _test-output-stream " 8d/copy-address *(ebp+0xfffffffc) 0x00000001/r32" "F - test-convert-get-on-local-variable/9") - 5276 # reclaim c - 5277 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %ecx" "F - test-convert-get-on-local-variable/10") - 5278 # reclaim a - 5279 (check-next-stream-line-equal _test-output-stream " 81 0/subop/add %esp 0x00000008/imm32" "F - test-convert-get-on-local-variable/11") - 5280 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-get-on-local-variable/12") - 5281 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-get-on-local-variable/13") - 5282 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-get-on-local-variable/14") - 5283 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-get-on-local-variable/15") - 5284 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-get-on-local-variable/16") - 5285 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-get-on-local-variable/17") - 5286 # . epilogue - 5287 89/<- %esp 5/r32/ebp - 5288 5d/pop-to-ebp - 5289 c3/return - 5290 - 5291 test-convert-get-on-function-argument: - 5292 # . prologue - 5293 55/push-ebp - 5294 89/<- %ebp 4/r32/esp - 5295 # setup - 5296 (clear-stream _test-input-stream) - 5297 (clear-stream $_test-input-buffered-file->buffer) - 5298 (clear-stream _test-output-stream) - 5299 (clear-stream $_test-output-buffered-file->buffer) - 5300 # - 5301 (write _test-input-stream "fn foo a: t {\n") - 5302 (write _test-input-stream " var c/ecx: (addr int) <- get a, y\n") - 5303 (write _test-input-stream "}\n") - 5304 (write _test-input-stream "type t {\n") - 5305 (write _test-input-stream " x: int\n") - 5306 (write _test-input-stream " y: int\n") - 5307 (write _test-input-stream "}\n") - 5308 # convert - 5309 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) - 5310 (flush _test-output-buffered-file) - 5311 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 5317 # check output - 5318 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-get-on-function-argument/0") - 5319 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-get-on-function-argument/1") - 5320 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-get-on-function-argument/2") - 5321 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-get-on-function-argument/3") - 5322 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-get-on-function-argument/4") - 5323 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-get-on-function-argument/5") - 5324 # var c - 5325 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %ecx" "F - test-convert-get-on-function-argument/6") - 5326 # get - 5327 (check-next-stream-line-equal _test-output-stream " 8d/copy-address *(ebp+0x0000000c) 0x00000001/r32" "F - test-convert-get-on-function-argument/7") - 5328 # reclaim c - 5329 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %ecx" "F - test-convert-get-on-function-argument/8") - 5330 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-get-on-function-argument/9") - 5331 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-get-on-function-argument/10") - 5332 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-get-on-function-argument/11") - 5333 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-get-on-function-argument/12") - 5334 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-get-on-function-argument/13") - 5335 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-get-on-function-argument/14") - 5336 # . epilogue - 5337 89/<- %esp 5/r32/ebp - 5338 5d/pop-to-ebp - 5339 c3/return - 5340 - 5341 test-convert-get-on-function-argument-with-known-type: - 5342 # . prologue - 5343 55/push-ebp - 5344 89/<- %ebp 4/r32/esp - 5345 # setup - 5346 (clear-stream _test-input-stream) - 5347 (clear-stream $_test-input-buffered-file->buffer) - 5348 (clear-stream _test-output-stream) - 5349 (clear-stream $_test-output-buffered-file->buffer) - 5350 # - 5351 (write _test-input-stream "type t {\n") - 5352 (write _test-input-stream " x: int\n") - 5353 (write _test-input-stream " y: int\n") - 5354 (write _test-input-stream "}\n") - 5355 (write _test-input-stream "fn foo a: t {\n") - 5356 (write _test-input-stream " var c/ecx: (addr int) <- get a, y\n") + 1388 (write _test-input-stream "fn foo -> result/ebx: int {\n") + 1389 (write _test-input-stream " result <- copy 3\n") + 1390 (write _test-input-stream "}\n") + 1391 # convert + 1392 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) + 1393 (flush _test-output-buffered-file) + 1394 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- + 1400 # check output + 1401 (check-next-stream-line-equal _test-output-stream "main:" "F - test-convert-function-call/0") + 1402 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-function-call/1") + 1403 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-function-call/2") + 1404 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-function-call/3") + 1405 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-call/4") + 1406 (check-next-stream-line-equal _test-output-stream "$main:0x00000001:loop:" "F - test-convert-function-call/5") + 1407 (check-next-stream-line-equal _test-output-stream " (foo)" "F - test-convert-function-call/6") + 1408 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-call/7") + 1409 (check-next-stream-line-equal _test-output-stream "$main:0x00000001:break:" "F - test-convert-function-call/8") + 1410 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-function-call/9") + 1411 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-function-call/10") + 1412 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-function-call/11") + 1413 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-function-call/12") + 1414 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-function-call/13") + 1415 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-function-call/14") + 1416 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-function-call/15") + 1417 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-function-call/16") + 1418 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-call/17") + 1419 (check-next-stream-line-equal _test-output-stream "$foo:0x00000002:loop:" "F - test-convert-function-call/18") + 1420 (check-next-stream-line-equal _test-output-stream " bb/copy-to-ebx 3/imm32" "F - test-convert-function-call/19") + 1421 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-call/20") + 1422 (check-next-stream-line-equal _test-output-stream "$foo:0x00000002:break:" "F - test-convert-function-call/21") + 1423 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-function-call/22") + 1424 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-function-call/23") + 1425 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-function-call/24") + 1426 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-function-call/25") + 1427 # . epilogue + 1428 89/<- %esp 5/r32/ebp + 1429 5d/pop-to-ebp + 1430 c3/return + 1431 + 1432 test-convert-function-call-with-inout-with-compound-type: + 1433 # . prologue + 1434 55/push-ebp + 1435 89/<- %ebp 4/r32/esp + 1436 # setup + 1437 (clear-stream _test-input-stream) + 1438 (clear-stream $_test-input-buffered-file->buffer) + 1439 (clear-stream _test-output-stream) + 1440 (clear-stream $_test-output-buffered-file->buffer) + 1441 # + 1442 (write _test-input-stream "fn f {\n") + 1443 (write _test-input-stream " var x: (addr int)\n") + 1444 (write _test-input-stream " g x\n") + 1445 (write _test-input-stream "}\n") + 1446 (write _test-input-stream "fn g a: (addr int) {\n") + 1447 (write _test-input-stream "}\n") + 1448 # convert + 1449 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) + 1450 (flush _test-output-buffered-file) + 1451 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- + 1457 # check output + 1458 (check-next-stream-line-equal _test-output-stream "f:" "F - test-convert-function-call-with-inout-with-compound-type/0") + 1459 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-function-call-with-inout-with-compound-type/1") + 1460 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-function-call-with-inout-with-compound-type/2") + 1461 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-function-call-with-inout-with-compound-type/3") + 1462 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-call-with-inout-with-compound-type/4") + 1463 (check-next-stream-line-equal _test-output-stream "$f:0x00000001:loop:" "F - test-convert-function-call-with-inout-with-compound-type/5") + 1464 (check-next-stream-line-equal _test-output-stream " 68/push 0/imm32" "F - test-convert-function-call-with-inout-with-compound-type/6") + 1465 (check-next-stream-line-equal _test-output-stream " (g *(ebp+0xfffffffc))" "F - test-convert-function-call-with-inout-with-compound-type/7") + 1466 (check-next-stream-line-equal _test-output-stream " 81 0/subop/add %esp 0x00000004/imm32" "F - test-convert-function-call-with-inout-with-compound-type/8") + 1467 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-call-with-inout-with-compound-type/9") + 1468 (check-next-stream-line-equal _test-output-stream "$f:0x00000001:break:" "F - test-convert-function-call-with-inout-with-compound-type/10") + 1469 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-function-call-with-inout-with-compound-type/11") + 1470 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-function-call-with-inout-with-compound-type/12") + 1471 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-function-call-with-inout-with-compound-type/13") + 1472 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-function-call-with-inout-with-compound-type/14") + 1473 (check-next-stream-line-equal _test-output-stream "g:" "F - test-convert-function-call-with-inout-with-compound-type/15") + 1474 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-function-call-with-inout-with-compound-type/16") + 1475 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-function-call-with-inout-with-compound-type/17") + 1476 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-function-call-with-inout-with-compound-type/18") + 1477 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-function-call-with-inout-with-compound-type/19") + 1478 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-function-call-with-inout-with-compound-type/20") + 1479 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-function-call-with-inout-with-compound-type/21") + 1480 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-function-call-with-inout-with-compound-type/22") + 1481 # . epilogue + 1482 89/<- %esp 5/r32/ebp + 1483 5d/pop-to-ebp + 1484 c3/return + 1485 + 1486 test-convert-function-call-with-inout-with-type-parameter: + 1487 # . prologue + 1488 55/push-ebp + 1489 89/<- %ebp 4/r32/esp + 1490 # setup + 1491 (clear-stream _test-input-stream) + 1492 (clear-stream $_test-input-buffered-file->buffer) + 1493 (clear-stream _test-output-stream) + 1494 (clear-stream $_test-output-buffered-file->buffer) + 1495 (clear-stream _test-error-stream) + 1496 (clear-stream $_test-error-buffered-file->buffer) + 1497 # var ed/edx: exit-descriptor = tailor-exit-descriptor(16) + 1498 68/push 0/imm32 + 1499 68/push 0/imm32 + 1500 89/<- %edx 4/r32/esp + 1501 (tailor-exit-descriptor %edx 0x10) + 1502 # + 1503 (write _test-input-stream "fn f {\n") + 1504 (write _test-input-stream " var x: (addr int)\n") + 1505 (write _test-input-stream " g x\n") + 1506 (write _test-input-stream "}\n") + 1507 (write _test-input-stream "fn g a: (addr _) {\n") + 1508 (write _test-input-stream "}\n") + 1509 # convert + 1510 (convert-mu _test-input-buffered-file _test-output-buffered-file _test-error-buffered-file %edx) + 1511 # registers except esp clobbered at this point + 1512 # restore ed + 1513 89/<- %edx 4/r32/esp + 1514 (flush _test-output-buffered-file) + 1515 (flush _test-error-buffered-file) + 1516 +-- 6 lines: #? # dump _test-error-stream ------------------------------------------------------------------------------------------------------------------------------------------ + 1522 # no error; types matched + 1523 (check-stream-equal _test-error-stream "" "F - test-convert-function-call-with-inout-with-type-parameter: error stream should be empty") + 1524 # don't bother checking the generated code; that's in the test 'test-local-clobbered-by-fn-output' below + 1525 # don't restore from ebp + 1526 81 0/subop/add %esp 8/imm32 + 1527 # . epilogue + 1528 5d/pop-to-ebp + 1529 c3/return + 1530 + 1531 test-convert-function-call-with-incorrect-inout-type: + 1532 # . prologue + 1533 55/push-ebp + 1534 89/<- %ebp 4/r32/esp + 1535 # setup + 1536 (clear-stream _test-input-stream) + 1537 (clear-stream $_test-input-buffered-file->buffer) + 1538 (clear-stream _test-output-stream) + 1539 (clear-stream $_test-output-buffered-file->buffer) + 1540 (clear-stream _test-error-stream) + 1541 (clear-stream $_test-error-buffered-file->buffer) + 1542 # var ed/edx: exit-descriptor = tailor-exit-descriptor(16) + 1543 68/push 0/imm32 + 1544 68/push 0/imm32 + 1545 89/<- %edx 4/r32/esp + 1546 (tailor-exit-descriptor %edx 0x10) + 1547 # + 1548 (write _test-input-stream "fn f {\n") + 1549 (write _test-input-stream " var x: int\n") + 1550 (write _test-input-stream " g x\n") + 1551 (write _test-input-stream "}\n") + 1552 (write _test-input-stream "fn g a: foo {\n") + 1553 (write _test-input-stream "}\n") + 1554 # convert + 1555 (convert-mu _test-input-buffered-file _test-output-buffered-file _test-error-buffered-file %edx) + 1556 # registers except esp clobbered at this point + 1557 # restore ed + 1558 89/<- %edx 4/r32/esp + 1559 (flush _test-output-buffered-file) + 1560 (flush _test-error-buffered-file) + 1561 +-- 6 lines: #? # dump _test-error-stream ------------------------------------------------------------------------------------------------------------------------------------------ + 1567 # check output + 1568 (check-stream-equal _test-output-stream "" "F - test-convert-function-call-with-incorrect-inout-type: output should be empty") + 1569 (check-next-stream-line-equal _test-error-stream "fn f: call g: type for inout 'x' is not right" "F - test-convert-function-call-with-incorrect-inout-type: error message") + 1570 # check that stop(1) was called + 1571 (check-ints-equal *(edx+4) 2 "F - test-convert-function-call-with-incorrect-inout-type: exit status") + 1572 # don't restore from ebp + 1573 81 0/subop/add %esp 8/imm32 + 1574 5d/pop-to-ebp + 1575 c3/return + 1576 + 1577 test-convert-function-call-with-inout-with-incorrect-compound-type: + 1578 # . prologue + 1579 55/push-ebp + 1580 89/<- %ebp 4/r32/esp + 1581 # setup + 1582 (clear-stream _test-input-stream) + 1583 (clear-stream $_test-input-buffered-file->buffer) + 1584 (clear-stream _test-output-stream) + 1585 (clear-stream $_test-output-buffered-file->buffer) + 1586 (clear-stream _test-error-stream) + 1587 (clear-stream $_test-error-buffered-file->buffer) + 1588 # var ed/edx: exit-descriptor = tailor-exit-descriptor(16) + 1589 68/push 0/imm32 + 1590 68/push 0/imm32 + 1591 89/<- %edx 4/r32/esp + 1592 (tailor-exit-descriptor %edx 0x10) + 1593 # + 1594 (write _test-input-stream "fn f {\n") + 1595 (write _test-input-stream " var x: (addr int)\n") + 1596 (write _test-input-stream " g x\n") + 1597 (write _test-input-stream "}\n") + 1598 (write _test-input-stream "fn g a: (addr bool) {\n") + 1599 (write _test-input-stream "}\n") + 1600 # convert + 1601 (convert-mu _test-input-buffered-file _test-output-buffered-file _test-error-buffered-file %edx) + 1602 # registers except esp clobbered at this point + 1603 # restore ed + 1604 89/<- %edx 4/r32/esp + 1605 (flush _test-output-buffered-file) + 1606 (flush _test-error-buffered-file) + 1607 +-- 6 lines: #? # dump _test-error-stream ------------------------------------------------------------------------------------------------------------------------------------------ + 1613 # check output + 1614 (check-stream-equal _test-output-stream "" "F - test-convert-function-call-with-inout-with-incorrect-compound-type: output should be empty") + 1615 (check-next-stream-line-equal _test-error-stream "fn f: call g: type for inout 'x' is not right" "F - test-convert-function-call-with-inout-with-incorrect-compound-type: error message") + 1616 # don't restore from ebp + 1617 81 0/subop/add %esp 8/imm32 + 1618 # . epilogue + 1619 5d/pop-to-ebp + 1620 c3/return + 1621 + 1622 test-convert-function-call-with-inout-with-multiple-type-parameters: + 1623 # . prologue + 1624 55/push-ebp + 1625 89/<- %ebp 4/r32/esp + 1626 # setup + 1627 (clear-stream _test-input-stream) + 1628 (clear-stream $_test-input-buffered-file->buffer) + 1629 (clear-stream _test-output-stream) + 1630 (clear-stream $_test-output-buffered-file->buffer) + 1631 (clear-stream _test-error-stream) + 1632 (clear-stream $_test-error-buffered-file->buffer) + 1633 # var ed/edx: exit-descriptor = tailor-exit-descriptor(16) + 1634 68/push 0/imm32 + 1635 68/push 0/imm32 + 1636 89/<- %edx 4/r32/esp + 1637 (tailor-exit-descriptor %edx 0x10) + 1638 # + 1639 (write _test-input-stream "fn f {\n") + 1640 (write _test-input-stream " var x: (addr int)\n") + 1641 (write _test-input-stream " var y: (addr int)\n") + 1642 (write _test-input-stream " g x, y\n") + 1643 (write _test-input-stream "}\n") + 1644 (write _test-input-stream "fn g a: (addr _), b: (addr _) {\n") + 1645 (write _test-input-stream "}\n") + 1646 # convert + 1647 (convert-mu _test-input-buffered-file _test-output-buffered-file _test-error-buffered-file %edx) + 1648 # registers except esp clobbered at this point + 1649 # restore ed + 1650 89/<- %edx 4/r32/esp + 1651 (flush _test-output-buffered-file) + 1652 (flush _test-error-buffered-file) + 1653 +-- 6 lines: #? # dump _test-error-stream ------------------------------------------------------------------------------------------------------------------------------------------ + 1659 # no errors + 1660 (check-stream-equal _test-error-stream "" "F - test-convert-function-call-with-inout-with-multiple-type-parameters: error stream should be empty") + 1661 # don't bother checking the generated code + 1662 # don't restore from ebp + 1663 81 0/subop/add %esp 8/imm32 + 1664 # . epilogue + 1665 5d/pop-to-ebp + 1666 c3/return + 1667 + 1668 test-convert-function-call-with-inout-with-incompatible-type-parameters: + 1669 # . prologue + 1670 55/push-ebp + 1671 89/<- %ebp 4/r32/esp + 1672 # setup + 1673 (clear-stream _test-input-stream) + 1674 (clear-stream $_test-input-buffered-file->buffer) + 1675 (clear-stream _test-output-stream) + 1676 (clear-stream $_test-output-buffered-file->buffer) + 1677 (clear-stream _test-error-stream) + 1678 (clear-stream $_test-error-buffered-file->buffer) + 1679 # var ed/edx: exit-descriptor = tailor-exit-descriptor(16) + 1680 68/push 0/imm32 + 1681 68/push 0/imm32 + 1682 89/<- %edx 4/r32/esp + 1683 (tailor-exit-descriptor %edx 0x10) + 1684 # + 1685 (write _test-input-stream "fn f {\n") + 1686 (write _test-input-stream " var x: (addr int)\n") + 1687 (write _test-input-stream " var y: (addr boolean)\n") + 1688 (write _test-input-stream " g x, y\n") + 1689 (write _test-input-stream "}\n") + 1690 (write _test-input-stream "fn g a: (addr _T), b: (addr _T) {\n") + 1691 (write _test-input-stream "}\n") + 1692 # convert + 1693 (convert-mu _test-input-buffered-file _test-output-buffered-file _test-error-buffered-file %edx) + 1694 # registers except esp clobbered at this point + 1695 # restore ed + 1696 89/<- %edx 4/r32/esp + 1697 (flush _test-output-buffered-file) + 1698 (flush _test-error-buffered-file) + 1699 +-- 6 lines: #? # dump _test-error-stream ------------------------------------------------------------------------------------------------------------------------------------------ + 1705 # check output + 1706 (check-stream-equal _test-output-stream "" "F - test-convert-function-call-with-inout-with-incompatible-type-parameters: output should be empty") + 1707 (check-next-stream-line-equal _test-error-stream "fn f: call g: type for inout 'y' is not right" "F - test-convert-function-call-with-inout-with-incompatible-type-parameters: error message") + 1708 # don't restore from ebp + 1709 81 0/subop/add %esp 8/imm32 + 1710 # . epilogue + 1711 5d/pop-to-ebp + 1712 c3/return + 1713 + 1714 test-convert-function-call-with-too-few-inouts: + 1715 # . prologue + 1716 55/push-ebp + 1717 89/<- %ebp 4/r32/esp + 1718 # setup + 1719 (clear-stream _test-input-stream) + 1720 (clear-stream $_test-input-buffered-file->buffer) + 1721 (clear-stream _test-output-stream) + 1722 (clear-stream $_test-output-buffered-file->buffer) + 1723 (clear-stream _test-error-stream) + 1724 (clear-stream $_test-error-buffered-file->buffer) + 1725 # var ed/edx: exit-descriptor = tailor-exit-descriptor(16) + 1726 68/push 0/imm32 + 1727 68/push 0/imm32 + 1728 89/<- %edx 4/r32/esp + 1729 (tailor-exit-descriptor %edx 0x10) + 1730 # + 1731 (write _test-input-stream "fn f {\n") + 1732 (write _test-input-stream " g\n") + 1733 (write _test-input-stream "}\n") + 1734 (write _test-input-stream "fn g a: int {\n") + 1735 (write _test-input-stream "}\n") + 1736 # convert + 1737 (convert-mu _test-input-buffered-file _test-output-buffered-file _test-error-buffered-file %edx) + 1738 # registers except esp clobbered at this point + 1739 # restore ed + 1740 89/<- %edx 4/r32/esp + 1741 (flush _test-output-buffered-file) + 1742 (flush _test-error-buffered-file) + 1743 +-- 6 lines: #? # dump _test-error-stream ------------------------------------------------------------------------------------------------------------------------------------------ + 1749 # check output + 1750 (check-stream-equal _test-output-stream "" "F - test-convert-function-call-with-too-few-inouts: output should be empty") + 1751 (check-next-stream-line-equal _test-error-stream "fn f: call g: too few inouts" "F - test-convert-function-call-with-too-few-inouts: error message") + 1752 # check that stop(1) was called + 1753 (check-ints-equal *(edx+4) 2 "F - test-convert-function-call-with-too-few-inouts: exit status") + 1754 # don't restore from ebp + 1755 81 0/subop/add %esp 8/imm32 + 1756 5d/pop-to-ebp + 1757 c3/return + 1758 + 1759 test-convert-function-call-with-too-many-inouts: + 1760 # . prologue + 1761 55/push-ebp + 1762 89/<- %ebp 4/r32/esp + 1763 # setup + 1764 (clear-stream _test-input-stream) + 1765 (clear-stream $_test-input-buffered-file->buffer) + 1766 (clear-stream _test-output-stream) + 1767 (clear-stream $_test-output-buffered-file->buffer) + 1768 (clear-stream _test-error-stream) + 1769 (clear-stream $_test-error-buffered-file->buffer) + 1770 # var ed/edx: exit-descriptor = tailor-exit-descriptor(16) + 1771 68/push 0/imm32 + 1772 68/push 0/imm32 + 1773 89/<- %edx 4/r32/esp + 1774 (tailor-exit-descriptor %edx 0x10) + 1775 # + 1776 (write _test-input-stream "fn f {\n") + 1777 (write _test-input-stream " var x: int\n") + 1778 (write _test-input-stream " g x\n") + 1779 (write _test-input-stream "}\n") + 1780 (write _test-input-stream "fn g {\n") + 1781 (write _test-input-stream "}\n") + 1782 # convert + 1783 (convert-mu _test-input-buffered-file _test-output-buffered-file _test-error-buffered-file %edx) + 1784 # registers except esp clobbered at this point + 1785 # restore ed + 1786 89/<- %edx 4/r32/esp + 1787 (flush _test-output-buffered-file) + 1788 (flush _test-error-buffered-file) + 1789 +-- 6 lines: #? # dump _test-error-stream ------------------------------------------------------------------------------------------------------------------------------------------ + 1795 # check output + 1796 (check-stream-equal _test-output-stream "" "F - test-convert-function-call-with-too-many-inouts: output should be empty") + 1797 (check-next-stream-line-equal _test-error-stream "fn f: call g: too many inouts" "F - test-convert-function-call-with-too-many-inouts: error message") + 1798 # check that stop(1) was called + 1799 (check-ints-equal *(edx+4) 2 "F - test-convert-function-call-with-too-many-inouts: exit status") + 1800 # don't restore from ebp + 1801 81 0/subop/add %esp 8/imm32 + 1802 5d/pop-to-ebp + 1803 c3/return + 1804 + 1805 test-convert-function-call-with-incorrect-output-type: + 1806 # . prologue + 1807 55/push-ebp + 1808 89/<- %ebp 4/r32/esp + 1809 # setup + 1810 (clear-stream _test-input-stream) + 1811 (clear-stream $_test-input-buffered-file->buffer) + 1812 (clear-stream _test-output-stream) + 1813 (clear-stream $_test-output-buffered-file->buffer) + 1814 (clear-stream _test-error-stream) + 1815 (clear-stream $_test-error-buffered-file->buffer) + 1816 # var ed/edx: exit-descriptor = tailor-exit-descriptor(16) + 1817 68/push 0/imm32 + 1818 68/push 0/imm32 + 1819 89/<- %edx 4/r32/esp + 1820 (tailor-exit-descriptor %edx 0x10) + 1821 # + 1822 (write _test-input-stream "fn f {\n") + 1823 (write _test-input-stream " var x/eax: int <- g\n") + 1824 (write _test-input-stream "}\n") + 1825 (write _test-input-stream "fn g -> a/eax: foo {\n") + 1826 (write _test-input-stream "}\n") + 1827 # convert + 1828 (convert-mu _test-input-buffered-file _test-output-buffered-file _test-error-buffered-file %edx) + 1829 # registers except esp clobbered at this point + 1830 # restore ed + 1831 89/<- %edx 4/r32/esp + 1832 (flush _test-output-buffered-file) + 1833 (flush _test-error-buffered-file) + 1834 +-- 6 lines: #? # dump _test-error-stream ------------------------------------------------------------------------------------------------------------------------------------------ + 1840 # check output + 1841 (check-stream-equal _test-output-stream "" "F - test-convert-function-call-with-incorrect-output-type: output should be empty") + 1842 (check-next-stream-line-equal _test-error-stream "fn f: call g: type for output 'x' is not right" "F - test-convert-function-call-with-incorrect-output-type: error message") + 1843 # check that stop(1) was called + 1844 (check-ints-equal *(edx+4) 2 "F - test-convert-function-call-with-incorrect-output-type: exit status") + 1845 # don't restore from ebp + 1846 81 0/subop/add %esp 8/imm32 + 1847 5d/pop-to-ebp + 1848 c3/return + 1849 + 1850 test-convert-function-call-with-too-few-outputs: + 1851 # . prologue + 1852 55/push-ebp + 1853 89/<- %ebp 4/r32/esp + 1854 # setup + 1855 (clear-stream _test-input-stream) + 1856 (clear-stream $_test-input-buffered-file->buffer) + 1857 (clear-stream _test-output-stream) + 1858 (clear-stream $_test-output-buffered-file->buffer) + 1859 (clear-stream _test-error-stream) + 1860 (clear-stream $_test-error-buffered-file->buffer) + 1861 # var ed/edx: exit-descriptor = tailor-exit-descriptor(16) + 1862 68/push 0/imm32 + 1863 68/push 0/imm32 + 1864 89/<- %edx 4/r32/esp + 1865 (tailor-exit-descriptor %edx 0x10) + 1866 # + 1867 (write _test-input-stream "fn f {\n") + 1868 (write _test-input-stream " g\n") + 1869 (write _test-input-stream "}\n") + 1870 (write _test-input-stream "fn g -> a/eax: int {\n") + 1871 (write _test-input-stream "}\n") + 1872 # convert + 1873 (convert-mu _test-input-buffered-file _test-output-buffered-file _test-error-buffered-file %edx) + 1874 # registers except esp clobbered at this point + 1875 # restore ed + 1876 89/<- %edx 4/r32/esp + 1877 (flush _test-output-buffered-file) + 1878 (flush _test-error-buffered-file) + 1879 +-- 6 lines: #? # dump _test-error-stream ------------------------------------------------------------------------------------------------------------------------------------------ + 1885 # check output + 1886 (check-stream-equal _test-output-stream "" "F - test-convert-function-call-with-too-few-outputs: output should be empty") + 1887 (check-next-stream-line-equal _test-error-stream "fn f: call g: too few outputs" "F - test-convert-function-call-with-too-few-outputs: error message") + 1888 # check that stop(1) was called + 1889 (check-ints-equal *(edx+4) 2 "F - test-convert-function-call-with-too-few-outputs: exit status") + 1890 # don't restore from ebp + 1891 81 0/subop/add %esp 8/imm32 + 1892 5d/pop-to-ebp + 1893 c3/return + 1894 + 1895 test-convert-function-call-with-too-many-outputs: + 1896 # . prologue + 1897 55/push-ebp + 1898 89/<- %ebp 4/r32/esp + 1899 # setup + 1900 (clear-stream _test-input-stream) + 1901 (clear-stream $_test-input-buffered-file->buffer) + 1902 (clear-stream _test-output-stream) + 1903 (clear-stream $_test-output-buffered-file->buffer) + 1904 (clear-stream _test-error-stream) + 1905 (clear-stream $_test-error-buffered-file->buffer) + 1906 # var ed/edx: exit-descriptor = tailor-exit-descriptor(16) + 1907 68/push 0/imm32 + 1908 68/push 0/imm32 + 1909 89/<- %edx 4/r32/esp + 1910 (tailor-exit-descriptor %edx 0x10) + 1911 # + 1912 (write _test-input-stream "fn f {\n") + 1913 (write _test-input-stream " var x/eax: int <- g\n") + 1914 (write _test-input-stream "}\n") + 1915 (write _test-input-stream "fn g {\n") + 1916 (write _test-input-stream "}\n") + 1917 # convert + 1918 (convert-mu _test-input-buffered-file _test-output-buffered-file _test-error-buffered-file %edx) + 1919 # registers except esp clobbered at this point + 1920 # restore ed + 1921 89/<- %edx 4/r32/esp + 1922 (flush _test-output-buffered-file) + 1923 (flush _test-error-buffered-file) + 1924 +-- 6 lines: #? # dump _test-error-stream ------------------------------------------------------------------------------------------------------------------------------------------ + 1930 # check output + 1931 (check-stream-equal _test-output-stream "" "F - test-convert-function-call-with-too-many-outputs: output should be empty") + 1932 (check-next-stream-line-equal _test-error-stream "fn f: call g: too many outputs" "F - test-convert-function-call-with-too-many-outputs: error message") + 1933 # check that stop(1) was called + 1934 (check-ints-equal *(edx+4) 2 "F - test-convert-function-call-with-too-many-outputs: exit status") + 1935 # don't restore from ebp + 1936 81 0/subop/add %esp 8/imm32 + 1937 5d/pop-to-ebp + 1938 c3/return + 1939 + 1940 test-convert-function-call-with-incorrect-output-register: + 1941 # . prologue + 1942 55/push-ebp + 1943 89/<- %ebp 4/r32/esp + 1944 # setup + 1945 (clear-stream _test-input-stream) + 1946 (clear-stream $_test-input-buffered-file->buffer) + 1947 (clear-stream _test-output-stream) + 1948 (clear-stream $_test-output-buffered-file->buffer) + 1949 (clear-stream _test-error-stream) + 1950 (clear-stream $_test-error-buffered-file->buffer) + 1951 # var ed/edx: exit-descriptor = tailor-exit-descriptor(16) + 1952 68/push 0/imm32 + 1953 68/push 0/imm32 + 1954 89/<- %edx 4/r32/esp + 1955 (tailor-exit-descriptor %edx 0x10) + 1956 # + 1957 (write _test-input-stream "fn f {\n") + 1958 (write _test-input-stream " var x/ecx: int <- g\n") + 1959 (write _test-input-stream "}\n") + 1960 (write _test-input-stream "fn g -> a/eax: int {\n") + 1961 (write _test-input-stream "}\n") + 1962 # convert + 1963 (convert-mu _test-input-buffered-file _test-output-buffered-file _test-error-buffered-file %edx) + 1964 # registers except esp clobbered at this point + 1965 # restore ed + 1966 89/<- %edx 4/r32/esp + 1967 (flush _test-output-buffered-file) + 1968 (flush _test-error-buffered-file) + 1969 +-- 6 lines: #? # dump _test-error-stream ------------------------------------------------------------------------------------------------------------------------------------------ + 1975 # check output + 1976 (check-stream-equal _test-output-stream "" "F - test-convert-function-call-with-incorrect-output-register: output should be empty") + 1977 (check-next-stream-line-equal _test-error-stream "fn f: call g: register for output 'x' is not right" "F - test-convert-function-call-with-incorrect-output-register: error message") + 1978 # check that stop(1) was called + 1979 (check-ints-equal *(edx+4) 2 "F - test-convert-function-call-with-incorrect-output-register: exit status") + 1980 # don't restore from ebp + 1981 81 0/subop/add %esp 8/imm32 + 1982 5d/pop-to-ebp + 1983 c3/return + 1984 + 1985 test-convert-function-with-local-var-dereferenced: + 1986 # . prologue + 1987 55/push-ebp + 1988 89/<- %ebp 4/r32/esp + 1989 # setup + 1990 (clear-stream _test-input-stream) + 1991 (clear-stream $_test-input-buffered-file->buffer) + 1992 (clear-stream _test-output-stream) + 1993 (clear-stream $_test-output-buffered-file->buffer) + 1994 # + 1995 (write _test-input-stream "fn foo {\n") + 1996 (write _test-input-stream " var x/ecx: (addr int) <- copy 0\n") + 1997 (write _test-input-stream " increment *x\n") + 1998 (write _test-input-stream "}\n") + 1999 # convert + 2000 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) + 2001 (flush _test-output-buffered-file) + 2002 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- + 2008 # check output + 2009 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-function-with-local-var-dereferenced/0") + 2010 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-function-with-local-var-dereferenced/1") + 2011 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-function-with-local-var-dereferenced/2") + 2012 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-function-with-local-var-dereferenced/3") + 2013 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-local-var-dereferenced/4") + 2014 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-function-with-local-var-dereferenced/5") + 2015 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %ecx" "F - test-convert-function-with-local-var-dereferenced/6") + 2016 (check-next-stream-line-equal _test-output-stream " b9/copy-to-ecx 0/imm32" "F - test-convert-function-with-local-var-dereferenced/7") + 2017 (check-next-stream-line-equal _test-output-stream " ff 0/subop/increment *ecx" "F - test-convert-function-with-local-var-dereferenced/8") + 2018 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %ecx" "F - test-convert-function-with-local-var-dereferenced/9") + 2019 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-local-var-dereferenced/10") + 2020 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-function-with-local-var-dereferenced/11") + 2021 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-function-with-local-var-dereferenced/12") + 2022 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-function-with-local-var-dereferenced/13") + 2023 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-function-with-local-var-dereferenced/14") + 2024 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-function-with-local-var-dereferenced/15") + 2025 # . epilogue + 2026 89/<- %esp 5/r32/ebp + 2027 5d/pop-to-ebp + 2028 c3/return + 2029 + 2030 # variables of type 'byte' are not allowed on the stack + 2031 test-convert-function-with-byte-operations: + 2032 # . prologue + 2033 55/push-ebp + 2034 89/<- %ebp 4/r32/esp + 2035 # setup + 2036 (clear-stream _test-input-stream) + 2037 (clear-stream $_test-input-buffered-file->buffer) + 2038 (clear-stream _test-output-stream) + 2039 (clear-stream $_test-output-buffered-file->buffer) + 2040 # + 2041 (write _test-input-stream "fn foo {\n") + 2042 (write _test-input-stream " var x/eax: byte <- copy 0\n") + 2043 (write _test-input-stream " var y/ecx: byte <- copy 0\n") + 2044 (write _test-input-stream " y <- copy-byte x\n") + 2045 (write _test-input-stream " var z/edx: (addr byte) <- copy 0\n") + 2046 (write _test-input-stream " y <- copy-byte *z\n") + 2047 (write _test-input-stream " copy-byte-to *z, x\n") + 2048 (write _test-input-stream "}\n") + 2049 # convert + 2050 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) + 2051 (flush _test-output-buffered-file) + 2052 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- + 2058 # check output + 2059 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-function-with-byte-operations/0") + 2060 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-function-with-byte-operations/1") + 2061 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-function-with-byte-operations/2") + 2062 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-function-with-byte-operations/3") + 2063 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-byte-operations/4") + 2064 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-function-with-byte-operations/5") + 2065 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %eax" "F - test-convert-function-with-byte-operations/6") + 2066 (check-next-stream-line-equal _test-output-stream " b8/copy-to-eax 0/imm32" "F - test-convert-function-with-byte-operations/7") + 2067 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %ecx" "F - test-convert-function-with-byte-operations/8") + 2068 (check-next-stream-line-equal _test-output-stream " b9/copy-to-ecx 0/imm32" "F - test-convert-function-with-byte-operations/9") + 2069 (check-next-stream-line-equal _test-output-stream " 8a/byte-> %eax 0x00000001/r32" "F - test-convert-function-with-byte-operations/10") + 2070 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %edx" "F - test-convert-function-with-byte-operations/11") + 2071 (check-next-stream-line-equal _test-output-stream " ba/copy-to-edx 0/imm32" "F - test-convert-function-with-byte-operations/12") + 2072 (check-next-stream-line-equal _test-output-stream " 8a/byte-> *edx 0x00000001/r32" "F - test-convert-function-with-byte-operations/13") + 2073 (check-next-stream-line-equal _test-output-stream " 88/byte<- *edx 0x00000000/r32" "F - test-convert-function-with-byte-operations/14") + 2074 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %edx" "F - test-convert-function-with-byte-operations/15") + 2075 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %ecx" "F - test-convert-function-with-byte-operations/16") + 2076 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %eax" "F - test-convert-function-with-byte-operations/17") + 2077 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-byte-operations/18") + 2078 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-function-with-byte-operations/19") + 2079 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-function-with-byte-operations/20") + 2080 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-function-with-byte-operations/21") + 2081 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-function-with-byte-operations/22") + 2082 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-function-with-byte-operations/23") + 2083 # . epilogue + 2084 89/<- %esp 5/r32/ebp + 2085 5d/pop-to-ebp + 2086 c3/return + 2087 + 2088 # variables of type 'byte' _can_ be function args. They then occupy 4 bytes. + 2089 test-copy-byte-var-from-fn-arg: + 2090 # . prologue + 2091 55/push-ebp + 2092 89/<- %ebp 4/r32/esp + 2093 # setup + 2094 (clear-stream _test-input-stream) + 2095 (clear-stream $_test-input-buffered-file->buffer) + 2096 (clear-stream _test-output-stream) + 2097 (clear-stream $_test-output-buffered-file->buffer) + 2098 # + 2099 (write _test-input-stream "fn foo x: byte, y: int {\n") + 2100 (write _test-input-stream " var a/eax: byte <- copy x\n") + 2101 (write _test-input-stream " var b/eax: int <- copy y\n") + 2102 (write _test-input-stream "}\n") + 2103 # convert + 2104 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) + 2105 (flush _test-output-buffered-file) + 2106 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- + 2112 # check output + 2113 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-copy-byte-from-fn-arg/0") + 2114 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-copy-byte-from-fn-arg/1") + 2115 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-copy-byte-from-fn-arg/2") + 2116 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-copy-byte-from-fn-arg/3") + 2117 (check-next-stream-line-equal _test-output-stream " {" "F - test-copy-byte-from-fn-arg/4") + 2118 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-copy-byte-from-fn-arg/5") + 2119 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %eax" "F - test-copy-byte-from-fn-arg/6") + 2120 (check-next-stream-line-equal _test-output-stream " 8b/-> *(ebp+0x00000008) 0x00000000/r32" "F - test-copy-byte-from-fn-arg/7") + 2121 (check-next-stream-line-equal _test-output-stream " 8b/-> *(ebp+0x0000000c) 0x00000000/r32" "F - test-copy-byte-from-fn-arg/8") + 2122 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %eax" "F - test-copy-byte-from-fn-arg/9") + 2123 (check-next-stream-line-equal _test-output-stream " }" "F - test-copy-byte-from-fn-arg/10") + 2124 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-copy-byte-from-fn-arg/11") + 2125 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-copy-byte-from-fn-arg/12") + 2126 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-copy-byte-from-fn-arg/13") + 2127 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-copy-byte-from-fn-arg/14") + 2128 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-copy-byte-from-fn-arg/15") + 2129 # . epilogue + 2130 89/<- %esp 5/r32/ebp + 2131 5d/pop-to-ebp + 2132 c3/return + 2133 + 2134 test-convert-compare-register-with-literal: + 2135 # . prologue + 2136 55/push-ebp + 2137 89/<- %ebp 4/r32/esp + 2138 # setup + 2139 (clear-stream _test-input-stream) + 2140 (clear-stream $_test-input-buffered-file->buffer) + 2141 (clear-stream _test-output-stream) + 2142 (clear-stream $_test-output-buffered-file->buffer) + 2143 # + 2144 (write _test-input-stream "fn foo {\n") + 2145 (write _test-input-stream " var x/ecx: int <- copy 0\n") + 2146 (write _test-input-stream " compare x, 0\n") + 2147 (write _test-input-stream "}\n") + 2148 # convert + 2149 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) + 2150 (flush _test-output-buffered-file) + 2151 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- + 2157 # check output + 2158 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-compare-register-with-literal/0") + 2159 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-compare-register-with-literal/1") + 2160 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-compare-register-with-literal/2") + 2161 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-compare-register-with-literal/3") + 2162 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-compare-register-with-literal/4") + 2163 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-compare-register-with-literal/5") + 2164 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %ecx" "F - test-convert-compare-register-with-literal/6") + 2165 (check-next-stream-line-equal _test-output-stream " b9/copy-to-ecx 0/imm32" "F - test-convert-compare-register-with-literal/7") + 2166 (check-next-stream-line-equal _test-output-stream " 81 7/subop/compare %ecx 0/imm32" "F - test-convert-compare-register-with-literal/8") + 2167 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %ecx" "F - test-convert-compare-register-with-literal/9") + 2168 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-compare-register-with-literal/10") + 2169 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-compare-register-with-literal/11") + 2170 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-compare-register-with-literal/12") + 2171 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-compare-register-with-literal/13") + 2172 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-compare-register-with-literal/14") + 2173 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-compare-register-with-literal/15") + 2174 # . epilogue + 2175 89/<- %esp 5/r32/ebp + 2176 5d/pop-to-ebp + 2177 c3/return + 2178 + 2179 test-unknown-variable: + 2180 # . prologue + 2181 55/push-ebp + 2182 89/<- %ebp 4/r32/esp + 2183 # setup + 2184 (clear-stream _test-input-stream) + 2185 (clear-stream $_test-input-buffered-file->buffer) + 2186 (clear-stream _test-output-stream) + 2187 (clear-stream $_test-output-buffered-file->buffer) + 2188 (clear-stream _test-error-stream) + 2189 (clear-stream $_test-error-buffered-file->buffer) + 2190 # var ed/edx: exit-descriptor = tailor-exit-descriptor(16) + 2191 68/push 0/imm32 + 2192 68/push 0/imm32 + 2193 89/<- %edx 4/r32/esp + 2194 (tailor-exit-descriptor %edx 0x10) + 2195 # + 2196 (write _test-input-stream "fn foo {\n") + 2197 (write _test-input-stream " compare x, 0\n") + 2198 (write _test-input-stream "}\n") + 2199 # convert + 2200 (convert-mu _test-input-buffered-file _test-output-buffered-file _test-error-buffered-file %edx) + 2201 # registers except esp clobbered at this point + 2202 # restore ed + 2203 89/<- %edx 4/r32/esp + 2204 (flush _test-output-buffered-file) + 2205 (flush _test-error-buffered-file) + 2206 +-- 6 lines: #? # dump _test-error-stream ------------------------------------------------------------------------------------------------------------------------------------------ + 2212 # check output + 2213 (check-stream-equal _test-output-stream "" "F - test-unknown-variable: output should be empty") + 2214 (check-next-stream-line-equal _test-error-stream "fn foo: unknown variable 'x'" "F - test-unknown-variable: error message") + 2215 # check that stop(1) was called + 2216 (check-ints-equal *(edx+4) 2 "F - test-unknown-variable: exit status") + 2217 # don't restore from ebp + 2218 81 0/subop/add %esp 8/imm32 + 2219 # . epilogue + 2220 5d/pop-to-ebp + 2221 c3/return + 2222 + 2223 test-convert-function-with-local-var-in-block: + 2224 # . prologue + 2225 55/push-ebp + 2226 89/<- %ebp 4/r32/esp + 2227 # setup + 2228 (clear-stream _test-input-stream) + 2229 (clear-stream $_test-input-buffered-file->buffer) + 2230 (clear-stream _test-output-stream) + 2231 (clear-stream $_test-output-buffered-file->buffer) + 2232 # + 2233 (write _test-input-stream "fn foo {\n") + 2234 (write _test-input-stream " {\n") + 2235 (write _test-input-stream " var x: int\n") + 2236 (write _test-input-stream " increment x\n") + 2237 (write _test-input-stream " }\n") + 2238 (write _test-input-stream "}\n") + 2239 # convert + 2240 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) + 2241 (flush _test-output-buffered-file) + 2242 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- + 2248 # check output + 2249 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-function-with-local-var-in-block/0") + 2250 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-function-with-local-var-in-block/1") + 2251 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-function-with-local-var-in-block/2") + 2252 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-function-with-local-var-in-block/3") + 2253 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-local-var-in-block/4") + 2254 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-function-with-local-var-in-block/5") + 2255 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-local-var-in-block/6") + 2256 (check-next-stream-line-equal _test-output-stream "$foo:0x00000002:loop:" "F - test-convert-function-with-local-var-in-block/7") + 2257 (check-next-stream-line-equal _test-output-stream " 68/push 0/imm32" "F - test-convert-function-with-local-var-in-block/8") + 2258 (check-next-stream-line-equal _test-output-stream " ff 0/subop/increment *(ebp+0xfffffffc)" "F - test-convert-function-with-local-var-in-block/9") + 2259 (check-next-stream-line-equal _test-output-stream " 81 0/subop/add %esp 0x00000004/imm32" "F - test-convert-function-with-local-var-in-block/10") + 2260 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-local-var-in-block/11") + 2261 (check-next-stream-line-equal _test-output-stream "$foo:0x00000002:break:" "F - test-convert-function-with-local-var-in-block/12") + 2262 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-local-var-in-block/13") + 2263 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-function-with-local-var-in-block/14") + 2264 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-function-with-local-var-in-block/15") + 2265 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-function-with-local-var-in-block/16") + 2266 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-function-with-local-var-in-block/17") + 2267 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-function-with-local-var-in-block/18") + 2268 # . epilogue + 2269 89/<- %esp 5/r32/ebp + 2270 5d/pop-to-ebp + 2271 c3/return + 2272 + 2273 test-convert-function-with-local-var-in-named-block: + 2274 # . prologue + 2275 55/push-ebp + 2276 89/<- %ebp 4/r32/esp + 2277 # setup + 2278 (clear-stream _test-input-stream) + 2279 (clear-stream $_test-input-buffered-file->buffer) + 2280 (clear-stream _test-output-stream) + 2281 (clear-stream $_test-output-buffered-file->buffer) + 2282 # + 2283 (write _test-input-stream "fn foo {\n") + 2284 (write _test-input-stream " $bar: {\n") + 2285 (write _test-input-stream " var x: int\n") + 2286 (write _test-input-stream " increment x\n") + 2287 (write _test-input-stream " }\n") + 2288 (write _test-input-stream "}\n") + 2289 # convert + 2290 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) + 2291 (flush _test-output-buffered-file) + 2292 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- + 2298 # check output + 2299 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-function-with-local-var-in-named-block/0") + 2300 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-function-with-local-var-in-named-block/1") + 2301 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-function-with-local-var-in-named-block/2") + 2302 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-function-with-local-var-in-named-block/3") + 2303 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-local-var-in-named-block/4") + 2304 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-function-with-local-var-in-named-block/5") + 2305 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-local-var-in-named-block/6") + 2306 (check-next-stream-line-equal _test-output-stream "$bar:loop:" "F - test-convert-function-with-local-var-in-named-block/7") + 2307 (check-next-stream-line-equal _test-output-stream " 68/push 0/imm32" "F - test-convert-function-with-local-var-in-named-block/8") + 2308 (check-next-stream-line-equal _test-output-stream " ff 0/subop/increment *(ebp+0xfffffffc)" "F - test-convert-function-with-local-var-in-named-block/9") + 2309 (check-next-stream-line-equal _test-output-stream " 81 0/subop/add %esp 0x00000004/imm32" "F - test-convert-function-with-local-var-in-named-block/10") + 2310 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-local-var-in-named-block/11") + 2311 (check-next-stream-line-equal _test-output-stream "$bar:break:" "F - test-convert-function-with-local-var-in-named-block/12") + 2312 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-local-var-in-named-block/13") + 2313 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-function-with-local-var-in-named-block/14") + 2314 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-function-with-local-var-in-named-block/15") + 2315 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-function-with-local-var-in-named-block/16") + 2316 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-function-with-local-var-in-named-block/17") + 2317 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-function-with-local-var-in-named-block/18") + 2318 # . epilogue + 2319 89/<- %esp 5/r32/ebp + 2320 5d/pop-to-ebp + 2321 c3/return + 2322 + 2323 test-unknown-variable-in-named-block: + 2324 # . prologue + 2325 55/push-ebp + 2326 89/<- %ebp 4/r32/esp + 2327 # setup + 2328 (clear-stream _test-input-stream) + 2329 (clear-stream $_test-input-buffered-file->buffer) + 2330 (clear-stream _test-output-stream) + 2331 (clear-stream $_test-output-buffered-file->buffer) + 2332 (clear-stream _test-error-stream) + 2333 (clear-stream $_test-error-buffered-file->buffer) + 2334 # var ed/edx: exit-descriptor = tailor-exit-descriptor(16) + 2335 68/push 0/imm32 + 2336 68/push 0/imm32 + 2337 89/<- %edx 4/r32/esp + 2338 (tailor-exit-descriptor %edx 0x10) + 2339 # + 2340 (write _test-input-stream "fn foo {\n") + 2341 (write _test-input-stream " $a: {\n") + 2342 (write _test-input-stream " compare x, 0\n") + 2343 (write _test-input-stream " }\n") + 2344 (write _test-input-stream "}\n") + 2345 # convert + 2346 (convert-mu _test-input-buffered-file _test-output-buffered-file _test-error-buffered-file %edx) + 2347 # registers except esp clobbered at this point + 2348 # restore ed + 2349 89/<- %edx 4/r32/esp + 2350 (flush _test-output-buffered-file) + 2351 (flush _test-error-buffered-file) + 2352 +-- 6 lines: #? # dump _test-error-stream ------------------------------------------------------------------------------------------------------------------------------------------ + 2358 # check output + 2359 (check-stream-equal _test-output-stream "" "F - test-unknown-variable-in-named-block: output should be empty") + 2360 (check-next-stream-line-equal _test-error-stream "fn foo: unknown variable 'x'" "F - test-unknown-variable-in-named-block: error message") + 2361 # check that stop(1) was called + 2362 (check-ints-equal *(edx+4) 2 "F - test-unknown-variable-in-named-block: exit status") + 2363 # don't restore from ebp + 2364 81 0/subop/add %esp 8/imm32 + 2365 # . epilogue + 2366 5d/pop-to-ebp + 2367 c3/return + 2368 + 2369 test-always-shadow-outermost-reg-vars-in-function: + 2370 # . prologue + 2371 55/push-ebp + 2372 89/<- %ebp 4/r32/esp + 2373 # setup + 2374 (clear-stream _test-input-stream) + 2375 (clear-stream $_test-input-buffered-file->buffer) + 2376 (clear-stream _test-output-stream) + 2377 (clear-stream $_test-output-buffered-file->buffer) + 2378 # + 2379 (write _test-input-stream "fn foo {\n") + 2380 (write _test-input-stream " var x/ecx: int <- copy 3\n") + 2381 (write _test-input-stream "}\n") + 2382 # convert + 2383 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) + 2384 (flush _test-output-buffered-file) + 2385 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- + 2391 # check output + 2392 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-always-shadow-outermost-reg-vars-in-function/0") + 2393 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-always-shadow-outermost-reg-vars-in-function/1") + 2394 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-always-shadow-outermost-reg-vars-in-function/2") + 2395 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-always-shadow-outermost-reg-vars-in-function/3") + 2396 (check-next-stream-line-equal _test-output-stream " {" "F - test-always-shadow-outermost-reg-vars-in-function/4") + 2397 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-always-shadow-outermost-reg-vars-in-function/5") + 2398 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %ecx" "F - test-convert-compare-register-with-literal/6") + 2399 (check-next-stream-line-equal _test-output-stream " b9/copy-to-ecx 3/imm32" "F - test-always-shadow-outermost-reg-vars-in-function/8") + 2400 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %ecx" "F - test-convert-compare-register-with-literal/9") + 2401 (check-next-stream-line-equal _test-output-stream " }" "F - test-always-shadow-outermost-reg-vars-in-function/12") + 2402 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-always-shadow-outermost-reg-vars-in-function/13") + 2403 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-always-shadow-outermost-reg-vars-in-function/14") + 2404 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-always-shadow-outermost-reg-vars-in-function/15") + 2405 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-always-shadow-outermost-reg-vars-in-function/16") + 2406 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-always-shadow-outermost-reg-vars-in-function/17") + 2407 # . epilogue + 2408 89/<- %esp 5/r32/ebp + 2409 5d/pop-to-ebp + 2410 c3/return + 2411 + 2412 _pending-test-clobber-dead-local: + 2413 # . prologue + 2414 55/push-ebp + 2415 89/<- %ebp 4/r32/esp + 2416 # setup + 2417 (clear-stream _test-input-stream) + 2418 (clear-stream $_test-input-buffered-file->buffer) + 2419 (clear-stream _test-output-stream) + 2420 (clear-stream $_test-output-buffered-file->buffer) + 2421 # + 2422 (write _test-input-stream "fn foo {\n") + 2423 (write _test-input-stream " var x/ecx: int <- copy 3\n") + 2424 (write _test-input-stream " {\n") + 2425 (write _test-input-stream " var y/ecx: int <- copy 4\n") + 2426 (write _test-input-stream " }\n") + 2427 (write _test-input-stream "}\n") + 2428 # convert + 2429 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) + 2430 (flush _test-output-buffered-file) + 2431 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- + 2437 # check output + 2438 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-clobber-dead-local/0") + 2439 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-clobber-dead-local/1") + 2440 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-clobber-dead-local/2") + 2441 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-clobber-dead-local/3") + 2442 (check-next-stream-line-equal _test-output-stream " {" "F - test-clobber-dead-local/4") + 2443 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-clobber-dead-local/5") + 2444 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %ecx" "F - test-clobber-dead-local/6") + 2445 (check-next-stream-line-equal _test-output-stream " b9/copy-to-ecx 3/imm32" "F - test-clobber-dead-local/7") + 2446 (check-next-stream-line-equal _test-output-stream " {" "F - test-clobber-dead-local/8") + 2447 (check-next-stream-line-equal _test-output-stream "$foo:0x00000002:loop:" "F - test-clobber-dead-local/9") + 2448 (check-next-stream-line-equal _test-output-stream " b9/copy-to-ecx 4/imm32" "F - test-clobber-dead-local/10") # no push/pop here + 2449 (check-next-stream-line-equal _test-output-stream " }" "F - test-clobber-dead-local/11") + 2450 (check-next-stream-line-equal _test-output-stream "$foo:0x00000002:break:" "F - test-clobber-dead-local/12") + 2451 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %ecx" "F - test-clobber-dead-local/13") + 2452 (check-next-stream-line-equal _test-output-stream " }" "F - test-clobber-dead-local/14") + 2453 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-clobber-dead-local/15") + 2454 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-clobber-dead-local/16") + 2455 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-clobber-dead-local/17") + 2456 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-clobber-dead-local/18") + 2457 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-clobber-dead-local/19") + 2458 # . epilogue + 2459 89/<- %esp 5/r32/ebp + 2460 5d/pop-to-ebp + 2461 c3/return + 2462 + 2463 test-shadow-live-local: + 2464 # . prologue + 2465 55/push-ebp + 2466 89/<- %ebp 4/r32/esp + 2467 # setup + 2468 (clear-stream _test-input-stream) + 2469 (clear-stream $_test-input-buffered-file->buffer) + 2470 (clear-stream _test-output-stream) + 2471 (clear-stream $_test-output-buffered-file->buffer) + 2472 # + 2473 (write _test-input-stream "fn foo {\n") + 2474 (write _test-input-stream " var x/ecx: int <- copy 3\n") + 2475 (write _test-input-stream " {\n") + 2476 (write _test-input-stream " var y/ecx: int <- copy 4\n") + 2477 (write _test-input-stream " }\n") + 2478 (write _test-input-stream " x <- increment\n") + 2479 (write _test-input-stream "}\n") + 2480 # convert + 2481 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) + 2482 (flush _test-output-buffered-file) + 2483 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- + 2489 # check output + 2490 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-shadow-live-local/0") + 2491 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-shadow-live-local/1") + 2492 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-shadow-live-local/2") + 2493 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-shadow-live-local/3") + 2494 (check-next-stream-line-equal _test-output-stream " {" "F - test-shadow-live-local/4") + 2495 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-shadow-live-local/5") + 2496 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %ecx" "F - test-shadow-live-local/6") + 2497 (check-next-stream-line-equal _test-output-stream " b9/copy-to-ecx 3/imm32" "F - test-shadow-live-local/7") + 2498 (check-next-stream-line-equal _test-output-stream " {" "F - test-shadow-live-local/8") + 2499 (check-next-stream-line-equal _test-output-stream "$foo:0x00000002:loop:" "F - test-shadow-live-local/9") + 2500 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %ecx" "F - test-shadow-live-local/10") + 2501 (check-next-stream-line-equal _test-output-stream " b9/copy-to-ecx 4/imm32" "F - test-shadow-live-local/11") + 2502 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %ecx" "F - test-shadow-live-local/12") + 2503 (check-next-stream-line-equal _test-output-stream " }" "F - test-shadow-live-local/13") + 2504 (check-next-stream-line-equal _test-output-stream "$foo:0x00000002:break:" "F - test-shadow-live-local/14") + 2505 (check-next-stream-line-equal _test-output-stream " 41/increment-ecx" "F - test-shadow-live-local/15") + 2506 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %ecx" "F - test-shadow-live-local/16") + 2507 (check-next-stream-line-equal _test-output-stream " }" "F - test-shadow-live-local/17") + 2508 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-shadow-live-local/18") + 2509 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-shadow-live-local/19") + 2510 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-shadow-live-local/20") + 2511 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-shadow-live-local/21") + 2512 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-shadow-live-local/22") + 2513 # . epilogue + 2514 89/<- %esp 5/r32/ebp + 2515 5d/pop-to-ebp + 2516 c3/return + 2517 + 2518 test-shadow-name: + 2519 # . prologue + 2520 55/push-ebp + 2521 89/<- %ebp 4/r32/esp + 2522 # setup + 2523 (clear-stream _test-input-stream) + 2524 (clear-stream $_test-input-buffered-file->buffer) + 2525 (clear-stream _test-output-stream) + 2526 (clear-stream $_test-output-buffered-file->buffer) + 2527 # + 2528 (write _test-input-stream "fn foo {\n") + 2529 (write _test-input-stream " var x/ecx: int <- copy 3\n") + 2530 (write _test-input-stream " {\n") + 2531 (write _test-input-stream " var x/edx: int <- copy 4\n") + 2532 (write _test-input-stream " }\n") + 2533 (write _test-input-stream " x <- increment\n") + 2534 (write _test-input-stream "}\n") + 2535 # convert + 2536 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) + 2537 (flush _test-output-buffered-file) + 2538 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- + 2544 # check output + 2545 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-shadow-name/0") + 2546 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-shadow-name/1") + 2547 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-shadow-name/2") + 2548 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-shadow-name/3") + 2549 (check-next-stream-line-equal _test-output-stream " {" "F - test-shadow-name/4") + 2550 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-shadow-name/5") + 2551 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %ecx" "F - test-shadow-name/6") + 2552 (check-next-stream-line-equal _test-output-stream " b9/copy-to-ecx 3/imm32" "F - test-shadow-name/7") + 2553 (check-next-stream-line-equal _test-output-stream " {" "F - test-shadow-name/8") + 2554 (check-next-stream-line-equal _test-output-stream "$foo:0x00000002:loop:" "F - test-shadow-name/9") + 2555 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %edx" "F - test-shadow-name/10") + 2556 (check-next-stream-line-equal _test-output-stream " ba/copy-to-edx 4/imm32" "F - test-shadow-name/11") + 2557 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %edx" "F - test-shadow-name/12") + 2558 (check-next-stream-line-equal _test-output-stream " }" "F - test-shadow-name/13") + 2559 (check-next-stream-line-equal _test-output-stream "$foo:0x00000002:break:" "F - test-shadow-name/14") + 2560 (check-next-stream-line-equal _test-output-stream " 41/increment-ecx" "F - test-shadow-name/15") + 2561 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %ecx" "F - test-shadow-name/16") + 2562 (check-next-stream-line-equal _test-output-stream " }" "F - test-shadow-name/17") + 2563 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-shadow-name/18") + 2564 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-shadow-name/19") + 2565 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-shadow-name/20") + 2566 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-shadow-name/21") + 2567 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-shadow-name/22") + 2568 # . epilogue + 2569 89/<- %esp 5/r32/ebp + 2570 5d/pop-to-ebp + 2571 c3/return + 2572 + 2573 test-shadow-name-2: + 2574 # . prologue + 2575 55/push-ebp + 2576 89/<- %ebp 4/r32/esp + 2577 # setup + 2578 (clear-stream _test-input-stream) + 2579 (clear-stream $_test-input-buffered-file->buffer) + 2580 (clear-stream _test-output-stream) + 2581 (clear-stream $_test-output-buffered-file->buffer) + 2582 # + 2583 (write _test-input-stream "fn foo {\n") + 2584 (write _test-input-stream " var x/ecx: int <- copy 3\n") + 2585 (write _test-input-stream " {\n") + 2586 (write _test-input-stream " var x/edx: int <- copy 4\n") + 2587 (write _test-input-stream " var y/ecx: int <- copy 5\n") + 2588 (write _test-input-stream " }\n") + 2589 (write _test-input-stream " x <- increment\n") + 2590 (write _test-input-stream "}\n") + 2591 # convert + 2592 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) + 2593 (flush _test-output-buffered-file) + 2594 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- + 2600 # check output + 2601 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-shadow-name-2/0") + 2602 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-shadow-name-2/1") + 2603 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-shadow-name-2/2") + 2604 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-shadow-name-2/3") + 2605 (check-next-stream-line-equal _test-output-stream " {" "F - test-shadow-name-2/4") + 2606 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-shadow-name-2/5") + 2607 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %ecx" "F - test-shadow-name-2/6") + 2608 (check-next-stream-line-equal _test-output-stream " b9/copy-to-ecx 3/imm32" "F - test-shadow-name-2/7") + 2609 (check-next-stream-line-equal _test-output-stream " {" "F - test-shadow-name-2/8") + 2610 (check-next-stream-line-equal _test-output-stream "$foo:0x00000002:loop:" "F - test-shadow-name-2/9") + 2611 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %edx" "F - test-shadow-name-2/10") + 2612 (check-next-stream-line-equal _test-output-stream " ba/copy-to-edx 4/imm32" "F - test-shadow-name-2/11") + 2613 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %ecx" "F - test-shadow-name-2/12") + 2614 (check-next-stream-line-equal _test-output-stream " b9/copy-to-ecx 5/imm32" "F - test-shadow-name-2/13") + 2615 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %ecx" "F - test-shadow-name-2/14") + 2616 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %edx" "F - test-shadow-name-2/15") + 2617 (check-next-stream-line-equal _test-output-stream " }" "F - test-shadow-name-2/16") + 2618 (check-next-stream-line-equal _test-output-stream "$foo:0x00000002:break:" "F - test-shadow-name-2/17") + 2619 (check-next-stream-line-equal _test-output-stream " 41/increment-ecx" "F - test-shadow-name-2/18") + 2620 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %ecx" "F - test-shadow-name-2/19") + 2621 (check-next-stream-line-equal _test-output-stream " }" "F - test-shadow-name-2/20") + 2622 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-shadow-name-2/21") + 2623 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-shadow-name-2/22") + 2624 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-shadow-name-2/23") + 2625 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-shadow-name-2/24") + 2626 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-shadow-name-2/25") + 2627 # . epilogue + 2628 89/<- %esp 5/r32/ebp + 2629 5d/pop-to-ebp + 2630 c3/return + 2631 + 2632 test-do-not-spill-same-register-in-block: + 2633 # . prologue + 2634 55/push-ebp + 2635 89/<- %ebp 4/r32/esp + 2636 # setup + 2637 (clear-stream _test-input-stream) + 2638 (clear-stream $_test-input-buffered-file->buffer) + 2639 (clear-stream _test-output-stream) + 2640 (clear-stream $_test-output-buffered-file->buffer) + 2641 # + 2642 (write _test-input-stream "fn foo {\n") + 2643 (write _test-input-stream " var x/ecx: int <- copy 3\n") + 2644 (write _test-input-stream " var y/ecx: int <- copy 4\n") + 2645 (write _test-input-stream " y <- increment\n") + 2646 (write _test-input-stream "}\n") + 2647 # convert + 2648 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) + 2649 (flush _test-output-buffered-file) + 2650 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- + 2656 # check output + 2657 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-do-not-spill-same-register-in-block/0") + 2658 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-do-not-spill-same-register-in-block/1") + 2659 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-do-not-spill-same-register-in-block/2") + 2660 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-do-not-spill-same-register-in-block/3") + 2661 (check-next-stream-line-equal _test-output-stream " {" "F - test-do-not-spill-same-register-in-block/4") + 2662 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-do-not-spill-same-register-in-block/5") + 2663 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %ecx" "F - test-do-not-spill-same-register-in-block/6") + 2664 (check-next-stream-line-equal _test-output-stream " b9/copy-to-ecx 3/imm32" "F - test-do-not-spill-same-register-in-block/7") + 2665 (check-next-stream-line-equal _test-output-stream " b9/copy-to-ecx 4/imm32" "F - test-do-not-spill-same-register-in-block/8") + 2666 (check-next-stream-line-equal _test-output-stream " 41/increment-ecx" "F - test-do-not-spill-same-register-in-block/9") + 2667 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %ecx" "F - test-do-not-spill-same-register-in-block/10") + 2668 (check-next-stream-line-equal _test-output-stream " }" "F - test-do-not-spill-same-register-in-block/11") + 2669 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-do-not-spill-same-register-in-block/12") + 2670 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-do-not-spill-same-register-in-block/13") + 2671 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-do-not-spill-same-register-in-block/14") + 2672 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-do-not-spill-same-register-in-block/15") + 2673 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-do-not-spill-same-register-in-block/16") + 2674 # . epilogue + 2675 89/<- %esp 5/r32/ebp + 2676 5d/pop-to-ebp + 2677 c3/return + 2678 + 2679 test-spill-different-register-in-block: + 2680 # . prologue + 2681 55/push-ebp + 2682 89/<- %ebp 4/r32/esp + 2683 # setup + 2684 (clear-stream _test-input-stream) + 2685 (clear-stream $_test-input-buffered-file->buffer) + 2686 (clear-stream _test-output-stream) + 2687 (clear-stream $_test-output-buffered-file->buffer) + 2688 # + 2689 (write _test-input-stream "fn foo {\n") + 2690 (write _test-input-stream " var x/eax: int <- copy 3\n") + 2691 (write _test-input-stream " var y/ecx: int <- copy 4\n") + 2692 (write _test-input-stream " y <- increment\n") + 2693 (write _test-input-stream "}\n") + 2694 # convert + 2695 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) + 2696 (flush _test-output-buffered-file) + 2697 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- + 2703 # check output + 2704 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-spill-different-register-in-block/0") + 2705 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-spill-different-register-in-block/1") + 2706 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-spill-different-register-in-block/2") + 2707 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-spill-different-register-in-block/3") + 2708 (check-next-stream-line-equal _test-output-stream " {" "F - test-spill-different-register-in-block/4") + 2709 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-spill-different-register-in-block/5") + 2710 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %eax" "F - test-spill-different-register-in-block/6") + 2711 (check-next-stream-line-equal _test-output-stream " b8/copy-to-eax 3/imm32" "F - test-spill-different-register-in-block/7") + 2712 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %ecx" "F - test-spill-different-register-in-block/8") + 2713 (check-next-stream-line-equal _test-output-stream " b9/copy-to-ecx 4/imm32" "F - test-spill-different-register-in-block/9") + 2714 (check-next-stream-line-equal _test-output-stream " 41/increment-ecx" "F - test-spill-different-register-in-block/10") + 2715 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %ecx" "F - test-spill-different-register-in-block/11") + 2716 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %eax" "F - test-spill-different-register-in-block/12") + 2717 (check-next-stream-line-equal _test-output-stream " }" "F - test-spill-different-register-in-block/13") + 2718 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-spill-different-register-in-block/14") + 2719 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-spill-different-register-in-block/15") + 2720 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-spill-different-register-in-block/16") + 2721 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-spill-different-register-in-block/17") + 2722 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-spill-different-register-in-block/18") + 2723 # . epilogue + 2724 89/<- %esp 5/r32/ebp + 2725 5d/pop-to-ebp + 2726 c3/return + 2727 + 2728 test-shadow-live-output: + 2729 # . prologue + 2730 55/push-ebp + 2731 89/<- %ebp 4/r32/esp + 2732 # setup + 2733 (clear-stream _test-input-stream) + 2734 (clear-stream $_test-input-buffered-file->buffer) + 2735 (clear-stream _test-output-stream) + 2736 (clear-stream $_test-output-buffered-file->buffer) + 2737 # + 2738 (write _test-input-stream "fn foo -> x/ecx: int {\n") + 2739 (write _test-input-stream " x <- copy 3\n") + 2740 (write _test-input-stream " {\n") + 2741 (write _test-input-stream " var y/ecx: int <- copy 4\n") + 2742 (write _test-input-stream " }\n") + 2743 (write _test-input-stream " x <- increment\n") + 2744 (write _test-input-stream "}\n") + 2745 # convert + 2746 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) + 2747 (flush _test-output-buffered-file) + 2748 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- + 2754 # check output + 2755 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-shadow-live-output/0") + 2756 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-shadow-live-output/1") + 2757 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-shadow-live-output/2") + 2758 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-shadow-live-output/3") + 2759 (check-next-stream-line-equal _test-output-stream " {" "F - test-shadow-live-output/4") + 2760 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-shadow-live-output/5") + 2761 (check-next-stream-line-equal _test-output-stream " b9/copy-to-ecx 3/imm32" "F - test-shadow-live-output/7") # no push because it's an output reg + 2762 (check-next-stream-line-equal _test-output-stream " {" "F - test-shadow-live-output/8") + 2763 (check-next-stream-line-equal _test-output-stream "$foo:0x00000002:loop:" "F - test-shadow-live-output/9") + 2764 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %ecx" "F - test-shadow-live-output/10") + 2765 (check-next-stream-line-equal _test-output-stream " b9/copy-to-ecx 4/imm32" "F - test-shadow-live-output/11") + 2766 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %ecx" "F - test-shadow-live-output/12") + 2767 (check-next-stream-line-equal _test-output-stream " }" "F - test-shadow-live-output/13") + 2768 (check-next-stream-line-equal _test-output-stream "$foo:0x00000002:break:" "F - test-shadow-live-output/14") + 2769 (check-next-stream-line-equal _test-output-stream " 41/increment-ecx" "F - test-shadow-live-output/15") + 2770 (check-next-stream-line-equal _test-output-stream " }" "F - test-shadow-live-output/17") + 2771 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-shadow-live-output/18") + 2772 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-shadow-live-output/19") + 2773 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-shadow-live-output/20") + 2774 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-shadow-live-output/21") + 2775 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-shadow-live-output/21") + 2776 # . epilogue + 2777 89/<- %esp 5/r32/ebp + 2778 5d/pop-to-ebp + 2779 c3/return + 2780 + 2781 test-stmt-defines-output-in-same-register-as-inout: + 2782 # . prologue + 2783 55/push-ebp + 2784 89/<- %ebp 4/r32/esp + 2785 # setup + 2786 (clear-stream _test-input-stream) + 2787 (clear-stream $_test-input-buffered-file->buffer) + 2788 (clear-stream _test-output-stream) + 2789 (clear-stream $_test-output-buffered-file->buffer) + 2790 (clear-stream _test-error-stream) + 2791 (clear-stream $_test-error-buffered-file->buffer) + 2792 # var ed/edx: exit-descriptor = tailor-exit-descriptor(16) + 2793 68/push 0/imm32 + 2794 68/push 0/imm32 + 2795 89/<- %edx 4/r32/esp + 2796 (tailor-exit-descriptor %edx 0x10) + 2797 # + 2798 (write _test-input-stream "fn foo -> x/ecx: int {\n") + 2799 (write _test-input-stream " var y/ecx: int <- copy 4\n") + 2800 (write _test-input-stream " x <- copy y\n") # writing to a fn output is currently the only way for a statement to define a new var + 2801 (write _test-input-stream "}\n") + 2802 # convert + 2803 (convert-mu _test-input-buffered-file _test-output-buffered-file _test-error-buffered-file %edx) + 2804 # registers except esp clobbered at this point + 2805 # restore ed + 2806 89/<- %edx 4/r32/esp + 2807 (flush _test-output-buffered-file) + 2808 (flush _test-error-buffered-file) + 2809 +-- 6 lines: #? # dump _test-error-stream ------------------------------------------------------------------------------------------------------------------------------------------ + 2815 # no error; we looked up 'y' correctly before pushing the binding for 'x' + 2816 (check-stream-equal _test-error-stream "" "F - test-stmt-defines-output-in-same-register-as-inout: error stream should be empty") + 2817 # don't bother checking the generated code; that's in the test 'test-local-clobbered-by-fn-output' below + 2818 # don't restore from ebp + 2819 81 0/subop/add %esp 8/imm32 + 2820 # . epilogue + 2821 5d/pop-to-ebp + 2822 c3/return + 2823 + 2824 test-local-clobbered-by-fn-output: + 2825 # . prologue + 2826 55/push-ebp + 2827 89/<- %ebp 4/r32/esp + 2828 # setup + 2829 (clear-stream _test-input-stream) + 2830 (clear-stream $_test-input-buffered-file->buffer) + 2831 (clear-stream _test-output-stream) + 2832 (clear-stream $_test-output-buffered-file->buffer) + 2833 # + 2834 (write _test-input-stream "fn foo -> x/ecx: int {\n") + 2835 (write _test-input-stream " var y/ecx: int <- copy 4\n") + 2836 (write _test-input-stream " x <- copy y\n") + 2837 (write _test-input-stream "}\n") + 2838 # convert + 2839 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) + 2840 (flush _test-output-buffered-file) + 2841 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- + 2847 # check output + 2848 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-local-clobbered-by-fn-output/0") + 2849 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-local-clobbered-by-fn-output/1") + 2850 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-local-clobbered-by-fn-output/2") + 2851 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-local-clobbered-by-fn-output/3") + 2852 (check-next-stream-line-equal _test-output-stream " {" "F - test-local-clobbered-by-fn-output/4") + 2853 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-local-clobbered-by-fn-output/5") + 2854 (check-next-stream-line-equal _test-output-stream " b9/copy-to-ecx 4/imm32" "F - test-local-clobbered-by-fn-output/6") # no push because it's an output reg + 2855 (check-next-stream-line-equal _test-output-stream " 89/<- %ecx 0x00000001/r32" "F - test-local-clobbered-by-fn-output/7") + 2856 (check-next-stream-line-equal _test-output-stream " }" "F - test-local-clobbered-by-fn-output/8") + 2857 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-local-clobbered-by-fn-output/9") + 2858 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-local-clobbered-by-fn-output/10") + 2859 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-local-clobbered-by-fn-output/11") + 2860 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-local-clobbered-by-fn-output/12") + 2861 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-local-clobbered-by-fn-output/13") + 2862 # . epilogue + 2863 89/<- %esp 5/r32/ebp + 2864 5d/pop-to-ebp + 2865 c3/return + 2866 + 2867 test-read-output: + 2868 # . prologue + 2869 55/push-ebp + 2870 89/<- %ebp 4/r32/esp + 2871 # setup + 2872 (clear-stream _test-input-stream) + 2873 (clear-stream $_test-input-buffered-file->buffer) + 2874 (clear-stream _test-output-stream) + 2875 (clear-stream $_test-output-buffered-file->buffer) + 2876 # + 2877 (write _test-input-stream "fn foo -> x/ecx: int {\n") + 2878 (write _test-input-stream " x <- copy 0x34\n") + 2879 (write _test-input-stream " compare x, 0x35\n") + 2880 (write _test-input-stream "}\n") + 2881 # convert + 2882 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) + 2883 (flush _test-output-buffered-file) + 2884 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- + 2890 # check output + 2891 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-read-output/0") + 2892 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-read-output/1") + 2893 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-read-output/2") + 2894 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-read-output/3") + 2895 (check-next-stream-line-equal _test-output-stream " {" "F - test-read-output/4") + 2896 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-read-output/5") + 2897 (check-next-stream-line-equal _test-output-stream " b9/copy-to-ecx 0x34/imm32" "F - test-read-output/6") + 2898 (check-next-stream-line-equal _test-output-stream " 81 7/subop/compare %ecx 0x35/imm32" "F - test-read-output/7") + 2899 (check-next-stream-line-equal _test-output-stream " }" "F - test-read-output/8") + 2900 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-read-output/9") + 2901 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-read-output/10") + 2902 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-read-output/11") + 2903 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-read-output/12") + 2904 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-read-output/13") + 2905 # . epilogue + 2906 89/<- %esp 5/r32/ebp + 2907 5d/pop-to-ebp + 2908 c3/return + 2909 + 2910 test-fn-output-written-in-inner-block: + 2911 # . prologue + 2912 55/push-ebp + 2913 89/<- %ebp 4/r32/esp + 2914 # setup + 2915 (clear-stream _test-input-stream) + 2916 (clear-stream $_test-input-buffered-file->buffer) + 2917 (clear-stream _test-output-stream) + 2918 (clear-stream $_test-output-buffered-file->buffer) + 2919 # + 2920 (write _test-input-stream "fn foo -> out/edi: int {\n") + 2921 (write _test-input-stream " var a/eax: int <- copy 3\n") # define outer local + 2922 (write _test-input-stream " {\n") + 2923 (write _test-input-stream " var a/ecx: int <- copy 4\n") # shadow outer local + 2924 (write _test-input-stream " out <- copy a\n") # write to fn output + 2925 (write _test-input-stream " }\n") + 2926 (write _test-input-stream " compare a, 0\n") # use outer local + 2927 (write _test-input-stream "}\n") + 2928 # convert + 2929 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) + 2930 (flush _test-output-buffered-file) + 2931 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- + 2937 # no error; defining 'out' didn't interfere with the reclamation of 'b' + 2938 # check output + 2939 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-fn-output-written-in-inner-block/0") + 2940 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-fn-output-written-in-inner-block/1") + 2941 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-fn-output-written-in-inner-block/2") + 2942 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-fn-output-written-in-inner-block/3") + 2943 (check-next-stream-line-equal _test-output-stream " {" "F - test-fn-output-written-in-inner-block/4") + 2944 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-fn-output-written-in-inner-block/5") + 2945 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %eax" "F - test-fn-output-written-in-inner-block/6") + 2946 (check-next-stream-line-equal _test-output-stream " b8/copy-to-eax 3/imm32" "F - test-fn-output-written-in-inner-block/7") + 2947 (check-next-stream-line-equal _test-output-stream " {" "F - test-fn-output-written-in-inner-block/8") + 2948 (check-next-stream-line-equal _test-output-stream "$foo:0x00000002:loop:" "F - test-fn-output-written-in-inner-block/9") + 2949 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %ecx" "F - test-fn-output-written-in-inner-block/10") + 2950 (check-next-stream-line-equal _test-output-stream " b9/copy-to-ecx 4/imm32" "F - test-fn-output-written-in-inner-block/10") + 2951 (check-next-stream-line-equal _test-output-stream " 89/<- %edi 0x00000001/r32" "F - test-fn-output-written-in-inner-block/11") + 2952 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %ecx" "F - test-fn-output-written-in-inner-block/12") + 2953 (check-next-stream-line-equal _test-output-stream " }" "F - test-fn-output-written-in-inner-block/13") + 2954 (check-next-stream-line-equal _test-output-stream "$foo:0x00000002:break:" "F - test-fn-output-written-in-inner-block/14") + 2955 (check-next-stream-line-equal _test-output-stream " 3d/compare-eax-with 0/imm32" "F - test-fn-output-written-in-inner-block/15") + 2956 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %eax" "F - test-fn-output-written-in-inner-block/16") + 2957 (check-next-stream-line-equal _test-output-stream " }" "F - test-fn-output-written-in-inner-block/17") + 2958 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-fn-output-written-in-inner-block/18") + 2959 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-fn-output-written-in-inner-block/19") + 2960 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-fn-output-written-in-inner-block/20") + 2961 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-fn-output-written-in-inner-block/21") + 2962 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-fn-output-written-in-inner-block/22") + 2963 # . epilogue + 2964 89/<- %esp 5/r32/ebp + 2965 5d/pop-to-ebp + 2966 c3/return + 2967 + 2968 test-convert-function-with-branches-in-block: + 2969 # . prologue + 2970 55/push-ebp + 2971 89/<- %ebp 4/r32/esp + 2972 # setup + 2973 (clear-stream _test-input-stream) + 2974 (clear-stream $_test-input-buffered-file->buffer) + 2975 (clear-stream _test-output-stream) + 2976 (clear-stream $_test-output-buffered-file->buffer) + 2977 # + 2978 (write _test-input-stream "fn foo x: int {\n") + 2979 (write _test-input-stream " {\n") + 2980 (write _test-input-stream " break-if->=\n") + 2981 (write _test-input-stream " loop-if-addr<\n") + 2982 (write _test-input-stream " increment x\n") + 2983 (write _test-input-stream " loop\n") + 2984 (write _test-input-stream " }\n") + 2985 (write _test-input-stream "}\n") + 2986 # convert + 2987 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) + 2988 (flush _test-output-buffered-file) + 2989 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- + 2995 # check output + 2996 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-function-with-branches-in-block/0") + 2997 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-function-with-branches-in-block/1") + 2998 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-function-with-branches-in-block/2") + 2999 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-function-with-branches-in-block/3") + 3000 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-branches-in-block/4") + 3001 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-function-with-branches-in-block/5") + 3002 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-branches-in-block/6") + 3003 (check-next-stream-line-equal _test-output-stream "$foo:0x00000002:loop:" "F - test-convert-function-with-branches-in-block/7") + 3004 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-branches-in-block/8") + 3005 (check-next-stream-line-equal _test-output-stream " 0f 8c/jump-if-< break/disp32" "F - test-convert-function-with-branches-in-block/9") + 3006 (check-next-stream-line-equal _test-output-stream " e9/jump $foo:0x00000002:break/disp32" "F - test-convert-function-with-branches-in-block/10") + 3007 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-branches-in-block/11") + 3008 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-branches-in-block/12") + 3009 (check-next-stream-line-equal _test-output-stream " 0f 83/jump-if-addr>= break/disp32" "F - test-convert-function-with-branches-in-block/13") + 3010 (check-next-stream-line-equal _test-output-stream " e9/jump $foo:0x00000002:loop/disp32" "F - test-convert-function-with-branches-in-block/14") + 3011 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-branches-in-block/15") + 3012 (check-next-stream-line-equal _test-output-stream " ff 0/subop/increment *(ebp+0x00000008)" "F - test-convert-function-with-branches-in-block/16") + 3013 (check-next-stream-line-equal _test-output-stream " e9/jump loop/disp32" "F - test-convert-function-with-branches-in-block/17") + 3014 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-branches-in-block/18") + 3015 (check-next-stream-line-equal _test-output-stream "$foo:0x00000002:break:" "F - test-convert-function-with-branches-in-block/19") + 3016 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-branches-in-block/20") + 3017 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-function-with-branches-in-block/21") + 3018 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-function-with-branches-in-block/22") + 3019 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-function-with-branches-in-block/23") + 3020 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-function-with-branches-in-block/24") + 3021 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-function-with-branches-in-block/25") + 3022 # . epilogue + 3023 89/<- %esp 5/r32/ebp + 3024 5d/pop-to-ebp + 3025 c3/return + 3026 + 3027 test-convert-function-with-branches-in-named-block: + 3028 # . prologue + 3029 55/push-ebp + 3030 89/<- %ebp 4/r32/esp + 3031 # setup + 3032 (clear-stream _test-input-stream) + 3033 (clear-stream $_test-input-buffered-file->buffer) + 3034 (clear-stream _test-output-stream) + 3035 (clear-stream $_test-output-buffered-file->buffer) + 3036 # + 3037 (write _test-input-stream "fn foo x: int {\n") + 3038 (write _test-input-stream " $bar: {\n") + 3039 (write _test-input-stream " break-if->= $bar\n") + 3040 (write _test-input-stream " loop-if-addr< $bar\n") + 3041 (write _test-input-stream " increment x\n") + 3042 (write _test-input-stream " loop\n") + 3043 (write _test-input-stream " }\n") + 3044 (write _test-input-stream "}\n") + 3045 # convert + 3046 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) + 3047 (flush _test-output-buffered-file) + 3048 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- + 3054 # check output + 3055 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-function-with-branches-in-named-block/0") + 3056 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-function-with-branches-in-named-block/1") + 3057 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-function-with-branches-in-named-block/2") + 3058 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-function-with-branches-in-named-block/3") + 3059 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-branches-in-named-block/4") + 3060 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-function-with-branches-in-named-block/5") + 3061 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-branches-in-named-block/6") + 3062 (check-next-stream-line-equal _test-output-stream "$bar:loop:" "F - test-convert-function-with-branches-in-named-block/7") + 3063 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-branches-in-named-block/8") + 3064 (check-next-stream-line-equal _test-output-stream " 0f 8c/jump-if-< break/disp32" "F - test-convert-function-with-branches-in-named-block/9") + 3065 (check-next-stream-line-equal _test-output-stream " e9/jump $bar:break/disp32" "F - test-convert-function-with-branches-in-named-block/10") + 3066 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-branches-in-named-block/11") + 3067 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-branches-in-named-block/12") + 3068 (check-next-stream-line-equal _test-output-stream " 0f 83/jump-if-addr>= break/disp32" "F - test-convert-function-with-branches-in-named-block/13") + 3069 (check-next-stream-line-equal _test-output-stream " e9/jump $bar:loop/disp32" "F - test-convert-function-with-branches-in-named-block/14") + 3070 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-branches-in-named-block/15") + 3071 (check-next-stream-line-equal _test-output-stream " ff 0/subop/increment *(ebp+0x00000008)" "F - test-convert-function-with-branches-in-named-block/16") + 3072 (check-next-stream-line-equal _test-output-stream " e9/jump loop/disp32" "F - test-convert-function-with-branches-in-named-block/17") + 3073 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-branches-in-named-block/18") + 3074 (check-next-stream-line-equal _test-output-stream "$bar:break:" "F - test-convert-function-with-branches-in-named-block/19") + 3075 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-branches-in-named-block/20") + 3076 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-function-with-branches-in-named-block/21") + 3077 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-function-with-branches-in-named-block/22") + 3078 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-function-with-branches-in-named-block/23") + 3079 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-function-with-branches-in-named-block/24") + 3080 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-function-with-branches-in-named-block/25") + 3081 # . epilogue + 3082 89/<- %esp 5/r32/ebp + 3083 5d/pop-to-ebp + 3084 c3/return + 3085 + 3086 test-convert-function-with-var-in-nested-block: + 3087 # . prologue + 3088 55/push-ebp + 3089 89/<- %ebp 4/r32/esp + 3090 # setup + 3091 (clear-stream _test-input-stream) + 3092 (clear-stream $_test-input-buffered-file->buffer) + 3093 (clear-stream _test-output-stream) + 3094 (clear-stream $_test-output-buffered-file->buffer) + 3095 # + 3096 (write _test-input-stream "fn foo x: int {\n") + 3097 (write _test-input-stream " {\n") + 3098 (write _test-input-stream " {\n") + 3099 (write _test-input-stream " var x: int\n") + 3100 (write _test-input-stream " increment x\n") + 3101 (write _test-input-stream " }\n") + 3102 (write _test-input-stream " }\n") + 3103 (write _test-input-stream "}\n") + 3104 # convert + 3105 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) + 3106 (flush _test-output-buffered-file) + 3107 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- + 3113 # check output + 3114 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-function-with-var-in-nested-block/0") + 3115 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-function-with-var-in-nested-block/1") + 3116 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-function-with-var-in-nested-block/2") + 3117 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-function-with-var-in-nested-block/3") + 3118 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-var-in-nested-block/4") + 3119 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-function-with-var-in-nested-block/5") + 3120 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-var-in-nested-block/6") + 3121 (check-next-stream-line-equal _test-output-stream "$foo:0x00000002:loop:" "F - test-convert-function-with-var-in-nested-block/7") + 3122 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-var-in-nested-block/8") + 3123 (check-next-stream-line-equal _test-output-stream "$foo:0x00000003:loop:" "F - test-convert-function-with-var-in-nested-block/9") + 3124 (check-next-stream-line-equal _test-output-stream " 68/push 0/imm32" "F - test-convert-function-with-var-in-nested-block/10") + 3125 (check-next-stream-line-equal _test-output-stream " ff 0/subop/increment *(ebp+0xfffffffc)" "F - test-convert-function-with-var-in-nested-block/11") + 3126 (check-next-stream-line-equal _test-output-stream " 81 0/subop/add %esp 0x00000004/imm32" "F - test-convert-function-with-var-in-nested-block/12") + 3127 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-var-in-nested-block/13") + 3128 (check-next-stream-line-equal _test-output-stream "$foo:0x00000003:break:" "F - test-convert-function-with-var-in-nested-block/14") + 3129 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-var-in-nested-block/15") + 3130 (check-next-stream-line-equal _test-output-stream "$foo:0x00000002:break:" "F - test-convert-function-with-var-in-nested-block/16") + 3131 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-var-in-nested-block/17") + 3132 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-function-with-var-in-nested-block/18") + 3133 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-function-with-var-in-nested-block/19") + 3134 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-function-with-var-in-nested-block/20") + 3135 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-function-with-var-in-nested-block/21") + 3136 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-function-with-var-in-nested-block/22") + 3137 # . epilogue + 3138 89/<- %esp 5/r32/ebp + 3139 5d/pop-to-ebp + 3140 c3/return + 3141 + 3142 test-convert-function-with-multiple-vars-in-nested-blocks: + 3143 # . prologue + 3144 55/push-ebp + 3145 89/<- %ebp 4/r32/esp + 3146 # setup + 3147 (clear-stream _test-input-stream) + 3148 (clear-stream $_test-input-buffered-file->buffer) + 3149 (clear-stream _test-output-stream) + 3150 (clear-stream $_test-output-buffered-file->buffer) + 3151 # + 3152 (write _test-input-stream "fn foo x: int {\n") + 3153 (write _test-input-stream " {\n") + 3154 (write _test-input-stream " var x/eax: int <- copy 0\n") + 3155 (write _test-input-stream " {\n") + 3156 (write _test-input-stream " var y: int\n") + 3157 (write _test-input-stream " x <- add y\n") + 3158 (write _test-input-stream " }\n") + 3159 (write _test-input-stream " }\n") + 3160 (write _test-input-stream "}\n") + 3161 # convert + 3162 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) + 3163 (flush _test-output-buffered-file) + 3164 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- + 3170 # check output + 3171 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-function-with-multiple-vars-in-nested-blocks/0") + 3172 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-function-with-multiple-vars-in-nested-blocks/1") + 3173 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-function-with-multiple-vars-in-nested-blocks/2") + 3174 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-function-with-multiple-vars-in-nested-blocks/3") + 3175 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-multiple-vars-in-nested-blocks/4") + 3176 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-function-with-multiple-vars-in-nested-blocks/5") + 3177 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-multiple-vars-in-nested-blocks/6") + 3178 (check-next-stream-line-equal _test-output-stream "$foo:0x00000002:loop:" "F - test-convert-function-with-multiple-vars-in-nested-blocks/7") + 3179 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %eax" "F - test-convert-function-with-multiple-vars-in-nested-blocks/8") + 3180 (check-next-stream-line-equal _test-output-stream " b8/copy-to-eax 0/imm32" "F - test-convert-function-with-multiple-vars-in-nested-blocks/9") + 3181 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-multiple-vars-in-nested-blocks/10") + 3182 (check-next-stream-line-equal _test-output-stream "$foo:0x00000003:loop:" "F - test-convert-function-with-multiple-vars-in-nested-blocks/11") + 3183 (check-next-stream-line-equal _test-output-stream " 68/push 0/imm32" "F - test-convert-function-with-multiple-vars-in-nested-blocks/12") + 3184 (check-next-stream-line-equal _test-output-stream " 03/add *(ebp+0xfffffff8) 0x00000000/r32" "F - test-convert-function-with-multiple-vars-in-nested-blocks/13") + 3185 (check-next-stream-line-equal _test-output-stream " 81 0/subop/add %esp 0x00000004/imm32" "F - test-convert-function-with-multiple-vars-in-nested-blocks/14") + 3186 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-multiple-vars-in-nested-blocks/15") + 3187 (check-next-stream-line-equal _test-output-stream "$foo:0x00000003:break:" "F - test-convert-function-with-multiple-vars-in-nested-blocks/16") + 3188 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %eax" "F - test-convert-function-with-multiple-vars-in-nested-blocks/17") + 3189 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-multiple-vars-in-nested-blocks/18") + 3190 (check-next-stream-line-equal _test-output-stream "$foo:0x00000002:break:" "F - test-convert-function-with-multiple-vars-in-nested-blocks/19") + 3191 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-multiple-vars-in-nested-blocks/20") + 3192 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-function-with-multiple-vars-in-nested-blocks/21") + 3193 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-function-with-multiple-vars-in-nested-blocks/22") + 3194 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-function-with-multiple-vars-in-nested-blocks/23") + 3195 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-function-with-multiple-vars-in-nested-blocks/24") + 3196 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-function-with-multiple-vars-in-nested-blocks/25") + 3197 # . epilogue + 3198 89/<- %esp 5/r32/ebp + 3199 5d/pop-to-ebp + 3200 c3/return + 3201 + 3202 test-convert-function-with-branches-and-local-vars: + 3203 # A conditional 'break' after a 'var' in a block is converted into a + 3204 # nested block that performs all necessary cleanup before jumping. This + 3205 # results in some ugly code duplication. + 3206 # . prologue + 3207 55/push-ebp + 3208 89/<- %ebp 4/r32/esp + 3209 # setup + 3210 (clear-stream _test-input-stream) + 3211 (clear-stream $_test-input-buffered-file->buffer) + 3212 (clear-stream _test-output-stream) + 3213 (clear-stream $_test-output-buffered-file->buffer) + 3214 # + 3215 (write _test-input-stream "fn foo {\n") + 3216 (write _test-input-stream " {\n") + 3217 (write _test-input-stream " var x: int\n") + 3218 (write _test-input-stream " break-if->=\n") + 3219 (write _test-input-stream " increment x\n") + 3220 (write _test-input-stream " }\n") + 3221 (write _test-input-stream "}\n") + 3222 # convert + 3223 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) + 3224 (flush _test-output-buffered-file) + 3225 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- + 3231 # check output + 3232 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-function-with-branches-and-local-vars/0") + 3233 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-function-with-branches-and-local-vars/1") + 3234 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-function-with-branches-and-local-vars/2") + 3235 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-function-with-branches-and-local-vars/3") + 3236 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-branches-and-local-vars/4") + 3237 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-function-with-branches-and-local-vars/5") + 3238 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-branches-and-local-vars/6") + 3239 (check-next-stream-line-equal _test-output-stream "$foo:0x00000002:loop:" "F - test-convert-function-with-branches-and-local-vars/7") + 3240 (check-next-stream-line-equal _test-output-stream " 68/push 0/imm32" "F - test-convert-function-with-branches-and-local-vars/8") + 3241 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-branches-and-local-vars/9") + 3242 (check-next-stream-line-equal _test-output-stream " 0f 8c/jump-if-< break/disp32" "F - test-convert-function-with-branches-and-local-vars/10") + 3243 (check-next-stream-line-equal _test-output-stream " 81 0/subop/add %esp 0x00000004/imm32" "F - test-convert-function-with-branches-and-local-vars/11") + 3244 (check-next-stream-line-equal _test-output-stream " e9/jump $foo:0x00000002:break/disp32" "F - test-convert-function-with-branches-and-local-vars/12") + 3245 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-branches-and-local-vars/13") + 3246 (check-next-stream-line-equal _test-output-stream " ff 0/subop/increment *(ebp+0xfffffffc)" "F - test-convert-function-with-branches-and-local-vars/14") + 3247 (check-next-stream-line-equal _test-output-stream " 81 0/subop/add %esp 0x00000004/imm32" "F - test-convert-function-with-branches-and-local-vars/15") + 3248 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-branches-and-local-vars/16") + 3249 (check-next-stream-line-equal _test-output-stream "$foo:0x00000002:break:" "F - test-convert-function-with-branches-and-local-vars/17") + 3250 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-branches-and-local-vars/18") + 3251 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-function-with-branches-and-local-vars/19") + 3252 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-function-with-branches-and-local-vars/20") + 3253 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-function-with-branches-and-local-vars/21") + 3254 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-function-with-branches-and-local-vars/22") + 3255 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-function-with-branches-and-local-vars/23") + 3256 # . epilogue + 3257 89/<- %esp 5/r32/ebp + 3258 5d/pop-to-ebp + 3259 c3/return + 3260 + 3261 test-convert-function-with-conditional-loops-and-local-vars: + 3262 # A conditional 'loop' after a 'var' in a block is converted into a nested + 3263 # block that performs all necessary cleanup before jumping. This results + 3264 # in some ugly code duplication. + 3265 # . prologue + 3266 55/push-ebp + 3267 89/<- %ebp 4/r32/esp + 3268 # setup + 3269 (clear-stream _test-input-stream) + 3270 (clear-stream $_test-input-buffered-file->buffer) + 3271 (clear-stream _test-output-stream) + 3272 (clear-stream $_test-output-buffered-file->buffer) + 3273 # + 3274 (write _test-input-stream "fn foo {\n") + 3275 (write _test-input-stream " {\n") + 3276 (write _test-input-stream " var x: int\n") + 3277 (write _test-input-stream " loop-if->=\n") + 3278 (write _test-input-stream " increment x\n") + 3279 (write _test-input-stream " }\n") + 3280 (write _test-input-stream "}\n") + 3281 # convert + 3282 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) + 3283 (flush _test-output-buffered-file) + 3284 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- + 3290 # check output + 3291 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-function-with-conditional-loops-and-local-vars/0") + 3292 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-function-with-conditional-loops-and-local-vars/1") + 3293 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-function-with-conditional-loops-and-local-vars/2") + 3294 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-function-with-conditional-loops-and-local-vars/3") + 3295 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-conditional-loops-and-local-vars/4") + 3296 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-function-with-conditional-loops-and-local-vars/5") + 3297 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-conditional-loops-and-local-vars/6") + 3298 (check-next-stream-line-equal _test-output-stream "$foo:0x00000002:loop:" "F - test-convert-function-with-conditional-loops-and-local-vars/7") + 3299 (check-next-stream-line-equal _test-output-stream " 68/push 0/imm32" "F - test-convert-function-with-conditional-loops-and-local-vars/8") + 3300 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-conditional-loops-and-local-vars/9") + 3301 (check-next-stream-line-equal _test-output-stream " 0f 8c/jump-if-< break/disp32" "F - test-convert-function-with-conditional-loops-and-local-vars/10") + 3302 (check-next-stream-line-equal _test-output-stream " 81 0/subop/add %esp 0x00000004/imm32" "F - test-convert-function-with-conditional-loops-and-local-vars/11") + 3303 (check-next-stream-line-equal _test-output-stream " e9/jump $foo:0x00000002:loop/disp32" "F - test-convert-function-with-conditional-loops-and-local-vars/12") + 3304 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-conditional-loops-and-local-vars/13") + 3305 (check-next-stream-line-equal _test-output-stream " ff 0/subop/increment *(ebp+0xfffffffc)" "F - test-convert-function-with-conditional-loops-and-local-vars/14") + 3306 (check-next-stream-line-equal _test-output-stream " 81 0/subop/add %esp 0x00000004/imm32" "F - test-convert-function-with-conditional-loops-and-local-vars/15") + 3307 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-conditional-loops-and-local-vars/16") + 3308 (check-next-stream-line-equal _test-output-stream "$foo:0x00000002:break:" "F - test-convert-function-with-conditional-loops-and-local-vars/17") + 3309 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-conditional-loops-and-local-vars/18") + 3310 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-function-with-conditional-loops-and-local-vars/19") + 3311 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-function-with-conditional-loops-and-local-vars/20") + 3312 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-function-with-conditional-loops-and-local-vars/21") + 3313 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-function-with-conditional-loops-and-local-vars/22") + 3314 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-function-with-conditional-loops-and-local-vars/23") + 3315 # . epilogue + 3316 89/<- %esp 5/r32/ebp + 3317 5d/pop-to-ebp + 3318 c3/return + 3319 + 3320 test-convert-function-with-unconditional-loops-and-local-vars: + 3321 # An unconditional 'loop' after a 'var' in a block is emitted _after_ the + 3322 # regular block cleanup. Any instructions after 'loop' are dead and + 3323 # therefore skipped. + 3324 # . prologue + 3325 55/push-ebp + 3326 89/<- %ebp 4/r32/esp + 3327 # setup + 3328 (clear-stream _test-input-stream) + 3329 (clear-stream $_test-input-buffered-file->buffer) + 3330 (clear-stream _test-output-stream) + 3331 (clear-stream $_test-output-buffered-file->buffer) + 3332 # + 3333 (write _test-input-stream "fn foo {\n") + 3334 (write _test-input-stream " {\n") + 3335 (write _test-input-stream " var x: int\n") + 3336 (write _test-input-stream " loop\n") + 3337 (write _test-input-stream " increment x\n") + 3338 (write _test-input-stream " }\n") + 3339 (write _test-input-stream "}\n") + 3340 # convert + 3341 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) + 3342 (flush _test-output-buffered-file) + 3343 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- + 3349 # check output + 3350 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-function-with-unconditional-loops-and-local-vars/0") + 3351 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-function-with-unconditional-loops-and-local-vars/1") + 3352 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-function-with-unconditional-loops-and-local-vars/2") + 3353 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-function-with-unconditional-loops-and-local-vars/3") + 3354 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-unconditional-loops-and-local-vars/4") + 3355 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-function-with-unconditional-loops-and-local-vars/5") + 3356 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-unconditional-loops-and-local-vars/6") + 3357 (check-next-stream-line-equal _test-output-stream "$foo:0x00000002:loop:" "F - test-convert-function-with-unconditional-loops-and-local-vars/7") + 3358 (check-next-stream-line-equal _test-output-stream " 68/push 0/imm32" "F - test-convert-function-with-unconditional-loops-and-local-vars/8") + 3359 (check-next-stream-line-equal _test-output-stream " 81 0/subop/add %esp 0x00000004/imm32" "F - test-convert-function-with-unconditional-loops-and-local-vars/9") + 3360 (check-next-stream-line-equal _test-output-stream " e9/jump loop/disp32" "F - test-convert-function-with-unconditional-loops-and-local-vars/10") + 3361 # not emitted: ff 0/subop/increment *(ebp+0xfffffffc) + 3362 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-unconditional-loops-and-local-vars/11") + 3363 (check-next-stream-line-equal _test-output-stream "$foo:0x00000002:break:" "F - test-convert-function-with-unconditional-loops-and-local-vars/12") + 3364 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-unconditional-loops-and-local-vars/13") + 3365 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-function-with-unconditional-loops-and-local-vars/14") + 3366 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-function-with-unconditional-loops-and-local-vars/15") + 3367 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-function-with-unconditional-loops-and-local-vars/16") + 3368 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-function-with-unconditional-loops-and-local-vars/17") + 3369 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-function-with-unconditional-loops-and-local-vars/18") + 3370 # . epilogue + 3371 89/<- %esp 5/r32/ebp + 3372 5d/pop-to-ebp + 3373 c3/return + 3374 + 3375 test-convert-function-with-branches-and-loops-and-local-vars: + 3376 # . prologue + 3377 55/push-ebp + 3378 89/<- %ebp 4/r32/esp + 3379 # setup + 3380 (clear-stream _test-input-stream) + 3381 (clear-stream $_test-input-buffered-file->buffer) + 3382 (clear-stream _test-output-stream) + 3383 (clear-stream $_test-output-buffered-file->buffer) + 3384 # + 3385 (write _test-input-stream "fn foo {\n") + 3386 (write _test-input-stream " {\n") + 3387 (write _test-input-stream " var x: int\n") + 3388 (write _test-input-stream " break-if->=\n") + 3389 (write _test-input-stream " increment x\n") + 3390 (write _test-input-stream " loop\n") + 3391 (write _test-input-stream " }\n") + 3392 (write _test-input-stream "}\n") + 3393 # convert + 3394 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) + 3395 (flush _test-output-buffered-file) + 3396 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- + 3402 # check output + 3403 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-function-with-branches-and-loops-and-local-vars/0") + 3404 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-function-with-branches-and-loops-and-local-vars/1") + 3405 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-function-with-branches-and-loops-and-local-vars/2") + 3406 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-function-with-branches-and-loops-and-local-vars/3") + 3407 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-branches-and-loops-and-local-vars/4") + 3408 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-function-with-branches-and-loops-and-local-vars/5") + 3409 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-branches-and-loops-and-local-vars/6") + 3410 (check-next-stream-line-equal _test-output-stream "$foo:0x00000002:loop:" "F - test-convert-function-with-branches-and-loops-and-local-vars/7") + 3411 (check-next-stream-line-equal _test-output-stream " 68/push 0/imm32" "F - test-convert-function-with-branches-and-loops-and-local-vars/8") + 3412 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-branches-and-loops-and-local-vars/9") + 3413 (check-next-stream-line-equal _test-output-stream " 0f 8c/jump-if-< break/disp32" "F - test-convert-function-with-branches-and-loops-and-local-vars/10") + 3414 (check-next-stream-line-equal _test-output-stream " 81 0/subop/add %esp 0x00000004/imm32" "F - test-convert-function-with-branches-and-loops-and-local-vars/11") + 3415 (check-next-stream-line-equal _test-output-stream " e9/jump $foo:0x00000002:break/disp32" "F - test-convert-function-with-branches-and-loops-and-local-vars/12") + 3416 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-branches-and-loops-and-local-vars/13") + 3417 (check-next-stream-line-equal _test-output-stream " ff 0/subop/increment *(ebp+0xfffffffc)" "F - test-convert-function-with-branches-and-loops-and-local-vars/14") + 3418 (check-next-stream-line-equal _test-output-stream " 81 0/subop/add %esp 0x00000004/imm32" "F - test-convert-function-with-branches-and-loops-and-local-vars/15") + 3419 (check-next-stream-line-equal _test-output-stream " e9/jump loop/disp32" "F - test-convert-function-with-branches-and-loops-and-local-vars/16") + 3420 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-branches-and-loops-and-local-vars/17") + 3421 (check-next-stream-line-equal _test-output-stream "$foo:0x00000002:break:" "F - test-convert-function-with-branches-and-loops-and-local-vars/18") + 3422 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-branches-and-loops-and-local-vars/19") + 3423 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-function-with-branches-and-loops-and-local-vars/20") + 3424 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-function-with-branches-and-loops-and-local-vars/21") + 3425 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-function-with-branches-and-loops-and-local-vars/22") + 3426 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-function-with-branches-and-loops-and-local-vars/23") + 3427 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-function-with-branches-and-loops-and-local-vars/24") + 3428 # . epilogue + 3429 89/<- %esp 5/r32/ebp + 3430 5d/pop-to-ebp + 3431 c3/return + 3432 + 3433 test-convert-function-with-nonlocal-branches-and-loops-and-local-vars: + 3434 # . prologue + 3435 55/push-ebp + 3436 89/<- %ebp 4/r32/esp + 3437 # setup + 3438 (clear-stream _test-input-stream) + 3439 (clear-stream $_test-input-buffered-file->buffer) + 3440 (clear-stream _test-output-stream) + 3441 (clear-stream $_test-output-buffered-file->buffer) + 3442 # + 3443 (write _test-input-stream "fn foo {\n") + 3444 (write _test-input-stream " a: {\n") + 3445 (write _test-input-stream " var x: int\n") + 3446 (write _test-input-stream " {\n") + 3447 (write _test-input-stream " var y: int\n") + 3448 (write _test-input-stream " break-if->= a\n") + 3449 (write _test-input-stream " increment x\n") + 3450 (write _test-input-stream " loop\n") + 3451 (write _test-input-stream " }\n") + 3452 (write _test-input-stream " }\n") + 3453 (write _test-input-stream "}\n") + 3454 # convert + 3455 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) + 3456 (flush _test-output-buffered-file) + 3457 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- + 3463 # check output + 3464 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars/0") + 3465 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars/1") + 3466 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars/2") + 3467 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars/3") + 3468 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars/4") + 3469 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars/5") + 3470 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars/6") + 3471 (check-next-stream-line-equal _test-output-stream "a:loop:" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars/7") + 3472 (check-next-stream-line-equal _test-output-stream " 68/push 0/imm32" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars/8") + 3473 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars/9") + 3474 (check-next-stream-line-equal _test-output-stream "$foo:0x00000003:loop:" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars/10") + 3475 (check-next-stream-line-equal _test-output-stream " 68/push 0/imm32" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars/11") + 3476 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars/12") + 3477 (check-next-stream-line-equal _test-output-stream " 0f 8c/jump-if-< break/disp32" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars/13") + 3478 (check-next-stream-line-equal _test-output-stream " 81 0/subop/add %esp 0x00000004/imm32" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars/14") + 3479 (check-next-stream-line-equal _test-output-stream " 81 0/subop/add %esp 0x00000004/imm32" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars/15") + 3480 (check-next-stream-line-equal _test-output-stream " e9/jump a:break/disp32" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars/16") + 3481 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars/17") + 3482 (check-next-stream-line-equal _test-output-stream " ff 0/subop/increment *(ebp+0xfffffffc)" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars/18") + 3483 (check-next-stream-line-equal _test-output-stream " 81 0/subop/add %esp 0x00000004/imm32" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars/19") + 3484 (check-next-stream-line-equal _test-output-stream " e9/jump loop/disp32" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars/20") + 3485 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars/21") + 3486 (check-next-stream-line-equal _test-output-stream "$foo:0x00000003:break:" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars/22") + 3487 (check-next-stream-line-equal _test-output-stream " 81 0/subop/add %esp 0x00000004/imm32" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars/23") + 3488 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars/24") + 3489 (check-next-stream-line-equal _test-output-stream "a:break:" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars/25") + 3490 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars/26") + 3491 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars/27") + 3492 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars/28") + 3493 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars/29") + 3494 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars/30") + 3495 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars/31") + 3496 # . epilogue + 3497 89/<- %esp 5/r32/ebp + 3498 5d/pop-to-ebp + 3499 c3/return + 3500 + 3501 test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-2: + 3502 # . prologue + 3503 55/push-ebp + 3504 89/<- %ebp 4/r32/esp + 3505 # setup + 3506 (clear-stream _test-input-stream) + 3507 (clear-stream $_test-input-buffered-file->buffer) + 3508 (clear-stream _test-output-stream) + 3509 (clear-stream $_test-output-buffered-file->buffer) + 3510 # non-local conditional branch from a block without a local variable, + 3511 # unwinding a local on the stack + 3512 (write _test-input-stream "fn foo {\n") + 3513 (write _test-input-stream " a: {\n") + 3514 (write _test-input-stream " var x: int\n") + 3515 (write _test-input-stream " {\n") + 3516 (write _test-input-stream " break-if->= a\n") + 3517 (write _test-input-stream " }\n") + 3518 (write _test-input-stream " }\n") + 3519 (write _test-input-stream "}\n") + 3520 # convert + 3521 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) + 3522 (flush _test-output-buffered-file) + 3523 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- + 3529 # check output + 3530 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-2/0") + 3531 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-2/1") + 3532 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-2/2") + 3533 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-2/3") + 3534 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-2/4") + 3535 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-2/5") + 3536 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-2/6") + 3537 (check-next-stream-line-equal _test-output-stream "a:loop:" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-2/7") + 3538 (check-next-stream-line-equal _test-output-stream " 68/push 0/imm32" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-2/8") + 3539 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-2/9") + 3540 (check-next-stream-line-equal _test-output-stream "$foo:0x00000003:loop:" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-2/10") + 3541 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-2/11") + 3542 (check-next-stream-line-equal _test-output-stream " 0f 8c/jump-if-< break/disp32" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-2/12") + 3543 (check-next-stream-line-equal _test-output-stream " 81 0/subop/add %esp 0x00000004/imm32" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-2/13") + 3544 (check-next-stream-line-equal _test-output-stream " e9/jump a:break/disp32" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-2/14") + 3545 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-2/15") + 3546 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-2/16") + 3547 (check-next-stream-line-equal _test-output-stream "$foo:0x00000003:break:" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-2/17") + 3548 (check-next-stream-line-equal _test-output-stream " 81 0/subop/add %esp 0x00000004/imm32" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-2/18") + 3549 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-2/19") + 3550 (check-next-stream-line-equal _test-output-stream "a:break:" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-2/20") + 3551 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-2/21") + 3552 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-2/22") + 3553 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-2/23") + 3554 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-2/24") + 3555 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-2/25") + 3556 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-2/26") + 3557 # . epilogue + 3558 89/<- %esp 5/r32/ebp + 3559 5d/pop-to-ebp + 3560 c3/return + 3561 + 3562 test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-3: + 3563 # . prologue + 3564 55/push-ebp + 3565 89/<- %ebp 4/r32/esp + 3566 # setup + 3567 (clear-stream _test-input-stream) + 3568 (clear-stream $_test-input-buffered-file->buffer) + 3569 (clear-stream _test-output-stream) + 3570 (clear-stream $_test-output-buffered-file->buffer) + 3571 # non-local unconditional branch from a block without a local variable, + 3572 # unwinding a local on the stack + 3573 (write _test-input-stream "fn foo {\n") + 3574 (write _test-input-stream " a: {\n") + 3575 (write _test-input-stream " var x: int\n") + 3576 (write _test-input-stream " {\n") + 3577 (write _test-input-stream " break a\n") + 3578 (write _test-input-stream " }\n") + 3579 (write _test-input-stream " }\n") + 3580 (write _test-input-stream "}\n") + 3581 # convert + 3582 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) + 3583 (flush _test-output-buffered-file) + 3584 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- + 3590 # check output + 3591 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-3/0") + 3592 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-3/1") + 3593 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-3/2") + 3594 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-3/3") + 3595 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-3/4") + 3596 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-3/5") + 3597 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-3/6") + 3598 (check-next-stream-line-equal _test-output-stream "a:loop:" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-3/7") + 3599 (check-next-stream-line-equal _test-output-stream " 68/push 0/imm32" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-3/8") + 3600 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-3/9") + 3601 (check-next-stream-line-equal _test-output-stream "$foo:0x00000003:loop:" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-3/10") + 3602 (check-next-stream-line-equal _test-output-stream " 81 0/subop/add %esp 0x00000004/imm32" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-3/11") + 3603 (check-next-stream-line-equal _test-output-stream " e9/jump a:break/disp32" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-3/12") + 3604 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-3/14") + 3605 (check-next-stream-line-equal _test-output-stream "$foo:0x00000003:break:" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-3/15") + 3606 (check-next-stream-line-equal _test-output-stream " 81 0/subop/add %esp 0x00000004/imm32" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-3/16") + 3607 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-3/17") + 3608 (check-next-stream-line-equal _test-output-stream "a:break:" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-3/18") + 3609 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-3/19") + 3610 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-3/20") + 3611 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-3/21") + 3612 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-3/22") + 3613 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-3/23") + 3614 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-3/24") + 3615 # . epilogue + 3616 89/<- %esp 5/r32/ebp + 3617 5d/pop-to-ebp + 3618 c3/return + 3619 + 3620 test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-4: + 3621 # . prologue + 3622 55/push-ebp + 3623 89/<- %ebp 4/r32/esp + 3624 # setup + 3625 (clear-stream _test-input-stream) + 3626 (clear-stream $_test-input-buffered-file->buffer) + 3627 (clear-stream _test-output-stream) + 3628 (clear-stream $_test-output-buffered-file->buffer) + 3629 # + 3630 (write _test-input-stream "fn foo {\n") + 3631 (write _test-input-stream " a: {\n") + 3632 (write _test-input-stream " var x/esi: int <- copy 0\n") + 3633 (write _test-input-stream " {\n") + 3634 (write _test-input-stream " break a\n") + 3635 (write _test-input-stream " }\n") + 3636 (write _test-input-stream " }\n") + 3637 (write _test-input-stream "}\n") + 3638 # convert + 3639 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) + 3640 (flush _test-output-buffered-file) + 3641 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- + 3647 # check output + 3648 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-4/0") + 3649 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-4/1") + 3650 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-4/2") + 3651 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-4/3") + 3652 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-4/4") + 3653 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-4/5") + 3654 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-4/6") + 3655 (check-next-stream-line-equal _test-output-stream "a:loop:" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-4/7") + 3656 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %esi" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-4/8") + 3657 (check-next-stream-line-equal _test-output-stream " be/copy-to-esi 0/imm32" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-4/9") + 3658 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-4/10") + 3659 (check-next-stream-line-equal _test-output-stream "$foo:0x00000003:loop:" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-4/11") + 3660 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %esi" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-4/12") + 3661 (check-next-stream-line-equal _test-output-stream " e9/jump a:break/disp32" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-4/13") + 3662 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-4/14") + 3663 (check-next-stream-line-equal _test-output-stream "$foo:0x00000003:break:" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-4/15") + 3664 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %esi" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-4/16") + 3665 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-4/17") + 3666 (check-next-stream-line-equal _test-output-stream "a:break:" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-4/18") + 3667 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-4/19") + 3668 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-4/20") + 3669 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-4/21") + 3670 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-4/22") + 3671 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-4/23") + 3672 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-function-with-nonlocal-branches-and-loops-and-local-vars-4/24") + 3673 # . epilogue + 3674 89/<- %esp 5/r32/ebp + 3675 5d/pop-to-ebp + 3676 c3/return + 3677 + 3678 test-convert-function-with-nonlocal-unconditional-break-and-local-vars: + 3679 # . prologue + 3680 55/push-ebp + 3681 89/<- %ebp 4/r32/esp + 3682 # setup + 3683 (clear-stream _test-input-stream) + 3684 (clear-stream $_test-input-buffered-file->buffer) + 3685 (clear-stream _test-output-stream) + 3686 (clear-stream $_test-output-buffered-file->buffer) + 3687 # + 3688 (write _test-input-stream "fn foo {\n") + 3689 (write _test-input-stream " a: {\n") + 3690 (write _test-input-stream " var x: int\n") + 3691 (write _test-input-stream " {\n") + 3692 (write _test-input-stream " var y: int\n") + 3693 (write _test-input-stream " break a\n") + 3694 (write _test-input-stream " increment x\n") + 3695 (write _test-input-stream " }\n") + 3696 (write _test-input-stream " }\n") + 3697 (write _test-input-stream "}\n") + 3698 # convert + 3699 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) + 3700 (flush _test-output-buffered-file) + 3701 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- + 3707 # check output + 3708 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-function-with-nonlocal-unconditional-break-and-local-vars/0") + 3709 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-function-with-nonlocal-unconditional-break-and-local-vars/1") + 3710 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-function-with-nonlocal-unconditional-break-and-local-vars/2") + 3711 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-function-with-nonlocal-unconditional-break-and-local-vars/3") + 3712 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-nonlocal-unconditional-break-and-local-vars/4") + 3713 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-function-with-nonlocal-unconditional-break-and-local-vars/5") + 3714 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-nonlocal-unconditional-break-and-local-vars/6") + 3715 (check-next-stream-line-equal _test-output-stream "a:loop:" "F - test-convert-function-with-nonlocal-unconditional-break-and-local-vars/7") + 3716 (check-next-stream-line-equal _test-output-stream " 68/push 0/imm32" "F - test-convert-function-with-nonlocal-unconditional-break-and-local-vars/8") + 3717 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-nonlocal-unconditional-break-and-local-vars/9") + 3718 (check-next-stream-line-equal _test-output-stream "$foo:0x00000003:loop:" "F - test-convert-function-with-nonlocal-unconditional-break-and-local-vars/10") + 3719 (check-next-stream-line-equal _test-output-stream " 68/push 0/imm32" "F - test-convert-function-with-nonlocal-unconditional-break-and-local-vars/11") + 3720 (check-next-stream-line-equal _test-output-stream " 81 0/subop/add %esp 0x00000004/imm32" "F - test-convert-function-with-nonlocal-unconditional-break-and-local-vars/12") + 3721 (check-next-stream-line-equal _test-output-stream " 81 0/subop/add %esp 0x00000004/imm32" "F - test-convert-function-with-nonlocal-unconditional-break-and-local-vars/13") + 3722 (check-next-stream-line-equal _test-output-stream " e9/jump a:break/disp32" "F - test-convert-function-with-nonlocal-unconditional-break-and-local-vars/14") + 3723 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-nonlocal-unconditional-break-and-local-vars/15") + 3724 (check-next-stream-line-equal _test-output-stream "$foo:0x00000003:break:" "F - test-convert-function-with-nonlocal-unconditional-break-and-local-vars/16") + 3725 (check-next-stream-line-equal _test-output-stream " 81 0/subop/add %esp 0x00000004/imm32" "F - test-convert-function-with-nonlocal-unconditional-break-and-local-vars/17") + 3726 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-nonlocal-unconditional-break-and-local-vars/18") + 3727 (check-next-stream-line-equal _test-output-stream "a:break:" "F - test-convert-function-with-nonlocal-unconditional-break-and-local-vars/19") + 3728 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-nonlocal-unconditional-break-and-local-vars/20") + 3729 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-function-with-nonlocal-unconditional-break-and-local-vars/21") + 3730 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-function-with-nonlocal-unconditional-break-and-local-vars/22") + 3731 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-function-with-nonlocal-unconditional-break-and-local-vars/23") + 3732 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-function-with-nonlocal-unconditional-break-and-local-vars/24") + 3733 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-function-with-nonlocal-unconditional-break-and-local-vars/25") + 3734 # . epilogue + 3735 89/<- %esp 5/r32/ebp + 3736 5d/pop-to-ebp + 3737 c3/return + 3738 + 3739 test-convert-function-with-unconditional-break-and-local-vars: + 3740 # . prologue + 3741 55/push-ebp + 3742 89/<- %ebp 4/r32/esp + 3743 # setup + 3744 (clear-stream _test-input-stream) + 3745 (clear-stream $_test-input-buffered-file->buffer) + 3746 (clear-stream _test-output-stream) + 3747 (clear-stream $_test-output-buffered-file->buffer) + 3748 # + 3749 (write _test-input-stream "fn foo {\n") + 3750 (write _test-input-stream " {\n") + 3751 (write _test-input-stream " var x: int\n") + 3752 (write _test-input-stream " {\n") + 3753 (write _test-input-stream " var y: int\n") + 3754 (write _test-input-stream " break\n") + 3755 (write _test-input-stream " increment x\n") + 3756 (write _test-input-stream " }\n") + 3757 (write _test-input-stream " }\n") + 3758 (write _test-input-stream "}\n") + 3759 # convert + 3760 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) + 3761 (flush _test-output-buffered-file) + 3762 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- + 3768 # check output + 3769 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-function-with-unconditional-break-and-local-vars/0") + 3770 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-function-with-unconditional-break-and-local-vars/1") + 3771 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-function-with-unconditional-break-and-local-vars/2") + 3772 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-function-with-unconditional-break-and-local-vars/3") + 3773 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-unconditional-break-and-local-vars/4") + 3774 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-function-with-unconditional-break-and-local-vars/5") + 3775 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-unconditional-break-and-local-vars/6") + 3776 (check-next-stream-line-equal _test-output-stream "$foo:0x00000002:loop:" "F - test-convert-function-with-unconditional-break-and-local-vars/7") + 3777 (check-next-stream-line-equal _test-output-stream " 68/push 0/imm32" "F - test-convert-function-with-unconditional-break-and-local-vars/8") + 3778 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-unconditional-break-and-local-vars/9") + 3779 (check-next-stream-line-equal _test-output-stream "$foo:0x00000003:loop:" "F - test-convert-function-with-unconditional-break-and-local-vars/10") + 3780 (check-next-stream-line-equal _test-output-stream " 68/push 0/imm32" "F - test-convert-function-with-unconditional-break-and-local-vars/11") + 3781 (check-next-stream-line-equal _test-output-stream " 81 0/subop/add %esp 0x00000004/imm32" "F - test-convert-function-with-unconditional-break-and-local-vars/12") + 3782 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-unconditional-break-and-local-vars/13") + 3783 (check-next-stream-line-equal _test-output-stream "$foo:0x00000003:break:" "F - test-convert-function-with-unconditional-break-and-local-vars/14") + 3784 (check-next-stream-line-equal _test-output-stream " 81 0/subop/add %esp 0x00000004/imm32" "F - test-convert-function-with-unconditional-break-and-local-vars/15") + 3785 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-unconditional-break-and-local-vars/16") + 3786 (check-next-stream-line-equal _test-output-stream "$foo:0x00000002:break:" "F - test-convert-function-with-unconditional-break-and-local-vars/17") + 3787 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-unconditional-break-and-local-vars/18") + 3788 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-function-with-unconditional-break-and-local-vars/19") + 3789 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-function-with-unconditional-break-and-local-vars/20") + 3790 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-function-with-unconditional-break-and-local-vars/21") + 3791 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-function-with-unconditional-break-and-local-vars/22") + 3792 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-function-with-unconditional-break-and-local-vars/23") + 3793 # . epilogue + 3794 89/<- %esp 5/r32/ebp + 3795 5d/pop-to-ebp + 3796 c3/return + 3797 + 3798 test-convert-function-with-nonlocal-unconditional-loop-and-local-vars: + 3799 # . prologue + 3800 55/push-ebp + 3801 89/<- %ebp 4/r32/esp + 3802 # setup + 3803 (clear-stream _test-input-stream) + 3804 (clear-stream $_test-input-buffered-file->buffer) + 3805 (clear-stream _test-output-stream) + 3806 (clear-stream $_test-output-buffered-file->buffer) + 3807 # + 3808 (write _test-input-stream "fn foo {\n") + 3809 (write _test-input-stream " a: {\n") + 3810 (write _test-input-stream " var x: int\n") + 3811 (write _test-input-stream " {\n") + 3812 (write _test-input-stream " var y: int\n") + 3813 (write _test-input-stream " loop a\n") + 3814 (write _test-input-stream " increment x\n") + 3815 (write _test-input-stream " }\n") + 3816 (write _test-input-stream " }\n") + 3817 (write _test-input-stream "}\n") + 3818 # convert + 3819 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) + 3820 (flush _test-output-buffered-file) + 3821 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- + 3827 # check output + 3828 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-function-with-nonlocal-unconditional-loop-and-local-vars/0") + 3829 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-function-with-nonlocal-unconditional-loop-and-local-vars/1") + 3830 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-function-with-nonlocal-unconditional-loop-and-local-vars/2") + 3831 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-function-with-nonlocal-unconditional-loop-and-local-vars/3") + 3832 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-nonlocal-unconditional-loop-and-local-vars/4") + 3833 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-function-with-nonlocal-unconditional-loop-and-local-vars/5") + 3834 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-nonlocal-unconditional-loop-and-local-vars/6") + 3835 (check-next-stream-line-equal _test-output-stream "a:loop:" "F - test-convert-function-with-nonlocal-unconditional-loop-and-local-vars/7") + 3836 (check-next-stream-line-equal _test-output-stream " 68/push 0/imm32" "F - test-convert-function-with-nonlocal-unconditional-loop-and-local-vars/8") + 3837 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-nonlocal-unconditional-loop-and-local-vars/9") + 3838 (check-next-stream-line-equal _test-output-stream "$foo:0x00000003:loop:" "F - test-convert-function-with-nonlocal-unconditional-loop-and-local-vars/10") + 3839 (check-next-stream-line-equal _test-output-stream " 68/push 0/imm32" "F - test-convert-function-with-nonlocal-unconditional-loop-and-local-vars/11") + 3840 (check-next-stream-line-equal _test-output-stream " 81 0/subop/add %esp 0x00000004/imm32" "F - test-convert-function-with-nonlocal-unconditional-loop-and-local-vars/12") + 3841 (check-next-stream-line-equal _test-output-stream " 81 0/subop/add %esp 0x00000004/imm32" "F - test-convert-function-with-nonlocal-unconditional-loop-and-local-vars/13") + 3842 (check-next-stream-line-equal _test-output-stream " e9/jump a:loop/disp32" "F - test-convert-function-with-nonlocal-unconditional-loop-and-local-vars/14") + 3843 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-nonlocal-unconditional-loop-and-local-vars/15") + 3844 (check-next-stream-line-equal _test-output-stream "$foo:0x00000003:break:" "F - test-convert-function-with-nonlocal-unconditional-loop-and-local-vars/16") + 3845 (check-next-stream-line-equal _test-output-stream " 81 0/subop/add %esp 0x00000004/imm32" "F - test-convert-function-with-nonlocal-unconditional-loop-and-local-vars/17") + 3846 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-nonlocal-unconditional-loop-and-local-vars/18") + 3847 (check-next-stream-line-equal _test-output-stream "a:break:" "F - test-convert-function-with-nonlocal-unconditional-loop-and-local-vars/19") + 3848 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-nonlocal-unconditional-loop-and-local-vars/20") + 3849 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-function-with-nonlocal-unconditional-loop-and-local-vars/21") + 3850 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-function-with-nonlocal-unconditional-loop-and-local-vars/22") + 3851 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-function-with-nonlocal-unconditional-loop-and-local-vars/23") + 3852 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-function-with-nonlocal-unconditional-loop-and-local-vars/24") + 3853 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-function-with-nonlocal-unconditional-loop-and-local-vars/25") + 3854 # . epilogue + 3855 89/<- %esp 5/r32/ebp + 3856 5d/pop-to-ebp + 3857 c3/return + 3858 + 3859 test-convert-function-with-local-array-var-in-mem: + 3860 # . prologue + 3861 55/push-ebp + 3862 89/<- %ebp 4/r32/esp + 3863 # setup + 3864 (clear-stream _test-input-stream) + 3865 (clear-stream $_test-input-buffered-file->buffer) + 3866 (clear-stream _test-output-stream) + 3867 (clear-stream $_test-output-buffered-file->buffer) + 3868 # + 3869 (write _test-input-stream "fn foo {\n") + 3870 (write _test-input-stream " var x: (array int 3)\n") + 3871 (write _test-input-stream "}\n") + 3872 # convert + 3873 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) + 3874 (flush _test-output-buffered-file) + 3875 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- + 3881 # check output + 3882 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-function-with-local-array-var-in-mem/0") + 3883 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-function-with-local-array-var-in-mem/1") + 3884 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-function-with-local-array-var-in-mem/2") + 3885 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-function-with-local-array-var-in-mem/3") + 3886 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-local-array-var-in-mem/4") + 3887 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-function-with-local-array-var-in-mem/5") + 3888 # define x + 3889 (check-next-stream-line-equal _test-output-stream " (push-n-zero-bytes 0x0000000c)" "F - test-convert-function-with-local-array-var-in-mem/7") + 3890 (check-next-stream-line-equal _test-output-stream " 68/push 0x0000000c/imm32" "F - test-convert-function-with-local-array-var-in-mem/8") + 3891 # reclaim x + 3892 (check-next-stream-line-equal _test-output-stream " 81 0/subop/add %esp 0x00000010/imm32" "F - test-convert-function-with-local-array-var-in-mem/9") + 3893 # + 3894 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-local-array-var-in-mem/10") + 3895 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-function-with-local-array-var-in-mem/11") + 3896 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-function-with-local-array-var-in-mem/12") + 3897 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-function-with-local-array-var-in-mem/13") + 3898 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-function-with-local-array-var-in-mem/14") + 3899 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-function-with-local-array-var-in-mem/15") + 3900 # . epilogue + 3901 89/<- %esp 5/r32/ebp + 3902 5d/pop-to-ebp + 3903 c3/return + 3904 + 3905 test-array-size-in-hex: + 3906 # . prologue + 3907 55/push-ebp + 3908 89/<- %ebp 4/r32/esp + 3909 # setup + 3910 (clear-stream _test-input-stream) + 3911 (clear-stream $_test-input-buffered-file->buffer) + 3912 (clear-stream _test-output-stream) + 3913 (clear-stream $_test-output-buffered-file->buffer) + 3914 (clear-stream _test-error-stream) + 3915 (clear-stream $_test-error-buffered-file->buffer) + 3916 # var ed/edx: exit-descriptor = tailor-exit-descriptor(16) + 3917 68/push 0/imm32 + 3918 68/push 0/imm32 + 3919 89/<- %edx 4/r32/esp + 3920 (tailor-exit-descriptor %edx 0x10) + 3921 # + 3922 (write _test-input-stream "fn foo {\n") + 3923 (write _test-input-stream " var x: (array int 10)\n") + 3924 (write _test-input-stream "}\n") + 3925 # convert + 3926 (convert-mu _test-input-buffered-file _test-output-buffered-file _test-error-buffered-file %edx) + 3927 # registers except esp clobbered at this point + 3928 # restore ed + 3929 89/<- %edx 4/r32/esp + 3930 (flush _test-output-buffered-file) + 3931 (flush _test-error-buffered-file) + 3932 +-- 6 lines: #? # dump _test-error-stream ------------------------------------------------------------------------------------------------------------------------------------------ + 3938 # check output + 3939 (check-stream-equal _test-output-stream "" "F - test-array-size-in-hex: output should be empty") + 3940 (check-next-stream-line-equal _test-error-stream "literal integers are always hex in Mu; either start '10' with a '0x' to be unambiguous, or convert it to decimal." "F - test-array-size-in-hex: error message") + 3941 # check that stop(1) was called + 3942 (check-ints-equal *(edx+4) 2 "F - test-array-size-in-hex: exit status") + 3943 # don't restore from ebp + 3944 81 0/subop/add %esp 8/imm32 + 3945 # . epilogue + 3946 5d/pop-to-ebp + 3947 c3/return + 3948 + 3949 test-convert-function-with-populate: + 3950 # . prologue + 3951 55/push-ebp + 3952 89/<- %ebp 4/r32/esp + 3953 # setup + 3954 (clear-stream _test-input-stream) + 3955 (clear-stream $_test-input-buffered-file->buffer) + 3956 (clear-stream _test-output-stream) + 3957 (clear-stream $_test-output-buffered-file->buffer) + 3958 # + 3959 (write _test-input-stream "fn foo {\n") + 3960 (write _test-input-stream " var x/ecx: (addr handle array int) <- copy 0\n") + 3961 (write _test-input-stream " populate x, 7\n") + 3962 (write _test-input-stream "}\n") + 3963 # convert + 3964 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) + 3965 (flush _test-output-buffered-file) + 3966 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- + 3972 # check output + 3973 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-function-with-populate/0") + 3974 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-function-with-populate/1") + 3975 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-function-with-populate/2") + 3976 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-function-with-populate/3") + 3977 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-populate/4") + 3978 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-function-with-populate/5") + 3979 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %ecx" "F - test-convert-function-with-populate/6") + 3980 (check-next-stream-line-equal _test-output-stream " b9/copy-to-ecx 0/imm32" "F - test-convert-function-with-populate/7") + 3981 (check-next-stream-line-equal _test-output-stream " (allocate-array2 Heap 0x00000004 7 %ecx)" "F - test-convert-function-with-populate/8") # 4 = size-of(int) + 3982 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %ecx" "F - test-convert-function-with-populate/9") + 3983 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-populate/10") + 3984 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-function-with-populate/11") + 3985 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-function-with-populate/12") + 3986 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-function-with-populate/13") + 3987 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-function-with-populate/14") + 3988 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-function-with-populate/15") + 3989 # . epilogue + 3990 89/<- %esp 5/r32/ebp + 3991 5d/pop-to-ebp + 3992 c3/return + 3993 + 3994 # special-case for size(byte) when allocating array + 3995 test-convert-function-with-local-array-of-bytes-in-mem: + 3996 # . prologue + 3997 55/push-ebp + 3998 89/<- %ebp 4/r32/esp + 3999 # setup + 4000 (clear-stream _test-input-stream) + 4001 (clear-stream $_test-input-buffered-file->buffer) + 4002 (clear-stream _test-output-stream) + 4003 (clear-stream $_test-output-buffered-file->buffer) + 4004 # + 4005 (write _test-input-stream "fn foo {\n") + 4006 (write _test-input-stream " var x: (array byte 3)\n") + 4007 (write _test-input-stream "}\n") + 4008 # convert + 4009 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) + 4010 (flush _test-output-buffered-file) + 4011 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- + 4017 # check output + 4018 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-function-with-local-array-of-bytes-in-mem/0") + 4019 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-function-with-local-array-of-bytes-in-mem/1") + 4020 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-function-with-local-array-of-bytes-in-mem/2") + 4021 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-function-with-local-array-of-bytes-in-mem/3") + 4022 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-local-array-of-bytes-in-mem/4") + 4023 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-function-with-local-array-of-bytes-in-mem/5") + 4024 # define x + 4025 (check-next-stream-line-equal _test-output-stream " (push-n-zero-bytes 0x00000003)" "F - test-convert-function-with-local-array-of-bytes-in-mem/7") + 4026 (check-next-stream-line-equal _test-output-stream " 68/push 0x00000003/imm32" "F - test-convert-function-with-local-array-of-bytes-in-mem/8") + 4027 # reclaim x + 4028 (check-next-stream-line-equal _test-output-stream " 81 0/subop/add %esp 0x00000007/imm32" "F - test-convert-function-with-local-array-of-bytes-in-mem/9") + 4029 # + 4030 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-local-array-of-bytes-in-mem/10") + 4031 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-function-with-local-array-of-bytes-in-mem/11") + 4032 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-function-with-local-array-of-bytes-in-mem/12") + 4033 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-function-with-local-array-of-bytes-in-mem/13") + 4034 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-function-with-local-array-of-bytes-in-mem/14") + 4035 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-function-with-local-array-of-bytes-in-mem/15") + 4036 # . epilogue + 4037 89/<- %esp 5/r32/ebp + 4038 5d/pop-to-ebp + 4039 c3/return + 4040 + 4041 test-convert-address: + 4042 # . prologue + 4043 55/push-ebp + 4044 89/<- %ebp 4/r32/esp + 4045 # setup + 4046 (clear-stream _test-input-stream) + 4047 (clear-stream $_test-input-buffered-file->buffer) + 4048 (clear-stream _test-output-stream) + 4049 (clear-stream $_test-output-buffered-file->buffer) + 4050 # + 4051 (write _test-input-stream "fn foo {\n") + 4052 (write _test-input-stream " var a: int\n") + 4053 (write _test-input-stream " var b/eax: (addr int) <- address a\n") + 4054 (write _test-input-stream "}\n") + 4055 # convert + 4056 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) + 4057 (flush _test-output-buffered-file) + 4058 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- + 4064 # check output + 4065 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-address/0") + 4066 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-address/1") + 4067 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-address/2") + 4068 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-address/3") + 4069 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-address/4") + 4070 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-address/5") + 4071 (check-next-stream-line-equal _test-output-stream " 68/push 0/imm32" "F - test-convert-address/6") + 4072 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %eax" "F - test-convert-address/7") + 4073 (check-next-stream-line-equal _test-output-stream " 8d/copy-address *(ebp+0xfffffffc) 0x00000000/r32" "F - test-convert-address/8") + 4074 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %eax" "F - test-convert-address/9") + 4075 (check-next-stream-line-equal _test-output-stream " 81 0/subop/add %esp 0x00000004/imm32" "F - test-convert-address/10") + 4076 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-address/11") + 4077 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-address/12") + 4078 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-address/13") + 4079 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-address/14") + 4080 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-address/15") + 4081 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-address/16") + 4082 # . epilogue + 4083 89/<- %esp 5/r32/ebp + 4084 5d/pop-to-ebp + 4085 c3/return + 4086 + 4087 test-convert-length-of-array: + 4088 # . prologue + 4089 55/push-ebp + 4090 89/<- %ebp 4/r32/esp + 4091 # setup + 4092 (clear-stream _test-input-stream) + 4093 (clear-stream $_test-input-buffered-file->buffer) + 4094 (clear-stream _test-output-stream) + 4095 (clear-stream $_test-output-buffered-file->buffer) + 4096 # + 4097 (write _test-input-stream "fn foo a: (addr array int) {\n") + 4098 (write _test-input-stream " var b/eax: (addr array int) <- copy a\n") + 4099 (write _test-input-stream " var c/eax: int <- length b\n") + 4100 (write _test-input-stream "}\n") + 4101 # convert + 4102 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) + 4103 (flush _test-output-buffered-file) + 4104 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- + 4110 # check output + 4111 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-length-of-array/0") + 4112 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-length-of-array/1") + 4113 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-length-of-array/2") + 4114 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-length-of-array/3") + 4115 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-length-of-array/4") + 4116 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-length-of-array/5") + 4117 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %eax" "F - test-convert-length-of-array/6") + 4118 (check-next-stream-line-equal _test-output-stream " 8b/-> *(ebp+0x00000008) 0x00000000/r32" "F - test-convert-length-of-array/7") + 4119 (check-next-stream-line-equal _test-output-stream " 8b/-> *eax 0x00000000/r32" "F - test-convert-length-of-array/8") + 4120 (check-next-stream-line-equal _test-output-stream " c1/shift 5/subop/>> %eax 0x00000002/imm8" "F - test-convert-length-of-array/9") + 4121 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %eax" "F - test-convert-length-of-array/10") + 4122 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-length-of-array/11") + 4123 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-length-of-array/12") + 4124 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-length-of-array/13") + 4125 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-length-of-array/14") + 4126 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-length-of-array/15") + 4127 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-length-of-array/16") + 4128 # . epilogue + 4129 89/<- %esp 5/r32/ebp + 4130 5d/pop-to-ebp + 4131 c3/return + 4132 + 4133 # special-case for size(byte) when computing array length + 4134 test-convert-length-of-array-of-bytes: + 4135 # . prologue + 4136 55/push-ebp + 4137 89/<- %ebp 4/r32/esp + 4138 # setup + 4139 (clear-stream _test-input-stream) + 4140 (clear-stream $_test-input-buffered-file->buffer) + 4141 (clear-stream _test-output-stream) + 4142 (clear-stream $_test-output-buffered-file->buffer) + 4143 # + 4144 (write _test-input-stream "fn foo a: (addr array byte) {\n") + 4145 (write _test-input-stream " var b/eax: (addr array byte) <- copy a\n") + 4146 (write _test-input-stream " var c/eax: int <- length b\n") + 4147 (write _test-input-stream "}\n") + 4148 # convert + 4149 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) + 4150 (flush _test-output-buffered-file) + 4151 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- + 4157 # check output + 4158 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-length-of-array-of-bytes/0") + 4159 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-length-of-array-of-bytes/1") + 4160 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-length-of-array-of-bytes/2") + 4161 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-length-of-array-of-bytes/3") + 4162 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-length-of-array-of-bytes/4") + 4163 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-length-of-array-of-bytes/5") + 4164 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %eax" "F - test-convert-length-of-array-of-bytes/6") + 4165 (check-next-stream-line-equal _test-output-stream " 8b/-> *(ebp+0x00000008) 0x00000000/r32" "F - test-convert-length-of-array-of-bytes/7") + 4166 (check-next-stream-line-equal _test-output-stream " 8b/-> *eax 0x00000000/r32" "F - test-convert-length-of-array-of-bytes/8") + 4167 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %eax" "F - test-convert-length-of-array-of-bytes/9") + 4168 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-length-of-array-of-bytes/10") + 4169 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-length-of-array-of-bytes/11") + 4170 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-length-of-array-of-bytes/12") + 4171 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-length-of-array-of-bytes/13") + 4172 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-length-of-array-of-bytes/14") + 4173 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-length-of-array-of-bytes/15") + 4174 # . epilogue + 4175 89/<- %esp 5/r32/ebp + 4176 5d/pop-to-ebp + 4177 c3/return + 4178 + 4179 test-convert-length-of-array-on-stack: + 4180 # . prologue + 4181 55/push-ebp + 4182 89/<- %ebp 4/r32/esp + 4183 # setup + 4184 (clear-stream _test-input-stream) + 4185 (clear-stream $_test-input-buffered-file->buffer) + 4186 (clear-stream _test-output-stream) + 4187 (clear-stream $_test-output-buffered-file->buffer) + 4188 # + 4189 (write _test-input-stream "fn foo {\n") + 4190 (write _test-input-stream " var a: (array int 3)\n") + 4191 (write _test-input-stream " var b/eax: int <- length a\n") + 4192 (write _test-input-stream "}\n") + 4193 # convert + 4194 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) + 4195 (flush _test-output-buffered-file) + 4196 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- + 4202 # check output + 4203 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-length-of-array-on-stack/0") + 4204 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-length-of-array-on-stack/1") + 4205 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-length-of-array-on-stack/2") + 4206 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-length-of-array-on-stack/3") + 4207 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-length-of-array-on-stack/4") + 4208 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-length-of-array-on-stack/5") + 4209 # define x + 4210 (check-next-stream-line-equal _test-output-stream " (push-n-zero-bytes 0x0000000c)" "F - test-convert-length-of-array-on-stack/6") + 4211 (check-next-stream-line-equal _test-output-stream " 68/push 0x0000000c/imm32" "F - test-convert-length-of-array-on-stack/7") + 4212 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %eax" "F - test-convert-length-of-array-on-stack/8") + 4213 (check-next-stream-line-equal _test-output-stream " 8b/-> *(ebp+0xfffffff0) 0x00000000/r32" "F - test-convert-length-of-array-on-stack/9") + 4214 (check-next-stream-line-equal _test-output-stream " c1/shift 5/subop/>> %eax 0x00000002/imm8" "F - test-convert-length-of-array-on-stack/10") + 4215 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %eax" "F - test-convert-length-of-array-on-stack/11") + 4216 (check-next-stream-line-equal _test-output-stream " 81 0/subop/add %esp 0x00000010/imm32" "F - test-convert-length-of-array-on-stack/12") + 4217 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-length-of-array-on-stack/13") + 4218 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-length-of-array-on-stack/14") + 4219 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-length-of-array-on-stack/15") + 4220 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-length-of-array-on-stack/16") + 4221 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-length-of-array-on-stack/17") + 4222 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-length-of-array-on-stack/18") + 4223 # . epilogue + 4224 89/<- %esp 5/r32/ebp + 4225 5d/pop-to-ebp + 4226 c3/return + 4227 + 4228 test-reg-var-def-with-read-of-same-register: + 4229 # . prologue + 4230 55/push-ebp + 4231 89/<- %ebp 4/r32/esp + 4232 # setup + 4233 (clear-stream _test-input-stream) + 4234 (clear-stream $_test-input-buffered-file->buffer) + 4235 (clear-stream _test-output-stream) + 4236 (clear-stream $_test-output-buffered-file->buffer) + 4237 (clear-stream _test-error-stream) + 4238 (clear-stream $_test-error-buffered-file->buffer) + 4239 # var ed/edx: exit-descriptor = tailor-exit-descriptor(16) # bytes of args in call to convert-mu + 4240 68/push 0/imm32 + 4241 68/push 0/imm32 + 4242 89/<- %edx 4/r32/esp + 4243 (tailor-exit-descriptor %edx 0x10) + 4244 # + 4245 (write _test-input-stream "fn foo {\n") + 4246 (write _test-input-stream " var arr/eax: (addr array int) <- copy 0\n") + 4247 (write _test-input-stream " var idx/ecx: int <- copy 3\n") + 4248 (write _test-input-stream " var x/eax: (addr int) <- index arr, idx\n") + 4249 (write _test-input-stream "}\n") + 4250 # convert + 4251 (convert-mu _test-input-buffered-file _test-output-buffered-file _test-error-buffered-file %edx) + 4252 # registers except esp could be clobbered at this point (though they shouldn't be) + 4253 # restore ed + 4254 89/<- %edx 4/r32/esp + 4255 (flush _test-output-buffered-file) + 4256 (flush _test-error-buffered-file) + 4257 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- + 4263 (check-stream-equal _test-error-stream "" "F - test-reg-var-def-with-read-of-same-register: error stream should be empty") + 4264 # check output + 4265 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-reg-var-def-with-read-of-same-register/0") + 4266 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-reg-var-def-with-read-of-same-register/1") + 4267 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-reg-var-def-with-read-of-same-register/2") + 4268 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-reg-var-def-with-read-of-same-register/3") + 4269 (check-next-stream-line-equal _test-output-stream " {" "F - test-reg-var-def-with-read-of-same-register/4") + 4270 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-reg-var-def-with-read-of-same-register/5") + 4271 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %eax" "F - test-reg-var-def-with-read-of-same-register/6") + 4272 (check-next-stream-line-equal _test-output-stream " b8/copy-to-eax 0/imm32" "F - test-reg-var-def-with-read-of-same-register/7") + 4273 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %ecx" "F - test-reg-var-def-with-read-of-same-register/8") + 4274 (check-next-stream-line-equal _test-output-stream " b9/copy-to-ecx 3/imm32" "F - test-reg-var-def-with-read-of-same-register/9") + 4275 (check-next-stream-line-equal _test-output-stream " 8d/copy-address *(eax + ecx<<0x00000002 + 4) 0x00000000/r32" "F - test-reg-var-def-with-read-of-same-register/11") + 4276 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %ecx" "F - test-reg-var-def-with-read-of-same-register/13") + 4277 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %eax" "F - test-reg-var-def-with-read-of-same-register/14") + 4278 (check-next-stream-line-equal _test-output-stream " }" "F - test-reg-var-def-with-read-of-same-register/15") + 4279 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-reg-var-def-with-read-of-same-register/16") + 4280 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-reg-var-def-with-read-of-same-register/17") + 4281 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-reg-var-def-with-read-of-same-register/18") + 4282 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-reg-var-def-with-read-of-same-register/19") + 4283 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-reg-var-def-with-read-of-same-register/20") + 4284 # don't restore from ebp + 4285 81 0/subop/add %esp 8/imm32 + 4286 # . epilogue + 4287 5d/pop-to-ebp + 4288 c3/return + 4289 + 4290 test-convert-index-into-array: + 4291 # . prologue + 4292 55/push-ebp + 4293 89/<- %ebp 4/r32/esp + 4294 # setup + 4295 (clear-stream _test-input-stream) + 4296 (clear-stream $_test-input-buffered-file->buffer) + 4297 (clear-stream _test-output-stream) + 4298 (clear-stream $_test-output-buffered-file->buffer) + 4299 # + 4300 (write _test-input-stream "fn foo {\n") + 4301 (write _test-input-stream " var arr/eax: (addr array int) <- copy 0\n") + 4302 (write _test-input-stream " var idx/ecx: int <- copy 3\n") + 4303 (write _test-input-stream " var x/eax: (addr int) <- index arr, idx\n") + 4304 (write _test-input-stream "}\n") + 4305 # convert + 4306 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) + 4307 (flush _test-output-buffered-file) + 4308 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- + 4314 # check output + 4315 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-index-into-array/0") + 4316 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-index-into-array/1") + 4317 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-index-into-array/2") + 4318 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-index-into-array/3") + 4319 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-index-into-array/4") + 4320 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-index-into-array/5") + 4321 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %eax" "F - test-convert-index-into-array/6") + 4322 (check-next-stream-line-equal _test-output-stream " b8/copy-to-eax 0/imm32" "F - test-convert-index-into-array/7") + 4323 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %ecx" "F - test-convert-index-into-array/8") + 4324 (check-next-stream-line-equal _test-output-stream " b9/copy-to-ecx 3/imm32" "F - test-convert-index-into-array/9") + 4325 (check-next-stream-line-equal _test-output-stream " 8d/copy-address *(eax + ecx<<0x00000002 + 4) 0x00000000/r32" "F - test-convert-index-into-array/10") + 4326 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %ecx" "F - test-convert-index-into-array/11") + 4327 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %eax" "F - test-convert-index-into-array/12") + 4328 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-index-into-array/13") + 4329 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-index-into-array/14") + 4330 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-index-into-array/15") + 4331 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-index-into-array/16") + 4332 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-index-into-array/17") + 4333 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-index-into-array/18") + 4334 # . epilogue + 4335 89/<- %esp 5/r32/ebp + 4336 5d/pop-to-ebp + 4337 c3/return + 4338 + 4339 test-convert-index-into-array-of-bytes: + 4340 # . prologue + 4341 55/push-ebp + 4342 89/<- %ebp 4/r32/esp + 4343 # setup + 4344 (clear-stream _test-input-stream) + 4345 (clear-stream $_test-input-buffered-file->buffer) + 4346 (clear-stream _test-output-stream) + 4347 (clear-stream $_test-output-buffered-file->buffer) + 4348 # + 4349 (write _test-input-stream "fn foo {\n") + 4350 (write _test-input-stream " var arr/eax: (addr array byte) <- copy 0\n") + 4351 (write _test-input-stream " var idx/ecx: int <- copy 3\n") + 4352 (write _test-input-stream " var x/eax: (addr byte) <- index arr, idx\n") + 4353 (write _test-input-stream "}\n") + 4354 # convert + 4355 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) + 4356 (flush _test-output-buffered-file) + 4357 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- + 4363 # check output + 4364 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-index-into-array-of-bytes/0") + 4365 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-index-into-array-of-bytes/1") + 4366 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-index-into-array-of-bytes/2") + 4367 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-index-into-array-of-bytes/3") + 4368 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-index-into-array-of-bytes/4") + 4369 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-index-into-array-of-bytes/5") + 4370 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %eax" "F - test-convert-index-into-array-of-bytes/6") + 4371 (check-next-stream-line-equal _test-output-stream " b8/copy-to-eax 0/imm32" "F - test-convert-index-into-array-of-bytes/7") + 4372 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %ecx" "F - test-convert-index-into-array-of-bytes/8") + 4373 (check-next-stream-line-equal _test-output-stream " b9/copy-to-ecx 3/imm32" "F - test-convert-index-into-array-of-bytes/9") + 4374 (check-next-stream-line-equal _test-output-stream " 8d/copy-address *(eax + ecx<<0x00000000 + 4) 0x00000000/r32" "F - test-convert-index-into-array-of-bytes/11") + 4375 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %ecx" "F - test-convert-index-into-array-of-bytes/13") + 4376 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %eax" "F - test-convert-index-into-array-of-bytes/14") + 4377 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-index-into-array-of-bytes/15") + 4378 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-index-into-array-of-bytes/16") + 4379 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-index-into-array-of-bytes/17") + 4380 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-index-into-array-of-bytes/18") + 4381 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-index-into-array-of-bytes/19") + 4382 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-index-into-array-of-bytes/20") + 4383 # . epilogue + 4384 89/<- %esp 5/r32/ebp + 4385 5d/pop-to-ebp + 4386 c3/return + 4387 + 4388 test-convert-index-into-array-with-literal: + 4389 # . prologue + 4390 55/push-ebp + 4391 89/<- %ebp 4/r32/esp + 4392 # setup + 4393 (clear-stream _test-input-stream) + 4394 (clear-stream $_test-input-buffered-file->buffer) + 4395 (clear-stream _test-output-stream) + 4396 (clear-stream $_test-output-buffered-file->buffer) + 4397 # + 4398 (write _test-input-stream "fn foo {\n") + 4399 (write _test-input-stream " var arr/eax: (addr array int) <- copy 0\n") + 4400 (write _test-input-stream " var x/eax: (addr int) <- index arr, 2\n") + 4401 (write _test-input-stream "}\n") + 4402 # convert + 4403 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) + 4404 (flush _test-output-buffered-file) + 4405 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- + 4411 # check output + 4412 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-index-into-array-with-literal/0") + 4413 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-index-into-array-with-literal/1") + 4414 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-index-into-array-with-literal/2") + 4415 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-index-into-array-with-literal/3") + 4416 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-index-into-array-with-literal/4") + 4417 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-index-into-array-with-literal/5") + 4418 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %eax" "F - test-convert-index-into-array-with-literal/6") + 4419 (check-next-stream-line-equal _test-output-stream " b8/copy-to-eax 0/imm32" "F - test-convert-index-into-array-with-literal/7") + 4420 # 2 * 4 bytes/elem + 4 bytes for size = offset 12 + 4421 (check-next-stream-line-equal _test-output-stream " 8d/copy-address *(eax + 0x0000000c) 0x00000000/r32" "F - test-convert-index-into-array-with-literal/8") + 4422 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %eax" "F - test-convert-index-into-array-with-literal/9") + 4423 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-index-into-array-with-literal/10") + 4424 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-index-into-array-with-literal/11") + 4425 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-index-into-array-with-literal/12") + 4426 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-index-into-array-with-literal/13") + 4427 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-index-into-array-with-literal/14") + 4428 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-index-into-array-with-literal/15") + 4429 # . epilogue + 4430 89/<- %esp 5/r32/ebp + 4431 5d/pop-to-ebp + 4432 c3/return + 4433 + 4434 test-convert-index-into-array-of-bytes-with-literal: + 4435 # . prologue + 4436 55/push-ebp + 4437 89/<- %ebp 4/r32/esp + 4438 # setup + 4439 (clear-stream _test-input-stream) + 4440 (clear-stream $_test-input-buffered-file->buffer) + 4441 (clear-stream _test-output-stream) + 4442 (clear-stream $_test-output-buffered-file->buffer) + 4443 # + 4444 (write _test-input-stream "fn foo {\n") + 4445 (write _test-input-stream " var arr/eax: (addr array byte) <- copy 0\n") + 4446 (write _test-input-stream " var x/eax: (addr byte) <- index arr, 2\n") + 4447 (write _test-input-stream "}\n") + 4448 # convert + 4449 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) + 4450 (flush _test-output-buffered-file) + 4451 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- + 4457 # check output + 4458 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-index-into-array-of-bytes-with-literal/0") + 4459 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-index-into-array-of-bytes-with-literal/1") + 4460 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-index-into-array-of-bytes-with-literal/2") + 4461 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-index-into-array-of-bytes-with-literal/3") + 4462 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-index-into-array-of-bytes-with-literal/4") + 4463 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-index-into-array-of-bytes-with-literal/5") + 4464 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %eax" "F - test-convert-index-into-array-of-bytes-with-literal/6") + 4465 (check-next-stream-line-equal _test-output-stream " b8/copy-to-eax 0/imm32" "F - test-convert-index-into-array-of-bytes-with-literal/7") + 4466 # 2 * 1 byte/elem + 4 bytes for size = offset 6 + 4467 (check-next-stream-line-equal _test-output-stream " 8d/copy-address *(eax + 0x00000006) 0x00000000/r32" "F - test-convert-index-into-array-of-bytes-with-literal/8") + 4468 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %eax" "F - test-convert-index-into-array-of-bytes-with-literal/9") + 4469 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-index-into-array-of-bytes-with-literal/10") + 4470 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-index-into-array-of-bytes-with-literal/11") + 4471 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-index-into-array-of-bytes-with-literal/12") + 4472 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-index-into-array-of-bytes-with-literal/13") + 4473 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-index-into-array-of-bytes-with-literal/14") + 4474 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-index-into-array-of-bytes-with-literal/15") + 4475 # . epilogue + 4476 89/<- %esp 5/r32/ebp + 4477 5d/pop-to-ebp + 4478 c3/return + 4479 + 4480 test-convert-index-into-array-on-stack: + 4481 # . prologue + 4482 55/push-ebp + 4483 89/<- %ebp 4/r32/esp + 4484 # setup + 4485 (clear-stream _test-input-stream) + 4486 (clear-stream $_test-input-buffered-file->buffer) + 4487 (clear-stream _test-output-stream) + 4488 (clear-stream $_test-output-buffered-file->buffer) + 4489 # + 4490 (write _test-input-stream "fn foo {\n") + 4491 (write _test-input-stream " var arr: (array int 3)\n") + 4492 (write _test-input-stream " var idx/eax: int <- copy 2\n") + 4493 (write _test-input-stream " var x/eax: (addr int) <- index arr, idx\n") + 4494 (write _test-input-stream "}\n") + 4495 # convert + 4496 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) + 4497 (flush _test-output-buffered-file) + 4498 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- + 4504 # check output + 4505 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-index-into-array-on-stack/0") + 4506 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-index-into-array-on-stack/1") + 4507 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-index-into-array-on-stack/2") + 4508 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-index-into-array-on-stack/3") + 4509 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-index-into-array-on-stack/4") + 4510 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-index-into-array-on-stack/5") + 4511 # var arr + 4512 (check-next-stream-line-equal _test-output-stream " (push-n-zero-bytes 0x0000000c)" "F - test-convert-index-into-array-on-stack/6") + 4513 (check-next-stream-line-equal _test-output-stream " 68/push 0x0000000c/imm32" "F - test-convert-index-into-array-on-stack/7") + 4514 # var idx + 4515 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %eax" "F - test-convert-index-into-array-on-stack/8") + 4516 (check-next-stream-line-equal _test-output-stream " b8/copy-to-eax 2/imm32" "F - test-convert-index-into-array-on-stack/9") + 4517 # var x is at (ebp-0x10) + idx<<2 + 4 = ebp + idx<<2 - 0xc + 4518 (check-next-stream-line-equal _test-output-stream " 8d/copy-address *(ebp + eax<<0x00000002 + 0xfffffff4) 0x00000000/r32" "F - test-convert-index-into-array-on-stack/10") + 4519 # reclaim idx + 4520 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %eax" "F - test-convert-index-into-array-on-stack/11") + 4521 # reclaim arr + 4522 (check-next-stream-line-equal _test-output-stream " 81 0/subop/add %esp 0x00000010/imm32" "F - test-convert-index-into-array-on-stack/12") + 4523 # + 4524 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-index-into-array-on-stack/13") + 4525 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-index-into-array-on-stack/14") + 4526 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-index-into-array-on-stack/15") + 4527 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-index-into-array-on-stack/16") + 4528 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-index-into-array-on-stack/17") + 4529 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-index-into-array-on-stack/18") + 4530 # . epilogue + 4531 89/<- %esp 5/r32/ebp + 4532 5d/pop-to-ebp + 4533 c3/return + 4534 + 4535 test-convert-index-into-array-on-stack-with-literal: + 4536 # . prologue + 4537 55/push-ebp + 4538 89/<- %ebp 4/r32/esp + 4539 # setup + 4540 (clear-stream _test-input-stream) + 4541 (clear-stream $_test-input-buffered-file->buffer) + 4542 (clear-stream _test-output-stream) + 4543 (clear-stream $_test-output-buffered-file->buffer) + 4544 # + 4545 (write _test-input-stream "fn foo {\n") + 4546 (write _test-input-stream " var arr: (array int 3)\n") + 4547 (write _test-input-stream " var x/eax: (addr int) <- index arr, 2\n") + 4548 (write _test-input-stream "}\n") + 4549 # convert + 4550 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) + 4551 (flush _test-output-buffered-file) + 4552 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- + 4558 # check output + 4559 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-index-into-array-on-stack-with-literal/0") + 4560 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-index-into-array-on-stack-with-literal/1") + 4561 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-index-into-array-on-stack-with-literal/2") + 4562 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-index-into-array-on-stack-with-literal/3") + 4563 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-index-into-array-on-stack-with-literal/4") + 4564 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-index-into-array-on-stack-with-literal/5") + 4565 # var arr + 4566 (check-next-stream-line-equal _test-output-stream " (push-n-zero-bytes 0x0000000c)" "F - test-convert-index-into-array-on-stack-with-literal/6") + 4567 (check-next-stream-line-equal _test-output-stream " 68/push 0x0000000c/imm32" "F - test-convert-index-into-array-on-stack-with-literal/7") + 4568 # var x + 4569 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %eax" "F - test-convert-index-into-array-on-stack-with-literal/8") + 4570 # x is at (ebp-0x10) + 4 + 2*4 = ebp-4 + 4571 (check-next-stream-line-equal _test-output-stream " 8d/copy-address *(ebp + 0xfffffffc) 0x00000000/r32" "F - test-convert-index-into-array-on-stack-with-literal/9") + 4572 # reclaim x + 4573 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %eax" "F - test-convert-index-into-array-on-stack-with-literal/10") + 4574 # reclaim arr + 4575 (check-next-stream-line-equal _test-output-stream " 81 0/subop/add %esp 0x00000010/imm32" "F - test-convert-index-into-array-on-stack-with-literal/11") + 4576 # + 4577 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-index-into-array-on-stack-with-literal/12") + 4578 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-index-into-array-on-stack-with-literal/13") + 4579 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-index-into-array-on-stack-with-literal/14") + 4580 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-index-into-array-on-stack-with-literal/15") + 4581 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-index-into-array-on-stack-with-literal/16") + 4582 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-index-into-array-on-stack-with-literal/17") + 4583 # . epilogue + 4584 89/<- %esp 5/r32/ebp + 4585 5d/pop-to-ebp + 4586 c3/return + 4587 + 4588 test-convert-index-into-array-of-bytes-on-stack-with-literal: + 4589 # . prologue + 4590 55/push-ebp + 4591 89/<- %ebp 4/r32/esp + 4592 # setup + 4593 (clear-stream _test-input-stream) + 4594 (clear-stream $_test-input-buffered-file->buffer) + 4595 (clear-stream _test-output-stream) + 4596 (clear-stream $_test-output-buffered-file->buffer) + 4597 # + 4598 (write _test-input-stream "fn foo {\n") + 4599 (write _test-input-stream " var arr: (array byte 3)\n") + 4600 (write _test-input-stream " var x/eax: (addr byte) <- index arr, 2\n") + 4601 (write _test-input-stream "}\n") + 4602 # convert + 4603 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) + 4604 (flush _test-output-buffered-file) + 4605 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- + 4611 # check output + 4612 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-index-into-array-of-bytes-on-stack-with-literal/0") + 4613 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-index-into-array-of-bytes-on-stack-with-literal/1") + 4614 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-index-into-array-of-bytes-on-stack-with-literal/2") + 4615 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-index-into-array-of-bytes-on-stack-with-literal/3") + 4616 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-index-into-array-of-bytes-on-stack-with-literal/4") + 4617 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-index-into-array-of-bytes-on-stack-with-literal/5") + 4618 # var arr + 4619 (check-next-stream-line-equal _test-output-stream " (push-n-zero-bytes 0x00000003)" "F - test-convert-index-into-array-of-bytes-on-stack-with-literal/6") + 4620 (check-next-stream-line-equal _test-output-stream " 68/push 0x00000003/imm32" "F - test-convert-index-into-array-of-bytes-on-stack-with-literal/7") + 4621 # var x + 4622 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %eax" "F - test-convert-index-into-array-of-bytes-on-stack-with-literal/8") + 4623 # x is at (ebp-7) + 4 + 2 = ebp-1 + 4624 (check-next-stream-line-equal _test-output-stream " 8d/copy-address *(ebp + 0xffffffff) 0x00000000/r32" "F - test-convert-index-into-array-of-bytes-on-stack-with-literal/9") + 4625 # reclaim x + 4626 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %eax" "F - test-convert-index-into-array-of-bytes-on-stack-with-literal/10") + 4627 # reclaim arr + 4628 (check-next-stream-line-equal _test-output-stream " 81 0/subop/add %esp 0x00000007/imm32" "F - test-convert-index-into-array-of-bytes-on-stack-with-literal/11") + 4629 # + 4630 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-index-into-array-of-bytes-on-stack-with-literal/12") + 4631 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-index-into-array-of-bytes-on-stack-with-literal/13") + 4632 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-index-into-array-of-bytes-on-stack-with-literal/14") + 4633 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-index-into-array-of-bytes-on-stack-with-literal/15") + 4634 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-index-into-array-of-bytes-on-stack-with-literal/16") + 4635 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-index-into-array-of-bytes-on-stack-with-literal/17") + 4636 # . epilogue + 4637 89/<- %esp 5/r32/ebp + 4638 5d/pop-to-ebp + 4639 c3/return + 4640 + 4641 test-convert-index-into-array-using-offset: + 4642 # . prologue + 4643 55/push-ebp + 4644 89/<- %ebp 4/r32/esp + 4645 # setup + 4646 (clear-stream _test-input-stream) + 4647 (clear-stream $_test-input-buffered-file->buffer) + 4648 (clear-stream _test-output-stream) + 4649 (clear-stream $_test-output-buffered-file->buffer) + 4650 # + 4651 (write _test-input-stream "fn foo {\n") + 4652 (write _test-input-stream " var arr/eax: (addr array int) <- copy 0\n") + 4653 (write _test-input-stream " var idx/ecx: int <- copy 3\n") + 4654 (write _test-input-stream " var off/ecx: (offset int) <- compute-offset arr, idx\n") + 4655 (write _test-input-stream " var x/eax: (addr int) <- index arr, off\n") + 4656 (write _test-input-stream "}\n") + 4657 # convert + 4658 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) + 4659 (flush _test-output-buffered-file) + 4660 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- + 4666 # check output + 4667 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-index-into-array-using-offset/0") + 4668 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-index-into-array-using-offset/1") + 4669 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-index-into-array-using-offset/2") + 4670 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-index-into-array-using-offset/3") + 4671 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-index-into-array-using-offset/4") + 4672 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-index-into-array-using-offset/5") + 4673 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %eax" "F - test-convert-index-into-array-using-offset/6") + 4674 (check-next-stream-line-equal _test-output-stream " b8/copy-to-eax 0/imm32" "F - test-convert-index-into-array-using-offset/7") + 4675 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %ecx" "F - test-convert-index-into-array-using-offset/8") + 4676 (check-next-stream-line-equal _test-output-stream " b9/copy-to-ecx 3/imm32" "F - test-convert-index-into-array-using-offset/9") + 4677 (check-next-stream-line-equal _test-output-stream " 69/multiply %ecx 0x00000004/imm32 0x00000001/r32" "F - test-convert-index-into-array-using-offset/10") + 4678 (check-next-stream-line-equal _test-output-stream " 8d/copy-address *(eax + ecx + 4) 0x00000000/r32" "F - test-convert-index-into-array-using-offset/11") + 4679 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %ecx" "F - test-convert-index-into-array-using-offset/12") + 4680 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %eax" "F - test-convert-index-into-array-using-offset/13") + 4681 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-index-into-array-using-offset/14") + 4682 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-index-into-array-using-offset/15") + 4683 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-index-into-array-using-offset/16") + 4684 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-index-into-array-using-offset/17") + 4685 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-index-into-array-using-offset/18") + 4686 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-index-into-array-using-offset/19") + 4687 # . epilogue + 4688 89/<- %esp 5/r32/ebp + 4689 5d/pop-to-ebp + 4690 c3/return + 4691 + 4692 test-convert-index-into-array-of-bytes-using-offset: + 4693 # . prologue + 4694 55/push-ebp + 4695 89/<- %ebp 4/r32/esp + 4696 # setup + 4697 (clear-stream _test-input-stream) + 4698 (clear-stream $_test-input-buffered-file->buffer) + 4699 (clear-stream _test-output-stream) + 4700 (clear-stream $_test-output-buffered-file->buffer) + 4701 # + 4702 (write _test-input-stream "fn foo {\n") + 4703 (write _test-input-stream " var arr/eax: (addr array byte) <- copy 0\n") + 4704 (write _test-input-stream " var idx/ecx: int <- copy 3\n") + 4705 (write _test-input-stream " var off/ecx: (offset byte) <- compute-offset arr, idx\n") + 4706 (write _test-input-stream " var x/eax: (addr byte) <- index arr, off\n") + 4707 (write _test-input-stream "}\n") + 4708 # convert + 4709 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) + 4710 (flush _test-output-buffered-file) + 4711 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- + 4717 # check output + 4718 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-index-into-array-of-bytes-using-offset/0") + 4719 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-index-into-array-of-bytes-using-offset/1") + 4720 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-index-into-array-of-bytes-using-offset/2") + 4721 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-index-into-array-of-bytes-using-offset/3") + 4722 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-index-into-array-of-bytes-using-offset/4") + 4723 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-index-into-array-of-bytes-using-offset/5") + 4724 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %eax" "F - test-convert-index-into-array-of-bytes-using-offset/6") + 4725 (check-next-stream-line-equal _test-output-stream " b8/copy-to-eax 0/imm32" "F - test-convert-index-into-array-of-bytes-using-offset/7") + 4726 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %ecx" "F - test-convert-index-into-array-of-bytes-using-offset/8") + 4727 (check-next-stream-line-equal _test-output-stream " b9/copy-to-ecx 3/imm32" "F - test-convert-index-into-array-of-bytes-using-offset/9") + 4728 (check-next-stream-line-equal _test-output-stream " 69/multiply %ecx 0x00000001/imm32 0x00000001/r32" "F - test-convert-index-into-array-of-bytes-using-offset/10") + 4729 (check-next-stream-line-equal _test-output-stream " 8d/copy-address *(eax + ecx + 4) 0x00000000/r32" "F - test-convert-index-into-array-of-bytes-using-offset/11") + 4730 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %ecx" "F - test-convert-index-into-array-of-bytes-using-offset/12") + 4731 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %eax" "F - test-convert-index-into-array-of-bytes-using-offset/13") + 4732 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-index-into-array-of-bytes-using-offset/14") + 4733 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-index-into-array-of-bytes-using-offset/15") + 4734 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-index-into-array-of-bytes-using-offset/16") + 4735 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-index-into-array-of-bytes-using-offset/17") + 4736 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-index-into-array-of-bytes-using-offset/18") + 4737 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-index-into-array-of-bytes-using-offset/19") + 4738 # . epilogue + 4739 89/<- %esp 5/r32/ebp + 4740 5d/pop-to-ebp + 4741 c3/return + 4742 + 4743 test-convert-index-into-array-using-offset-on-stack: + 4744 # . prologue + 4745 55/push-ebp + 4746 89/<- %ebp 4/r32/esp + 4747 # setup + 4748 (clear-stream _test-input-stream) + 4749 (clear-stream $_test-input-buffered-file->buffer) + 4750 (clear-stream _test-output-stream) + 4751 (clear-stream $_test-output-buffered-file->buffer) + 4752 # + 4753 (write _test-input-stream "fn foo {\n") + 4754 (write _test-input-stream " var arr/eax: (addr array int) <- copy 0\n") + 4755 (write _test-input-stream " var idx: int\n") + 4756 (write _test-input-stream " var off/ecx: (offset int) <- compute-offset arr, idx\n") + 4757 (write _test-input-stream " var x/eax: (addr int) <- index arr, off\n") + 4758 (write _test-input-stream "}\n") + 4759 # convert + 4760 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) + 4761 (flush _test-output-buffered-file) + 4762 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- + 4768 # check output + 4769 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-index-into-array-using-offset-on-stack/0") + 4770 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-index-into-array-using-offset-on-stack/1") + 4771 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-index-into-array-using-offset-on-stack/2") + 4772 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-index-into-array-using-offset-on-stack/3") + 4773 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-index-into-array-using-offset-on-stack/4") + 4774 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-index-into-array-using-offset-on-stack/5") + 4775 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %eax" "F - test-convert-index-into-array-using-offset-on-stack/6") + 4776 (check-next-stream-line-equal _test-output-stream " b8/copy-to-eax 0/imm32" "F - test-convert-index-into-array-using-offset-on-stack/7") + 4777 (check-next-stream-line-equal _test-output-stream " 68/push 0/imm32" "F - test-convert-index-into-array-using-offset-on-stack/8") + 4778 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %ecx" "F - test-convert-index-into-array-using-offset-on-stack/9") + 4779 (check-next-stream-line-equal _test-output-stream " 69/multiply *(ebp+0xfffffff8) 0x00000004/imm32 0x00000001/r32" "F - test-convert-index-into-array-using-offset-on-stack/10") + 4780 (check-next-stream-line-equal _test-output-stream " 8d/copy-address *(eax + ecx + 4) 0x00000000/r32" "F - test-convert-index-into-array-using-offset-on-stack/11") + 4781 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %ecx" "F - test-convert-index-into-array-using-offset-on-stack/12") + 4782 (check-next-stream-line-equal _test-output-stream " 81 0/subop/add %esp 0x00000004/imm32" "F - test-convert-index-into-array-using-offset-on-stack/13") + 4783 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %eax" "F - test-convert-index-into-array-using-offset-on-stack/14") + 4784 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-index-into-array-using-offset-on-stack/15") + 4785 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-index-into-array-using-offset-on-stack/16") + 4786 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-index-into-array-using-offset-on-stack/17") + 4787 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-index-into-array-using-offset-on-stack/18") + 4788 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-index-into-array-using-offset-on-stack/19") + 4789 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-index-into-array-using-offset-on-stack/20") + 4790 # . epilogue + 4791 89/<- %esp 5/r32/ebp + 4792 5d/pop-to-ebp + 4793 c3/return + 4794 + 4795 test-convert-index-into-array-of-bytes-using-offset-on-stack: + 4796 # . prologue + 4797 55/push-ebp + 4798 89/<- %ebp 4/r32/esp + 4799 # setup + 4800 (clear-stream _test-input-stream) + 4801 (clear-stream $_test-input-buffered-file->buffer) + 4802 (clear-stream _test-output-stream) + 4803 (clear-stream $_test-output-buffered-file->buffer) + 4804 # + 4805 (write _test-input-stream "fn foo {\n") + 4806 (write _test-input-stream " var arr/eax: (addr array byte) <- copy 0\n") + 4807 (write _test-input-stream " var idx: int\n") + 4808 (write _test-input-stream " var off/ecx: (offset byte) <- compute-offset arr, idx\n") + 4809 (write _test-input-stream " var x/eax: (addr byte) <- index arr, off\n") + 4810 (write _test-input-stream "}\n") + 4811 # convert + 4812 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) + 4813 (flush _test-output-buffered-file) + 4814 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- + 4820 # check output + 4821 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-index-into-array-of-bytes-using-offset-on-stack/0") + 4822 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-index-into-array-of-bytes-using-offset-on-stack/1") + 4823 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-index-into-array-of-bytes-using-offset-on-stack/2") + 4824 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-index-into-array-of-bytes-using-offset-on-stack/3") + 4825 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-index-into-array-of-bytes-using-offset-on-stack/4") + 4826 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-index-into-array-of-bytes-using-offset-on-stack/5") + 4827 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %eax" "F - test-convert-index-into-array-of-bytes-using-offset-on-stack/6") + 4828 (check-next-stream-line-equal _test-output-stream " b8/copy-to-eax 0/imm32" "F - test-convert-index-into-array-of-bytes-using-offset-on-stack/7") + 4829 (check-next-stream-line-equal _test-output-stream " 68/push 0/imm32" "F - test-convert-index-into-array-of-bytes-using-offset-on-stack/8") + 4830 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %ecx" "F - test-convert-index-into-array-of-bytes-using-offset-on-stack/9") + 4831 (check-next-stream-line-equal _test-output-stream " 69/multiply *(ebp+0xfffffff8) 0x00000001/imm32 0x00000001/r32" "F - test-convert-index-into-array-of-bytes-using-offset-on-stack/10") + 4832 (check-next-stream-line-equal _test-output-stream " 8d/copy-address *(eax + ecx + 4) 0x00000000/r32" "F - test-convert-index-into-array-of-bytes-using-offset-on-stack/11") + 4833 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %ecx" "F - test-convert-index-into-array-of-bytes-using-offset-on-stack/12") + 4834 (check-next-stream-line-equal _test-output-stream " 81 0/subop/add %esp 0x00000004/imm32" "F - test-convert-index-into-array-of-bytes-using-offset-on-stack/13") + 4835 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %eax" "F - test-convert-index-into-array-of-bytes-using-offset-on-stack/14") + 4836 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-index-into-array-of-bytes-using-offset-on-stack/15") + 4837 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-index-into-array-of-bytes-using-offset-on-stack/16") + 4838 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-index-into-array-of-bytes-using-offset-on-stack/17") + 4839 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-index-into-array-of-bytes-using-offset-on-stack/18") + 4840 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-index-into-array-of-bytes-using-offset-on-stack/19") + 4841 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-index-into-array-of-bytes-using-offset-on-stack/20") + 4842 # . epilogue + 4843 89/<- %esp 5/r32/ebp + 4844 5d/pop-to-ebp + 4845 c3/return + 4846 + 4847 test-convert-function-and-type-definition: + 4848 # . prologue + 4849 55/push-ebp + 4850 89/<- %ebp 4/r32/esp + 4851 # setup + 4852 (clear-stream _test-input-stream) + 4853 (clear-stream $_test-input-buffered-file->buffer) + 4854 (clear-stream _test-output-stream) + 4855 (clear-stream $_test-output-buffered-file->buffer) + 4856 # + 4857 (write _test-input-stream "fn foo a: (addr t) {\n") + 4858 (write _test-input-stream " var _a/eax: (addr t) <- copy a\n") + 4859 (write _test-input-stream " var b/ecx: (addr int) <- get _a, x\n") + 4860 (write _test-input-stream " var c/ecx: (addr int) <- get _a, y\n") + 4861 (write _test-input-stream "}\n") + 4862 (write _test-input-stream "type t {\n") + 4863 (write _test-input-stream " x: int\n") + 4864 (write _test-input-stream " y: int\n") + 4865 (write _test-input-stream "}\n") + 4866 # convert + 4867 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) + 4868 (flush _test-output-buffered-file) + 4869 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- + 4875 # check output + 4876 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-function-and-type-definition/0") + 4877 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-function-and-type-definition/1") + 4878 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-function-and-type-definition/2") + 4879 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-function-and-type-definition/3") + 4880 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-and-type-definition/4") + 4881 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-function-and-type-definition/5") + 4882 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %eax" "F - test-convert-function-and-type-definition/6") + 4883 (check-next-stream-line-equal _test-output-stream " 8b/-> *(ebp+0x00000008) 0x00000000/r32" "F - test-convert-function-and-type-definition/7") + 4884 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %ecx" "F - test-convert-function-and-type-definition/8") + 4885 (check-next-stream-line-equal _test-output-stream " 8d/copy-address *(eax + 0x00000000) 0x00000001/r32" "F - test-convert-function-and-type-definition/9") + 4886 (check-next-stream-line-equal _test-output-stream " 8d/copy-address *(eax + 0x00000004) 0x00000001/r32" "F - test-convert-function-and-type-definition/11") + 4887 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %ecx" "F - test-convert-function-and-type-definition/13") + 4888 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %eax" "F - test-convert-function-and-type-definition/14") + 4889 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-and-type-definition/15") + 4890 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-function-and-type-definition/16") + 4891 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-function-and-type-definition/17") + 4892 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-function-and-type-definition/18") + 4893 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-function-and-type-definition/19") + 4894 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-function-and-type-definition/20") + 4895 # . epilogue + 4896 89/<- %esp 5/r32/ebp + 4897 5d/pop-to-ebp + 4898 c3/return + 4899 + 4900 test-type-definition-with-array: + 4901 # . prologue + 4902 55/push-ebp + 4903 89/<- %ebp 4/r32/esp + 4904 # setup + 4905 (clear-stream _test-input-stream) + 4906 (clear-stream $_test-input-buffered-file->buffer) + 4907 (clear-stream _test-output-stream) + 4908 (clear-stream $_test-output-buffered-file->buffer) + 4909 (clear-stream _test-error-stream) + 4910 (clear-stream $_test-error-buffered-file->buffer) + 4911 # var ed/edx: exit-descriptor = tailor-exit-descriptor(16) + 4912 68/push 0/imm32 + 4913 68/push 0/imm32 + 4914 89/<- %edx 4/r32/esp + 4915 (tailor-exit-descriptor %edx 0x10) + 4916 # + 4917 (write _test-input-stream "type t {\n") + 4918 (write _test-input-stream " a: (array int 3)\n") + 4919 (write _test-input-stream "}\n") + 4920 # convert + 4921 (convert-mu _test-input-buffered-file _test-output-buffered-file _test-error-buffered-file %edx) + 4922 # registers except esp clobbered at this point + 4923 # restore ed + 4924 89/<- %edx 4/r32/esp + 4925 (flush _test-output-buffered-file) + 4926 (flush _test-error-buffered-file) + 4927 +-- 6 lines: #? # dump _test-error-stream ------------------------------------------------------------------------------------------------------------------------------------------ + 4933 # check output + 4934 (check-stream-equal _test-output-stream "" "F - test-type-definition-with-array: output should be empty") + 4935 (check-next-stream-line-equal _test-error-stream "type t: 'array' elements not allowed for now" "F - test-type-definition-with-array: error message") + 4936 # check that stop(1) was called + 4937 (check-ints-equal *(edx+4) 2 "F - test-type-definition-with-array: exit status") + 4938 # don't restore from ebp + 4939 81 0/subop/add %esp 8/imm32 + 4940 # . epilogue + 4941 5d/pop-to-ebp + 4942 c3/return + 4943 + 4944 test-type-definition-with-addr: + 4945 # . prologue + 4946 55/push-ebp + 4947 89/<- %ebp 4/r32/esp + 4948 # setup + 4949 (clear-stream _test-input-stream) + 4950 (clear-stream $_test-input-buffered-file->buffer) + 4951 (clear-stream _test-output-stream) + 4952 (clear-stream $_test-output-buffered-file->buffer) + 4953 (clear-stream _test-error-stream) + 4954 (clear-stream $_test-error-buffered-file->buffer) + 4955 # var ed/edx: exit-descriptor = tailor-exit-descriptor(16) + 4956 68/push 0/imm32 + 4957 68/push 0/imm32 + 4958 89/<- %edx 4/r32/esp + 4959 (tailor-exit-descriptor %edx 0x10) + 4960 # + 4961 (write _test-input-stream "type t {\n") + 4962 (write _test-input-stream " a: (addr int)\n") + 4963 (write _test-input-stream "}\n") + 4964 # convert + 4965 (convert-mu _test-input-buffered-file _test-output-buffered-file _test-error-buffered-file %edx) + 4966 # registers except esp clobbered at this point + 4967 # restore ed + 4968 89/<- %edx 4/r32/esp + 4969 (flush _test-output-buffered-file) + 4970 (flush _test-error-buffered-file) + 4971 +-- 6 lines: #? # dump _test-error-stream ------------------------------------------------------------------------------------------------------------------------------------------ + 4977 # check output + 4978 (check-stream-equal _test-output-stream "" "F - test-type-definition-with-addr: output should be empty") + 4979 (check-next-stream-line-equal _test-error-stream "type t: 'addr' elements not allowed" "F - test-type-definition-with-addr: error message") + 4980 # check that stop(1) was called + 4981 (check-ints-equal *(edx+4) 2 "F - test-type-definition-with-addr: exit status") + 4982 # don't restore from ebp + 4983 81 0/subop/add %esp 8/imm32 + 4984 # . epilogue + 4985 5d/pop-to-ebp + 4986 c3/return + 4987 + 4988 test-convert-function-with-local-var-with-user-defined-type: + 4989 # . prologue + 4990 55/push-ebp + 4991 89/<- %ebp 4/r32/esp + 4992 # setup + 4993 (clear-stream _test-input-stream) + 4994 (clear-stream $_test-input-buffered-file->buffer) + 4995 (clear-stream _test-output-stream) + 4996 (clear-stream $_test-output-buffered-file->buffer) + 4997 # + 4998 (write _test-input-stream "fn foo {\n") + 4999 (write _test-input-stream " var a: t\n") + 5000 (write _test-input-stream "}\n") + 5001 (write _test-input-stream "type t {\n") + 5002 (write _test-input-stream " x: int\n") + 5003 (write _test-input-stream " y: int\n") + 5004 (write _test-input-stream "}\n") + 5005 # convert + 5006 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) + 5007 (flush _test-output-buffered-file) + 5008 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- + 5014 # check output + 5015 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-function-with-local-var-with-user-defined-type/0") + 5016 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-function-with-local-var-with-user-defined-type/1") + 5017 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-function-with-local-var-with-user-defined-type/2") + 5018 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-function-with-local-var-with-user-defined-type/3") + 5019 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-with-local-var-with-user-defined-type/4") + 5020 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-function-with-local-var-with-user-defined-type/5") + 5021 (check-next-stream-line-equal _test-output-stream " 68/push 0/imm32" "F - test-convert-function-with-local-var-with-user-defined-type/6") + 5022 (check-next-stream-line-equal _test-output-stream " 68/push 0/imm32" "F - test-convert-function-with-local-var-with-user-defined-type/7") + 5023 (check-next-stream-line-equal _test-output-stream " 81 0/subop/add %esp 0x00000008/imm32" "F - test-convert-function-with-local-var-with-user-defined-type/8") + 5024 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-with-local-var-with-user-defined-type/9") + 5025 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-function-with-local-var-with-user-defined-type/10") + 5026 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-function-with-local-var-with-user-defined-type/11") + 5027 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-function-with-local-var-with-user-defined-type/12") + 5028 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-function-with-local-var-with-user-defined-type/13") + 5029 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-function-with-local-var-with-user-defined-type/14") + 5030 # . epilogue + 5031 89/<- %esp 5/r32/ebp + 5032 5d/pop-to-ebp + 5033 c3/return + 5034 + 5035 test-convert-function-call-with-arg-of-user-defined-type: + 5036 # . prologue + 5037 55/push-ebp + 5038 89/<- %ebp 4/r32/esp + 5039 # setup + 5040 (clear-stream _test-input-stream) + 5041 (clear-stream $_test-input-buffered-file->buffer) + 5042 (clear-stream _test-output-stream) + 5043 (clear-stream $_test-output-buffered-file->buffer) + 5044 # + 5045 (write _test-input-stream "fn f {\n") + 5046 (write _test-input-stream " var a: t\n") + 5047 (write _test-input-stream " foo a\n") + 5048 (write _test-input-stream "}\n") + 5049 (write _test-input-stream "fn foo x: t {\n") + 5050 (write _test-input-stream "}\n") + 5051 (write _test-input-stream "type t {\n") + 5052 (write _test-input-stream " x: int\n") + 5053 (write _test-input-stream " y: int\n") + 5054 (write _test-input-stream "}\n") + 5055 # convert + 5056 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) + 5057 (flush _test-output-buffered-file) + 5058 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- + 5064 # check output + 5065 (check-next-stream-line-equal _test-output-stream "f:" "F - test-convert-function-call-with-arg-of-user-defined-type/0") + 5066 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-function-call-with-arg-of-user-defined-type/1") + 5067 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-function-call-with-arg-of-user-defined-type/2") + 5068 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-function-call-with-arg-of-user-defined-type/3") + 5069 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-call-with-arg-of-user-defined-type/4") + 5070 (check-next-stream-line-equal _test-output-stream "$f:0x00000001:loop:" "F - test-convert-function-call-with-arg-of-user-defined-type/5") + 5071 # var a: t + 5072 (check-next-stream-line-equal _test-output-stream " 68/push 0/imm32" "F - test-convert-function-call-with-arg-of-user-defined-type/6") + 5073 (check-next-stream-line-equal _test-output-stream " 68/push 0/imm32" "F - test-convert-function-call-with-arg-of-user-defined-type/7") + 5074 # foo a + 5075 (check-next-stream-line-equal _test-output-stream " (foo *(ebp+0xfffffff8) *(ebp+0xfffffffc))" "F - test-convert-function-call-with-arg-of-user-defined-type/8") + 5076 # + 5077 (check-next-stream-line-equal _test-output-stream " 81 0/subop/add %esp 0x00000008/imm32" "F - test-convert-function-call-with-arg-of-user-defined-type/9") + 5078 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-call-with-arg-of-user-defined-type/10") + 5079 (check-next-stream-line-equal _test-output-stream "$f:0x00000001:break:" "F - test-convert-function-call-with-arg-of-user-defined-type/11") + 5080 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-function-call-with-arg-of-user-defined-type/12") + 5081 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-function-call-with-arg-of-user-defined-type/13") + 5082 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-function-call-with-arg-of-user-defined-type/14") + 5083 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-function-call-with-arg-of-user-defined-type/15") + 5084 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-function-call-with-arg-of-user-defined-type/16") + 5085 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-function-call-with-arg-of-user-defined-type/17") + 5086 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-function-call-with-arg-of-user-defined-type/18") + 5087 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-function-call-with-arg-of-user-defined-type/19") + 5088 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-function-call-with-arg-of-user-defined-type/20") + 5089 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-function-call-with-arg-of-user-defined-type/21") + 5090 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-function-call-with-arg-of-user-defined-type/22") + 5091 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-function-call-with-arg-of-user-defined-type/23") + 5092 # . epilogue + 5093 89/<- %esp 5/r32/ebp + 5094 5d/pop-to-ebp + 5095 c3/return + 5096 + 5097 test-convert-function-call-with-arg-of-user-defined-type-register-indirect: + 5098 # . prologue + 5099 55/push-ebp + 5100 89/<- %ebp 4/r32/esp + 5101 # setup + 5102 (clear-stream _test-input-stream) + 5103 (clear-stream $_test-input-buffered-file->buffer) + 5104 (clear-stream _test-output-stream) + 5105 (clear-stream $_test-output-buffered-file->buffer) + 5106 # + 5107 (write _test-input-stream "fn f {\n") + 5108 (write _test-input-stream " var a/eax: (addr t) <- copy 0\n") + 5109 (write _test-input-stream " foo *a\n") + 5110 (write _test-input-stream "}\n") + 5111 (write _test-input-stream "fn foo x: t {\n") + 5112 (write _test-input-stream "}\n") + 5113 (write _test-input-stream "type t {\n") + 5114 (write _test-input-stream " x: int\n") + 5115 (write _test-input-stream " y: int\n") + 5116 (write _test-input-stream "}\n") + 5117 # convert + 5118 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) + 5119 (flush _test-output-buffered-file) + 5120 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- + 5126 # check output + 5127 (check-next-stream-line-equal _test-output-stream "f:" "F - test-convert-function-call-with-arg-of-user-defined-type/0") + 5128 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-function-call-with-arg-of-user-defined-type/1") + 5129 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-function-call-with-arg-of-user-defined-type/2") + 5130 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-function-call-with-arg-of-user-defined-type/3") + 5131 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-call-with-arg-of-user-defined-type/4") + 5132 (check-next-stream-line-equal _test-output-stream "$f:0x00000001:loop:" "F - test-convert-function-call-with-arg-of-user-defined-type/5") + 5133 # var a + 5134 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %eax" "F - test-convert-function-call-with-arg-of-user-defined-type/6") + 5135 (check-next-stream-line-equal _test-output-stream " b8/copy-to-eax 0/imm32" "F - test-convert-function-call-with-arg-of-user-defined-type/7") + 5136 # foo a + 5137 (check-next-stream-line-equal _test-output-stream " (foo *(eax+0x00000000) *(eax+0x00000004))" "F - test-convert-function-call-with-arg-of-user-defined-type/8") + 5138 # + 5139 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %eax" "F - test-convert-function-call-with-arg-of-user-defined-type/9") + 5140 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-call-with-arg-of-user-defined-type/10") + 5141 (check-next-stream-line-equal _test-output-stream "$f:0x00000001:break:" "F - test-convert-function-call-with-arg-of-user-defined-type/11") + 5142 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-function-call-with-arg-of-user-defined-type/12") + 5143 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-function-call-with-arg-of-user-defined-type/13") + 5144 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-function-call-with-arg-of-user-defined-type/14") + 5145 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-function-call-with-arg-of-user-defined-type/15") + 5146 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-function-call-with-arg-of-user-defined-type/16") + 5147 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-function-call-with-arg-of-user-defined-type/17") + 5148 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-function-call-with-arg-of-user-defined-type/18") + 5149 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-function-call-with-arg-of-user-defined-type/19") + 5150 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-function-call-with-arg-of-user-defined-type/20") + 5151 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-function-call-with-arg-of-user-defined-type/21") + 5152 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-function-call-with-arg-of-user-defined-type/22") + 5153 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-function-call-with-arg-of-user-defined-type/23") + 5154 # . epilogue + 5155 89/<- %esp 5/r32/ebp + 5156 5d/pop-to-ebp + 5157 c3/return + 5158 + 5159 # we don't have special support for call-by-reference; just explicitly create + 5160 # a new variable with the address of the arg + 5161 test-convert-function-call-with-arg-of-user-defined-type-by-reference: + 5162 # . prologue + 5163 55/push-ebp + 5164 89/<- %ebp 4/r32/esp + 5165 # setup + 5166 (clear-stream _test-input-stream) + 5167 (clear-stream $_test-input-buffered-file->buffer) + 5168 (clear-stream _test-output-stream) + 5169 (clear-stream $_test-output-buffered-file->buffer) + 5170 # + 5171 (write _test-input-stream "fn f {\n") + 5172 (write _test-input-stream " var a: t\n") + 5173 (write _test-input-stream " var b/eax: (addr t) <- address a\n") + 5174 (write _test-input-stream " foo b\n") + 5175 (write _test-input-stream "}\n") + 5176 (write _test-input-stream "fn foo x: (addr t) {\n") + 5177 (write _test-input-stream " var x/ecx: (addr int) <- copy x\n") + 5178 (write _test-input-stream " increment *x\n") + 5179 (write _test-input-stream "}\n") + 5180 (write _test-input-stream "type t {\n") + 5181 (write _test-input-stream " x: int\n") + 5182 (write _test-input-stream " y: int\n") + 5183 (write _test-input-stream "}\n") + 5184 # convert + 5185 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) + 5186 (flush _test-output-buffered-file) + 5187 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- + 5193 # check output + 5194 (check-next-stream-line-equal _test-output-stream "f:" "F - test-convert-function-call-with-arg-of-user-defined-type-by-reference/0") + 5195 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-function-call-with-arg-of-user-defined-type-by-reference/1") + 5196 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-function-call-with-arg-of-user-defined-type-by-reference/2") + 5197 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-function-call-with-arg-of-user-defined-type-by-reference/3") + 5198 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-call-with-arg-of-user-defined-type-by-reference/4") + 5199 (check-next-stream-line-equal _test-output-stream "$f:0x00000001:loop:" "F - test-convert-function-call-with-arg-of-user-defined-type-by-reference/5") + 5200 # var a: t + 5201 (check-next-stream-line-equal _test-output-stream " 68/push 0/imm32" "F - test-convert-function-call-with-arg-of-user-defined-type-by-reference/6") + 5202 (check-next-stream-line-equal _test-output-stream " 68/push 0/imm32" "F - test-convert-function-call-with-arg-of-user-defined-type-by-reference/7") + 5203 # var b/eax: (addr t) + 5204 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %eax" "F - test-convert-function-call-with-arg-of-user-defined-type-by-reference/8") + 5205 (check-next-stream-line-equal _test-output-stream " 8d/copy-address *(ebp+0xfffffff8) 0x00000000/r32" "F - test-convert-function-call-with-arg-of-user-defined-type-by-reference/9") + 5206 # foo a + 5207 (check-next-stream-line-equal _test-output-stream " (foo %eax)" "F - test-convert-function-call-with-arg-of-user-defined-type-by-reference/10") + 5208 # + 5209 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %eax" "F - test-convert-function-call-with-arg-of-user-defined-type-by-reference/11") + 5210 (check-next-stream-line-equal _test-output-stream " 81 0/subop/add %esp 0x00000008/imm32" "F - test-convert-function-call-with-arg-of-user-defined-type-by-reference/12") + 5211 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-call-with-arg-of-user-defined-type-by-reference/13") + 5212 (check-next-stream-line-equal _test-output-stream "$f:0x00000001:break:" "F - test-convert-function-call-with-arg-of-user-defined-type-by-reference/14") + 5213 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-function-call-with-arg-of-user-defined-type-by-reference/15") + 5214 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-function-call-with-arg-of-user-defined-type-by-reference/16") + 5215 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-function-call-with-arg-of-user-defined-type-by-reference/17") + 5216 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-function-call-with-arg-of-user-defined-type-by-reference/18") + 5217 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-function-call-with-arg-of-user-defined-type-by-reference/19") + 5218 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-function-call-with-arg-of-user-defined-type-by-reference/20") + 5219 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-function-call-with-arg-of-user-defined-type-by-reference/21") + 5220 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-function-call-with-arg-of-user-defined-type-by-reference/22") + 5221 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-function-call-with-arg-of-user-defined-type-by-reference/23") + 5222 (check-next-stream-line-equal _test-output-stream "$foo:0x00000002:loop:" "F - test-convert-function-call-with-arg-of-user-defined-type-by-reference/24") + 5223 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %ecx" "F - test-convert-function-call-with-arg-of-user-defined-type-by-reference/25") + 5224 (check-next-stream-line-equal _test-output-stream " 8b/-> *(ebp+0x00000008) 0x00000001/r32" "F - test-convert-function-call-with-arg-of-user-defined-type-by-reference/26") + 5225 (check-next-stream-line-equal _test-output-stream " ff 0/subop/increment *ecx" "F - test-convert-function-call-with-arg-of-user-defined-type-by-reference/27") + 5226 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %ecx" "F - test-convert-function-call-with-arg-of-user-defined-type-by-reference/28") + 5227 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-function-call-with-arg-of-user-defined-type-by-reference/29") + 5228 (check-next-stream-line-equal _test-output-stream "$foo:0x00000002:break:" "F - test-convert-function-call-with-arg-of-user-defined-type-by-reference/30") + 5229 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-function-call-with-arg-of-user-defined-type-by-reference/31") + 5230 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-function-call-with-arg-of-user-defined-type-by-reference/32") + 5231 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-function-call-with-arg-of-user-defined-type-by-reference/33") + 5232 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-function-call-with-arg-of-user-defined-type-by-reference/34") + 5233 # . epilogue + 5234 89/<- %esp 5/r32/ebp + 5235 5d/pop-to-ebp + 5236 c3/return + 5237 + 5238 test-convert-get-on-local-variable: + 5239 # . prologue + 5240 55/push-ebp + 5241 89/<- %ebp 4/r32/esp + 5242 # setup + 5243 (clear-stream _test-input-stream) + 5244 (clear-stream $_test-input-buffered-file->buffer) + 5245 (clear-stream _test-output-stream) + 5246 (clear-stream $_test-output-buffered-file->buffer) + 5247 # + 5248 (write _test-input-stream "fn foo {\n") + 5249 (write _test-input-stream " var a: t\n") + 5250 (write _test-input-stream " var c/ecx: (addr int) <- get a, y\n") + 5251 (write _test-input-stream "}\n") + 5252 (write _test-input-stream "type t {\n") + 5253 (write _test-input-stream " x: int\n") + 5254 (write _test-input-stream " y: int\n") + 5255 (write _test-input-stream "}\n") + 5256 # convert + 5257 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) + 5258 (flush _test-output-buffered-file) + 5259 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- + 5265 # check output + 5266 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-get-on-local-variable/0") + 5267 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-get-on-local-variable/1") + 5268 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-get-on-local-variable/2") + 5269 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-get-on-local-variable/3") + 5270 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-get-on-local-variable/4") + 5271 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-get-on-local-variable/5") + 5272 # var a + 5273 (check-next-stream-line-equal _test-output-stream " 68/push 0/imm32" "F - test-convert-get-on-local-variable/6") + 5274 (check-next-stream-line-equal _test-output-stream " 68/push 0/imm32" "F - test-convert-get-on-local-variable/7") + 5275 # var c + 5276 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %ecx" "F - test-convert-get-on-local-variable/8") + 5277 # get + 5278 (check-next-stream-line-equal _test-output-stream " 8d/copy-address *(ebp+0xfffffffc) 0x00000001/r32" "F - test-convert-get-on-local-variable/9") + 5279 # reclaim c + 5280 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %ecx" "F - test-convert-get-on-local-variable/10") + 5281 # reclaim a + 5282 (check-next-stream-line-equal _test-output-stream " 81 0/subop/add %esp 0x00000008/imm32" "F - test-convert-get-on-local-variable/11") + 5283 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-get-on-local-variable/12") + 5284 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-get-on-local-variable/13") + 5285 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-get-on-local-variable/14") + 5286 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-get-on-local-variable/15") + 5287 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-get-on-local-variable/16") + 5288 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-get-on-local-variable/17") + 5289 # . epilogue + 5290 89/<- %esp 5/r32/ebp + 5291 5d/pop-to-ebp + 5292 c3/return + 5293 + 5294 test-convert-get-on-function-argument: + 5295 # . prologue + 5296 55/push-ebp + 5297 89/<- %ebp 4/r32/esp + 5298 # setup + 5299 (clear-stream _test-input-stream) + 5300 (clear-stream $_test-input-buffered-file->buffer) + 5301 (clear-stream _test-output-stream) + 5302 (clear-stream $_test-output-buffered-file->buffer) + 5303 # + 5304 (write _test-input-stream "fn foo a: t {\n") + 5305 (write _test-input-stream " var c/ecx: (addr int) <- get a, y\n") + 5306 (write _test-input-stream "}\n") + 5307 (write _test-input-stream "type t {\n") + 5308 (write _test-input-stream " x: int\n") + 5309 (write _test-input-stream " y: int\n") + 5310 (write _test-input-stream "}\n") + 5311 # convert + 5312 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) + 5313 (flush _test-output-buffered-file) + 5314 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- + 5320 # check output + 5321 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-get-on-function-argument/0") + 5322 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-get-on-function-argument/1") + 5323 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-get-on-function-argument/2") + 5324 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-get-on-function-argument/3") + 5325 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-get-on-function-argument/4") + 5326 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-get-on-function-argument/5") + 5327 # var c + 5328 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %ecx" "F - test-convert-get-on-function-argument/6") + 5329 # get + 5330 (check-next-stream-line-equal _test-output-stream " 8d/copy-address *(ebp+0x0000000c) 0x00000001/r32" "F - test-convert-get-on-function-argument/7") + 5331 # reclaim c + 5332 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %ecx" "F - test-convert-get-on-function-argument/8") + 5333 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-get-on-function-argument/9") + 5334 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-get-on-function-argument/10") + 5335 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-get-on-function-argument/11") + 5336 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-get-on-function-argument/12") + 5337 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-get-on-function-argument/13") + 5338 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-get-on-function-argument/14") + 5339 # . epilogue + 5340 89/<- %esp 5/r32/ebp + 5341 5d/pop-to-ebp + 5342 c3/return + 5343 + 5344 test-convert-get-on-function-argument-with-known-type: + 5345 # . prologue + 5346 55/push-ebp + 5347 89/<- %ebp 4/r32/esp + 5348 # setup + 5349 (clear-stream _test-input-stream) + 5350 (clear-stream $_test-input-buffered-file->buffer) + 5351 (clear-stream _test-output-stream) + 5352 (clear-stream $_test-output-buffered-file->buffer) + 5353 # + 5354 (write _test-input-stream "type t {\n") + 5355 (write _test-input-stream " x: int\n") + 5356 (write _test-input-stream " y: int\n") 5357 (write _test-input-stream "}\n") - 5358 # convert - 5359 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) - 5360 (flush _test-output-buffered-file) - 5361 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 5367 # check output - 5368 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-get-on-function-argument-with-known-type/0") - 5369 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-get-on-function-argument-with-known-type/1") - 5370 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-get-on-function-argument-with-known-type/2") - 5371 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-get-on-function-argument-with-known-type/3") - 5372 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-get-on-function-argument-with-known-type/4") - 5373 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-get-on-function-argument-with-known-type/5") - 5374 # var c - 5375 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %ecx" "F - test-convert-get-on-function-argument-with-known-type/6") - 5376 # get - 5377 (check-next-stream-line-equal _test-output-stream " 8d/copy-address *(ebp+0x0000000c) 0x00000001/r32" "F - test-convert-get-on-function-argument-with-known-type/7") - 5378 # reclaim c - 5379 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %ecx" "F - test-convert-get-on-function-argument-with-known-type/8") - 5380 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-get-on-function-argument-with-known-type/9") - 5381 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-get-on-function-argument-with-known-type/10") - 5382 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-get-on-function-argument-with-known-type/11") - 5383 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-get-on-function-argument-with-known-type/12") - 5384 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-get-on-function-argument-with-known-type/13") - 5385 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-get-on-function-argument-with-known-type/14") - 5386 # . epilogue - 5387 89/<- %esp 5/r32/ebp - 5388 5d/pop-to-ebp - 5389 c3/return - 5390 - 5391 test-add-with-too-many-inouts: - 5392 # . prologue - 5393 55/push-ebp - 5394 89/<- %ebp 4/r32/esp - 5395 # setup - 5396 (clear-stream _test-input-stream) - 5397 (clear-stream $_test-input-buffered-file->buffer) - 5398 (clear-stream _test-output-stream) - 5399 (clear-stream $_test-output-buffered-file->buffer) - 5400 (clear-stream _test-error-stream) - 5401 (clear-stream $_test-error-buffered-file->buffer) - 5402 # var ed/edx: exit-descriptor = tailor-exit-descriptor(16) - 5403 68/push 0/imm32 - 5404 68/push 0/imm32 - 5405 89/<- %edx 4/r32/esp - 5406 (tailor-exit-descriptor %edx 0x10) - 5407 # - 5408 (write _test-input-stream "fn foo {\n") - 5409 (write _test-input-stream " var a: int\n") - 5410 (write _test-input-stream " var b/ecx: int <- add a, 0\n") - 5411 (write _test-input-stream "}\n") - 5412 # convert - 5413 (convert-mu _test-input-buffered-file _test-output-buffered-file _test-error-buffered-file %edx) - 5414 # registers except esp clobbered at this point - 5415 # restore ed - 5416 89/<- %edx 4/r32/esp - 5417 (flush _test-output-buffered-file) - 5418 (flush _test-error-buffered-file) - 5419 +-- 6 lines: #? # dump _test-error-stream --------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 5425 # check output - 5426 (check-stream-equal _test-output-stream "" "F - test-add-with-too-many-inouts: output should be empty") - 5427 (check-next-stream-line-equal _test-error-stream "fn foo: stmt add: too many inouts; most primitives support at most two arguments, across inouts and outputs" "F - test-add-with-too-many-inouts: error message") - 5428 # check that stop(1) was called - 5429 (check-ints-equal *(edx+4) 2 "F - test-add-with-too-many-inouts: exit status") - 5430 # don't restore from ebp - 5431 81 0/subop/add %esp 8/imm32 - 5432 # . epilogue - 5433 5d/pop-to-ebp - 5434 c3/return - 5435 - 5436 test-add-with-too-many-inouts-2: - 5437 # . prologue - 5438 55/push-ebp - 5439 89/<- %ebp 4/r32/esp - 5440 # setup - 5441 (clear-stream _test-input-stream) - 5442 (clear-stream $_test-input-buffered-file->buffer) - 5443 (clear-stream _test-output-stream) - 5444 (clear-stream $_test-output-buffered-file->buffer) - 5445 (clear-stream _test-error-stream) - 5446 (clear-stream $_test-error-buffered-file->buffer) - 5447 # var ed/edx: exit-descriptor = tailor-exit-descriptor(16) - 5448 68/push 0/imm32 - 5449 68/push 0/imm32 - 5450 89/<- %edx 4/r32/esp - 5451 (tailor-exit-descriptor %edx 0x10) - 5452 # - 5453 (write _test-input-stream "fn foo {\n") - 5454 (write _test-input-stream " var a: int\n") - 5455 (write _test-input-stream " add-to a, 0, 1\n") - 5456 (write _test-input-stream "}\n") - 5457 # convert - 5458 (convert-mu _test-input-buffered-file _test-output-buffered-file _test-error-buffered-file %edx) - 5459 # registers except esp clobbered at this point - 5460 # restore ed - 5461 89/<- %edx 4/r32/esp - 5462 (flush _test-output-buffered-file) - 5463 (flush _test-error-buffered-file) - 5464 +-- 6 lines: #? # dump _test-error-stream --------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 5470 # check output - 5471 (check-stream-equal _test-output-stream "" "F - test-add-with-too-many-inouts-2: output should be empty") - 5472 (check-next-stream-line-equal _test-error-stream "fn foo: stmt add-to: too many inouts; most primitives support at most two arguments, across inouts and outputs" "F - test-add-with-too-many-inouts-2: error message") - 5473 # check that stop(1) was called - 5474 (check-ints-equal *(edx+4) 2 "F - test-add-with-too-many-inouts-2: exit status") - 5475 # don't restore from ebp - 5476 81 0/subop/add %esp 8/imm32 - 5477 # . epilogue - 5478 5d/pop-to-ebp - 5479 c3/return - 5480 - 5481 test-add-with-too-many-outputs: - 5482 # . prologue - 5483 55/push-ebp - 5484 89/<- %ebp 4/r32/esp - 5485 # setup - 5486 (clear-stream _test-input-stream) - 5487 (clear-stream $_test-input-buffered-file->buffer) - 5488 (clear-stream _test-output-stream) - 5489 (clear-stream $_test-output-buffered-file->buffer) - 5490 (clear-stream _test-error-stream) - 5491 (clear-stream $_test-error-buffered-file->buffer) - 5492 # var ed/edx: exit-descriptor = tailor-exit-descriptor(16) - 5493 68/push 0/imm32 - 5494 68/push 0/imm32 - 5495 89/<- %edx 4/r32/esp - 5496 (tailor-exit-descriptor %edx 0x10) - 5497 # - 5498 (write _test-input-stream "fn foo {\n") - 5499 (write _test-input-stream " var a/eax: int <- copy 0\n") - 5500 (write _test-input-stream " var b/ebx: int <- copy 0\n") - 5501 (write _test-input-stream " var c/ecx: int <- copy 0\n") - 5502 (write _test-input-stream " c, b <- add a\n") - 5503 (write _test-input-stream "}\n") - 5504 # convert - 5505 (convert-mu _test-input-buffered-file _test-output-buffered-file _test-error-buffered-file %edx) - 5506 # registers except esp clobbered at this point - 5507 # restore ed - 5508 89/<- %edx 4/r32/esp - 5509 (flush _test-output-buffered-file) - 5510 (flush _test-error-buffered-file) - 5511 +-- 6 lines: #? # dump _test-error-stream --------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 5517 # check output - 5518 (check-stream-equal _test-output-stream "" "F - test-add-with-too-many-outputs: output should be empty") - 5519 (check-next-stream-line-equal _test-error-stream "fn foo: stmt add: too many outputs; most primitives support at most one output" "F - test-add-with-too-many-outputs: error message") - 5520 # check that stop(1) was called - 5521 (check-ints-equal *(edx+4) 2 "F - test-add-with-too-many-outputs: exit status") - 5522 # don't restore from ebp - 5523 81 0/subop/add %esp 8/imm32 - 5524 # . epilogue - 5525 5d/pop-to-ebp - 5526 c3/return - 5527 - 5528 test-add-with-non-number: - 5529 # . prologue - 5530 55/push-ebp - 5531 89/<- %ebp 4/r32/esp - 5532 # setup - 5533 (clear-stream _test-input-stream) - 5534 (clear-stream $_test-input-buffered-file->buffer) - 5535 (clear-stream _test-output-stream) - 5536 (clear-stream $_test-output-buffered-file->buffer) - 5537 (clear-stream _test-error-stream) - 5538 (clear-stream $_test-error-buffered-file->buffer) - 5539 # var ed/edx: exit-descriptor = tailor-exit-descriptor(16) - 5540 68/push 0/imm32 - 5541 68/push 0/imm32 - 5542 89/<- %edx 4/r32/esp - 5543 (tailor-exit-descriptor %edx 0x10) - 5544 # - 5545 (write _test-input-stream "fn foo {\n") - 5546 (write _test-input-stream " var a: int\n") - 5547 (write _test-input-stream " var b/ecx: (addr int) <- add a\n") - 5548 (write _test-input-stream "}\n") - 5549 # convert - 5550 (convert-mu _test-input-buffered-file _test-output-buffered-file _test-error-buffered-file %edx) - 5551 # registers except esp clobbered at this point - 5552 # restore ed - 5553 89/<- %edx 4/r32/esp - 5554 (flush _test-output-buffered-file) - 5555 (flush _test-error-buffered-file) - 5556 +-- 6 lines: #? # dump _test-error-stream --------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 5562 # check output - 5563 (check-stream-equal _test-output-stream "" "F - test-add-with-non-number: output should be empty") - 5564 (check-next-stream-line-equal _test-error-stream "fn foo: stmt add: only non-addr scalar args permitted" "F - test-add-with-non-number: error message") - 5565 # check that stop(1) was called - 5566 (check-ints-equal *(edx+4) 2 "F - test-add-with-non-number: exit status") - 5567 # don't restore from ebp - 5568 81 0/subop/add %esp 8/imm32 - 5569 # . epilogue - 5570 5d/pop-to-ebp - 5571 c3/return - 5572 - 5573 test-add-with-addr-dereferenced: - 5574 # . prologue - 5575 55/push-ebp - 5576 89/<- %ebp 4/r32/esp - 5577 # setup - 5578 (clear-stream _test-input-stream) - 5579 (clear-stream $_test-input-buffered-file->buffer) - 5580 (clear-stream _test-output-stream) - 5581 (clear-stream $_test-output-buffered-file->buffer) - 5582 # - 5583 (write _test-input-stream "fn foo {\n") - 5584 (write _test-input-stream " var a/eax: (addr int) <- copy 0\n") - 5585 (write _test-input-stream " add-to *a, 1\n") - 5586 (write _test-input-stream "}\n") - 5587 # convert - 5588 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) - 5589 (flush _test-output-buffered-file) - 5590 # no error - 5591 # . epilogue - 5592 89/<- %esp 5/r32/ebp - 5593 5d/pop-to-ebp - 5594 c3/return - 5595 - 5596 test-get-with-wrong-field: - 5597 # . prologue - 5598 55/push-ebp - 5599 89/<- %ebp 4/r32/esp - 5600 # setup - 5601 (clear-stream _test-input-stream) - 5602 (clear-stream $_test-input-buffered-file->buffer) - 5603 (clear-stream _test-output-stream) - 5604 (clear-stream $_test-output-buffered-file->buffer) - 5605 (clear-stream _test-error-stream) - 5606 (clear-stream $_test-error-buffered-file->buffer) - 5607 # var ed/edx: exit-descriptor = tailor-exit-descriptor(16) - 5608 68/push 0/imm32 - 5609 68/push 0/imm32 - 5610 89/<- %edx 4/r32/esp - 5611 (tailor-exit-descriptor %edx 0x10) - 5612 # - 5613 (write _test-input-stream "fn foo {\n") - 5614 (write _test-input-stream " var a: t\n") - 5615 (write _test-input-stream " var c/ecx: (addr int) <- get a, y\n") - 5616 (write _test-input-stream "}\n") - 5617 (write _test-input-stream "type t {\n") - 5618 (write _test-input-stream " x: int\n") + 5358 (write _test-input-stream "fn foo a: t {\n") + 5359 (write _test-input-stream " var c/ecx: (addr int) <- get a, y\n") + 5360 (write _test-input-stream "}\n") + 5361 # convert + 5362 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) + 5363 (flush _test-output-buffered-file) + 5364 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- + 5370 # check output + 5371 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-get-on-function-argument-with-known-type/0") + 5372 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-get-on-function-argument-with-known-type/1") + 5373 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-get-on-function-argument-with-known-type/2") + 5374 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-get-on-function-argument-with-known-type/3") + 5375 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-get-on-function-argument-with-known-type/4") + 5376 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-get-on-function-argument-with-known-type/5") + 5377 # var c + 5378 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %ecx" "F - test-convert-get-on-function-argument-with-known-type/6") + 5379 # get + 5380 (check-next-stream-line-equal _test-output-stream " 8d/copy-address *(ebp+0x0000000c) 0x00000001/r32" "F - test-convert-get-on-function-argument-with-known-type/7") + 5381 # reclaim c + 5382 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %ecx" "F - test-convert-get-on-function-argument-with-known-type/8") + 5383 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-get-on-function-argument-with-known-type/9") + 5384 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-get-on-function-argument-with-known-type/10") + 5385 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-get-on-function-argument-with-known-type/11") + 5386 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-get-on-function-argument-with-known-type/12") + 5387 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-get-on-function-argument-with-known-type/13") + 5388 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-get-on-function-argument-with-known-type/14") + 5389 # . epilogue + 5390 89/<- %esp 5/r32/ebp + 5391 5d/pop-to-ebp + 5392 c3/return + 5393 + 5394 test-add-with-too-many-inouts: + 5395 # . prologue + 5396 55/push-ebp + 5397 89/<- %ebp 4/r32/esp + 5398 # setup + 5399 (clear-stream _test-input-stream) + 5400 (clear-stream $_test-input-buffered-file->buffer) + 5401 (clear-stream _test-output-stream) + 5402 (clear-stream $_test-output-buffered-file->buffer) + 5403 (clear-stream _test-error-stream) + 5404 (clear-stream $_test-error-buffered-file->buffer) + 5405 # var ed/edx: exit-descriptor = tailor-exit-descriptor(16) + 5406 68/push 0/imm32 + 5407 68/push 0/imm32 + 5408 89/<- %edx 4/r32/esp + 5409 (tailor-exit-descriptor %edx 0x10) + 5410 # + 5411 (write _test-input-stream "fn foo {\n") + 5412 (write _test-input-stream " var a: int\n") + 5413 (write _test-input-stream " var b/ecx: int <- add a, 0\n") + 5414 (write _test-input-stream "}\n") + 5415 # convert + 5416 (convert-mu _test-input-buffered-file _test-output-buffered-file _test-error-buffered-file %edx) + 5417 # registers except esp clobbered at this point + 5418 # restore ed + 5419 89/<- %edx 4/r32/esp + 5420 (flush _test-output-buffered-file) + 5421 (flush _test-error-buffered-file) + 5422 +-- 6 lines: #? # dump _test-error-stream ------------------------------------------------------------------------------------------------------------------------------------------ + 5428 # check output + 5429 (check-stream-equal _test-output-stream "" "F - test-add-with-too-many-inouts: output should be empty") + 5430 (check-next-stream-line-equal _test-error-stream "fn foo: stmt add: too many inouts; most primitives support at most two arguments, across inouts and outputs" "F - test-add-with-too-many-inouts: error message") + 5431 # check that stop(1) was called + 5432 (check-ints-equal *(edx+4) 2 "F - test-add-with-too-many-inouts: exit status") + 5433 # don't restore from ebp + 5434 81 0/subop/add %esp 8/imm32 + 5435 # . epilogue + 5436 5d/pop-to-ebp + 5437 c3/return + 5438 + 5439 test-add-with-too-many-inouts-2: + 5440 # . prologue + 5441 55/push-ebp + 5442 89/<- %ebp 4/r32/esp + 5443 # setup + 5444 (clear-stream _test-input-stream) + 5445 (clear-stream $_test-input-buffered-file->buffer) + 5446 (clear-stream _test-output-stream) + 5447 (clear-stream $_test-output-buffered-file->buffer) + 5448 (clear-stream _test-error-stream) + 5449 (clear-stream $_test-error-buffered-file->buffer) + 5450 # var ed/edx: exit-descriptor = tailor-exit-descriptor(16) + 5451 68/push 0/imm32 + 5452 68/push 0/imm32 + 5453 89/<- %edx 4/r32/esp + 5454 (tailor-exit-descriptor %edx 0x10) + 5455 # + 5456 (write _test-input-stream "fn foo {\n") + 5457 (write _test-input-stream " var a: int\n") + 5458 (write _test-input-stream " add-to a, 0, 1\n") + 5459 (write _test-input-stream "}\n") + 5460 # convert + 5461 (convert-mu _test-input-buffered-file _test-output-buffered-file _test-error-buffered-file %edx) + 5462 # registers except esp clobbered at this point + 5463 # restore ed + 5464 89/<- %edx 4/r32/esp + 5465 (flush _test-output-buffered-file) + 5466 (flush _test-error-buffered-file) + 5467 +-- 6 lines: #? # dump _test-error-stream ------------------------------------------------------------------------------------------------------------------------------------------ + 5473 # check output + 5474 (check-stream-equal _test-output-stream "" "F - test-add-with-too-many-inouts-2: output should be empty") + 5475 (check-next-stream-line-equal _test-error-stream "fn foo: stmt add-to: too many inouts; most primitives support at most two arguments, across inouts and outputs" "F - test-add-with-too-many-inouts-2: error message") + 5476 # check that stop(1) was called + 5477 (check-ints-equal *(edx+4) 2 "F - test-add-with-too-many-inouts-2: exit status") + 5478 # don't restore from ebp + 5479 81 0/subop/add %esp 8/imm32 + 5480 # . epilogue + 5481 5d/pop-to-ebp + 5482 c3/return + 5483 + 5484 test-add-with-too-many-outputs: + 5485 # . prologue + 5486 55/push-ebp + 5487 89/<- %ebp 4/r32/esp + 5488 # setup + 5489 (clear-stream _test-input-stream) + 5490 (clear-stream $_test-input-buffered-file->buffer) + 5491 (clear-stream _test-output-stream) + 5492 (clear-stream $_test-output-buffered-file->buffer) + 5493 (clear-stream _test-error-stream) + 5494 (clear-stream $_test-error-buffered-file->buffer) + 5495 # var ed/edx: exit-descriptor = tailor-exit-descriptor(16) + 5496 68/push 0/imm32 + 5497 68/push 0/imm32 + 5498 89/<- %edx 4/r32/esp + 5499 (tailor-exit-descriptor %edx 0x10) + 5500 # + 5501 (write _test-input-stream "fn foo {\n") + 5502 (write _test-input-stream " var a/eax: int <- copy 0\n") + 5503 (write _test-input-stream " var b/ebx: int <- copy 0\n") + 5504 (write _test-input-stream " var c/ecx: int <- copy 0\n") + 5505 (write _test-input-stream " c, b <- add a\n") + 5506 (write _test-input-stream "}\n") + 5507 # convert + 5508 (convert-mu _test-input-buffered-file _test-output-buffered-file _test-error-buffered-file %edx) + 5509 # registers except esp clobbered at this point + 5510 # restore ed + 5511 89/<- %edx 4/r32/esp + 5512 (flush _test-output-buffered-file) + 5513 (flush _test-error-buffered-file) + 5514 +-- 6 lines: #? # dump _test-error-stream ------------------------------------------------------------------------------------------------------------------------------------------ + 5520 # check output + 5521 (check-stream-equal _test-output-stream "" "F - test-add-with-too-many-outputs: output should be empty") + 5522 (check-next-stream-line-equal _test-error-stream "fn foo: stmt add: too many outputs; most primitives support at most one output" "F - test-add-with-too-many-outputs: error message") + 5523 # check that stop(1) was called + 5524 (check-ints-equal *(edx+4) 2 "F - test-add-with-too-many-outputs: exit status") + 5525 # don't restore from ebp + 5526 81 0/subop/add %esp 8/imm32 + 5527 # . epilogue + 5528 5d/pop-to-ebp + 5529 c3/return + 5530 + 5531 test-add-with-non-number: + 5532 # . prologue + 5533 55/push-ebp + 5534 89/<- %ebp 4/r32/esp + 5535 # setup + 5536 (clear-stream _test-input-stream) + 5537 (clear-stream $_test-input-buffered-file->buffer) + 5538 (clear-stream _test-output-stream) + 5539 (clear-stream $_test-output-buffered-file->buffer) + 5540 (clear-stream _test-error-stream) + 5541 (clear-stream $_test-error-buffered-file->buffer) + 5542 # var ed/edx: exit-descriptor = tailor-exit-descriptor(16) + 5543 68/push 0/imm32 + 5544 68/push 0/imm32 + 5545 89/<- %edx 4/r32/esp + 5546 (tailor-exit-descriptor %edx 0x10) + 5547 # + 5548 (write _test-input-stream "fn foo {\n") + 5549 (write _test-input-stream " var a: int\n") + 5550 (write _test-input-stream " var b/ecx: (addr int) <- add a\n") + 5551 (write _test-input-stream "}\n") + 5552 # convert + 5553 (convert-mu _test-input-buffered-file _test-output-buffered-file _test-error-buffered-file %edx) + 5554 # registers except esp clobbered at this point + 5555 # restore ed + 5556 89/<- %edx 4/r32/esp + 5557 (flush _test-output-buffered-file) + 5558 (flush _test-error-buffered-file) + 5559 +-- 6 lines: #? # dump _test-error-stream ------------------------------------------------------------------------------------------------------------------------------------------ + 5565 # check output + 5566 (check-stream-equal _test-output-stream "" "F - test-add-with-non-number: output should be empty") + 5567 (check-next-stream-line-equal _test-error-stream "fn foo: stmt add: only non-addr scalar args permitted" "F - test-add-with-non-number: error message") + 5568 # check that stop(1) was called + 5569 (check-ints-equal *(edx+4) 2 "F - test-add-with-non-number: exit status") + 5570 # don't restore from ebp + 5571 81 0/subop/add %esp 8/imm32 + 5572 # . epilogue + 5573 5d/pop-to-ebp + 5574 c3/return + 5575 + 5576 test-add-with-addr-dereferenced: + 5577 # . prologue + 5578 55/push-ebp + 5579 89/<- %ebp 4/r32/esp + 5580 # setup + 5581 (clear-stream _test-input-stream) + 5582 (clear-stream $_test-input-buffered-file->buffer) + 5583 (clear-stream _test-output-stream) + 5584 (clear-stream $_test-output-buffered-file->buffer) + 5585 # + 5586 (write _test-input-stream "fn foo {\n") + 5587 (write _test-input-stream " var a/eax: (addr int) <- copy 0\n") + 5588 (write _test-input-stream " add-to *a, 1\n") + 5589 (write _test-input-stream "}\n") + 5590 # convert + 5591 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) + 5592 (flush _test-output-buffered-file) + 5593 # no error + 5594 # . epilogue + 5595 89/<- %esp 5/r32/ebp + 5596 5d/pop-to-ebp + 5597 c3/return + 5598 + 5599 test-get-with-wrong-field: + 5600 # . prologue + 5601 55/push-ebp + 5602 89/<- %ebp 4/r32/esp + 5603 # setup + 5604 (clear-stream _test-input-stream) + 5605 (clear-stream $_test-input-buffered-file->buffer) + 5606 (clear-stream _test-output-stream) + 5607 (clear-stream $_test-output-buffered-file->buffer) + 5608 (clear-stream _test-error-stream) + 5609 (clear-stream $_test-error-buffered-file->buffer) + 5610 # var ed/edx: exit-descriptor = tailor-exit-descriptor(16) + 5611 68/push 0/imm32 + 5612 68/push 0/imm32 + 5613 89/<- %edx 4/r32/esp + 5614 (tailor-exit-descriptor %edx 0x10) + 5615 # + 5616 (write _test-input-stream "fn foo {\n") + 5617 (write _test-input-stream " var a: t\n") + 5618 (write _test-input-stream " var c/ecx: (addr int) <- get a, y\n") 5619 (write _test-input-stream "}\n") - 5620 # convert - 5621 (convert-mu _test-input-buffered-file _test-output-buffered-file _test-error-buffered-file %edx) - 5622 # registers except esp clobbered at this point - 5623 # restore ed - 5624 89/<- %edx 4/r32/esp - 5625 (flush _test-output-buffered-file) - 5626 (flush _test-error-buffered-file) - 5627 +-- 6 lines: #? # dump _test-error-stream --------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 5633 # check output - 5634 (check-stream-equal _test-output-stream "" "F - test-get-with-wrong-field: output should be empty") - 5635 (check-next-stream-line-equal _test-error-stream "fn foo: stmt get: type 't' has no member called 'y'" "F - test-get-with-wrong-field: error message") - 5636 # check that stop(1) was called - 5637 (check-ints-equal *(edx+4) 2 "F - test-get-with-wrong-field: exit status") - 5638 # don't restore from ebp - 5639 81 0/subop/add %esp 8/imm32 - 5640 # . epilogue - 5641 5d/pop-to-ebp - 5642 c3/return - 5643 - 5644 test-get-with-wrong-base-type: - 5645 # . prologue - 5646 55/push-ebp - 5647 89/<- %ebp 4/r32/esp - 5648 # setup - 5649 (clear-stream _test-input-stream) - 5650 (clear-stream $_test-input-buffered-file->buffer) - 5651 (clear-stream _test-output-stream) - 5652 (clear-stream $_test-output-buffered-file->buffer) - 5653 (clear-stream _test-error-stream) - 5654 (clear-stream $_test-error-buffered-file->buffer) - 5655 # var ed/edx: exit-descriptor = tailor-exit-descriptor(16) - 5656 68/push 0/imm32 - 5657 68/push 0/imm32 - 5658 89/<- %edx 4/r32/esp - 5659 (tailor-exit-descriptor %edx 0x10) - 5660 # - 5661 (write _test-input-stream "fn foo {\n") - 5662 (write _test-input-stream " var a: int\n") - 5663 (write _test-input-stream " var c/ecx: (addr int) <- get a, y\n") - 5664 (write _test-input-stream "}\n") - 5665 # convert - 5666 (convert-mu _test-input-buffered-file _test-output-buffered-file _test-error-buffered-file %edx) - 5667 # registers except esp clobbered at this point - 5668 # restore ed - 5669 89/<- %edx 4/r32/esp - 5670 (flush _test-output-buffered-file) - 5671 (flush _test-error-buffered-file) - 5672 +-- 6 lines: #? # dump _test-error-stream --------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 5678 # check output - 5679 (check-stream-equal _test-output-stream "" "F - test-get-with-wrong-base-type: output should be empty") - 5680 (check-next-stream-line-equal _test-error-stream "fn foo: stmt get: var 'a' must have a 'type' definition" "F - test-get-with-wrong-base-type: error message") - 5681 # check that stop(1) was called - 5682 (check-ints-equal *(edx+4) 2 "F - test-get-with-wrong-base-type: exit status") - 5683 # don't restore from ebp - 5684 81 0/subop/add %esp 8/imm32 - 5685 # . epilogue - 5686 5d/pop-to-ebp - 5687 c3/return - 5688 - 5689 test-get-with-wrong-base-type-2: - 5690 # . prologue - 5691 55/push-ebp - 5692 89/<- %ebp 4/r32/esp - 5693 # setup - 5694 (clear-stream _test-input-stream) - 5695 (clear-stream $_test-input-buffered-file->buffer) - 5696 (clear-stream _test-output-stream) - 5697 (clear-stream $_test-output-buffered-file->buffer) - 5698 (clear-stream _test-error-stream) - 5699 (clear-stream $_test-error-buffered-file->buffer) - 5700 # var ed/edx: exit-descriptor = tailor-exit-descriptor(16) - 5701 68/push 0/imm32 - 5702 68/push 0/imm32 - 5703 89/<- %edx 4/r32/esp - 5704 (tailor-exit-descriptor %edx 0x10) - 5705 # - 5706 (write _test-input-stream "fn foo {\n") - 5707 (write _test-input-stream " var a: (addr t)\n") - 5708 (write _test-input-stream " var c/ecx: (addr int) <- get a, y\n") - 5709 (write _test-input-stream "}\n") - 5710 (write _test-input-stream "type t {\n") - 5711 (write _test-input-stream " x: int\n") + 5620 (write _test-input-stream "type t {\n") + 5621 (write _test-input-stream " x: int\n") + 5622 (write _test-input-stream "}\n") + 5623 # convert + 5624 (convert-mu _test-input-buffered-file _test-output-buffered-file _test-error-buffered-file %edx) + 5625 # registers except esp clobbered at this point + 5626 # restore ed + 5627 89/<- %edx 4/r32/esp + 5628 (flush _test-output-buffered-file) + 5629 (flush _test-error-buffered-file) + 5630 +-- 6 lines: #? # dump _test-error-stream ------------------------------------------------------------------------------------------------------------------------------------------ + 5636 # check output + 5637 (check-stream-equal _test-output-stream "" "F - test-get-with-wrong-field: output should be empty") + 5638 (check-next-stream-line-equal _test-error-stream "fn foo: stmt get: type 't' has no member called 'y'" "F - test-get-with-wrong-field: error message") + 5639 # check that stop(1) was called + 5640 (check-ints-equal *(edx+4) 2 "F - test-get-with-wrong-field: exit status") + 5641 # don't restore from ebp + 5642 81 0/subop/add %esp 8/imm32 + 5643 # . epilogue + 5644 5d/pop-to-ebp + 5645 c3/return + 5646 + 5647 test-get-with-wrong-base-type: + 5648 # . prologue + 5649 55/push-ebp + 5650 89/<- %ebp 4/r32/esp + 5651 # setup + 5652 (clear-stream _test-input-stream) + 5653 (clear-stream $_test-input-buffered-file->buffer) + 5654 (clear-stream _test-output-stream) + 5655 (clear-stream $_test-output-buffered-file->buffer) + 5656 (clear-stream _test-error-stream) + 5657 (clear-stream $_test-error-buffered-file->buffer) + 5658 # var ed/edx: exit-descriptor = tailor-exit-descriptor(16) + 5659 68/push 0/imm32 + 5660 68/push 0/imm32 + 5661 89/<- %edx 4/r32/esp + 5662 (tailor-exit-descriptor %edx 0x10) + 5663 # + 5664 (write _test-input-stream "fn foo {\n") + 5665 (write _test-input-stream " var a: int\n") + 5666 (write _test-input-stream " var c/ecx: (addr int) <- get a, y\n") + 5667 (write _test-input-stream "}\n") + 5668 # convert + 5669 (convert-mu _test-input-buffered-file _test-output-buffered-file _test-error-buffered-file %edx) + 5670 # registers except esp clobbered at this point + 5671 # restore ed + 5672 89/<- %edx 4/r32/esp + 5673 (flush _test-output-buffered-file) + 5674 (flush _test-error-buffered-file) + 5675 +-- 6 lines: #? # dump _test-error-stream ------------------------------------------------------------------------------------------------------------------------------------------ + 5681 # check output + 5682 (check-stream-equal _test-output-stream "" "F - test-get-with-wrong-base-type: output should be empty") + 5683 (check-next-stream-line-equal _test-error-stream "fn foo: stmt get: var 'a' must have a 'type' definition" "F - test-get-with-wrong-base-type: error message") + 5684 # check that stop(1) was called + 5685 (check-ints-equal *(edx+4) 2 "F - test-get-with-wrong-base-type: exit status") + 5686 # don't restore from ebp + 5687 81 0/subop/add %esp 8/imm32 + 5688 # . epilogue + 5689 5d/pop-to-ebp + 5690 c3/return + 5691 + 5692 test-get-with-wrong-base-type-2: + 5693 # . prologue + 5694 55/push-ebp + 5695 89/<- %ebp 4/r32/esp + 5696 # setup + 5697 (clear-stream _test-input-stream) + 5698 (clear-stream $_test-input-buffered-file->buffer) + 5699 (clear-stream _test-output-stream) + 5700 (clear-stream $_test-output-buffered-file->buffer) + 5701 (clear-stream _test-error-stream) + 5702 (clear-stream $_test-error-buffered-file->buffer) + 5703 # var ed/edx: exit-descriptor = tailor-exit-descriptor(16) + 5704 68/push 0/imm32 + 5705 68/push 0/imm32 + 5706 89/<- %edx 4/r32/esp + 5707 (tailor-exit-descriptor %edx 0x10) + 5708 # + 5709 (write _test-input-stream "fn foo {\n") + 5710 (write _test-input-stream " var a: (addr t)\n") + 5711 (write _test-input-stream " var c/ecx: (addr int) <- get a, y\n") 5712 (write _test-input-stream "}\n") - 5713 # convert - 5714 (convert-mu _test-input-buffered-file _test-output-buffered-file _test-error-buffered-file %edx) - 5715 # registers except esp clobbered at this point - 5716 # restore ed - 5717 89/<- %edx 4/r32/esp - 5718 (flush _test-output-buffered-file) - 5719 (flush _test-error-buffered-file) - 5720 +-- 6 lines: #? # dump _test-error-stream --------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 5726 # check output - 5727 (check-stream-equal _test-output-stream "" "F - test-get-with-wrong-base-type-2: output should be empty") - 5728 (check-next-stream-line-equal _test-error-stream "fn foo: stmt get: var 'a' is an 'addr' type, and so must live in a register" "F - test-get-with-wrong-base-type-2: error message") - 5729 # check that stop(1) was called - 5730 (check-ints-equal *(edx+4) 2 "F - test-get-with-wrong-base-type-2: exit status") - 5731 # don't restore from ebp - 5732 81 0/subop/add %esp 8/imm32 - 5733 # . epilogue - 5734 5d/pop-to-ebp - 5735 c3/return - 5736 - 5737 test-get-with-wrong-offset-type: - 5738 # . prologue - 5739 55/push-ebp - 5740 89/<- %ebp 4/r32/esp - 5741 # setup - 5742 (clear-stream _test-input-stream) - 5743 (clear-stream $_test-input-buffered-file->buffer) - 5744 (clear-stream _test-output-stream) - 5745 (clear-stream $_test-output-buffered-file->buffer) - 5746 (clear-stream _test-error-stream) - 5747 (clear-stream $_test-error-buffered-file->buffer) - 5748 # var ed/edx: exit-descriptor = tailor-exit-descriptor(16) - 5749 68/push 0/imm32 - 5750 68/push 0/imm32 - 5751 89/<- %edx 4/r32/esp - 5752 (tailor-exit-descriptor %edx 0x10) - 5753 # - 5754 (write _test-input-stream "fn foo {\n") - 5755 (write _test-input-stream " var a: t\n") - 5756 (write _test-input-stream " var b: int\n") - 5757 (write _test-input-stream " var c/ecx: (addr int) <- get a, b\n") - 5758 (write _test-input-stream "}\n") - 5759 (write _test-input-stream "type t {\n") - 5760 (write _test-input-stream " x: int\n") + 5713 (write _test-input-stream "type t {\n") + 5714 (write _test-input-stream " x: int\n") + 5715 (write _test-input-stream "}\n") + 5716 # convert + 5717 (convert-mu _test-input-buffered-file _test-output-buffered-file _test-error-buffered-file %edx) + 5718 # registers except esp clobbered at this point + 5719 # restore ed + 5720 89/<- %edx 4/r32/esp + 5721 (flush _test-output-buffered-file) + 5722 (flush _test-error-buffered-file) + 5723 +-- 6 lines: #? # dump _test-error-stream ------------------------------------------------------------------------------------------------------------------------------------------ + 5729 # check output + 5730 (check-stream-equal _test-output-stream "" "F - test-get-with-wrong-base-type-2: output should be empty") + 5731 (check-next-stream-line-equal _test-error-stream "fn foo: stmt get: var 'a' is an 'addr' type, and so must live in a register" "F - test-get-with-wrong-base-type-2: error message") + 5732 # check that stop(1) was called + 5733 (check-ints-equal *(edx+4) 2 "F - test-get-with-wrong-base-type-2: exit status") + 5734 # don't restore from ebp + 5735 81 0/subop/add %esp 8/imm32 + 5736 # . epilogue + 5737 5d/pop-to-ebp + 5738 c3/return + 5739 + 5740 test-get-with-wrong-offset-type: + 5741 # . prologue + 5742 55/push-ebp + 5743 89/<- %ebp 4/r32/esp + 5744 # setup + 5745 (clear-stream _test-input-stream) + 5746 (clear-stream $_test-input-buffered-file->buffer) + 5747 (clear-stream _test-output-stream) + 5748 (clear-stream $_test-output-buffered-file->buffer) + 5749 (clear-stream _test-error-stream) + 5750 (clear-stream $_test-error-buffered-file->buffer) + 5751 # var ed/edx: exit-descriptor = tailor-exit-descriptor(16) + 5752 68/push 0/imm32 + 5753 68/push 0/imm32 + 5754 89/<- %edx 4/r32/esp + 5755 (tailor-exit-descriptor %edx 0x10) + 5756 # + 5757 (write _test-input-stream "fn foo {\n") + 5758 (write _test-input-stream " var a: t\n") + 5759 (write _test-input-stream " var b: int\n") + 5760 (write _test-input-stream " var c/ecx: (addr int) <- get a, b\n") 5761 (write _test-input-stream "}\n") - 5762 # convert - 5763 (convert-mu _test-input-buffered-file _test-output-buffered-file _test-error-buffered-file %edx) - 5764 # registers except esp clobbered at this point - 5765 # restore ed - 5766 89/<- %edx 4/r32/esp - 5767 (flush _test-output-buffered-file) - 5768 (flush _test-error-buffered-file) - 5769 +-- 6 lines: #? # dump _test-error-stream --------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 5775 # check output - 5776 (check-stream-equal _test-output-stream "" "F - test-get-with-wrong-offset-type: output should be empty") - 5777 (check-next-stream-line-equal _test-error-stream "fn foo: stmt get: type 't' has no member called 'b'" "F - test-get-with-wrong-offset-type: error message") - 5778 # check that stop(1) was called - 5779 (check-ints-equal *(edx+4) 2 "F - test-get-with-wrong-offset-type: exit status") - 5780 # don't restore from ebp - 5781 81 0/subop/add %esp 8/imm32 - 5782 # . epilogue - 5783 5d/pop-to-ebp - 5784 c3/return - 5785 - 5786 test-get-with-wrong-output-type: - 5787 # . prologue - 5788 55/push-ebp - 5789 89/<- %ebp 4/r32/esp - 5790 # setup - 5791 (clear-stream _test-input-stream) - 5792 (clear-stream $_test-input-buffered-file->buffer) - 5793 (clear-stream _test-output-stream) - 5794 (clear-stream $_test-output-buffered-file->buffer) - 5795 (clear-stream _test-error-stream) - 5796 (clear-stream $_test-error-buffered-file->buffer) - 5797 # var ed/edx: exit-descriptor = tailor-exit-descriptor(16) - 5798 68/push 0/imm32 - 5799 68/push 0/imm32 - 5800 89/<- %edx 4/r32/esp - 5801 (tailor-exit-descriptor %edx 0x10) - 5802 # - 5803 (write _test-input-stream "fn foo {\n") - 5804 (write _test-input-stream " var a: t\n") - 5805 (write _test-input-stream " var c: (addr int)\n") - 5806 (write _test-input-stream " c <- get a, x\n") - 5807 (write _test-input-stream "}\n") - 5808 (write _test-input-stream "type t {\n") - 5809 (write _test-input-stream " x: int\n") + 5762 (write _test-input-stream "type t {\n") + 5763 (write _test-input-stream " x: int\n") + 5764 (write _test-input-stream "}\n") + 5765 # convert + 5766 (convert-mu _test-input-buffered-file _test-output-buffered-file _test-error-buffered-file %edx) + 5767 # registers except esp clobbered at this point + 5768 # restore ed + 5769 89/<- %edx 4/r32/esp + 5770 (flush _test-output-buffered-file) + 5771 (flush _test-error-buffered-file) + 5772 +-- 6 lines: #? # dump _test-error-stream ------------------------------------------------------------------------------------------------------------------------------------------ + 5778 # check output + 5779 (check-stream-equal _test-output-stream "" "F - test-get-with-wrong-offset-type: output should be empty") + 5780 (check-next-stream-line-equal _test-error-stream "fn foo: stmt get: type 't' has no member called 'b'" "F - test-get-with-wrong-offset-type: error message") + 5781 # check that stop(1) was called + 5782 (check-ints-equal *(edx+4) 2 "F - test-get-with-wrong-offset-type: exit status") + 5783 # don't restore from ebp + 5784 81 0/subop/add %esp 8/imm32 + 5785 # . epilogue + 5786 5d/pop-to-ebp + 5787 c3/return + 5788 + 5789 test-get-with-wrong-output-type: + 5790 # . prologue + 5791 55/push-ebp + 5792 89/<- %ebp 4/r32/esp + 5793 # setup + 5794 (clear-stream _test-input-stream) + 5795 (clear-stream $_test-input-buffered-file->buffer) + 5796 (clear-stream _test-output-stream) + 5797 (clear-stream $_test-output-buffered-file->buffer) + 5798 (clear-stream _test-error-stream) + 5799 (clear-stream $_test-error-buffered-file->buffer) + 5800 # var ed/edx: exit-descriptor = tailor-exit-descriptor(16) + 5801 68/push 0/imm32 + 5802 68/push 0/imm32 + 5803 89/<- %edx 4/r32/esp + 5804 (tailor-exit-descriptor %edx 0x10) + 5805 # + 5806 (write _test-input-stream "fn foo {\n") + 5807 (write _test-input-stream " var a: t\n") + 5808 (write _test-input-stream " var c: (addr int)\n") + 5809 (write _test-input-stream " c <- get a, x\n") 5810 (write _test-input-stream "}\n") - 5811 # convert - 5812 (convert-mu _test-input-buffered-file _test-output-buffered-file _test-error-buffered-file %edx) - 5813 # registers except esp clobbered at this point - 5814 # restore ed - 5815 89/<- %edx 4/r32/esp - 5816 (flush _test-output-buffered-file) - 5817 (flush _test-error-buffered-file) - 5818 +-- 6 lines: #? # dump _test-error-stream --------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 5824 # check output - 5825 (check-stream-equal _test-output-stream "" "F - test-get-with-wrong-output-type: output should be empty") - 5826 (check-next-stream-line-equal _test-error-stream "fn foo: stmt get: output 'c' is not in a register" "F - test-get-with-wrong-output-type: error message") - 5827 # check that stop(1) was called - 5828 (check-ints-equal *(edx+4) 2 "F - test-get-with-wrong-output-type: exit status") - 5829 # don't restore from ebp - 5830 81 0/subop/add %esp 8/imm32 - 5831 # . epilogue - 5832 5d/pop-to-ebp - 5833 c3/return - 5834 - 5835 test-get-with-wrong-output-type-2: - 5836 # . prologue - 5837 55/push-ebp - 5838 89/<- %ebp 4/r32/esp - 5839 # setup - 5840 (clear-stream _test-input-stream) - 5841 (clear-stream $_test-input-buffered-file->buffer) - 5842 (clear-stream _test-output-stream) - 5843 (clear-stream $_test-output-buffered-file->buffer) - 5844 (clear-stream _test-error-stream) - 5845 (clear-stream $_test-error-buffered-file->buffer) - 5846 # var ed/edx: exit-descriptor = tailor-exit-descriptor(16) - 5847 68/push 0/imm32 - 5848 68/push 0/imm32 - 5849 89/<- %edx 4/r32/esp - 5850 (tailor-exit-descriptor %edx 0x10) - 5851 # - 5852 (write _test-input-stream "fn foo {\n") - 5853 (write _test-input-stream " var a: t\n") - 5854 (write _test-input-stream " var c/ecx: int <- get a, x\n") - 5855 (write _test-input-stream "}\n") - 5856 (write _test-input-stream "type t {\n") - 5857 (write _test-input-stream " x: int\n") + 5811 (write _test-input-stream "type t {\n") + 5812 (write _test-input-stream " x: int\n") + 5813 (write _test-input-stream "}\n") + 5814 # convert + 5815 (convert-mu _test-input-buffered-file _test-output-buffered-file _test-error-buffered-file %edx) + 5816 # registers except esp clobbered at this point + 5817 # restore ed + 5818 89/<- %edx 4/r32/esp + 5819 (flush _test-output-buffered-file) + 5820 (flush _test-error-buffered-file) + 5821 +-- 6 lines: #? # dump _test-error-stream ------------------------------------------------------------------------------------------------------------------------------------------ + 5827 # check output + 5828 (check-stream-equal _test-output-stream "" "F - test-get-with-wrong-output-type: output should be empty") + 5829 (check-next-stream-line-equal _test-error-stream "fn foo: stmt get: output 'c' is not in a register" "F - test-get-with-wrong-output-type: error message") + 5830 # check that stop(1) was called + 5831 (check-ints-equal *(edx+4) 2 "F - test-get-with-wrong-output-type: exit status") + 5832 # don't restore from ebp + 5833 81 0/subop/add %esp 8/imm32 + 5834 # . epilogue + 5835 5d/pop-to-ebp + 5836 c3/return + 5837 + 5838 test-get-with-wrong-output-type-2: + 5839 # . prologue + 5840 55/push-ebp + 5841 89/<- %ebp 4/r32/esp + 5842 # setup + 5843 (clear-stream _test-input-stream) + 5844 (clear-stream $_test-input-buffered-file->buffer) + 5845 (clear-stream _test-output-stream) + 5846 (clear-stream $_test-output-buffered-file->buffer) + 5847 (clear-stream _test-error-stream) + 5848 (clear-stream $_test-error-buffered-file->buffer) + 5849 # var ed/edx: exit-descriptor = tailor-exit-descriptor(16) + 5850 68/push 0/imm32 + 5851 68/push 0/imm32 + 5852 89/<- %edx 4/r32/esp + 5853 (tailor-exit-descriptor %edx 0x10) + 5854 # + 5855 (write _test-input-stream "fn foo {\n") + 5856 (write _test-input-stream " var a: t\n") + 5857 (write _test-input-stream " var c/ecx: int <- get a, x\n") 5858 (write _test-input-stream "}\n") - 5859 # convert - 5860 (convert-mu _test-input-buffered-file _test-output-buffered-file _test-error-buffered-file %edx) - 5861 # registers except esp clobbered at this point - 5862 # restore ed - 5863 89/<- %edx 4/r32/esp - 5864 (flush _test-output-buffered-file) - 5865 (flush _test-error-buffered-file) - 5866 +-- 6 lines: #? # dump _test-error-stream --------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 5872 # check output - 5873 (check-stream-equal _test-output-stream "" "F - test-get-with-wrong-output-type-2: output should be empty") - 5874 (check-next-stream-line-equal _test-error-stream "fn foo: stmt get: output must be an address" "F - test-get-with-wrong-output-type-2: error message") - 5875 # check that stop(1) was called - 5876 (check-ints-equal *(edx+4) 2 "F - test-get-with-wrong-output-type-2: exit status") - 5877 # don't restore from ebp - 5878 81 0/subop/add %esp 8/imm32 - 5879 # . epilogue - 5880 5d/pop-to-ebp - 5881 c3/return - 5882 - 5883 test-get-with-wrong-output-type-3: - 5884 # . prologue - 5885 55/push-ebp - 5886 89/<- %ebp 4/r32/esp - 5887 # setup - 5888 (clear-stream _test-input-stream) - 5889 (clear-stream $_test-input-buffered-file->buffer) - 5890 (clear-stream _test-output-stream) - 5891 (clear-stream $_test-output-buffered-file->buffer) - 5892 (clear-stream _test-error-stream) - 5893 (clear-stream $_test-error-buffered-file->buffer) - 5894 # var ed/edx: exit-descriptor = tailor-exit-descriptor(16) - 5895 68/push 0/imm32 - 5896 68/push 0/imm32 - 5897 89/<- %edx 4/r32/esp - 5898 (tailor-exit-descriptor %edx 0x10) - 5899 # - 5900 (write _test-input-stream "fn foo {\n") - 5901 (write _test-input-stream " var a: t\n") - 5902 (write _test-input-stream " var c/ecx: (array int) <- get a, x\n") - 5903 (write _test-input-stream "}\n") - 5904 (write _test-input-stream "type t {\n") - 5905 (write _test-input-stream " x: int\n") + 5859 (write _test-input-stream "type t {\n") + 5860 (write _test-input-stream " x: int\n") + 5861 (write _test-input-stream "}\n") + 5862 # convert + 5863 (convert-mu _test-input-buffered-file _test-output-buffered-file _test-error-buffered-file %edx) + 5864 # registers except esp clobbered at this point + 5865 # restore ed + 5866 89/<- %edx 4/r32/esp + 5867 (flush _test-output-buffered-file) + 5868 (flush _test-error-buffered-file) + 5869 +-- 6 lines: #? # dump _test-error-stream ------------------------------------------------------------------------------------------------------------------------------------------ + 5875 # check output + 5876 (check-stream-equal _test-output-stream "" "F - test-get-with-wrong-output-type-2: output should be empty") + 5877 (check-next-stream-line-equal _test-error-stream "fn foo: stmt get: output must be an address" "F - test-get-with-wrong-output-type-2: error message") + 5878 # check that stop(1) was called + 5879 (check-ints-equal *(edx+4) 2 "F - test-get-with-wrong-output-type-2: exit status") + 5880 # don't restore from ebp + 5881 81 0/subop/add %esp 8/imm32 + 5882 # . epilogue + 5883 5d/pop-to-ebp + 5884 c3/return + 5885 + 5886 test-get-with-wrong-output-type-3: + 5887 # . prologue + 5888 55/push-ebp + 5889 89/<- %ebp 4/r32/esp + 5890 # setup + 5891 (clear-stream _test-input-stream) + 5892 (clear-stream $_test-input-buffered-file->buffer) + 5893 (clear-stream _test-output-stream) + 5894 (clear-stream $_test-output-buffered-file->buffer) + 5895 (clear-stream _test-error-stream) + 5896 (clear-stream $_test-error-buffered-file->buffer) + 5897 # var ed/edx: exit-descriptor = tailor-exit-descriptor(16) + 5898 68/push 0/imm32 + 5899 68/push 0/imm32 + 5900 89/<- %edx 4/r32/esp + 5901 (tailor-exit-descriptor %edx 0x10) + 5902 # + 5903 (write _test-input-stream "fn foo {\n") + 5904 (write _test-input-stream " var a: t\n") + 5905 (write _test-input-stream " var c/ecx: (array int) <- get a, x\n") 5906 (write _test-input-stream "}\n") - 5907 # convert - 5908 (convert-mu _test-input-buffered-file _test-output-buffered-file _test-error-buffered-file %edx) - 5909 # registers except esp clobbered at this point - 5910 # restore ed - 5911 89/<- %edx 4/r32/esp - 5912 (flush _test-output-buffered-file) - 5913 (flush _test-error-buffered-file) - 5914 +-- 6 lines: #? # dump _test-error-stream --------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 5920 # check output - 5921 (check-stream-equal _test-output-stream "" "F - test-get-with-wrong-output-type-3: output should be empty") - 5922 (check-next-stream-line-equal _test-error-stream "fn foo: stmt get: output must be an address" "F - test-get-with-wrong-output-type-3: error message") - 5923 # check that stop(1) was called - 5924 (check-ints-equal *(edx+4) 2 "F - test-get-with-wrong-output-type-3: exit status") - 5925 # don't restore from ebp - 5926 81 0/subop/add %esp 8/imm32 - 5927 # . epilogue - 5928 5d/pop-to-ebp - 5929 c3/return - 5930 - 5931 test-get-with-wrong-output-type-4: - 5932 # . prologue - 5933 55/push-ebp - 5934 89/<- %ebp 4/r32/esp - 5935 # setup - 5936 (clear-stream _test-input-stream) - 5937 (clear-stream $_test-input-buffered-file->buffer) - 5938 (clear-stream _test-output-stream) - 5939 (clear-stream $_test-output-buffered-file->buffer) - 5940 (clear-stream _test-error-stream) - 5941 (clear-stream $_test-error-buffered-file->buffer) - 5942 # var ed/edx: exit-descriptor = tailor-exit-descriptor(16) - 5943 68/push 0/imm32 - 5944 68/push 0/imm32 - 5945 89/<- %edx 4/r32/esp - 5946 (tailor-exit-descriptor %edx 0x10) - 5947 # - 5948 (write _test-input-stream "fn foo {\n") - 5949 (write _test-input-stream " var a: t\n") - 5950 (write _test-input-stream " var c/ecx: (addr boolean) <- get a, x\n") - 5951 (write _test-input-stream "}\n") - 5952 (write _test-input-stream "type t {\n") - 5953 (write _test-input-stream " x: int\n") + 5907 (write _test-input-stream "type t {\n") + 5908 (write _test-input-stream " x: int\n") + 5909 (write _test-input-stream "}\n") + 5910 # convert + 5911 (convert-mu _test-input-buffered-file _test-output-buffered-file _test-error-buffered-file %edx) + 5912 # registers except esp clobbered at this point + 5913 # restore ed + 5914 89/<- %edx 4/r32/esp + 5915 (flush _test-output-buffered-file) + 5916 (flush _test-error-buffered-file) + 5917 +-- 6 lines: #? # dump _test-error-stream ------------------------------------------------------------------------------------------------------------------------------------------ + 5923 # check output + 5924 (check-stream-equal _test-output-stream "" "F - test-get-with-wrong-output-type-3: output should be empty") + 5925 (check-next-stream-line-equal _test-error-stream "fn foo: stmt get: output must be an address" "F - test-get-with-wrong-output-type-3: error message") + 5926 # check that stop(1) was called + 5927 (check-ints-equal *(edx+4) 2 "F - test-get-with-wrong-output-type-3: exit status") + 5928 # don't restore from ebp + 5929 81 0/subop/add %esp 8/imm32 + 5930 # . epilogue + 5931 5d/pop-to-ebp + 5932 c3/return + 5933 + 5934 test-get-with-wrong-output-type-4: + 5935 # . prologue + 5936 55/push-ebp + 5937 89/<- %ebp 4/r32/esp + 5938 # setup + 5939 (clear-stream _test-input-stream) + 5940 (clear-stream $_test-input-buffered-file->buffer) + 5941 (clear-stream _test-output-stream) + 5942 (clear-stream $_test-output-buffered-file->buffer) + 5943 (clear-stream _test-error-stream) + 5944 (clear-stream $_test-error-buffered-file->buffer) + 5945 # var ed/edx: exit-descriptor = tailor-exit-descriptor(16) + 5946 68/push 0/imm32 + 5947 68/push 0/imm32 + 5948 89/<- %edx 4/r32/esp + 5949 (tailor-exit-descriptor %edx 0x10) + 5950 # + 5951 (write _test-input-stream "fn foo {\n") + 5952 (write _test-input-stream " var a: t\n") + 5953 (write _test-input-stream " var c/ecx: (addr boolean) <- get a, x\n") 5954 (write _test-input-stream "}\n") - 5955 # convert - 5956 (convert-mu _test-input-buffered-file _test-output-buffered-file _test-error-buffered-file %edx) - 5957 # registers except esp clobbered at this point - 5958 # restore ed - 5959 89/<- %edx 4/r32/esp - 5960 (flush _test-output-buffered-file) - 5961 (flush _test-error-buffered-file) - 5962 +-- 6 lines: #? # dump _test-error-stream --------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 5968 # check output - 5969 (check-stream-equal _test-output-stream "" "F - test-get-with-wrong-output-type-4: output should be empty") - 5970 (check-next-stream-line-equal _test-error-stream "fn foo: stmt get: wrong output type for member 'x' of type 't'" "F - test-get-with-wrong-output-type-4: error message") - 5971 # check that stop(1) was called - 5972 (check-ints-equal *(edx+4) 2 "F - test-get-with-wrong-output-type-4: exit status") - 5973 # don't restore from ebp - 5974 81 0/subop/add %esp 8/imm32 - 5975 # . epilogue - 5976 5d/pop-to-ebp - 5977 c3/return - 5978 - 5979 test-get-with-wrong-output-type-5: - 5980 # . prologue - 5981 55/push-ebp - 5982 89/<- %ebp 4/r32/esp - 5983 # setup - 5984 (clear-stream _test-input-stream) - 5985 (clear-stream $_test-input-buffered-file->buffer) - 5986 (clear-stream _test-output-stream) - 5987 (clear-stream $_test-output-buffered-file->buffer) - 5988 # - 5989 (write _test-input-stream "fn foo {\n") - 5990 (write _test-input-stream " var a: t\n") - 5991 (write _test-input-stream " var c/ecx: (addr handle int) <- get a, x\n") - 5992 (write _test-input-stream "}\n") - 5993 (write _test-input-stream "type t {\n") - 5994 (write _test-input-stream " x: (handle int)\n") + 5955 (write _test-input-stream "type t {\n") + 5956 (write _test-input-stream " x: int\n") + 5957 (write _test-input-stream "}\n") + 5958 # convert + 5959 (convert-mu _test-input-buffered-file _test-output-buffered-file _test-error-buffered-file %edx) + 5960 # registers except esp clobbered at this point + 5961 # restore ed + 5962 89/<- %edx 4/r32/esp + 5963 (flush _test-output-buffered-file) + 5964 (flush _test-error-buffered-file) + 5965 +-- 6 lines: #? # dump _test-error-stream ------------------------------------------------------------------------------------------------------------------------------------------ + 5971 # check output + 5972 (check-stream-equal _test-output-stream "" "F - test-get-with-wrong-output-type-4: output should be empty") + 5973 (check-next-stream-line-equal _test-error-stream "fn foo: stmt get: wrong output type for member 'x' of type 't'" "F - test-get-with-wrong-output-type-4: error message") + 5974 # check that stop(1) was called + 5975 (check-ints-equal *(edx+4) 2 "F - test-get-with-wrong-output-type-4: exit status") + 5976 # don't restore from ebp + 5977 81 0/subop/add %esp 8/imm32 + 5978 # . epilogue + 5979 5d/pop-to-ebp + 5980 c3/return + 5981 + 5982 test-get-with-wrong-output-type-5: + 5983 # . prologue + 5984 55/push-ebp + 5985 89/<- %ebp 4/r32/esp + 5986 # setup + 5987 (clear-stream _test-input-stream) + 5988 (clear-stream $_test-input-buffered-file->buffer) + 5989 (clear-stream _test-output-stream) + 5990 (clear-stream $_test-output-buffered-file->buffer) + 5991 # + 5992 (write _test-input-stream "fn foo {\n") + 5993 (write _test-input-stream " var a: t\n") + 5994 (write _test-input-stream " var c/ecx: (addr handle int) <- get a, x\n") 5995 (write _test-input-stream "}\n") - 5996 # convert - 5997 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) - 5998 (flush _test-output-buffered-file) - 5999 # no errors - 6000 # . epilogue - 6001 89/<- %esp 5/r32/ebp - 6002 5d/pop-to-ebp - 6003 c3/return - 6004 - 6005 test-get-with-too-few-inouts: - 6006 # . prologue - 6007 55/push-ebp - 6008 89/<- %ebp 4/r32/esp - 6009 # setup - 6010 (clear-stream _test-input-stream) - 6011 (clear-stream $_test-input-buffered-file->buffer) - 6012 (clear-stream _test-output-stream) - 6013 (clear-stream $_test-output-buffered-file->buffer) - 6014 (clear-stream _test-error-stream) - 6015 (clear-stream $_test-error-buffered-file->buffer) - 6016 # var ed/edx: exit-descriptor = tailor-exit-descriptor(16) - 6017 68/push 0/imm32 - 6018 68/push 0/imm32 - 6019 89/<- %edx 4/r32/esp - 6020 (tailor-exit-descriptor %edx 0x10) - 6021 # - 6022 (write _test-input-stream "fn foo {\n") - 6023 (write _test-input-stream " var a: t\n") - 6024 (write _test-input-stream " var c/ecx: (addr int) <- get a\n") - 6025 (write _test-input-stream "}\n") - 6026 (write _test-input-stream "type t {\n") - 6027 (write _test-input-stream " x: int\n") + 5996 (write _test-input-stream "type t {\n") + 5997 (write _test-input-stream " x: (handle int)\n") + 5998 (write _test-input-stream "}\n") + 5999 # convert + 6000 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) + 6001 (flush _test-output-buffered-file) + 6002 # no errors + 6003 # . epilogue + 6004 89/<- %esp 5/r32/ebp + 6005 5d/pop-to-ebp + 6006 c3/return + 6007 + 6008 test-get-with-too-few-inouts: + 6009 # . prologue + 6010 55/push-ebp + 6011 89/<- %ebp 4/r32/esp + 6012 # setup + 6013 (clear-stream _test-input-stream) + 6014 (clear-stream $_test-input-buffered-file->buffer) + 6015 (clear-stream _test-output-stream) + 6016 (clear-stream $_test-output-buffered-file->buffer) + 6017 (clear-stream _test-error-stream) + 6018 (clear-stream $_test-error-buffered-file->buffer) + 6019 # var ed/edx: exit-descriptor = tailor-exit-descriptor(16) + 6020 68/push 0/imm32 + 6021 68/push 0/imm32 + 6022 89/<- %edx 4/r32/esp + 6023 (tailor-exit-descriptor %edx 0x10) + 6024 # + 6025 (write _test-input-stream "fn foo {\n") + 6026 (write _test-input-stream " var a: t\n") + 6027 (write _test-input-stream " var c/ecx: (addr int) <- get a\n") 6028 (write _test-input-stream "}\n") - 6029 # convert - 6030 (convert-mu _test-input-buffered-file _test-output-buffered-file _test-error-buffered-file %edx) - 6031 # registers except esp clobbered at this point - 6032 # restore ed - 6033 89/<- %edx 4/r32/esp - 6034 (flush _test-output-buffered-file) - 6035 (flush _test-error-buffered-file) - 6036 +-- 6 lines: #? # dump _test-error-stream --------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 6042 # check output - 6043 (check-stream-equal _test-output-stream "" "F - test-get-with-too-few-inouts: output should be empty") - 6044 (check-next-stream-line-equal _test-error-stream "fn foo: stmt get: too few inouts (2 required)" "F - test-get-with-too-few-inouts: error message") - 6045 # check that stop(1) was called - 6046 (check-ints-equal *(edx+4) 2 "F - test-get-with-too-few-inouts: exit status") - 6047 # don't restore from ebp - 6048 81 0/subop/add %esp 8/imm32 - 6049 # . epilogue - 6050 5d/pop-to-ebp - 6051 c3/return - 6052 - 6053 test-get-with-too-many-inouts: - 6054 # . prologue - 6055 55/push-ebp - 6056 89/<- %ebp 4/r32/esp - 6057 # setup - 6058 (clear-stream _test-input-stream) - 6059 (clear-stream $_test-input-buffered-file->buffer) - 6060 (clear-stream _test-output-stream) - 6061 (clear-stream $_test-output-buffered-file->buffer) - 6062 (clear-stream _test-error-stream) - 6063 (clear-stream $_test-error-buffered-file->buffer) - 6064 # var ed/edx: exit-descriptor = tailor-exit-descriptor(16) - 6065 68/push 0/imm32 - 6066 68/push 0/imm32 - 6067 89/<- %edx 4/r32/esp - 6068 (tailor-exit-descriptor %edx 0x10) - 6069 # - 6070 (write _test-input-stream "fn foo {\n") - 6071 (write _test-input-stream " var a: t\n") - 6072 (write _test-input-stream " var c/ecx: (addr int) <- get a, x, 0\n") - 6073 (write _test-input-stream "}\n") - 6074 (write _test-input-stream "type t {\n") - 6075 (write _test-input-stream " x: int\n") + 6029 (write _test-input-stream "type t {\n") + 6030 (write _test-input-stream " x: int\n") + 6031 (write _test-input-stream "}\n") + 6032 # convert + 6033 (convert-mu _test-input-buffered-file _test-output-buffered-file _test-error-buffered-file %edx) + 6034 # registers except esp clobbered at this point + 6035 # restore ed + 6036 89/<- %edx 4/r32/esp + 6037 (flush _test-output-buffered-file) + 6038 (flush _test-error-buffered-file) + 6039 +-- 6 lines: #? # dump _test-error-stream ------------------------------------------------------------------------------------------------------------------------------------------ + 6045 # check output + 6046 (check-stream-equal _test-output-stream "" "F - test-get-with-too-few-inouts: output should be empty") + 6047 (check-next-stream-line-equal _test-error-stream "fn foo: stmt get: too few inouts (2 required)" "F - test-get-with-too-few-inouts: error message") + 6048 # check that stop(1) was called + 6049 (check-ints-equal *(edx+4) 2 "F - test-get-with-too-few-inouts: exit status") + 6050 # don't restore from ebp + 6051 81 0/subop/add %esp 8/imm32 + 6052 # . epilogue + 6053 5d/pop-to-ebp + 6054 c3/return + 6055 + 6056 test-get-with-too-many-inouts: + 6057 # . prologue + 6058 55/push-ebp + 6059 89/<- %ebp 4/r32/esp + 6060 # setup + 6061 (clear-stream _test-input-stream) + 6062 (clear-stream $_test-input-buffered-file->buffer) + 6063 (clear-stream _test-output-stream) + 6064 (clear-stream $_test-output-buffered-file->buffer) + 6065 (clear-stream _test-error-stream) + 6066 (clear-stream $_test-error-buffered-file->buffer) + 6067 # var ed/edx: exit-descriptor = tailor-exit-descriptor(16) + 6068 68/push 0/imm32 + 6069 68/push 0/imm32 + 6070 89/<- %edx 4/r32/esp + 6071 (tailor-exit-descriptor %edx 0x10) + 6072 # + 6073 (write _test-input-stream "fn foo {\n") + 6074 (write _test-input-stream " var a: t\n") + 6075 (write _test-input-stream " var c/ecx: (addr int) <- get a, x, 0\n") 6076 (write _test-input-stream "}\n") - 6077 # convert - 6078 (convert-mu _test-input-buffered-file _test-output-buffered-file _test-error-buffered-file %edx) - 6079 # registers except esp clobbered at this point - 6080 # restore ed - 6081 89/<- %edx 4/r32/esp - 6082 (flush _test-output-buffered-file) - 6083 (flush _test-error-buffered-file) - 6084 +-- 6 lines: #? # dump _test-error-stream --------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 6090 # check output - 6091 (check-stream-equal _test-output-stream "" "F - test-get-with-too-many-inouts: output should be empty") - 6092 (check-next-stream-line-equal _test-error-stream "fn foo: stmt get: too many inouts (2 required)" "F - test-get-with-too-many-inouts: error message") - 6093 # check that stop(1) was called - 6094 (check-ints-equal *(edx+4) 2 "F - test-get-with-too-many-inouts: exit status") - 6095 # don't restore from ebp - 6096 81 0/subop/add %esp 8/imm32 - 6097 # . epilogue - 6098 5d/pop-to-ebp - 6099 c3/return - 6100 - 6101 test-get-with-no-output: - 6102 # . prologue - 6103 55/push-ebp - 6104 89/<- %ebp 4/r32/esp - 6105 # setup - 6106 (clear-stream _test-input-stream) - 6107 (clear-stream $_test-input-buffered-file->buffer) - 6108 (clear-stream _test-output-stream) - 6109 (clear-stream $_test-output-buffered-file->buffer) - 6110 (clear-stream _test-error-stream) - 6111 (clear-stream $_test-error-buffered-file->buffer) - 6112 # var ed/edx: exit-descriptor = tailor-exit-descriptor(16) - 6113 68/push 0/imm32 - 6114 68/push 0/imm32 - 6115 89/<- %edx 4/r32/esp - 6116 (tailor-exit-descriptor %edx 0x10) - 6117 # - 6118 (write _test-input-stream "fn foo {\n") - 6119 (write _test-input-stream " var a: t\n") - 6120 (write _test-input-stream " get a, x\n") - 6121 (write _test-input-stream "}\n") - 6122 (write _test-input-stream "type t {\n") - 6123 (write _test-input-stream " x: int\n") + 6077 (write _test-input-stream "type t {\n") + 6078 (write _test-input-stream " x: int\n") + 6079 (write _test-input-stream "}\n") + 6080 # convert + 6081 (convert-mu _test-input-buffered-file _test-output-buffered-file _test-error-buffered-file %edx) + 6082 # registers except esp clobbered at this point + 6083 # restore ed + 6084 89/<- %edx 4/r32/esp + 6085 (flush _test-output-buffered-file) + 6086 (flush _test-error-buffered-file) + 6087 +-- 6 lines: #? # dump _test-error-stream ------------------------------------------------------------------------------------------------------------------------------------------ + 6093 # check output + 6094 (check-stream-equal _test-output-stream "" "F - test-get-with-too-many-inouts: output should be empty") + 6095 (check-next-stream-line-equal _test-error-stream "fn foo: stmt get: too many inouts (2 required)" "F - test-get-with-too-many-inouts: error message") + 6096 # check that stop(1) was called + 6097 (check-ints-equal *(edx+4) 2 "F - test-get-with-too-many-inouts: exit status") + 6098 # don't restore from ebp + 6099 81 0/subop/add %esp 8/imm32 + 6100 # . epilogue + 6101 5d/pop-to-ebp + 6102 c3/return + 6103 + 6104 test-get-with-no-output: + 6105 # . prologue + 6106 55/push-ebp + 6107 89/<- %ebp 4/r32/esp + 6108 # setup + 6109 (clear-stream _test-input-stream) + 6110 (clear-stream $_test-input-buffered-file->buffer) + 6111 (clear-stream _test-output-stream) + 6112 (clear-stream $_test-output-buffered-file->buffer) + 6113 (clear-stream _test-error-stream) + 6114 (clear-stream $_test-error-buffered-file->buffer) + 6115 # var ed/edx: exit-descriptor = tailor-exit-descriptor(16) + 6116 68/push 0/imm32 + 6117 68/push 0/imm32 + 6118 89/<- %edx 4/r32/esp + 6119 (tailor-exit-descriptor %edx 0x10) + 6120 # + 6121 (write _test-input-stream "fn foo {\n") + 6122 (write _test-input-stream " var a: t\n") + 6123 (write _test-input-stream " get a, x\n") 6124 (write _test-input-stream "}\n") - 6125 # convert - 6126 (convert-mu _test-input-buffered-file _test-output-buffered-file _test-error-buffered-file %edx) - 6127 # registers except esp clobbered at this point - 6128 # restore ed - 6129 89/<- %edx 4/r32/esp - 6130 (flush _test-output-buffered-file) - 6131 (flush _test-error-buffered-file) - 6132 +-- 6 lines: #? # dump _test-error-stream --------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 6138 # check output - 6139 (check-stream-equal _test-output-stream "" "F - test-get-with-no-output: output should be empty") - 6140 (check-next-stream-line-equal _test-error-stream "fn foo: stmt get: must have an output" "F - test-get-with-no-output: error message") - 6141 # check that stop(1) was called - 6142 (check-ints-equal *(edx+4) 2 "F - test-get-with-no-output: exit status") - 6143 # don't restore from ebp - 6144 81 0/subop/add %esp 8/imm32 - 6145 # . epilogue - 6146 5d/pop-to-ebp - 6147 c3/return - 6148 - 6149 test-get-with-too-many-outputs: - 6150 # . prologue - 6151 55/push-ebp - 6152 89/<- %ebp 4/r32/esp - 6153 # setup - 6154 (clear-stream _test-input-stream) - 6155 (clear-stream $_test-input-buffered-file->buffer) - 6156 (clear-stream _test-output-stream) - 6157 (clear-stream $_test-output-buffered-file->buffer) - 6158 (clear-stream _test-error-stream) - 6159 (clear-stream $_test-error-buffered-file->buffer) - 6160 # var ed/edx: exit-descriptor = tailor-exit-descriptor(16) - 6161 68/push 0/imm32 - 6162 68/push 0/imm32 - 6163 89/<- %edx 4/r32/esp - 6164 (tailor-exit-descriptor %edx 0x10) - 6165 # - 6166 (write _test-input-stream "fn foo {\n") - 6167 (write _test-input-stream " var a: t\n") - 6168 (write _test-input-stream " var b: int\n") - 6169 (write _test-input-stream " var c/eax: (addr int) <- copy 0\n") - 6170 (write _test-input-stream " c, b <- get a, x\n") - 6171 (write _test-input-stream "}\n") - 6172 (write _test-input-stream "type t {\n") - 6173 (write _test-input-stream " x: int\n") + 6125 (write _test-input-stream "type t {\n") + 6126 (write _test-input-stream " x: int\n") + 6127 (write _test-input-stream "}\n") + 6128 # convert + 6129 (convert-mu _test-input-buffered-file _test-output-buffered-file _test-error-buffered-file %edx) + 6130 # registers except esp clobbered at this point + 6131 # restore ed + 6132 89/<- %edx 4/r32/esp + 6133 (flush _test-output-buffered-file) + 6134 (flush _test-error-buffered-file) + 6135 +-- 6 lines: #? # dump _test-error-stream ------------------------------------------------------------------------------------------------------------------------------------------ + 6141 # check output + 6142 (check-stream-equal _test-output-stream "" "F - test-get-with-no-output: output should be empty") + 6143 (check-next-stream-line-equal _test-error-stream "fn foo: stmt get: must have an output" "F - test-get-with-no-output: error message") + 6144 # check that stop(1) was called + 6145 (check-ints-equal *(edx+4) 2 "F - test-get-with-no-output: exit status") + 6146 # don't restore from ebp + 6147 81 0/subop/add %esp 8/imm32 + 6148 # . epilogue + 6149 5d/pop-to-ebp + 6150 c3/return + 6151 + 6152 test-get-with-too-many-outputs: + 6153 # . prologue + 6154 55/push-ebp + 6155 89/<- %ebp 4/r32/esp + 6156 # setup + 6157 (clear-stream _test-input-stream) + 6158 (clear-stream $_test-input-buffered-file->buffer) + 6159 (clear-stream _test-output-stream) + 6160 (clear-stream $_test-output-buffered-file->buffer) + 6161 (clear-stream _test-error-stream) + 6162 (clear-stream $_test-error-buffered-file->buffer) + 6163 # var ed/edx: exit-descriptor = tailor-exit-descriptor(16) + 6164 68/push 0/imm32 + 6165 68/push 0/imm32 + 6166 89/<- %edx 4/r32/esp + 6167 (tailor-exit-descriptor %edx 0x10) + 6168 # + 6169 (write _test-input-stream "fn foo {\n") + 6170 (write _test-input-stream " var a: t\n") + 6171 (write _test-input-stream " var b: int\n") + 6172 (write _test-input-stream " var c/eax: (addr int) <- copy 0\n") + 6173 (write _test-input-stream " c, b <- get a, x\n") 6174 (write _test-input-stream "}\n") - 6175 # convert - 6176 (convert-mu _test-input-buffered-file _test-output-buffered-file _test-error-buffered-file %edx) - 6177 # registers except esp clobbered at this point - 6178 # restore ed - 6179 89/<- %edx 4/r32/esp - 6180 (flush _test-output-buffered-file) - 6181 (flush _test-error-buffered-file) - 6182 +-- 6 lines: #? # dump _test-error-stream --------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 6188 # check output - 6189 (check-stream-equal _test-output-stream "" "F - test-get-with-too-many-outputs: output should be empty") - 6190 (check-next-stream-line-equal _test-error-stream "fn foo: stmt get: too many outputs (1 required)" "F - test-get-with-too-many-outputs: error message") - 6191 # check that stop(1) was called - 6192 (check-ints-equal *(edx+4) 2 "F - test-get-with-too-many-outputs: exit status") - 6193 # don't restore from ebp - 6194 81 0/subop/add %esp 8/imm32 - 6195 # . epilogue - 6196 5d/pop-to-ebp - 6197 c3/return - 6198 - 6199 test-convert-array-of-user-defined-types: - 6200 # . prologue - 6201 55/push-ebp - 6202 89/<- %ebp 4/r32/esp - 6203 # setup - 6204 (clear-stream _test-input-stream) - 6205 (clear-stream $_test-input-buffered-file->buffer) - 6206 (clear-stream _test-output-stream) - 6207 (clear-stream $_test-output-buffered-file->buffer) - 6208 # - 6209 (write _test-input-stream "type t {\n") # each t is 8 bytes, which is a power of 2 - 6210 (write _test-input-stream " x: int\n") - 6211 (write _test-input-stream " y: int\n") - 6212 (write _test-input-stream "}\n") - 6213 (write _test-input-stream "fn foo {\n") - 6214 (write _test-input-stream " var arr/eax: (addr array t) <- copy 0\n") - 6215 (write _test-input-stream " var idx/ecx: int <- copy 3\n") - 6216 (write _test-input-stream " var x/eax: (addr int) <- index arr, idx\n") - 6217 (write _test-input-stream "}\n") - 6218 # convert - 6219 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) - 6220 (flush _test-output-buffered-file) - 6221 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 6227 # check output - 6228 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-array-of-user-defined-types/0") - 6229 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-array-of-user-defined-types/1") - 6230 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-array-of-user-defined-types/2") - 6231 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-array-of-user-defined-types/3") - 6232 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-array-of-user-defined-types/4") - 6233 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-array-of-user-defined-types/5") - 6234 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %eax" "F - test-convert-array-of-user-defined-types/6") - 6235 (check-next-stream-line-equal _test-output-stream " b8/copy-to-eax 0/imm32" "F - test-convert-array-of-user-defined-types/7") - 6236 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %ecx" "F - test-convert-array-of-user-defined-types/8") - 6237 (check-next-stream-line-equal _test-output-stream " b9/copy-to-ecx 3/imm32" "F - test-convert-array-of-user-defined-types/9") - 6238 (check-next-stream-line-equal _test-output-stream " 8d/copy-address *(eax + ecx<<0x00000003 + 4) 0x00000000/r32" "F - test-convert-array-of-user-defined-types/11") - 6239 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %ecx" "F - test-convert-array-of-user-defined-types/13") - 6240 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %eax" "F - test-convert-array-of-user-defined-types/14") - 6241 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-array-of-user-defined-types/15") - 6242 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-array-of-user-defined-types/16") - 6243 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-array-of-user-defined-types/17") - 6244 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-array-of-user-defined-types/18") - 6245 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-array-of-user-defined-types/19") - 6246 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-array-of-user-defined-types/20") - 6247 # . epilogue - 6248 89/<- %esp 5/r32/ebp - 6249 5d/pop-to-ebp - 6250 c3/return - 6251 - 6252 test-convert-length-of-array-of-user-defined-types-to-eax: - 6253 # . prologue - 6254 55/push-ebp - 6255 89/<- %ebp 4/r32/esp - 6256 # setup - 6257 (clear-stream _test-input-stream) - 6258 (clear-stream $_test-input-buffered-file->buffer) - 6259 (clear-stream _test-output-stream) - 6260 (clear-stream $_test-output-buffered-file->buffer) - 6261 # - 6262 (write _test-input-stream "type t {\n") # size = 12, which is not a power of 2 - 6263 (write _test-input-stream " x: int\n") - 6264 (write _test-input-stream " y: int\n") - 6265 (write _test-input-stream " z: int\n") - 6266 (write _test-input-stream "}\n") - 6267 (write _test-input-stream "fn foo {\n") - 6268 (write _test-input-stream " var arr/eax: (addr array t) <- copy 0\n") - 6269 (write _test-input-stream " var x/eax: (addr t) <- length arr\n") - 6270 (write _test-input-stream "}\n") - 6271 # convert - 6272 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) - 6273 (flush _test-output-buffered-file) - 6274 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 6280 # check output - 6281 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-length-of-array-of-user-defined-types-to-eax/0") - 6282 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-length-of-array-of-user-defined-types-to-eax/1") - 6283 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-length-of-array-of-user-defined-types-to-eax/2") - 6284 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-length-of-array-of-user-defined-types-to-eax/3") - 6285 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-length-of-array-of-user-defined-types-to-eax/4") - 6286 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-length-of-array-of-user-defined-types-to-eax/5") - 6287 # var arr - 6288 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %eax" "F - test-convert-length-of-array-of-user-defined-types-to-eax/6") - 6289 (check-next-stream-line-equal _test-output-stream " b8/copy-to-eax 0/imm32" "F - test-convert-length-of-array-of-user-defined-types-to-eax/7") - 6290 # length instruction - 6291 (check-next-stream-line-equal _test-output-stream " 51/push-ecx" "F - test-convert-length-of-array-of-user-defined-types-to-eax/8") - 6292 (check-next-stream-line-equal _test-output-stream " 52/push-edx" "F - test-convert-length-of-array-of-user-defined-types-to-eax/9") - 6293 (check-next-stream-line-equal _test-output-stream " 8b/-> *eax 0x00000000/r32" "F - test-convert-length-of-array-of-user-defined-types-to-eax/10") - 6294 (check-next-stream-line-equal _test-output-stream " 31/xor %edx 2/r32/edx" "F - test-convert-length-of-array-of-user-defined-types-to-eax/11") - 6295 (check-next-stream-line-equal _test-output-stream " b9/copy-to-ecx 0x0000000c/imm32" "F - test-convert-length-of-array-of-user-defined-types-to-eax/12") - 6296 (check-next-stream-line-equal _test-output-stream " f7 7/subop/idiv-eax-edx-by %ecx" "F - test-convert-length-of-array-of-user-defined-types-to-eax/13") - 6297 (check-next-stream-line-equal _test-output-stream " 5a/pop-to-edx" "F - test-convert-length-of-array-of-user-defined-types-to-eax/14") - 6298 (check-next-stream-line-equal _test-output-stream " 59/pop-to-ecx" "F - test-convert-length-of-array-of-user-defined-types-to-eax/15") - 6299 # reclaim arr - 6300 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %eax" "F - test-convert-length-of-array-of-user-defined-types-to-eax/16") - 6301 # - 6302 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-length-of-array-of-user-defined-types-to-eax/17") - 6303 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-length-of-array-of-user-defined-types-to-eax/18") - 6304 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-length-of-array-of-user-defined-types-to-eax/19") - 6305 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-length-of-array-of-user-defined-types-to-eax/20") - 6306 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-length-of-array-of-user-defined-types-to-eax/21") - 6307 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-length-of-array-of-user-defined-types-to-eax/22") - 6308 # . epilogue - 6309 89/<- %esp 5/r32/ebp - 6310 5d/pop-to-ebp - 6311 c3/return - 6312 - 6313 test-convert-length-of-array-of-user-defined-types-to-ecx: - 6314 # . prologue - 6315 55/push-ebp - 6316 89/<- %ebp 4/r32/esp - 6317 # setup - 6318 (clear-stream _test-input-stream) - 6319 (clear-stream $_test-input-buffered-file->buffer) - 6320 (clear-stream _test-output-stream) - 6321 (clear-stream $_test-output-buffered-file->buffer) - 6322 # - 6323 (write _test-input-stream "type t {\n") # size = 12, which is not a power of 2 - 6324 (write _test-input-stream " x: int\n") - 6325 (write _test-input-stream " y: int\n") - 6326 (write _test-input-stream " z: int\n") - 6327 (write _test-input-stream "}\n") - 6328 (write _test-input-stream "fn foo {\n") - 6329 (write _test-input-stream " var arr/eax: (addr array t) <- copy 0\n") - 6330 (write _test-input-stream " var x/ecx: (addr t) <- length arr\n") - 6331 (write _test-input-stream "}\n") - 6332 # convert - 6333 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) - 6334 (flush _test-output-buffered-file) - 6335 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 6341 # check output - 6342 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-length-of-array-of-user-defined-types-to-ecx/0") - 6343 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-length-of-array-of-user-defined-types-to-ecx/1") - 6344 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-length-of-array-of-user-defined-types-to-ecx/2") - 6345 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-length-of-array-of-user-defined-types-to-ecx/3") - 6346 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-length-of-array-of-user-defined-types-to-ecx/4") - 6347 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-length-of-array-of-user-defined-types-to-ecx/5") - 6348 # var a - 6349 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %eax" "F - test-convert-length-of-array-of-user-defined-types-to-ecx/6") - 6350 (check-next-stream-line-equal _test-output-stream " b8/copy-to-eax 0/imm32" "F - test-convert-length-of-array-of-user-defined-types-to-ecx/7") - 6351 # var x - 6352 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %ecx" "F - test-convert-length-of-array-of-user-defined-types-to-ecx/8") - 6353 # length instruction - 6354 (check-next-stream-line-equal _test-output-stream " 50/push-eax" "F - test-convert-length-of-array-of-user-defined-types-to-ecx/9") - 6355 (check-next-stream-line-equal _test-output-stream " 52/push-edx" "F - test-convert-length-of-array-of-user-defined-types-to-ecx/10") - 6356 (check-next-stream-line-equal _test-output-stream " 8b/-> *eax 0x00000000/r32" "F - test-convert-length-of-array-of-user-defined-types-to-ecx/11") - 6357 (check-next-stream-line-equal _test-output-stream " 31/xor %edx 2/r32/edx" "F - test-convert-length-of-array-of-user-defined-types-to-ecx/12") - 6358 (check-next-stream-line-equal _test-output-stream " b9/copy-to-ecx 0x0000000c/imm32" "F - test-convert-length-of-array-of-user-defined-types-to-ecx/13") - 6359 (check-next-stream-line-equal _test-output-stream " f7 7/subop/idiv-eax-edx-by %ecx" "F - test-convert-length-of-array-of-user-defined-types-to-ecx/14") - 6360 (check-next-stream-line-equal _test-output-stream " 89/<- %ecx 0/r32/eax" "F - test-convert-length-of-array-of-user-defined-types-to-ecx/15") - 6361 (check-next-stream-line-equal _test-output-stream " 5a/pop-to-edx" "F - test-convert-length-of-array-of-user-defined-types-to-ecx/16") - 6362 (check-next-stream-line-equal _test-output-stream " 58/pop-to-eax" "F - test-convert-length-of-array-of-user-defined-types-to-ecx/17") - 6363 # reclaim x - 6364 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %ecx" "F - test-convert-length-of-array-of-user-defined-types-to-ecx/18") - 6365 # reclaim a - 6366 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %eax" "F - test-convert-length-of-array-of-user-defined-types-to-ecx/19") - 6367 # - 6368 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-length-of-array-of-user-defined-types-to-ecx/20") - 6369 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-length-of-array-of-user-defined-types-to-ecx/21") - 6370 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-length-of-array-of-user-defined-types-to-ecx/22") - 6371 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-length-of-array-of-user-defined-types-to-ecx/23") - 6372 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-length-of-array-of-user-defined-types-to-ecx/24") - 6373 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-length-of-array-of-user-defined-types-to-ecx/25") - 6374 # . epilogue - 6375 89/<- %esp 5/r32/ebp - 6376 5d/pop-to-ebp - 6377 c3/return - 6378 - 6379 test-convert-length-of-array-of-user-defined-types-to-edx: - 6380 # . prologue - 6381 55/push-ebp - 6382 89/<- %ebp 4/r32/esp - 6383 # setup - 6384 (clear-stream _test-input-stream) - 6385 (clear-stream $_test-input-buffered-file->buffer) - 6386 (clear-stream _test-output-stream) - 6387 (clear-stream $_test-output-buffered-file->buffer) - 6388 # - 6389 (write _test-input-stream "type t {\n") # size = 12, which is not a power of 2 - 6390 (write _test-input-stream " x: int\n") - 6391 (write _test-input-stream " y: int\n") - 6392 (write _test-input-stream " z: int\n") - 6393 (write _test-input-stream "}\n") - 6394 (write _test-input-stream "fn foo {\n") - 6395 (write _test-input-stream " var arr/eax: (addr array t) <- copy 0\n") - 6396 (write _test-input-stream " var x/edx: (addr t) <- length arr\n") - 6397 (write _test-input-stream "}\n") - 6398 # convert - 6399 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) - 6400 (flush _test-output-buffered-file) - 6401 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 6407 # check output - 6408 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-length-of-array-of-user-defined-types-to-edx/0") - 6409 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-length-of-array-of-user-defined-types-to-edx/1") - 6410 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-length-of-array-of-user-defined-types-to-edx/2") - 6411 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-length-of-array-of-user-defined-types-to-edx/3") - 6412 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-length-of-array-of-user-defined-types-to-edx/4") - 6413 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-length-of-array-of-user-defined-types-to-edx/5") - 6414 # var a - 6415 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %eax" "F - test-convert-length-of-array-of-user-defined-types-to-edx/6") - 6416 (check-next-stream-line-equal _test-output-stream " b8/copy-to-eax 0/imm32" "F - test-convert-length-of-array-of-user-defined-types-to-edx/7") - 6417 # var x - 6418 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %edx" "F - test-convert-length-of-array-of-user-defined-types-to-edx/8") - 6419 # length instruction - 6420 (check-next-stream-line-equal _test-output-stream " 50/push-eax" "F - test-convert-length-of-array-of-user-defined-types-to-edx/9") - 6421 (check-next-stream-line-equal _test-output-stream " 51/push-ecx" "F - test-convert-length-of-array-of-user-defined-types-to-edx/10") - 6422 (check-next-stream-line-equal _test-output-stream " 8b/-> *eax 0x00000000/r32" "F - test-convert-length-of-array-of-user-defined-types-to-edx/11") - 6423 (check-next-stream-line-equal _test-output-stream " 31/xor %edx 2/r32/edx" "F - test-convert-length-of-array-of-user-defined-types-to-edx/12") - 6424 (check-next-stream-line-equal _test-output-stream " b9/copy-to-ecx 0x0000000c/imm32" "F - test-convert-length-of-array-of-user-defined-types-to-edx/13") - 6425 (check-next-stream-line-equal _test-output-stream " f7 7/subop/idiv-eax-edx-by %ecx" "F - test-convert-length-of-array-of-user-defined-types-to-edx/14") - 6426 (check-next-stream-line-equal _test-output-stream " 89/<- %edx 0/r32/eax" "F - test-convert-length-of-array-of-user-defined-types-to-edx/15") - 6427 (check-next-stream-line-equal _test-output-stream " 59/pop-to-ecx" "F - test-convert-length-of-array-of-user-defined-types-to-edx/16") - 6428 (check-next-stream-line-equal _test-output-stream " 58/pop-to-eax" "F - test-convert-length-of-array-of-user-defined-types-to-edx/17") - 6429 # reclaim x - 6430 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %edx" "F - test-convert-length-of-array-of-user-defined-types-to-edx/18") - 6431 # reclaim a - 6432 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %eax" "F - test-convert-length-of-array-of-user-defined-types-to-edx/19") - 6433 # - 6434 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-length-of-array-of-user-defined-types-to-edx/20") - 6435 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-length-of-array-of-user-defined-types-to-edx/21") - 6436 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-length-of-array-of-user-defined-types-to-edx/22") - 6437 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-length-of-array-of-user-defined-types-to-edx/23") - 6438 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-length-of-array-of-user-defined-types-to-edx/24") - 6439 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-length-of-array-of-user-defined-types-to-edx/25") - 6440 # . epilogue - 6441 89/<- %esp 5/r32/ebp - 6442 5d/pop-to-ebp - 6443 c3/return - 6444 - 6445 test-convert-length-of-array-of-user-defined-types: - 6446 # . prologue - 6447 55/push-ebp - 6448 89/<- %ebp 4/r32/esp - 6449 # setup - 6450 (clear-stream _test-input-stream) - 6451 (clear-stream $_test-input-buffered-file->buffer) - 6452 (clear-stream _test-output-stream) - 6453 (clear-stream $_test-output-buffered-file->buffer) - 6454 # - 6455 (write _test-input-stream "type t {\n") # each t is 8 bytes, which is a power of 2 - 6456 (write _test-input-stream " x: int\n") - 6457 (write _test-input-stream " y: int\n") - 6458 (write _test-input-stream " z: int\n") - 6459 (write _test-input-stream "}\n") - 6460 (write _test-input-stream "fn foo {\n") - 6461 (write _test-input-stream " var arr/eax: (addr array t) <- copy 0\n") - 6462 (write _test-input-stream " var x/ebx: (addr t) <- length arr\n") - 6463 (write _test-input-stream "}\n") - 6464 # convert - 6465 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) - 6466 (flush _test-output-buffered-file) - 6467 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 6473 # check output - 6474 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-length-of-array-of-user-defined-types/0") - 6475 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-length-of-array-of-user-defined-types/1") - 6476 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-length-of-array-of-user-defined-types/2") - 6477 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-length-of-array-of-user-defined-types/3") - 6478 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-length-of-array-of-user-defined-types/4") - 6479 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-length-of-array-of-user-defined-types/5") - 6480 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %eax" "F - test-convert-length-of-array-of-user-defined-types/6") - 6481 (check-next-stream-line-equal _test-output-stream " b8/copy-to-eax 0/imm32" "F - test-convert-length-of-array-of-user-defined-types/7") - 6482 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %ebx" "F - test-convert-length-of-array-of-user-defined-types/8") - 6483 (check-next-stream-line-equal _test-output-stream " 50/push-eax" "F - test-convert-length-of-array-of-user-defined-types/9") - 6484 (check-next-stream-line-equal _test-output-stream " 51/push-ecx" "F - test-convert-length-of-array-of-user-defined-types/10") - 6485 (check-next-stream-line-equal _test-output-stream " 52/push-edx" "F - test-convert-length-of-array-of-user-defined-types/11") - 6486 (check-next-stream-line-equal _test-output-stream " 8b/-> *eax 0x00000000/r32" "F - test-convert-length-of-array-of-user-defined-types/12") - 6487 (check-next-stream-line-equal _test-output-stream " 31/xor %edx 2/r32/edx" "F - test-convert-length-of-array-of-user-defined-types/13") - 6488 (check-next-stream-line-equal _test-output-stream " b9/copy-to-ecx 0x0000000c/imm32" "F - test-convert-length-of-array-of-user-defined-types/14") - 6489 (check-next-stream-line-equal _test-output-stream " f7 7/subop/idiv-eax-edx-by %ecx" "F - test-convert-length-of-array-of-user-defined-types/15") - 6490 (check-next-stream-line-equal _test-output-stream " 89/<- %ebx 0/r32/eax" "F - test-convert-length-of-array-of-user-defined-types/16") - 6491 (check-next-stream-line-equal _test-output-stream " 5a/pop-to-edx" "F - test-convert-length-of-array-of-user-defined-types/17") - 6492 (check-next-stream-line-equal _test-output-stream " 59/pop-to-ecx" "F - test-convert-length-of-array-of-user-defined-types/18") - 6493 (check-next-stream-line-equal _test-output-stream " 58/pop-to-eax" "F - test-convert-length-of-array-of-user-defined-types/19") - 6494 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %ebx" "F - test-convert-length-of-array-of-user-defined-types/20") - 6495 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %eax" "F - test-convert-length-of-array-of-user-defined-types/21") - 6496 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-length-of-array-of-user-defined-types/22") - 6497 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-length-of-array-of-user-defined-types/23") - 6498 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-length-of-array-of-user-defined-types/24") - 6499 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-length-of-array-of-user-defined-types/25") - 6500 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-length-of-array-of-user-defined-types/26") - 6501 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-length-of-array-of-user-defined-types/27") - 6502 # . epilogue - 6503 89/<- %esp 5/r32/ebp - 6504 5d/pop-to-ebp - 6505 c3/return - 6506 - 6507 ####################################################### - 6508 # Parsing - 6509 ####################################################### - 6510 - 6511 == data - 6512 - 6513 # Global state added to each var record when parsing a function - 6514 Next-block-index: # (addr int) - 6515 1/imm32 - 6516 - 6517 Curr-block-depth: # (addr int) + 6175 (write _test-input-stream "type t {\n") + 6176 (write _test-input-stream " x: int\n") + 6177 (write _test-input-stream "}\n") + 6178 # convert + 6179 (convert-mu _test-input-buffered-file _test-output-buffered-file _test-error-buffered-file %edx) + 6180 # registers except esp clobbered at this point + 6181 # restore ed + 6182 89/<- %edx 4/r32/esp + 6183 (flush _test-output-buffered-file) + 6184 (flush _test-error-buffered-file) + 6185 +-- 6 lines: #? # dump _test-error-stream ------------------------------------------------------------------------------------------------------------------------------------------ + 6191 # check output + 6192 (check-stream-equal _test-output-stream "" "F - test-get-with-too-many-outputs: output should be empty") + 6193 (check-next-stream-line-equal _test-error-stream "fn foo: stmt get: too many outputs (1 required)" "F - test-get-with-too-many-outputs: error message") + 6194 # check that stop(1) was called + 6195 (check-ints-equal *(edx+4) 2 "F - test-get-with-too-many-outputs: exit status") + 6196 # don't restore from ebp + 6197 81 0/subop/add %esp 8/imm32 + 6198 # . epilogue + 6199 5d/pop-to-ebp + 6200 c3/return + 6201 + 6202 test-convert-array-of-user-defined-types: + 6203 # . prologue + 6204 55/push-ebp + 6205 89/<- %ebp 4/r32/esp + 6206 # setup + 6207 (clear-stream _test-input-stream) + 6208 (clear-stream $_test-input-buffered-file->buffer) + 6209 (clear-stream _test-output-stream) + 6210 (clear-stream $_test-output-buffered-file->buffer) + 6211 # + 6212 (write _test-input-stream "type t {\n") # each t is 8 bytes, which is a power of 2 + 6213 (write _test-input-stream " x: int\n") + 6214 (write _test-input-stream " y: int\n") + 6215 (write _test-input-stream "}\n") + 6216 (write _test-input-stream "fn foo {\n") + 6217 (write _test-input-stream " var arr/eax: (addr array t) <- copy 0\n") + 6218 (write _test-input-stream " var idx/ecx: int <- copy 3\n") + 6219 (write _test-input-stream " var x/eax: (addr int) <- index arr, idx\n") + 6220 (write _test-input-stream "}\n") + 6221 # convert + 6222 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) + 6223 (flush _test-output-buffered-file) + 6224 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- + 6230 # check output + 6231 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-array-of-user-defined-types/0") + 6232 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-array-of-user-defined-types/1") + 6233 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-array-of-user-defined-types/2") + 6234 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-array-of-user-defined-types/3") + 6235 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-array-of-user-defined-types/4") + 6236 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-array-of-user-defined-types/5") + 6237 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %eax" "F - test-convert-array-of-user-defined-types/6") + 6238 (check-next-stream-line-equal _test-output-stream " b8/copy-to-eax 0/imm32" "F - test-convert-array-of-user-defined-types/7") + 6239 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %ecx" "F - test-convert-array-of-user-defined-types/8") + 6240 (check-next-stream-line-equal _test-output-stream " b9/copy-to-ecx 3/imm32" "F - test-convert-array-of-user-defined-types/9") + 6241 (check-next-stream-line-equal _test-output-stream " 8d/copy-address *(eax + ecx<<0x00000003 + 4) 0x00000000/r32" "F - test-convert-array-of-user-defined-types/11") + 6242 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %ecx" "F - test-convert-array-of-user-defined-types/13") + 6243 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %eax" "F - test-convert-array-of-user-defined-types/14") + 6244 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-array-of-user-defined-types/15") + 6245 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-array-of-user-defined-types/16") + 6246 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-array-of-user-defined-types/17") + 6247 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-array-of-user-defined-types/18") + 6248 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-array-of-user-defined-types/19") + 6249 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-array-of-user-defined-types/20") + 6250 # . epilogue + 6251 89/<- %esp 5/r32/ebp + 6252 5d/pop-to-ebp + 6253 c3/return + 6254 + 6255 test-convert-length-of-array-of-user-defined-types-to-eax: + 6256 # . prologue + 6257 55/push-ebp + 6258 89/<- %ebp 4/r32/esp + 6259 # setup + 6260 (clear-stream _test-input-stream) + 6261 (clear-stream $_test-input-buffered-file->buffer) + 6262 (clear-stream _test-output-stream) + 6263 (clear-stream $_test-output-buffered-file->buffer) + 6264 # + 6265 (write _test-input-stream "type t {\n") # size = 12, which is not a power of 2 + 6266 (write _test-input-stream " x: int\n") + 6267 (write _test-input-stream " y: int\n") + 6268 (write _test-input-stream " z: int\n") + 6269 (write _test-input-stream "}\n") + 6270 (write _test-input-stream "fn foo {\n") + 6271 (write _test-input-stream " var arr/eax: (addr array t) <- copy 0\n") + 6272 (write _test-input-stream " var x/eax: (addr t) <- length arr\n") + 6273 (write _test-input-stream "}\n") + 6274 # convert + 6275 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) + 6276 (flush _test-output-buffered-file) + 6277 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- + 6283 # check output + 6284 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-length-of-array-of-user-defined-types-to-eax/0") + 6285 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-length-of-array-of-user-defined-types-to-eax/1") + 6286 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-length-of-array-of-user-defined-types-to-eax/2") + 6287 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-length-of-array-of-user-defined-types-to-eax/3") + 6288 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-length-of-array-of-user-defined-types-to-eax/4") + 6289 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-length-of-array-of-user-defined-types-to-eax/5") + 6290 # var arr + 6291 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %eax" "F - test-convert-length-of-array-of-user-defined-types-to-eax/6") + 6292 (check-next-stream-line-equal _test-output-stream " b8/copy-to-eax 0/imm32" "F - test-convert-length-of-array-of-user-defined-types-to-eax/7") + 6293 # length instruction + 6294 (check-next-stream-line-equal _test-output-stream " 51/push-ecx" "F - test-convert-length-of-array-of-user-defined-types-to-eax/8") + 6295 (check-next-stream-line-equal _test-output-stream " 52/push-edx" "F - test-convert-length-of-array-of-user-defined-types-to-eax/9") + 6296 (check-next-stream-line-equal _test-output-stream " 8b/-> *eax 0x00000000/r32" "F - test-convert-length-of-array-of-user-defined-types-to-eax/10") + 6297 (check-next-stream-line-equal _test-output-stream " 31/xor %edx 2/r32/edx" "F - test-convert-length-of-array-of-user-defined-types-to-eax/11") + 6298 (check-next-stream-line-equal _test-output-stream " b9/copy-to-ecx 0x0000000c/imm32" "F - test-convert-length-of-array-of-user-defined-types-to-eax/12") + 6299 (check-next-stream-line-equal _test-output-stream " f7 7/subop/idiv-eax-edx-by %ecx" "F - test-convert-length-of-array-of-user-defined-types-to-eax/13") + 6300 (check-next-stream-line-equal _test-output-stream " 5a/pop-to-edx" "F - test-convert-length-of-array-of-user-defined-types-to-eax/14") + 6301 (check-next-stream-line-equal _test-output-stream " 59/pop-to-ecx" "F - test-convert-length-of-array-of-user-defined-types-to-eax/15") + 6302 # reclaim arr + 6303 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %eax" "F - test-convert-length-of-array-of-user-defined-types-to-eax/16") + 6304 # + 6305 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-length-of-array-of-user-defined-types-to-eax/17") + 6306 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-length-of-array-of-user-defined-types-to-eax/18") + 6307 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-length-of-array-of-user-defined-types-to-eax/19") + 6308 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-length-of-array-of-user-defined-types-to-eax/20") + 6309 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-length-of-array-of-user-defined-types-to-eax/21") + 6310 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-length-of-array-of-user-defined-types-to-eax/22") + 6311 # . epilogue + 6312 89/<- %esp 5/r32/ebp + 6313 5d/pop-to-ebp + 6314 c3/return + 6315 + 6316 test-convert-length-of-array-of-user-defined-types-to-ecx: + 6317 # . prologue + 6318 55/push-ebp + 6319 89/<- %ebp 4/r32/esp + 6320 # setup + 6321 (clear-stream _test-input-stream) + 6322 (clear-stream $_test-input-buffered-file->buffer) + 6323 (clear-stream _test-output-stream) + 6324 (clear-stream $_test-output-buffered-file->buffer) + 6325 # + 6326 (write _test-input-stream "type t {\n") # size = 12, which is not a power of 2 + 6327 (write _test-input-stream " x: int\n") + 6328 (write _test-input-stream " y: int\n") + 6329 (write _test-input-stream " z: int\n") + 6330 (write _test-input-stream "}\n") + 6331 (write _test-input-stream "fn foo {\n") + 6332 (write _test-input-stream " var arr/eax: (addr array t) <- copy 0\n") + 6333 (write _test-input-stream " var x/ecx: (addr t) <- length arr\n") + 6334 (write _test-input-stream "}\n") + 6335 # convert + 6336 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) + 6337 (flush _test-output-buffered-file) + 6338 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- + 6344 # check output + 6345 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-length-of-array-of-user-defined-types-to-ecx/0") + 6346 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-length-of-array-of-user-defined-types-to-ecx/1") + 6347 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-length-of-array-of-user-defined-types-to-ecx/2") + 6348 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-length-of-array-of-user-defined-types-to-ecx/3") + 6349 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-length-of-array-of-user-defined-types-to-ecx/4") + 6350 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-length-of-array-of-user-defined-types-to-ecx/5") + 6351 # var a + 6352 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %eax" "F - test-convert-length-of-array-of-user-defined-types-to-ecx/6") + 6353 (check-next-stream-line-equal _test-output-stream " b8/copy-to-eax 0/imm32" "F - test-convert-length-of-array-of-user-defined-types-to-ecx/7") + 6354 # var x + 6355 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %ecx" "F - test-convert-length-of-array-of-user-defined-types-to-ecx/8") + 6356 # length instruction + 6357 (check-next-stream-line-equal _test-output-stream " 50/push-eax" "F - test-convert-length-of-array-of-user-defined-types-to-ecx/9") + 6358 (check-next-stream-line-equal _test-output-stream " 52/push-edx" "F - test-convert-length-of-array-of-user-defined-types-to-ecx/10") + 6359 (check-next-stream-line-equal _test-output-stream " 8b/-> *eax 0x00000000/r32" "F - test-convert-length-of-array-of-user-defined-types-to-ecx/11") + 6360 (check-next-stream-line-equal _test-output-stream " 31/xor %edx 2/r32/edx" "F - test-convert-length-of-array-of-user-defined-types-to-ecx/12") + 6361 (check-next-stream-line-equal _test-output-stream " b9/copy-to-ecx 0x0000000c/imm32" "F - test-convert-length-of-array-of-user-defined-types-to-ecx/13") + 6362 (check-next-stream-line-equal _test-output-stream " f7 7/subop/idiv-eax-edx-by %ecx" "F - test-convert-length-of-array-of-user-defined-types-to-ecx/14") + 6363 (check-next-stream-line-equal _test-output-stream " 89/<- %ecx 0/r32/eax" "F - test-convert-length-of-array-of-user-defined-types-to-ecx/15") + 6364 (check-next-stream-line-equal _test-output-stream " 5a/pop-to-edx" "F - test-convert-length-of-array-of-user-defined-types-to-ecx/16") + 6365 (check-next-stream-line-equal _test-output-stream " 58/pop-to-eax" "F - test-convert-length-of-array-of-user-defined-types-to-ecx/17") + 6366 # reclaim x + 6367 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %ecx" "F - test-convert-length-of-array-of-user-defined-types-to-ecx/18") + 6368 # reclaim a + 6369 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %eax" "F - test-convert-length-of-array-of-user-defined-types-to-ecx/19") + 6370 # + 6371 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-length-of-array-of-user-defined-types-to-ecx/20") + 6372 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-length-of-array-of-user-defined-types-to-ecx/21") + 6373 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-length-of-array-of-user-defined-types-to-ecx/22") + 6374 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-length-of-array-of-user-defined-types-to-ecx/23") + 6375 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-length-of-array-of-user-defined-types-to-ecx/24") + 6376 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-length-of-array-of-user-defined-types-to-ecx/25") + 6377 # . epilogue + 6378 89/<- %esp 5/r32/ebp + 6379 5d/pop-to-ebp + 6380 c3/return + 6381 + 6382 test-convert-length-of-array-of-user-defined-types-to-edx: + 6383 # . prologue + 6384 55/push-ebp + 6385 89/<- %ebp 4/r32/esp + 6386 # setup + 6387 (clear-stream _test-input-stream) + 6388 (clear-stream $_test-input-buffered-file->buffer) + 6389 (clear-stream _test-output-stream) + 6390 (clear-stream $_test-output-buffered-file->buffer) + 6391 # + 6392 (write _test-input-stream "type t {\n") # size = 12, which is not a power of 2 + 6393 (write _test-input-stream " x: int\n") + 6394 (write _test-input-stream " y: int\n") + 6395 (write _test-input-stream " z: int\n") + 6396 (write _test-input-stream "}\n") + 6397 (write _test-input-stream "fn foo {\n") + 6398 (write _test-input-stream " var arr/eax: (addr array t) <- copy 0\n") + 6399 (write _test-input-stream " var x/edx: (addr t) <- length arr\n") + 6400 (write _test-input-stream "}\n") + 6401 # convert + 6402 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) + 6403 (flush _test-output-buffered-file) + 6404 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- + 6410 # check output + 6411 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-length-of-array-of-user-defined-types-to-edx/0") + 6412 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-length-of-array-of-user-defined-types-to-edx/1") + 6413 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-length-of-array-of-user-defined-types-to-edx/2") + 6414 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-length-of-array-of-user-defined-types-to-edx/3") + 6415 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-length-of-array-of-user-defined-types-to-edx/4") + 6416 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-length-of-array-of-user-defined-types-to-edx/5") + 6417 # var a + 6418 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %eax" "F - test-convert-length-of-array-of-user-defined-types-to-edx/6") + 6419 (check-next-stream-line-equal _test-output-stream " b8/copy-to-eax 0/imm32" "F - test-convert-length-of-array-of-user-defined-types-to-edx/7") + 6420 # var x + 6421 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %edx" "F - test-convert-length-of-array-of-user-defined-types-to-edx/8") + 6422 # length instruction + 6423 (check-next-stream-line-equal _test-output-stream " 50/push-eax" "F - test-convert-length-of-array-of-user-defined-types-to-edx/9") + 6424 (check-next-stream-line-equal _test-output-stream " 51/push-ecx" "F - test-convert-length-of-array-of-user-defined-types-to-edx/10") + 6425 (check-next-stream-line-equal _test-output-stream " 8b/-> *eax 0x00000000/r32" "F - test-convert-length-of-array-of-user-defined-types-to-edx/11") + 6426 (check-next-stream-line-equal _test-output-stream " 31/xor %edx 2/r32/edx" "F - test-convert-length-of-array-of-user-defined-types-to-edx/12") + 6427 (check-next-stream-line-equal _test-output-stream " b9/copy-to-ecx 0x0000000c/imm32" "F - test-convert-length-of-array-of-user-defined-types-to-edx/13") + 6428 (check-next-stream-line-equal _test-output-stream " f7 7/subop/idiv-eax-edx-by %ecx" "F - test-convert-length-of-array-of-user-defined-types-to-edx/14") + 6429 (check-next-stream-line-equal _test-output-stream " 89/<- %edx 0/r32/eax" "F - test-convert-length-of-array-of-user-defined-types-to-edx/15") + 6430 (check-next-stream-line-equal _test-output-stream " 59/pop-to-ecx" "F - test-convert-length-of-array-of-user-defined-types-to-edx/16") + 6431 (check-next-stream-line-equal _test-output-stream " 58/pop-to-eax" "F - test-convert-length-of-array-of-user-defined-types-to-edx/17") + 6432 # reclaim x + 6433 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %edx" "F - test-convert-length-of-array-of-user-defined-types-to-edx/18") + 6434 # reclaim a + 6435 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %eax" "F - test-convert-length-of-array-of-user-defined-types-to-edx/19") + 6436 # + 6437 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-length-of-array-of-user-defined-types-to-edx/20") + 6438 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-length-of-array-of-user-defined-types-to-edx/21") + 6439 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-length-of-array-of-user-defined-types-to-edx/22") + 6440 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-length-of-array-of-user-defined-types-to-edx/23") + 6441 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-length-of-array-of-user-defined-types-to-edx/24") + 6442 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-length-of-array-of-user-defined-types-to-edx/25") + 6443 # . epilogue + 6444 89/<- %esp 5/r32/ebp + 6445 5d/pop-to-ebp + 6446 c3/return + 6447 + 6448 test-convert-length-of-array-of-user-defined-types: + 6449 # . prologue + 6450 55/push-ebp + 6451 89/<- %ebp 4/r32/esp + 6452 # setup + 6453 (clear-stream _test-input-stream) + 6454 (clear-stream $_test-input-buffered-file->buffer) + 6455 (clear-stream _test-output-stream) + 6456 (clear-stream $_test-output-buffered-file->buffer) + 6457 # + 6458 (write _test-input-stream "type t {\n") # each t is 8 bytes, which is a power of 2 + 6459 (write _test-input-stream " x: int\n") + 6460 (write _test-input-stream " y: int\n") + 6461 (write _test-input-stream " z: int\n") + 6462 (write _test-input-stream "}\n") + 6463 (write _test-input-stream "fn foo {\n") + 6464 (write _test-input-stream " var arr/eax: (addr array t) <- copy 0\n") + 6465 (write _test-input-stream " var x/ebx: (addr t) <- length arr\n") + 6466 (write _test-input-stream "}\n") + 6467 # convert + 6468 (convert-mu _test-input-buffered-file _test-output-buffered-file Stderr 0) + 6469 (flush _test-output-buffered-file) + 6470 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- + 6476 # check output + 6477 (check-next-stream-line-equal _test-output-stream "foo:" "F - test-convert-length-of-array-of-user-defined-types/0") + 6478 (check-next-stream-line-equal _test-output-stream " # . prologue" "F - test-convert-length-of-array-of-user-defined-types/1") + 6479 (check-next-stream-line-equal _test-output-stream " 55/push-ebp" "F - test-convert-length-of-array-of-user-defined-types/2") + 6480 (check-next-stream-line-equal _test-output-stream " 89/<- %ebp 4/r32/esp" "F - test-convert-length-of-array-of-user-defined-types/3") + 6481 (check-next-stream-line-equal _test-output-stream " {" "F - test-convert-length-of-array-of-user-defined-types/4") + 6482 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:loop:" "F - test-convert-length-of-array-of-user-defined-types/5") + 6483 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %eax" "F - test-convert-length-of-array-of-user-defined-types/6") + 6484 (check-next-stream-line-equal _test-output-stream " b8/copy-to-eax 0/imm32" "F - test-convert-length-of-array-of-user-defined-types/7") + 6485 (check-next-stream-line-equal _test-output-stream " ff 6/subop/push %ebx" "F - test-convert-length-of-array-of-user-defined-types/8") + 6486 (check-next-stream-line-equal _test-output-stream " 50/push-eax" "F - test-convert-length-of-array-of-user-defined-types/9") + 6487 (check-next-stream-line-equal _test-output-stream " 51/push-ecx" "F - test-convert-length-of-array-of-user-defined-types/10") + 6488 (check-next-stream-line-equal _test-output-stream " 52/push-edx" "F - test-convert-length-of-array-of-user-defined-types/11") + 6489 (check-next-stream-line-equal _test-output-stream " 8b/-> *eax 0x00000000/r32" "F - test-convert-length-of-array-of-user-defined-types/12") + 6490 (check-next-stream-line-equal _test-output-stream " 31/xor %edx 2/r32/edx" "F - test-convert-length-of-array-of-user-defined-types/13") + 6491 (check-next-stream-line-equal _test-output-stream " b9/copy-to-ecx 0x0000000c/imm32" "F - test-convert-length-of-array-of-user-defined-types/14") + 6492 (check-next-stream-line-equal _test-output-stream " f7 7/subop/idiv-eax-edx-by %ecx" "F - test-convert-length-of-array-of-user-defined-types/15") + 6493 (check-next-stream-line-equal _test-output-stream " 89/<- %ebx 0/r32/eax" "F - test-convert-length-of-array-of-user-defined-types/16") + 6494 (check-next-stream-line-equal _test-output-stream " 5a/pop-to-edx" "F - test-convert-length-of-array-of-user-defined-types/17") + 6495 (check-next-stream-line-equal _test-output-stream " 59/pop-to-ecx" "F - test-convert-length-of-array-of-user-defined-types/18") + 6496 (check-next-stream-line-equal _test-output-stream " 58/pop-to-eax" "F - test-convert-length-of-array-of-user-defined-types/19") + 6497 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %ebx" "F - test-convert-length-of-array-of-user-defined-types/20") + 6498 (check-next-stream-line-equal _test-output-stream " 8f 0/subop/pop %eax" "F - test-convert-length-of-array-of-user-defined-types/21") + 6499 (check-next-stream-line-equal _test-output-stream " }" "F - test-convert-length-of-array-of-user-defined-types/22") + 6500 (check-next-stream-line-equal _test-output-stream "$foo:0x00000001:break:" "F - test-convert-length-of-array-of-user-defined-types/23") + 6501 (check-next-stream-line-equal _test-output-stream " # . epilogue" "F - test-convert-length-of-array-of-user-defined-types/24") + 6502 (check-next-stream-line-equal _test-output-stream " 89/<- %esp 5/r32/ebp" "F - test-convert-length-of-array-of-user-defined-types/25") + 6503 (check-next-stream-line-equal _test-output-stream " 5d/pop-to-ebp" "F - test-convert-length-of-array-of-user-defined-types/26") + 6504 (check-next-stream-line-equal _test-output-stream " c3/return" "F - test-convert-length-of-array-of-user-defined-types/27") + 6505 # . epilogue + 6506 89/<- %esp 5/r32/ebp + 6507 5d/pop-to-ebp + 6508 c3/return + 6509 + 6510 ####################################################### + 6511 # Parsing + 6512 ####################################################### + 6513 + 6514 == data + 6515 + 6516 # Global state added to each var record when parsing a function + 6517 Next-block-index: # (addr int) 6518 1/imm32 6519 - 6520 == code - 6521 - 6522 parse-mu: # in: (addr buffered-file), err: (addr buffered-file), ed: (addr exit-descriptor) - 6523 # pseudocode - 6524 # var curr-function: (addr handle function) = Program->functions - 6525 # var curr-signature: (addr handle function) = Program->signatures - 6526 # var curr-type: (addr handle typeinfo) = Program->types - 6527 # var line: (stream byte 512) - 6528 # var word-slice: slice - 6529 # while true # line loop - 6530 # clear-stream(line) - 6531 # read-line-buffered(in, line) - 6532 # if (line->write == 0) break # end of file - 6533 # word-slice = next-mu-token(line) - 6534 # if slice-empty?(word-slice) # end of line - 6535 # continue - 6536 # else if slice-starts-with?(word-slice, "#") # comment - 6537 # continue # end of line - 6538 # else if slice-equal?(word-slice, "fn") - 6539 # var new-function: (handle function) = allocate(function) - 6540 # var vars: (stack live-var 256) - 6541 # populate-mu-function-header(line, new-function, vars) - 6542 # populate-mu-function-body(in, new-function, vars) - 6543 # assert(vars->top == 0) - 6544 # *curr-function = new-function - 6545 # curr-function = &new-function->next - 6546 # else if slice-equal?(word-slice, "sig") - 6547 # var new-function: (handle function) = allocate(function) - 6548 # populate-mu-function-signature(line, new-function) - 6549 # *curr-signature = new-function - 6550 # curr-signature = &new-function->next - 6551 # else if slice-equal?(word-slice, "type") - 6552 # word-slice = next-mu-token(line) - 6553 # type-id = pos-or-insert-slice(Type-id, word-slice) - 6554 # var new-type: (handle typeinfo) = find-or-create-typeinfo(type-id) - 6555 # assert(next-word(line) == "{") - 6556 # populate-mu-type(in, new-type) - 6557 # else - 6558 # abort() - 6559 # - 6560 # . prologue - 6561 55/push-ebp - 6562 89/<- %ebp 4/r32/esp - 6563 # var curr-signature: (addr handle function) at *(ebp-4) - 6564 68/push _Program-signatures/imm32 - 6565 # . save registers - 6566 50/push-eax - 6567 51/push-ecx - 6568 52/push-edx - 6569 53/push-ebx - 6570 56/push-esi - 6571 57/push-edi - 6572 # var line/ecx: (stream byte 512) - 6573 81 5/subop/subtract %esp 0x200/imm32 - 6574 68/push 0x200/imm32/size - 6575 68/push 0/imm32/read - 6576 68/push 0/imm32/write - 6577 89/<- %ecx 4/r32/esp - 6578 # var word-slice/edx: slice - 6579 68/push 0/imm32/end - 6580 68/push 0/imm32/start - 6581 89/<- %edx 4/r32/esp - 6582 # var curr-function/edi: (addr handle function) - 6583 bf/copy-to-edi _Program-functions/imm32 - 6584 # var vars/ebx: (stack live-var 256) - 6585 81 5/subop/subtract %esp 0xc00/imm32 - 6586 68/push 0xc00/imm32/size - 6587 68/push 0/imm32/top - 6588 89/<- %ebx 4/r32/esp - 6589 { - 6590 $parse-mu:line-loop: - 6591 (clear-stream %ecx) - 6592 (read-line-buffered *(ebp+8) %ecx) - 6593 # if (line->write == 0) break - 6594 81 7/subop/compare *ecx 0/imm32 - 6595 0f 84/jump-if-= break/disp32 - 6596 +-- 6 lines: #? # dump line --------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- - 6602 (next-mu-token %ecx %edx) - 6603 # if slice-empty?(word-slice) continue - 6604 (slice-empty? %edx) # => eax - 6605 3d/compare-eax-and 0/imm32/false - 6606 0f 85/jump-if-!= loop/disp32 - 6607 # if (*word-slice->start == "#") continue - 6608 # . eax = *word-slice->start - 6609 8b/-> *edx 0/r32/eax - 6610 8a/copy-byte *eax 0/r32/AL - 6611 81 4/subop/and %eax 0xff/imm32 - 6612 # . if (eax == '#') continue - 6613 3d/compare-eax-and 0x23/imm32/hash - 6614 0f 84/jump-if-= loop/disp32 - 6615 # if (slice-equal?(word-slice, "fn")) parse a function - 6616 { - 6617 $parse-mu:fn: - 6618 (slice-equal? %edx "fn") # => eax - 6619 3d/compare-eax-and 0/imm32/false - 6620 0f 84/jump-if-= break/disp32 - 6621 # var new-function/esi: (handle function) - 6622 68/push 0/imm32 - 6623 68/push 0/imm32 - 6624 89/<- %esi 4/r32/esp - 6625 # populate-mu-function(line, in, vars, new-function) - 6626 (allocate Heap *Function-size %esi) - 6627 # var new-function-addr/eax: (addr function) - 6628 (lookup *esi *(esi+4)) # => eax - 6629 # initialize vars - 6630 (clear-stack %ebx) - 6631 # - 6632 (populate-mu-function-header %ecx %eax %ebx *(ebp+0xc) *(ebp+0x10)) - 6633 (populate-mu-function-body *(ebp+8) %eax %ebx *(ebp+0xc) *(ebp+0x10)) - 6634 # *curr-function = new-function - 6635 8b/-> *esi 0/r32/eax - 6636 89/<- *edi 0/r32/eax - 6637 8b/-> *(esi+4) 0/r32/eax - 6638 89/<- *(edi+4) 0/r32/eax - 6639 # curr-function = &new-function->next - 6640 # . var tmp/eax: (addr function) = lookup(new-function) - 6641 (lookup *esi *(esi+4)) # => eax - 6642 # . curr-function = &tmp->next - 6643 8d/copy-address *(eax+0x20) 7/r32/edi # Function-next - 6644 # reclaim new-function - 6645 81 0/subop/add %esp 8/imm32 - 6646 # - 6647 e9/jump $parse-mu:line-loop/disp32 - 6648 } - 6649 # if (slice-equal?(word-slice, "sig")) parse a function signature - 6650 # Function signatures are for providing types to SubX functions. - 6651 { - 6652 $parse-mu:sig: - 6653 (slice-equal? %edx "sig") # => eax - 6654 3d/compare-eax-and 0/imm32/false - 6655 0f 84/jump-if-= break/disp32 - 6656 # edi = curr-function - 6657 57/push-edi - 6658 8b/-> *(ebp-4) 7/r32/edi - 6659 # var new-function/esi: (handle function) - 6660 68/push 0/imm32 - 6661 68/push 0/imm32 - 6662 89/<- %esi 4/r32/esp - 6663 # populate-mu-function(line, in, vars, new-function) - 6664 (allocate Heap *Function-size %esi) - 6665 # var new-function-addr/eax: (addr function) - 6666 (lookup *esi *(esi+4)) # => eax - 6667 # - 6668 (populate-mu-function-signature %ecx %eax *(ebp+0xc) *(ebp+0x10)) - 6669 # *curr-signature = new-function - 6670 8b/-> *esi 0/r32/eax - 6671 89/<- *edi 0/r32/eax - 6672 8b/-> *(esi+4) 0/r32/eax - 6673 89/<- *(edi+4) 0/r32/eax - 6674 # curr-signature = &new-function->next - 6675 # . var tmp/eax: (addr function) = lookup(new-function) - 6676 (lookup *esi *(esi+4)) # => eax - 6677 # . curr-function = &tmp->next - 6678 8d/copy-address *(eax+0x20) 7/r32/edi # Function-next - 6679 # reclaim new-function - 6680 81 0/subop/add %esp 8/imm32 - 6681 # save curr-function - 6682 89/<- *(ebp-4) 7/r32/edi - 6683 # restore edi - 6684 5f/pop-to-edi - 6685 # - 6686 e9/jump $parse-mu:line-loop/disp32 - 6687 } - 6688 # if (slice-equal?(word-slice, "type")) parse a type (struct/record) definition - 6689 { - 6690 $parse-mu:type: - 6691 (slice-equal? %edx "type") # => eax - 6692 3d/compare-eax-and 0/imm32 - 6693 0f 84/jump-if-= break/disp32 - 6694 (next-mu-token %ecx %edx) - 6695 # var type-id/eax: int - 6696 (pos-or-insert-slice Type-id %edx) # => eax - 6697 # spill - 6698 51/push-ecx - 6699 # var new-type/ecx: (handle typeinfo) - 6700 68/push 0/imm32 - 6701 68/push 0/imm32 - 6702 89/<- %ecx 4/r32/esp - 6703 (find-or-create-typeinfo %eax %ecx) - 6704 # - 6705 (lookup *ecx *(ecx+4)) # => eax - 6706 # TODO: ensure that 'line' has nothing else but '{' - 6707 #? (dump-typeinfos "=== aaa\n") - 6708 (populate-mu-type *(ebp+8) %eax *(ebp+0xc) *(ebp+0x10)) # => eax - 6709 #? (dump-typeinfos "=== zzz\n") - 6710 # reclaim new-type - 6711 81 0/subop/add %esp 8/imm32 - 6712 # restore - 6713 59/pop-to-ecx - 6714 e9/jump $parse-mu:line-loop/disp32 - 6715 } - 6716 # otherwise abort - 6717 e9/jump $parse-mu:error1/disp32 - 6718 } # end line loop - 6719 $parse-mu:end: - 6720 # . reclaim locals - 6721 81 0/subop/add %esp 0x20c/imm32 # line - 6722 81 0/subop/add %esp 0xc08/imm32 # vars - 6723 81 0/subop/add %esp 8/imm32 - 6724 # . restore registers - 6725 5f/pop-to-edi - 6726 5e/pop-to-esi - 6727 5b/pop-to-ebx - 6728 5a/pop-to-edx - 6729 59/pop-to-ecx - 6730 58/pop-to-eax - 6731 # . reclaim local - 6732 81 0/subop/add %esp 4/imm32 - 6733 # . epilogue - 6734 89/<- %esp 5/r32/ebp - 6735 5d/pop-to-ebp - 6736 c3/return - 6737 - 6738 $parse-mu:error1: - 6739 # error("unexpected top-level command: " word-slice "\n") - 6740 (write-buffered *(ebp+0xc) "unexpected top-level command: ") - 6741 (write-slice-buffered *(ebp+0xc) %edx) - 6742 (write-buffered *(ebp+0xc) "\n") - 6743 (flush *(ebp+0xc)) - 6744 (stop *(ebp+0x10) 1) - 6745 # never gets here - 6746 - 6747 $parse-mu:error2: - 6748 # error(vars->top " vars not reclaimed after fn '" new-function->name "'\n") - 6749 (write-int32-hex-buffered *(ebp+0xc) *ebx) - 6750 (write-buffered *(ebp+0xc) " vars not reclaimed after fn '") - 6751 (write-slice-buffered *(ebp+0xc) *eax) # Function-name - 6752 (write-buffered *(ebp+0xc) "'\n") - 6753 (flush *(ebp+0xc)) - 6754 (stop *(ebp+0x10) 1) - 6755 # never gets here - 6756 - 6757 # scenarios considered: - 6758 # ✗ fn foo # no block - 6759 # ✓ fn foo { - 6760 # ✗ fn foo { { - 6761 # ✗ fn foo { } - 6762 # ✗ fn foo { } { - 6763 # ✗ fn foo x { - 6764 # ✗ fn foo x: { - 6765 # ✓ fn foo x: int { - 6766 # ✓ fn foo x: int { - 6767 # ✓ fn foo x: int -> y/eax: int { - 6768 # TODO: - 6769 # disallow outputs of type `(... addr ...)` - 6770 # disallow inputs of type `(... addr ... addr ...)` - 6771 populate-mu-function-header: # first-line: (addr stream byte), out: (addr function), vars: (addr stack live-var), err: (addr buffered-file), ed: (addr exit-descriptor) - 6772 # pseudocode: - 6773 # var word-slice: slice - 6774 # next-mu-token(first-line, word-slice) - 6775 # assert(word-slice not in '{' '}' '->') - 6776 # out->name = slice-to-string(word-slice) - 6777 # ## inouts - 6778 # while true - 6779 # word-slice = next-mu-token(first-line) - 6780 # if (word-slice == '{') goto done - 6781 # if (word-slice == '->') break - 6782 # assert(word-slice != '}') - 6783 # var v: (handle var) = parse-var-with-type(word-slice, first-line) - 6784 # assert(v->register == null) - 6785 # # v->block-depth is implicitly 0 - 6786 # out->inouts = append(v, out->inouts) - 6787 # push(vars, {v, false}) - 6788 # ## outputs - 6789 # while true - 6790 # word-slice = next-mu-token(first-line) - 6791 # if (word-slice == '{') break - 6792 # assert(word-slice not in '}' '->') - 6793 # var v: (handle var) = parse-var-with-type(word-slice, first-line) - 6794 # assert(v->register != null) - 6795 # out->outputs = append(v, out->outputs) - 6796 # done: - 6797 # - 6798 # . prologue - 6799 55/push-ebp - 6800 89/<- %ebp 4/r32/esp - 6801 # . save registers - 6802 50/push-eax - 6803 51/push-ecx - 6804 52/push-edx - 6805 53/push-ebx - 6806 57/push-edi - 6807 # edi = out - 6808 8b/-> *(ebp+0xc) 7/r32/edi - 6809 # var word-slice/ecx: slice - 6810 68/push 0/imm32/end - 6811 68/push 0/imm32/start - 6812 89/<- %ecx 4/r32/esp - 6813 # var v/ebx: (handle var) - 6814 68/push 0/imm32 - 6815 68/push 0/imm32 - 6816 89/<- %ebx 4/r32/esp - 6817 # read function name - 6818 (next-mu-token *(ebp+8) %ecx) - 6819 # error checking - 6820 # if (word-slice == '{') abort - 6821 (slice-equal? %ecx "{") # => eax - 6822 3d/compare-eax-and 0/imm32/false - 6823 0f 85/jump-if-!= $populate-mu-function-header:error1/disp32 - 6824 # if (word-slice == '->') abort - 6825 (slice-equal? %ecx "->") # => eax - 6826 3d/compare-eax-and 0/imm32/false - 6827 0f 85/jump-if-!= $populate-mu-function-header:error1/disp32 - 6828 # if (word-slice == '}') abort - 6829 (slice-equal? %ecx "}") # => eax - 6830 3d/compare-eax-and 0/imm32/false - 6831 0f 85/jump-if-!= $populate-mu-function-header:error1/disp32 - 6832 # save function name - 6833 (slice-to-string Heap %ecx %edi) # Function-name - 6834 # save function inouts - 6835 { - 6836 $populate-mu-function-header:check-for-inout: - 6837 (next-mu-token *(ebp+8) %ecx) - 6838 # if (word-slice == '{') goto done - 6839 (slice-equal? %ecx "{") # => eax - 6840 3d/compare-eax-and 0/imm32/false - 6841 0f 85/jump-if-!= $populate-mu-function-header:done/disp32 - 6842 # if (word-slice == '->') break - 6843 (slice-equal? %ecx "->") # => eax - 6844 3d/compare-eax-and 0/imm32/false - 6845 0f 85/jump-if-!= break/disp32 - 6846 # if (word-slice == '}') abort - 6847 (slice-equal? %ecx "}") # => eax - 6848 3d/compare-eax-and 0/imm32/false - 6849 0f 85/jump-if-!= $populate-mu-function-header:error1/disp32 - 6850 # v = parse-var-with-type(word-slice, first-line) - 6851 (parse-var-with-type %ecx *(ebp+8) %ebx *(ebp+0x14) *(ebp+0x18)) - 6852 # assert(v->register == null) - 6853 # . eax: (addr var) = lookup(v) - 6854 (lookup *ebx *(ebx+4)) # => eax - 6855 81 7/subop/compare *(eax+0x18) 0/imm32 # Var-register - 6856 0f 85/jump-if-!= $populate-mu-function-header:error2/disp32 - 6857 # v->block-depth is implicitly 0 - 6858 # - 6859 # out->inouts = append(v, out->inouts) - 6860 8d/copy-address *(edi+8) 0/r32/eax # Function-inouts - 6861 (append-list Heap *ebx *(ebx+4) *(edi+8) *(edi+0xc) %eax) # Function-inouts, Function-inouts - 6862 # push(vars, {v, false}) - 6863 (push *(ebp+0x10) *ebx) - 6864 (push *(ebp+0x10) *(ebx+4)) - 6865 (push *(ebp+0x10) 0) # false - 6866 # - 6867 e9/jump loop/disp32 - 6868 } - 6869 # save function outputs - 6870 { - 6871 $populate-mu-function-header:check-for-out: - 6872 (next-mu-token *(ebp+8) %ecx) - 6873 # if (word-slice == '{') break - 6874 (slice-equal? %ecx "{") # => eax - 6875 3d/compare-eax-and 0/imm32/false - 6876 0f 85/jump-if-!= break/disp32 - 6877 # if (word-slice == '->') abort - 6878 (slice-equal? %ecx "->") # => eax - 6879 3d/compare-eax-and 0/imm32/false - 6880 0f 85/jump-if-!= $populate-mu-function-header:error1/disp32 - 6881 # if (word-slice == '}') abort - 6882 (slice-equal? %ecx "}") # => eax - 6883 3d/compare-eax-and 0/imm32/false - 6884 0f 85/jump-if-!= $populate-mu-function-header:error1/disp32 - 6885 # v = parse-var-with-type(word-slice, first-line) - 6886 (parse-var-with-type %ecx *(ebp+8) %ebx *(ebp+0x14) *(ebp+0x18)) - 6887 # assert(var->register != null) - 6888 # . eax: (addr var) = lookup(v) - 6889 (lookup *ebx *(ebx+4)) # => eax - 6890 81 7/subop/compare *(eax+0x18) 0/imm32 # Var-register - 6891 0f 84/jump-if-= $populate-mu-function-header:error3/disp32 - 6892 # out->outputs = append(v, out->outputs) - 6893 8d/copy-address *(edi+0x10) 0/r32/eax # Function-outputs - 6894 (append-list Heap *ebx *(ebx+4) *(edi+0x10) *(edi+0x14) %eax) # Function-outputs, Function-outputs - 6895 # - 6896 e9/jump loop/disp32 - 6897 } - 6898 $populate-mu-function-header:done: - 6899 (check-no-tokens-left *(ebp+8)) - 6900 $populate-mu-function-header:end: - 6901 # . reclaim locals - 6902 81 0/subop/add %esp 0x10/imm32 - 6903 # . restore registers - 6904 5f/pop-to-edi - 6905 5b/pop-to-ebx - 6906 5a/pop-to-edx - 6907 59/pop-to-ecx - 6908 58/pop-to-eax - 6909 # . epilogue - 6910 89/<- %esp 5/r32/ebp - 6911 5d/pop-to-ebp - 6912 c3/return - 6913 - 6914 $populate-mu-function-header:error1: - 6915 # error("function header not in form 'fn <name> {'") - 6916 (write-buffered *(ebp+0x14) "function header not in form 'fn <name> [inouts] [-> outputs] {' -- '") - 6917 (flush *(ebp+0x14)) - 6918 (rewind-stream *(ebp+8)) - 6919 (write-stream-data *(ebp+0x14) *(ebp+8)) - 6920 (write-buffered *(ebp+0x14) "'\n") - 6921 (flush *(ebp+0x14)) - 6922 (stop *(ebp+0x18) 1) - 6923 # never gets here - 6924 - 6925 $populate-mu-function-header:error2: - 6926 # error("fn " fn ": function inout '" var "' cannot be in a register") - 6927 (write-buffered *(ebp+0x14) "fn ") - 6928 50/push-eax - 6929 (lookup *edi *(edi+4)) # Function-name Function-name => eax - 6930 (write-buffered *(ebp+0x14) %eax) - 6931 58/pop-to-eax - 6932 (write-buffered *(ebp+0x14) ": function inout '") - 6933 (lookup *eax *(eax+4)) # Var-name Var-name => eax - 6934 (write-buffered *(ebp+0x10) %eax) - 6935 (write-buffered *(ebp+0x14) "' cannot be in a register") - 6936 (flush *(ebp+0x14)) - 6937 (stop *(ebp+0x18) 1) - 6938 # never gets here - 6939 - 6940 $populate-mu-function-header:error3: - 6941 # error("fn " fn ": function output '" var "' must be in a register") - 6942 (write-buffered *(ebp+0x14) "fn ") - 6943 50/push-eax - 6944 (lookup *edi *(edi+4)) # Function-name Function-name => eax - 6945 (write-buffered *(ebp+0x14) %eax) - 6946 58/pop-to-eax - 6947 (write-buffered *(ebp+0x14) ": function output '") - 6948 (lookup *ebx *(ebx+4)) # => eax - 6949 (lookup *eax *(eax+4)) # Var-name Var-name => eax - 6950 (write-buffered *(ebp+0x14) %eax) - 6951 (write-buffered *(ebp+0x14) "' must be in a register, in instruction '") - 6952 (rewind-stream *(ebp+8)) - 6953 (write-stream-data *(ebp+0x14) *(ebp+8)) - 6954 (write-buffered *(ebp+0x14) "'\n") - 6955 (flush *(ebp+0x14)) - 6956 (stop *(ebp+0x18) 1) - 6957 # never gets here - 6958 - 6959 # scenarios considered: - 6960 # ✓ fn foo - 6961 # ✗ fn foo { - 6962 # ✓ fn foo x - 6963 # ✓ fn foo x: int - 6964 # ✓ fn foo x: int -> y/eax: int - 6965 # TODO: - 6966 # disallow outputs of type `(... addr ...)` - 6967 # disallow inputs of type `(... addr ... addr ...)` - 6968 populate-mu-function-signature: # first-line: (addr stream byte), out: (addr function), err: (addr buffered-file), ed: (addr exit-descriptor) - 6969 # pseudocode: - 6970 # var word-slice: slice - 6971 # next-mu-token(first-line, word-slice) - 6972 # assert(word-slice not in '{' '}' '->') - 6973 # out->name = slice-to-string(word-slice) - 6974 # ## inouts - 6975 # while true - 6976 # word-slice = next-mu-token(first-line) - 6977 # if slice-empty?(word-slice) break - 6978 # if (word-slice == '->') break - 6979 # assert(word-slice not in '{' '}') - 6980 # var v: (handle var) = parse-var-with-type(word-slice, first-line) - 6981 # assert(v->register == null) - 6982 # # v->block-depth is implicitly 0 - 6983 # out->inouts = append(v, out->inouts) - 6984 # ## outputs - 6985 # while true - 6986 # word-slice = next-mu-token(first-line) - 6987 # if slice-empty?(word-slice) break - 6988 # assert(word-slice not in '{' '}' '->') - 6989 # var v: (handle var) = parse-var-with-type(word-slice, first-line) - 6990 # assert(v->register != null) - 6991 # out->outputs = append(v, out->outputs) - 6992 # - 6993 # . prologue - 6994 55/push-ebp - 6995 89/<- %ebp 4/r32/esp - 6996 # . save registers - 6997 50/push-eax - 6998 51/push-ecx - 6999 52/push-edx - 7000 53/push-ebx - 7001 57/push-edi - 7002 # edi = out - 7003 8b/-> *(ebp+0xc) 7/r32/edi - 7004 # var word-slice/ecx: slice - 7005 68/push 0/imm32/end - 7006 68/push 0/imm32/start - 7007 89/<- %ecx 4/r32/esp - 7008 # var v/ebx: (handle var) - 7009 68/push 0/imm32 - 7010 68/push 0/imm32 - 7011 89/<- %ebx 4/r32/esp - 7012 # read function name - 7013 (next-mu-token *(ebp+8) %ecx) - 7014 # error checking - 7015 # if (word-slice == '{') abort - 7016 (slice-equal? %ecx "{") # => eax - 7017 3d/compare-eax-and 0/imm32/false - 7018 0f 85/jump-if-!= $populate-mu-function-signature:error1/disp32 - 7019 # if (word-slice == '->') abort - 7020 (slice-equal? %ecx "->") # => eax - 7021 3d/compare-eax-and 0/imm32/false - 7022 0f 85/jump-if-!= $populate-mu-function-signature:error1/disp32 - 7023 # if (word-slice == '}') abort - 7024 (slice-equal? %ecx "}") # => eax - 7025 3d/compare-eax-and 0/imm32/false - 7026 0f 85/jump-if-!= $populate-mu-function-signature:error1/disp32 - 7027 # save function name - 7028 (slice-to-string Heap %ecx %edi) # Function-name - 7029 # save function inouts - 7030 { - 7031 $populate-mu-function-signature:check-for-inout: - 7032 (next-mu-token *(ebp+8) %ecx) - 7033 (slice-empty? %ecx) # => eax - 7034 3d/compare-eax-and 0/imm32/false - 7035 0f 85/jump-if-!= break/disp32 - 7036 # if (word-slice == '->') break - 7037 (slice-equal? %ecx "->") # => eax - 7038 3d/compare-eax-and 0/imm32/false - 7039 0f 85/jump-if-!= break/disp32 - 7040 # if (word-slice == '{') abort - 7041 (slice-equal? %ecx "{") # => eax - 7042 3d/compare-eax-and 0/imm32/false - 7043 0f 85/jump-if-!= $populate-mu-function-signature:error1/disp32 - 7044 # if (word-slice == '}') abort - 7045 (slice-equal? %ecx "}") # => eax - 7046 3d/compare-eax-and 0/imm32/false - 7047 0f 85/jump-if-!= $populate-mu-function-signature:error1/disp32 - 7048 # v = parse-var-with-type(word-slice, first-line) - 7049 (parse-var-with-type %ecx *(ebp+8) %ebx *(ebp+0x10) *(ebp+0x14)) - 7050 # assert(v->register == null) - 7051 # . eax: (addr var) = lookup(v) - 7052 (lookup *ebx *(ebx+4)) # => eax - 7053 81 7/subop/compare *(eax+0x18) 0/imm32 # Var-register - 7054 0f 85/jump-if-!= $populate-mu-function-signature:error2/disp32 - 7055 # v->block-depth is implicitly 0 - 7056 # - 7057 # out->inouts = append(v, out->inouts) - 7058 8d/copy-address *(edi+8) 0/r32/eax # Function-inouts - 7059 (append-list Heap *ebx *(ebx+4) *(edi+8) *(edi+0xc) %eax) # Function-inouts, Function-inouts - 7060 # - 7061 e9/jump loop/disp32 - 7062 } - 7063 # save function outputs - 7064 { - 7065 $populate-mu-function-signature:check-for-out: - 7066 (next-mu-token *(ebp+8) %ecx) - 7067 (slice-empty? %ecx) # => eax - 7068 3d/compare-eax-and 0/imm32/false - 7069 0f 85/jump-if-!= break/disp32 - 7070 # if (word-slice == '{') abort - 7071 (slice-equal? %ecx "{") # => eax - 7072 3d/compare-eax-and 0/imm32/false - 7073 0f 85/jump-if-!= $populate-mu-function-signature:error1/disp32 - 7074 # if (word-slice == '->') abort - 7075 (slice-equal? %ecx "->") # => eax - 7076 3d/compare-eax-and 0/imm32/false - 7077 0f 85/jump-if-!= $populate-mu-function-signature:error1/disp32 - 7078 # if (word-slice == '}') abort - 7079 (slice-equal? %ecx "}") # => eax - 7080 3d/compare-eax-and 0/imm32/false - 7081 0f 85/jump-if-!= $populate-mu-function-signature:error1/disp32 - 7082 # v = parse-var-with-type(word-slice, first-line) - 7083 (parse-var-with-type %ecx *(ebp+8) %ebx *(ebp+0x10) *(ebp+0x14)) - 7084 # assert(var->register != null) - 7085 # . eax: (addr var) = lookup(v) - 7086 (lookup *ebx *(ebx+4)) # => eax - 7087 81 7/subop/compare *(eax+0x18) 0/imm32 # Var-register - 7088 0f 84/jump-if-= $populate-mu-function-signature:error3/disp32 - 7089 # out->outputs = append(v, out->outputs) - 7090 8d/copy-address *(edi+0x10) 0/r32/eax # Function-outputs - 7091 (append-list Heap *ebx *(ebx+4) *(edi+0x10) *(edi+0x14) %eax) # Function-outputs, Function-outputs - 7092 # - 7093 e9/jump loop/disp32 - 7094 } - 7095 $populate-mu-function-signature:done: - 7096 (check-no-tokens-left *(ebp+8)) - 7097 $populate-mu-function-signature:end: - 7098 # . reclaim locals - 7099 81 0/subop/add %esp 0x10/imm32 - 7100 # . restore registers - 7101 5f/pop-to-edi - 7102 5b/pop-to-ebx - 7103 5a/pop-to-edx - 7104 59/pop-to-ecx - 7105 58/pop-to-eax - 7106 # . epilogue - 7107 89/<- %esp 5/r32/ebp - 7108 5d/pop-to-ebp - 7109 c3/return - 7110 - 7111 $populate-mu-function-signature:error1: - 7112 # error("function signature not in form 'fn <name> {'") - 7113 (write-buffered *(ebp+0x10) "function signature not in form 'fn <name> [inouts] [-> outputs] {' -- '") - 7114 (flush *(ebp+0x10)) - 7115 (rewind-stream *(ebp+8)) - 7116 (write-stream-data *(ebp+0x10) *(ebp+8)) - 7117 (write-buffered *(ebp+0x10) "'\n") - 7118 (flush *(ebp+0x10)) - 7119 (stop *(ebp+0x14) 1) - 7120 # never gets here - 7121 - 7122 $populate-mu-function-signature:error2: - 7123 # error("fn " fn ": function inout '" var "' cannot be in a register") - 7124 (write-buffered *(ebp+0x10) "fn ") - 7125 50/push-eax - 7126 (lookup *edi *(edi+4)) # Function-name Function-name => eax - 7127 (write-buffered *(ebp+0x10) %eax) - 7128 58/pop-to-eax - 7129 (write-buffered *(ebp+0x10) ": function inout '") - 7130 (lookup *eax *(eax+4)) # Var-name Var-name => eax - 7131 (write-buffered *(ebp+0x10) %eax) - 7132 (write-buffered *(ebp+0x10) "' cannot be in a register") - 7133 (flush *(ebp+0x10)) - 7134 (stop *(ebp+0x14) 1) - 7135 # never gets here - 7136 - 7137 $populate-mu-function-signature:error3: - 7138 # error("fn " fn ": function output '" var "' must be in a register") - 7139 (write-buffered *(ebp+0x10) "fn ") - 7140 50/push-eax - 7141 (lookup *edi *(edi+4)) # Function-name Function-name => eax - 7142 (write-buffered *(ebp+0x10) %eax) - 7143 58/pop-to-eax - 7144 (write-buffered *(ebp+0x10) ": function output '") - 7145 (lookup *ebx *(ebx+4)) # => eax - 7146 (lookup *eax *(eax+4)) # Var-name Var-name => eax - 7147 (write-buffered *(ebp+0x10) %eax) - 7148 (write-buffered *(ebp+0x10) "' must be in a register, in instruction '") - 7149 (rewind-stream *(ebp+8)) - 7150 (write-stream-data *(ebp+0x10) *(ebp+8)) - 7151 (write-buffered *(ebp+0x10) "'\n") - 7152 (flush *(ebp+0x10)) - 7153 (stop *(ebp+0x14) 1) - 7154 # never gets here - 7155 - 7156 test-function-header-with-arg: - 7157 # . prologue - 7158 55/push-ebp - 7159 89/<- %ebp 4/r32/esp - 7160 # setup - 7161 (clear-stream _test-input-stream) - 7162 (write _test-input-stream "foo n: int {\n") - 7163 # var result/ecx: function - 7164 2b/subtract *Function-size 4/r32/esp - 7165 89/<- %ecx 4/r32/esp - 7166 (zero-out %ecx *Function-size) - 7167 # var vars/ebx: (stack live-var 16) - 7168 81 5/subop/subtract %esp 0xc0/imm32 - 7169 68/push 0xc0/imm32/size - 7170 68/push 0/imm32/top - 7171 89/<- %ebx 4/r32/esp - 7172 # convert - 7173 (populate-mu-function-header _test-input-stream %ecx %ebx Stderr 0) - 7174 # check result->name - 7175 (lookup *ecx *(ecx+4)) # Function-name Function-name => eax - 7176 (check-strings-equal %eax "foo" "F - test-function-header-with-arg/name") - 7177 # var v/edx: (addr var) = result->inouts->value - 7178 (lookup *(ecx+8) *(ecx+0xc)) # Function-inouts Function-inouts => eax - 7179 (lookup *eax *(eax+4)) # List-value List-value => eax - 7180 89/<- %edx 0/r32/eax - 7181 # check v->name - 7182 (lookup *edx *(edx+4)) # Var-name Var-name => eax - 7183 (check-strings-equal %eax "n" "F - test-function-header-with-arg/inout:0") - 7184 # check v->type - 7185 (lookup *(edx+8) *(edx+0xc)) # Var-type Var-type => eax - 7186 (check-ints-equal *eax 1 "F - test-function-header-with-arg/inout:0/type:0") # Type-tree-is-atom - 7187 (check-ints-equal *(eax+4) 1 "F - test-function-header-with-arg/inout:0/type:1") # Type-tree-value - 7188 (check-ints-equal *(eax+0xc) 0 "F - test-function-header-with-arg/inout:0/type:2") # Type-tree-right - 7189 # . epilogue - 7190 89/<- %esp 5/r32/ebp - 7191 5d/pop-to-ebp - 7192 c3/return - 7193 - 7194 test-function-header-with-multiple-args: - 7195 # . prologue - 7196 55/push-ebp - 7197 89/<- %ebp 4/r32/esp - 7198 # setup - 7199 (clear-stream _test-input-stream) - 7200 (write _test-input-stream "foo a: int, b: int c: int {\n") - 7201 # result/ecx: function - 7202 2b/subtract *Function-size 4/r32/esp - 7203 89/<- %ecx 4/r32/esp - 7204 (zero-out %ecx *Function-size) - 7205 # var vars/ebx: (stack live-var 16) - 7206 81 5/subop/subtract %esp 0xc0/imm32 - 7207 68/push 0xc0/imm32/size - 7208 68/push 0/imm32/top - 7209 89/<- %ebx 4/r32/esp - 7210 # convert - 7211 (populate-mu-function-header _test-input-stream %ecx %ebx Stderr 0) - 7212 # check result->name - 7213 (lookup *ecx *(ecx+4)) # Function-name Function-name => eax - 7214 (check-strings-equal %eax "foo" "F - test-function-header-with-multiple-args/name") - 7215 # var inouts/edx: (addr list var) = lookup(result->inouts) - 7216 (lookup *(ecx+8) *(ecx+0xc)) # Function-inouts Function-inouts => eax - 7217 89/<- %edx 0/r32/eax - 7218 $test-function-header-with-multiple-args:inout0: - 7219 # var v/ebx: (addr var) = lookup(inouts->value) - 7220 (lookup *edx *(edx+4)) # List-value List-value => eax - 7221 89/<- %ebx 0/r32/eax - 7222 # check v->name - 7223 (lookup *ebx *(ebx+4)) # Var-name Var-name => eax - 7224 (check-strings-equal %eax "a" "F - test-function-header-with-multiple-args/inout:0") # Var-name - 7225 # check v->type - 7226 (lookup *(ebx+8) *(ebx+0xc)) # Var-type Var-type => eax - 7227 (check-ints-equal *eax 1 "F - test-function-header-with-multiple-args/inout:0/type:0") # Type-tree-is-atom - 7228 (check-ints-equal *(eax+4) 1 "F - test-function-header-with-multiple-args/inout:0/type:1") # Type-tree-value - 7229 (check-ints-equal *(eax+0xc) 0 "F - test-function-header-with-multiple-args/inout:0/type:2") # Type-tree-right - 7230 $test-function-header-with-multiple-args:inout1: - 7231 # inouts = lookup(inouts->next) - 7232 (lookup *(edx+8) *(edx+0xc)) # List-next List-next => eax - 7233 89/<- %edx 0/r32/eax - 7234 # v = lookup(inouts->value) - 7235 (lookup *edx *(edx+4)) # List-value List-value => eax - 7236 89/<- %ebx 0/r32/eax - 7237 # check v->name - 7238 (lookup *ebx *(ebx+4)) # Var-name Var-name => eax - 7239 (check-strings-equal %eax "b" "F - test-function-header-with-multiple-args/inout:1") # Var-name - 7240 # check v->type - 7241 (lookup *(ebx+8) *(ebx+0xc)) # Var-type Var-type => eax - 7242 (check-ints-equal *eax 1 "F - test-function-header-with-multiple-args/inout:1/type:0") # Type-tree-is-atom - 7243 (check-ints-equal *(eax+4) 1 "F - test-function-header-with-multiple-args/inout:1/type:1") # Type-tree-value - 7244 (check-ints-equal *(eax+0xc) 0 "F - test-function-header-with-multiple-args/inout:1/type:2") # Type-tree-right - 7245 $test-function-header-with-multiple-args:inout2: - 7246 # inouts = lookup(inouts->next) - 7247 (lookup *(edx+8) *(edx+0xc)) # List-next List-next => eax - 7248 89/<- %edx 0/r32/eax - 7249 # v = lookup(inouts->value) - 7250 (lookup *edx *(edx+4)) # List-value List-value => eax - 7251 89/<- %ebx 0/r32/eax - 7252 # check v->name - 7253 (lookup *ebx *(ebx+4)) # Var-name Var-name => eax - 7254 (check-strings-equal %eax "c" "F - test-function-header-with-multiple-args/inout:2") # Var-name - 7255 # check v->type - 7256 (lookup *(ebx+8) *(ebx+0xc)) # Var-type Var-type => eax - 7257 (check-ints-equal *eax 1 "F - test-function-header-with-multiple-args/inout:2/type:0") # Type-tree-is-atom - 7258 (check-ints-equal *(eax+4) 1 "F - test-function-header-with-multiple-args/inout:2/type:1") # Type-tree-value - 7259 (check-ints-equal *(eax+0xc) 0 "F - test-function-header-with-multiple-args/inout:2/type:2") # Type-tree-right - 7260 # . epilogue - 7261 89/<- %esp 5/r32/ebp - 7262 5d/pop-to-ebp - 7263 c3/return - 7264 - 7265 test-function-header-with-multiple-args-and-outputs: - 7266 # . prologue - 7267 55/push-ebp - 7268 89/<- %ebp 4/r32/esp - 7269 # setup - 7270 (clear-stream _test-input-stream) - 7271 (write _test-input-stream "foo a: int, b: int, c: int -> x/ecx: int y/edx: int {\n") - 7272 # result/ecx: function - 7273 2b/subtract *Function-size 4/r32/esp - 7274 89/<- %ecx 4/r32/esp - 7275 (zero-out %ecx *Function-size) - 7276 # var vars/ebx: (stack live-var 16) - 7277 81 5/subop/subtract %esp 0xc0/imm32 - 7278 68/push 0xc0/imm32/size - 7279 68/push 0/imm32/top - 7280 89/<- %ebx 4/r32/esp - 7281 # convert - 7282 (populate-mu-function-header _test-input-stream %ecx %ebx Stderr 0) - 7283 # check result->name - 7284 (lookup *ecx *(ecx+4)) # Function-name Function-name => eax - 7285 (check-strings-equal %eax "foo" "F - test-function-header-with-multiple-args-and-outputs/name") - 7286 # var inouts/edx: (addr list var) = lookup(result->inouts) - 7287 (lookup *(ecx+8) *(ecx+0xc)) # Function-inouts Function-inouts => eax - 7288 89/<- %edx 0/r32/eax - 7289 $test-function-header-with-multiple-args-and-outputs:inout0: - 7290 # var v/ebx: (addr var) = lookup(inouts->value) - 7291 (lookup *edx *(edx+4)) # List-value List-value => eax - 7292 89/<- %ebx 0/r32/eax - 7293 # check v->name - 7294 (lookup *ebx *(ebx+4)) # Var-name Var-name => eax - 7295 (check-strings-equal %eax "a" "F - test-function-header-with-multiple-args-and-outputs/inout:0") - 7296 # check v->type - 7297 (lookup *(ebx+8) *(ebx+0xc)) # Var-type Var-type => eax - 7298 (check-ints-equal *eax 1 "F - test-function-header-with-multiple-args-and-outputs/inout:0/type:0") # Type-tree-is-atom - 7299 (check-ints-equal *(eax+4) 1 "F - test-function-header-with-multiple-args-and-outputs/inout:0/type:1") # Type-tree-value - 7300 (check-ints-equal *(eax+0xc) 0 "F - test-function-header-with-multiple-args-and-outputs/inout:0/type:2") # Type-tree-right - 7301 $test-function-header-with-multiple-args-and-outputs:inout1: - 7302 # inouts = lookup(inouts->next) - 7303 (lookup *(edx+8) *(edx+0xc)) # List-next List-next => eax - 7304 89/<- %edx 0/r32/eax - 7305 # v = lookup(inouts->value) - 7306 (lookup *edx *(edx+4)) # List-value List-value => eax - 7307 89/<- %ebx 0/r32/eax - 7308 # check v->name - 7309 (lookup *ebx *(ebx+4)) # Var-name Var-name => eax - 7310 (check-strings-equal %eax "b" "F - test-function-header-with-multiple-args-and-outputs/inout:1") - 7311 # check v->type - 7312 (lookup *(ebx+8) *(ebx+0xc)) # Var-type Var-type => eax - 7313 (check-ints-equal *eax 1 "F - test-function-header-with-multiple-args-and-outputs/inout:1/type:0") # Type-tree-is-atom - 7314 (check-ints-equal *(eax+4) 1 "F - test-function-header-with-multiple-args-and-outputs/inout:1/type:1") # Type-tree-value - 7315 (check-ints-equal *(eax+0xc) 0 "F - test-function-header-with-multiple-args-and-outputs/inout:1/type:2") # Type-tree-right - 7316 $test-function-header-with-multiple-args-and-outputs:inout2: - 7317 # inouts = lookup(inouts->next) - 7318 (lookup *(edx+8) *(edx+0xc)) # List-next List-next => eax - 7319 89/<- %edx 0/r32/eax - 7320 # v = lookup(inouts->value) - 7321 (lookup *edx *(edx+4)) # List-value List-value => eax - 7322 89/<- %ebx 0/r32/eax - 7323 # check v->name - 7324 (lookup *ebx *(ebx+4)) # Var-name Var-name => eax - 7325 (check-strings-equal %eax "c" "F - test-function-header-with-multiple-args-and-outputs/inout:2") - 7326 # check v->type - 7327 (lookup *(ebx+8) *(ebx+0xc)) # Var-type Var-type => eax - 7328 (check-ints-equal *eax 1 "F - test-function-header-with-multiple-args-and-outputs/inout:2/type:0") # Type-tree-is-atom - 7329 (check-ints-equal *(eax+4) 1 "F - test-function-header-with-multiple-args-and-outputs/inout:2/type:1") # Type-tree-value - 7330 (check-ints-equal *(eax+0xc) 0 "F - test-function-header-with-multiple-args-and-outputs/inout:2/type:2") # Type-tree-right - 7331 $test-function-header-with-multiple-args-and-outputs:out0: - 7332 # var outputs/edx: (addr list var) = lookup(result->outputs) - 7333 (lookup *(ecx+0x10) *(ecx+0x14)) # Function-outputs Function-outputs => eax - 7334 89/<- %edx 0/r32/eax - 7335 # v = lookup(outputs->value) - 7336 (lookup *edx *(edx+4)) # List-value List-value => eax - 7337 89/<- %ebx 0/r32/eax - 7338 # check v->name - 7339 (lookup *ebx *(ebx+4)) # Var-name Var-name => eax - 7340 (check-strings-equal %eax "x" "F - test-function-header-with-multiple-args-and-outputs/output:0") - 7341 # check v->register - 7342 (lookup *(ebx+0x18) *(ebx+0x1c)) # Var-register Var-register => eax - 7343 (check-strings-equal %eax "ecx" "F - test-function-header-with-multiple-args-and-outputs/output:0/register") - 7344 # check v->type - 7345 (lookup *(ebx+8) *(ebx+0xc)) # Var-type Var-type => eax - 7346 (check-ints-equal *eax 1 "F - test-function-header-with-multiple-args-and-outputs/output:0/type:0") # Type-tree-is-atom - 7347 (check-ints-equal *(eax+4) 1 "F - test-function-header-with-multiple-args-and-outputs/output:0/type:1") # Type-tree-value - 7348 (check-ints-equal *(eax+0xc) 0 "F - test-function-header-with-multiple-args-and-outputs/output:0/type:2") # Type-tree-right - 7349 $test-function-header-with-multiple-args-and-outputs:out1: - 7350 # outputs = lookup(outputs->next) - 7351 (lookup *(edx+8) *(edx+0xc)) # List-next List-next => eax - 7352 89/<- %edx 0/r32/eax - 7353 # v = lookup(inouts->value) - 7354 (lookup *edx *(edx+4)) # List-value List-value => eax - 7355 89/<- %ebx 0/r32/eax - 7356 # check v->name - 7357 (lookup *ebx *(ebx+4)) # Var-name Var-name => eax - 7358 (check-strings-equal %eax "y" "F - test-function-header-with-multiple-args-and-outputs/output:1") - 7359 # check v->register - 7360 (lookup *(ebx+0x18) *(ebx+0x1c)) # Var-register Var-register => eax - 7361 (check-strings-equal %eax "edx" "F - test-function-header-with-multiple-args-and-outputs/output:1/register") - 7362 # check v->type - 7363 (lookup *(ebx+8) *(ebx+0xc)) # Var-type Var-type => eax - 7364 (check-ints-equal *eax 1 "F - test-function-header-with-multiple-args-and-outputs/output:1/type:0") # Type-tree-is-atom - 7365 (check-ints-equal *(eax+4) 1 "F - test-function-header-with-multiple-args-and-outputs/output:1/type:1") # Type-tree-value - 7366 (check-ints-equal *(eax+0c) 0 "F - test-function-header-with-multiple-args-and-outputs/output:1/type:2") # Type-tree-right - 7367 # . epilogue - 7368 89/<- %esp 5/r32/ebp - 7369 5d/pop-to-ebp - 7370 c3/return - 7371 - 7372 # format for variables with types - 7373 # x: int - 7374 # x: int, - 7375 # x/eax: int - 7376 # x/eax: int, - 7377 # ignores at most one trailing comma - 7378 # WARNING: modifies name - 7379 parse-var-with-type: # name: (addr slice), first-line: (addr stream byte), out: (addr handle var), err: (addr buffered-file), ed: (addr exit-descriptor) - 7380 # pseudocode: - 7381 # var s: slice - 7382 # if (!slice-ends-with(name, ":")) - 7383 # abort - 7384 # --name->end to skip ':' - 7385 # next-token-from-slice(name->start, name->end, '/', s) - 7386 # new-var-from-slice(s, out) - 7387 # ## register - 7388 # next-token-from-slice(s->end, name->end, '/', s) - 7389 # if (!slice-empty?(s)) - 7390 # out->register = slice-to-string(s) - 7391 # ## type - 7392 # var type: (handle type-tree) = parse-type(first-line) - 7393 # out->type = type - 7394 # - 7395 # . prologue - 7396 55/push-ebp - 7397 89/<- %ebp 4/r32/esp - 7398 # . save registers - 7399 50/push-eax - 7400 51/push-ecx - 7401 52/push-edx - 7402 53/push-ebx - 7403 56/push-esi - 7404 57/push-edi - 7405 # esi = name - 7406 8b/-> *(ebp+8) 6/r32/esi - 7407 # if (!slice-ends-with?(name, ":")) abort - 7408 8b/-> *(esi+4) 1/r32/ecx # Slice-end - 7409 49/decrement-ecx - 7410 8a/copy-byte *ecx 1/r32/CL - 7411 81 4/subop/and %ecx 0xff/imm32 - 7412 81 7/subop/compare %ecx 0x3a/imm32/colon - 7413 0f 85/jump-if-!= $parse-var-with-type:abort/disp32 - 7414 # --name->end to skip ':' - 7415 ff 1/subop/decrement *(esi+4) - 7416 # var s/ecx: slice - 7417 68/push 0/imm32/end - 7418 68/push 0/imm32/start - 7419 89/<- %ecx 4/r32/esp - 7420 $parse-var-with-type:parse-name: - 7421 (next-token-from-slice *esi *(esi+4) 0x2f %ecx) # Slice-start, Slice-end, '/' - 7422 $parse-var-with-type:create-var: - 7423 # new-var-from-slice(s, out) - 7424 (new-var-from-slice Heap %ecx *(ebp+0x10)) - 7425 # save out->register - 7426 $parse-var-with-type:save-register: - 7427 # . var out-addr/edi: (addr var) = lookup(*out) - 7428 8b/-> *(ebp+0x10) 7/r32/edi - 7429 (lookup *edi *(edi+4)) # => eax - 7430 89/<- %edi 0/r32/eax - 7431 # . s = next-token(...) - 7432 (next-token-from-slice *(ecx+4) *(esi+4) 0x2f %ecx) # s->end, name->end, '/' - 7433 # . if (!slice-empty?(s)) out->register = slice-to-string(s) - 7434 { - 7435 $parse-var-with-type:write-register: - 7436 (slice-empty? %ecx) # => eax - 7437 3d/compare-eax-and 0/imm32/false - 7438 75/jump-if-!= break/disp8 - 7439 # out->register = slice-to-string(s) - 7440 8d/copy-address *(edi+0x18) 0/r32/eax # Var-register - 7441 (slice-to-string Heap %ecx %eax) - 7442 } - 7443 $parse-var-with-type:save-type: - 7444 8d/copy-address *(edi+8) 0/r32/eax # Var-type - 7445 (parse-type Heap *(ebp+0xc) %eax *(ebp+0x14) *(ebp+0x18)) - 7446 $parse-var-with-type:end: - 7447 # . reclaim locals - 7448 81 0/subop/add %esp 8/imm32 - 7449 # . restore registers - 7450 5f/pop-to-edi - 7451 5e/pop-to-esi - 7452 5b/pop-to-ebx - 7453 5a/pop-to-edx - 7454 59/pop-to-ecx - 7455 58/pop-to-eax - 7456 # . epilogue - 7457 89/<- %esp 5/r32/ebp - 7458 5d/pop-to-ebp - 7459 c3/return - 7460 - 7461 $parse-var-with-type:abort: - 7462 # error("var should have form 'name: type' in '" line "'\n") - 7463 (write-buffered *(ebp+0x14) "var should have form 'name: type' in '") - 7464 (flush *(ebp+0x14)) - 7465 (rewind-stream *(ebp+0xc)) - 7466 (write-stream-data *(ebp+0x14) *(ebp+0xc)) - 7467 (write-buffered *(ebp+0x14) "'\n") - 7468 (flush *(ebp+0x14)) - 7469 (stop *(ebp+0x18) 1) - 7470 # never gets here - 7471 - 7472 parse-type: # ad: (addr allocation-descriptor), in: (addr stream byte), out: (addr handle type-tree), err: (addr buffered-file), ed: (addr exit-descriptor) - 7473 # pseudocode: - 7474 # var s: slice = next-mu-token(in) - 7475 # assert s != "" - 7476 # assert s != "->" - 7477 # assert s != "{" - 7478 # assert s != "}" - 7479 # if s == ")" - 7480 # return - 7481 # out = allocate(Type-tree) - 7482 # if s != "(" - 7483 # HACK: if s is an int, parse and return it - 7484 # out->is-atom? = true - 7485 # if (s[0] == "_") - 7486 # out->value = type-parameter - 7487 # out->parameter-name = slice-to-string(ad, s) - 7488 # else - 7489 # out->value = pos-or-insert-slice(Type-id, s) - 7490 # return - 7491 # out->left = parse-type(ad, in) - 7492 # out->right = parse-type-tree(ad, in) - 7493 # - 7494 # . prologue - 7495 55/push-ebp - 7496 89/<- %ebp 4/r32/esp - 7497 # . save registers - 7498 50/push-eax - 7499 51/push-ecx - 7500 52/push-edx - 7501 # clear out - 7502 (zero-out *(ebp+0x10) *Handle-size) - 7503 # var s/ecx: slice - 7504 68/push 0/imm32 - 7505 68/push 0/imm32 - 7506 89/<- %ecx 4/r32/esp - 7507 # s = next-mu-token(in) - 7508 (next-mu-token *(ebp+0xc) %ecx) - 7509 #? (write-buffered Stderr "tok: ") - 7510 #? (write-slice-buffered Stderr %ecx) - 7511 #? (write-buffered Stderr "$\n") - 7512 #? (flush Stderr) - 7513 # assert s != "" - 7514 (slice-equal? %ecx "") # => eax - 7515 3d/compare-eax-and 0/imm32/false - 7516 0f 85/jump-if-!= $parse-type:abort/disp32 - 7517 # assert s != "{" - 7518 (slice-equal? %ecx "{") # => eax - 7519 3d/compare-eax-and 0/imm32/false - 7520 0f 85/jump-if-!= $parse-type:abort/disp32 - 7521 # assert s != "}" - 7522 (slice-equal? %ecx "}") # => eax - 7523 3d/compare-eax-and 0/imm32/false - 7524 0f 85/jump-if-!= $parse-type:abort/disp32 - 7525 # assert s != "->" - 7526 (slice-equal? %ecx "->") # => eax - 7527 3d/compare-eax-and 0/imm32/false - 7528 0f 85/jump-if-!= $parse-type:abort/disp32 - 7529 # if (s == ")") return - 7530 (slice-equal? %ecx ")") # => eax - 7531 3d/compare-eax-and 0/imm32/false - 7532 0f 85/jump-if-!= $parse-type:end/disp32 - 7533 # out = new tree - 7534 (allocate *(ebp+8) *Type-tree-size *(ebp+0x10)) - 7535 # var out-addr/edx: (addr type-tree) = lookup(*out) - 7536 8b/-> *(ebp+0x10) 2/r32/edx - 7537 (lookup *edx *(edx+4)) # => eax - 7538 89/<- %edx 0/r32/eax - 7539 { - 7540 # if (s != "(") break - 7541 (slice-equal? %ecx "(") # => eax - 7542 3d/compare-eax-and 0/imm32/false - 7543 0f 85/jump-if-!= break/disp32 - 7544 # if s is a number, store it in the type's size field - 7545 { - 7546 $parse-type:check-for-int: - 7547 # var tmp/eax: byte = *s->slice - 7548 8b/-> *ecx 0/r32/eax - 7549 8a/copy-byte *eax 0/r32/AL - 7550 81 4/subop/and %eax 0xff/imm32 - 7551 # TODO: raise an error on `var x: (array int a)` - 7552 (is-decimal-digit? %eax) # => eax - 7553 3d/compare-eax-and 0/imm32/false - 7554 74/jump-if-= break/disp8 - 7555 # - 7556 (is-hex-int? %ecx) # => eax - 7557 3d/compare-eax-and 0/imm32/false - 7558 74/jump-if-= break/disp8 - 7559 $parse-type:int: - 7560 (check-mu-hex-int %ecx *(ebp+0x14) *(ebp+0x18)) - 7561 (parse-hex-int-from-slice %ecx) # => eax - 7562 c7 0/subop/copy *(edx+4) 9/imm32/type-id-array-capacity # Type-tree-value - 7563 89/<- *(edx+8) 0/r32/eax # Type-tree-value-size - 7564 e9/jump $parse-type:end/disp32 - 7565 } - 7566 $parse-type:atom: - 7567 # out->is-atom? = true - 7568 c7 0/subop/copy *edx 1/imm32/true # Type-tree-is-atom - 7569 { - 7570 $parse-type:check-for-type-parameter: - 7571 # var tmp/eax: byte = *s->slice - 7572 8b/-> *ecx 0/r32/eax - 7573 8a/copy-byte *eax 0/r32/AL - 7574 81 4/subop/and %eax 0xff/imm32 - 7575 # if (tmp != '_') break - 7576 3d/compare-eax-and 0x5f/imm32/_ - 7577 75/jump-if-!= break/disp8 - 7578 $parse-type:type-parameter: - 7579 # out->value = type-parameter - 7580 c7 0/subop/copy *(edx+4) 0xa/imm32/type-parameter # Type-tree-value - 7581 # out->parameter-name = slice-to-string(ad, s) - 7582 8d/copy-address *(edx+8) 0/r32/eax # Type-tree-parameter-name - 7583 (slice-to-string *(ebp+8) %ecx %eax) - 7584 e9/jump $parse-type:end/disp32 - 7585 } - 7586 $parse-type:non-type-parameter: - 7587 # out->value = pos-or-insert-slice(Type-id, s) - 7588 (pos-or-insert-slice Type-id %ecx) # => eax - 7589 89/<- *(edx+4) 0/r32/eax # Type-tree-value - 7590 e9/jump $parse-type:end/disp32 - 7591 } - 7592 $parse-type:non-atom: - 7593 # otherwise s == "(" - 7594 # out->left = parse-type(ad, in) - 7595 8d/copy-address *(edx+4) 0/r32/eax # Type-tree-left - 7596 (parse-type *(ebp+8) *(ebp+0xc) %eax *(ebp+0x14) *(ebp+0x18)) - 7597 # out->right = parse-type-tree(ad, in) - 7598 8d/copy-address *(edx+0xc) 0/r32/eax # Type-tree-right - 7599 (parse-type-tree *(ebp+8) *(ebp+0xc) %eax *(ebp+0x14) *(ebp+0x18)) - 7600 $parse-type:end: - 7601 # . reclaim locals - 7602 81 0/subop/add %esp 8/imm32 - 7603 # . restore registers - 7604 5a/pop-to-edx - 7605 59/pop-to-ecx - 7606 58/pop-to-eax - 7607 # . epilogue - 7608 89/<- %esp 5/r32/ebp - 7609 5d/pop-to-ebp - 7610 c3/return - 7611 - 7612 $parse-type:abort: - 7613 # error("unexpected token when parsing type: '" s "'\n") - 7614 (write-buffered *(ebp+0x14) "unexpected token when parsing type: '") - 7615 (write-slice-buffered *(ebp+0x14) %ecx) - 7616 (write-buffered *(ebp+0x14) "'\n") - 7617 (flush *(ebp+0x14)) - 7618 (stop *(ebp+0x18) 1) - 7619 # never gets here - 7620 - 7621 parse-type-tree: # ad: (addr allocation-descriptor), in: (addr stream byte), out: (addr handle type-tree), err: (addr buffered-file), ed: (addr exit-descriptor) - 7622 # pseudocode: - 7623 # var tmp: (handle type-tree) = parse-type(ad, in) - 7624 # if tmp == 0 - 7625 # return 0 - 7626 # out = allocate(Type-tree) - 7627 # out->left = tmp - 7628 # out->right = parse-type-tree(ad, in) - 7629 # - 7630 # . prologue - 7631 55/push-ebp - 7632 89/<- %ebp 4/r32/esp - 7633 # . save registers - 7634 50/push-eax - 7635 51/push-ecx - 7636 52/push-edx - 7637 # - 7638 (zero-out *(ebp+0x10) *Handle-size) - 7639 # var tmp/ecx: (handle type-tree) - 7640 68/push 0/imm32 - 7641 68/push 0/imm32 - 7642 89/<- %ecx 4/r32/esp - 7643 # tmp = parse-type(ad, in) - 7644 (parse-type *(ebp+8) *(ebp+0xc) %ecx *(ebp+0x14) *(ebp+0x18)) - 7645 # if (tmp == 0) return - 7646 81 7/subop/compare *ecx 0/imm32 - 7647 74/jump-if-= $parse-type-tree:end/disp8 - 7648 # out = new tree - 7649 (allocate *(ebp+8) *Type-tree-size *(ebp+0x10)) - 7650 # var out-addr/edx: (addr tree) = lookup(*out) - 7651 8b/-> *(ebp+0x10) 2/r32/edx - 7652 (lookup *edx *(edx+4)) # => eax - 7653 89/<- %edx 0/r32/eax - 7654 # out->left = tmp - 7655 8b/-> *ecx 0/r32/eax - 7656 89/<- *(edx+4) 0/r32/eax # Type-tree-left - 7657 8b/-> *(ecx+4) 0/r32/eax - 7658 89/<- *(edx+8) 0/r32/eax # Type-tree-left - 7659 # out->right = parse-type-tree(ad, in) - 7660 8d/copy-address *(edx+0xc) 0/r32/eax # Type-tree-right - 7661 (parse-type-tree *(ebp+8) *(ebp+0xc) %eax *(ebp+0x14) *(ebp+0x18)) - 7662 $parse-type-tree:end: - 7663 # . reclaim locals - 7664 81 0/subop/add %esp 8/imm32 - 7665 # . restore registers - 7666 5a/pop-to-edx - 7667 59/pop-to-ecx - 7668 58/pop-to-eax - 7669 # . epilogue - 7670 89/<- %esp 5/r32/ebp - 7671 5d/pop-to-ebp - 7672 c3/return - 7673 - 7674 next-mu-token: # in: (addr stream byte), out: (addr slice) - 7675 # pseudocode: - 7676 # start: - 7677 # skip-chars-matching-whitespace(in) - 7678 # if in->read >= in->write # end of in - 7679 # out = {0, 0} - 7680 # return - 7681 # out->start = &in->data[in->read] - 7682 # var curr-byte/eax: byte = in->data[in->read] - 7683 # if curr->byte == ',' # comment token - 7684 # ++in->read - 7685 # goto start - 7686 # if curr-byte == '#' # comment - 7687 # goto done # treat as eof - 7688 # if curr-byte == '"' # string literal - 7689 # skip-string(in) - 7690 # goto done # no metadata - 7691 # if curr-byte == '(' - 7692 # ++in->read - 7693 # goto done - 7694 # if curr-byte == ')' + 6520 Curr-block-depth: # (addr int) + 6521 1/imm32 + 6522 + 6523 == code + 6524 + 6525 parse-mu: # in: (addr buffered-file), err: (addr buffered-file), ed: (addr exit-descriptor) + 6526 # pseudocode + 6527 # var curr-function: (addr handle function) = Program->functions + 6528 # var curr-signature: (addr handle function) = Program->signatures + 6529 # var curr-type: (addr handle typeinfo) = Program->types + 6530 # var line: (stream byte 512) + 6531 # var word-slice: slice + 6532 # while true # line loop + 6533 # clear-stream(line) + 6534 # read-line-buffered(in, line) + 6535 # if (line->write == 0) break # end of file + 6536 # word-slice = next-mu-token(line) + 6537 # if slice-empty?(word-slice) # end of line + 6538 # continue + 6539 # else if slice-starts-with?(word-slice, "#") # comment + 6540 # continue # end of line + 6541 # else if slice-equal?(word-slice, "fn") + 6542 # var new-function: (handle function) = allocate(function) + 6543 # var vars: (stack live-var 256) + 6544 # populate-mu-function-header(line, new-function, vars) + 6545 # populate-mu-function-body(in, new-function, vars) + 6546 # assert(vars->top == 0) + 6547 # *curr-function = new-function + 6548 # curr-function = &new-function->next + 6549 # else if slice-equal?(word-slice, "sig") + 6550 # var new-function: (handle function) = allocate(function) + 6551 # populate-mu-function-signature(line, new-function) + 6552 # *curr-signature = new-function + 6553 # curr-signature = &new-function->next + 6554 # else if slice-equal?(word-slice, "type") + 6555 # word-slice = next-mu-token(line) + 6556 # type-id = pos-or-insert-slice(Type-id, word-slice) + 6557 # var new-type: (handle typeinfo) = find-or-create-typeinfo(type-id) + 6558 # assert(next-word(line) == "{") + 6559 # populate-mu-type(in, new-type) + 6560 # else + 6561 # abort() + 6562 # + 6563 # . prologue + 6564 55/push-ebp + 6565 89/<- %ebp 4/r32/esp + 6566 # var curr-signature: (addr handle function) at *(ebp-4) + 6567 68/push _Program-signatures/imm32 + 6568 # . save registers + 6569 50/push-eax + 6570 51/push-ecx + 6571 52/push-edx + 6572 53/push-ebx + 6573 56/push-esi + 6574 57/push-edi + 6575 # var line/ecx: (stream byte 512) + 6576 81 5/subop/subtract %esp 0x200/imm32 + 6577 68/push 0x200/imm32/size + 6578 68/push 0/imm32/read + 6579 68/push 0/imm32/write + 6580 89/<- %ecx 4/r32/esp + 6581 # var word-slice/edx: slice + 6582 68/push 0/imm32/end + 6583 68/push 0/imm32/start + 6584 89/<- %edx 4/r32/esp + 6585 # var curr-function/edi: (addr handle function) + 6586 bf/copy-to-edi _Program-functions/imm32 + 6587 # var vars/ebx: (stack live-var 256) + 6588 81 5/subop/subtract %esp 0xc00/imm32 + 6589 68/push 0xc00/imm32/size + 6590 68/push 0/imm32/top + 6591 89/<- %ebx 4/r32/esp + 6592 { + 6593 $parse-mu:line-loop: + 6594 (clear-stream %ecx) + 6595 (read-line-buffered *(ebp+8) %ecx) + 6596 # if (line->write == 0) break + 6597 81 7/subop/compare *ecx 0/imm32 + 6598 0f 84/jump-if-= break/disp32 + 6599 +-- 6 lines: #? # dump line ------------------------------------------------------------------------------------------------------------------------------------------------------ + 6605 (next-mu-token %ecx %edx) + 6606 # if slice-empty?(word-slice) continue + 6607 (slice-empty? %edx) # => eax + 6608 3d/compare-eax-and 0/imm32/false + 6609 0f 85/jump-if-!= loop/disp32 + 6610 # if (*word-slice->start == "#") continue + 6611 # . eax = *word-slice->start + 6612 8b/-> *edx 0/r32/eax + 6613 8a/copy-byte *eax 0/r32/AL + 6614 81 4/subop/and %eax 0xff/imm32 + 6615 # . if (eax == '#') continue + 6616 3d/compare-eax-and 0x23/imm32/hash + 6617 0f 84/jump-if-= loop/disp32 + 6618 # if (slice-equal?(word-slice, "fn")) parse a function + 6619 { + 6620 $parse-mu:fn: + 6621 (slice-equal? %edx "fn") # => eax + 6622 3d/compare-eax-and 0/imm32/false + 6623 0f 84/jump-if-= break/disp32 + 6624 # var new-function/esi: (handle function) + 6625 68/push 0/imm32 + 6626 68/push 0/imm32 + 6627 89/<- %esi 4/r32/esp + 6628 # populate-mu-function(line, in, vars, new-function) + 6629 (allocate Heap *Function-size %esi) + 6630 # var new-function-addr/eax: (addr function) + 6631 (lookup *esi *(esi+4)) # => eax + 6632 # initialize vars + 6633 (clear-stack %ebx) + 6634 # + 6635 (populate-mu-function-header %ecx %eax %ebx *(ebp+0xc) *(ebp+0x10)) + 6636 (populate-mu-function-body *(ebp+8) %eax %ebx *(ebp+0xc) *(ebp+0x10)) + 6637 # *curr-function = new-function + 6638 8b/-> *esi 0/r32/eax + 6639 89/<- *edi 0/r32/eax + 6640 8b/-> *(esi+4) 0/r32/eax + 6641 89/<- *(edi+4) 0/r32/eax + 6642 # curr-function = &new-function->next + 6643 # . var tmp/eax: (addr function) = lookup(new-function) + 6644 (lookup *esi *(esi+4)) # => eax + 6645 # . curr-function = &tmp->next + 6646 8d/copy-address *(eax+0x20) 7/r32/edi # Function-next + 6647 # reclaim new-function + 6648 81 0/subop/add %esp 8/imm32 + 6649 # + 6650 e9/jump $parse-mu:line-loop/disp32 + 6651 } + 6652 # if (slice-equal?(word-slice, "sig")) parse a function signature + 6653 # Function signatures are for providing types to SubX functions. + 6654 { + 6655 $parse-mu:sig: + 6656 (slice-equal? %edx "sig") # => eax + 6657 3d/compare-eax-and 0/imm32/false + 6658 0f 84/jump-if-= break/disp32 + 6659 # edi = curr-function + 6660 57/push-edi + 6661 8b/-> *(ebp-4) 7/r32/edi + 6662 # var new-function/esi: (handle function) + 6663 68/push 0/imm32 + 6664 68/push 0/imm32 + 6665 89/<- %esi 4/r32/esp + 6666 # populate-mu-function(line, in, vars, new-function) + 6667 (allocate Heap *Function-size %esi) + 6668 # var new-function-addr/eax: (addr function) + 6669 (lookup *esi *(esi+4)) # => eax + 6670 # + 6671 (populate-mu-function-signature %ecx %eax *(ebp+0xc) *(ebp+0x10)) + 6672 # *curr-signature = new-function + 6673 8b/-> *esi 0/r32/eax + 6674 89/<- *edi 0/r32/eax + 6675 8b/-> *(esi+4) 0/r32/eax + 6676 89/<- *(edi+4) 0/r32/eax + 6677 # curr-signature = &new-function->next + 6678 # . var tmp/eax: (addr function) = lookup(new-function) + 6679 (lookup *esi *(esi+4)) # => eax + 6680 # . curr-function = &tmp->next + 6681 8d/copy-address *(eax+0x20) 7/r32/edi # Function-next + 6682 # reclaim new-function + 6683 81 0/subop/add %esp 8/imm32 + 6684 # save curr-function + 6685 89/<- *(ebp-4) 7/r32/edi + 6686 # restore edi + 6687 5f/pop-to-edi + 6688 # + 6689 e9/jump $parse-mu:line-loop/disp32 + 6690 } + 6691 # if (slice-equal?(word-slice, "type")) parse a type (struct/record) definition + 6692 { + 6693 $parse-mu:type: + 6694 (slice-equal? %edx "type") # => eax + 6695 3d/compare-eax-and 0/imm32 + 6696 0f 84/jump-if-= break/disp32 + 6697 (next-mu-token %ecx %edx) + 6698 # var type-id/eax: int + 6699 (pos-or-insert-slice Type-id %edx) # => eax + 6700 # spill + 6701 51/push-ecx + 6702 # var new-type/ecx: (handle typeinfo) + 6703 68/push 0/imm32 + 6704 68/push 0/imm32 + 6705 89/<- %ecx 4/r32/esp + 6706 (find-or-create-typeinfo %eax %ecx) + 6707 # + 6708 (lookup *ecx *(ecx+4)) # => eax + 6709 # TODO: ensure that 'line' has nothing else but '{' + 6710 #? (dump-typeinfos "=== aaa\n") + 6711 (populate-mu-type *(ebp+8) %eax *(ebp+0xc) *(ebp+0x10)) # => eax + 6712 #? (dump-typeinfos "=== zzz\n") + 6713 # reclaim new-type + 6714 81 0/subop/add %esp 8/imm32 + 6715 # restore + 6716 59/pop-to-ecx + 6717 e9/jump $parse-mu:line-loop/disp32 + 6718 } + 6719 # otherwise abort + 6720 e9/jump $parse-mu:error1/disp32 + 6721 } # end line loop + 6722 $parse-mu:end: + 6723 # . reclaim locals + 6724 81 0/subop/add %esp 0x20c/imm32 # line + 6725 81 0/subop/add %esp 0xc08/imm32 # vars + 6726 81 0/subop/add %esp 8/imm32 + 6727 # . restore registers + 6728 5f/pop-to-edi + 6729 5e/pop-to-esi + 6730 5b/pop-to-ebx + 6731 5a/pop-to-edx + 6732 59/pop-to-ecx + 6733 58/pop-to-eax + 6734 # . reclaim local + 6735 81 0/subop/add %esp 4/imm32 + 6736 # . epilogue + 6737 89/<- %esp 5/r32/ebp + 6738 5d/pop-to-ebp + 6739 c3/return + 6740 + 6741 $parse-mu:error1: + 6742 # error("unexpected top-level command: " word-slice "\n") + 6743 (write-buffered *(ebp+0xc) "unexpected top-level command: ") + 6744 (write-slice-buffered *(ebp+0xc) %edx) + 6745 (write-buffered *(ebp+0xc) "\n") + 6746 (flush *(ebp+0xc)) + 6747 (stop *(ebp+0x10) 1) + 6748 # never gets here + 6749 + 6750 $parse-mu:error2: + 6751 # error(vars->top " vars not reclaimed after fn '" new-function->name "'\n") + 6752 (write-int32-hex-buffered *(ebp+0xc) *ebx) + 6753 (write-buffered *(ebp+0xc) " vars not reclaimed after fn '") + 6754 (write-slice-buffered *(ebp+0xc) *eax) # Function-name + 6755 (write-buffered *(ebp+0xc) "'\n") + 6756 (flush *(ebp+0xc)) + 6757 (stop *(ebp+0x10) 1) + 6758 # never gets here + 6759 + 6760 # scenarios considered: + 6761 # ✗ fn foo # no block + 6762 # ✓ fn foo { + 6763 # ✗ fn foo { { + 6764 # ✗ fn foo { } + 6765 # ✗ fn foo { } { + 6766 # ✗ fn foo x { + 6767 # ✗ fn foo x: { + 6768 # ✓ fn foo x: int { + 6769 # ✓ fn foo x: int { + 6770 # ✓ fn foo x: int -> y/eax: int { + 6771 # TODO: + 6772 # disallow outputs of type `(... addr ...)` + 6773 # disallow inputs of type `(... addr ... addr ...)` + 6774 populate-mu-function-header: # first-line: (addr stream byte), out: (addr function), vars: (addr stack live-var), err: (addr buffered-file), ed: (addr exit-descriptor) + 6775 # pseudocode: + 6776 # var word-slice: slice + 6777 # next-mu-token(first-line, word-slice) + 6778 # assert(word-slice not in '{' '}' '->') + 6779 # out->name = slice-to-string(word-slice) + 6780 # ## inouts + 6781 # while true + 6782 # word-slice = next-mu-token(first-line) + 6783 # if (word-slice == '{') goto done + 6784 # if (word-slice == '->') break + 6785 # assert(word-slice != '}') + 6786 # var v: (handle var) = parse-var-with-type(word-slice, first-line) + 6787 # assert(v->register == null) + 6788 # # v->block-depth is implicitly 0 + 6789 # out->inouts = append(v, out->inouts) + 6790 # push(vars, {v, false}) + 6791 # ## outputs + 6792 # while true + 6793 # word-slice = next-mu-token(first-line) + 6794 # if (word-slice == '{') break + 6795 # assert(word-slice not in '}' '->') + 6796 # var v: (handle var) = parse-var-with-type(word-slice, first-line) + 6797 # assert(v->register != null) + 6798 # out->outputs = append(v, out->outputs) + 6799 # done: + 6800 # + 6801 # . prologue + 6802 55/push-ebp + 6803 89/<- %ebp 4/r32/esp + 6804 # . save registers + 6805 50/push-eax + 6806 51/push-ecx + 6807 52/push-edx + 6808 53/push-ebx + 6809 57/push-edi + 6810 # edi = out + 6811 8b/-> *(ebp+0xc) 7/r32/edi + 6812 # var word-slice/ecx: slice + 6813 68/push 0/imm32/end + 6814 68/push 0/imm32/start + 6815 89/<- %ecx 4/r32/esp + 6816 # var v/ebx: (handle var) + 6817 68/push 0/imm32 + 6818 68/push 0/imm32 + 6819 89/<- %ebx 4/r32/esp + 6820 # read function name + 6821 (next-mu-token *(ebp+8) %ecx) + 6822 # error checking + 6823 # if (word-slice == '{') abort + 6824 (slice-equal? %ecx "{") # => eax + 6825 3d/compare-eax-and 0/imm32/false + 6826 0f 85/jump-if-!= $populate-mu-function-header:error1/disp32 + 6827 # if (word-slice == '->') abort + 6828 (slice-equal? %ecx "->") # => eax + 6829 3d/compare-eax-and 0/imm32/false + 6830 0f 85/jump-if-!= $populate-mu-function-header:error1/disp32 + 6831 # if (word-slice == '}') abort + 6832 (slice-equal? %ecx "}") # => eax + 6833 3d/compare-eax-and 0/imm32/false + 6834 0f 85/jump-if-!= $populate-mu-function-header:error1/disp32 + 6835 # save function name + 6836 (slice-to-string Heap %ecx %edi) # Function-name + 6837 # save function inouts + 6838 { + 6839 $populate-mu-function-header:check-for-inout: + 6840 (next-mu-token *(ebp+8) %ecx) + 6841 # if (word-slice == '{') goto done + 6842 (slice-equal? %ecx "{") # => eax + 6843 3d/compare-eax-and 0/imm32/false + 6844 0f 85/jump-if-!= $populate-mu-function-header:done/disp32 + 6845 # if (word-slice == '->') break + 6846 (slice-equal? %ecx "->") # => eax + 6847 3d/compare-eax-and 0/imm32/false + 6848 0f 85/jump-if-!= break/disp32 + 6849 # if (word-slice == '}') abort + 6850 (slice-equal? %ecx "}") # => eax + 6851 3d/compare-eax-and 0/imm32/false + 6852 0f 85/jump-if-!= $populate-mu-function-header:error1/disp32 + 6853 # v = parse-var-with-type(word-slice, first-line) + 6854 (parse-var-with-type %ecx *(ebp+8) %ebx *(ebp+0x14) *(ebp+0x18)) + 6855 # assert(v->register == null) + 6856 # . eax: (addr var) = lookup(v) + 6857 (lookup *ebx *(ebx+4)) # => eax + 6858 81 7/subop/compare *(eax+0x18) 0/imm32 # Var-register + 6859 0f 85/jump-if-!= $populate-mu-function-header:error2/disp32 + 6860 # v->block-depth is implicitly 0 + 6861 # + 6862 # out->inouts = append(v, out->inouts) + 6863 8d/copy-address *(edi+8) 0/r32/eax # Function-inouts + 6864 (append-list Heap *ebx *(ebx+4) *(edi+8) *(edi+0xc) %eax) # Function-inouts, Function-inouts + 6865 # push(vars, {v, false}) + 6866 (push *(ebp+0x10) *ebx) + 6867 (push *(ebp+0x10) *(ebx+4)) + 6868 (push *(ebp+0x10) 0) # false + 6869 # + 6870 e9/jump loop/disp32 + 6871 } + 6872 # save function outputs + 6873 { + 6874 $populate-mu-function-header:check-for-out: + 6875 (next-mu-token *(ebp+8) %ecx) + 6876 # if (word-slice == '{') break + 6877 (slice-equal? %ecx "{") # => eax + 6878 3d/compare-eax-and 0/imm32/false + 6879 0f 85/jump-if-!= break/disp32 + 6880 # if (word-slice == '->') abort + 6881 (slice-equal? %ecx "->") # => eax + 6882 3d/compare-eax-and 0/imm32/false + 6883 0f 85/jump-if-!= $populate-mu-function-header:error1/disp32 + 6884 # if (word-slice == '}') abort + 6885 (slice-equal? %ecx "}") # => eax + 6886 3d/compare-eax-and 0/imm32/false + 6887 0f 85/jump-if-!= $populate-mu-function-header:error1/disp32 + 6888 # v = parse-var-with-type(word-slice, first-line) + 6889 (parse-var-with-type %ecx *(ebp+8) %ebx *(ebp+0x14) *(ebp+0x18)) + 6890 # assert(var->register != null) + 6891 # . eax: (addr var) = lookup(v) + 6892 (lookup *ebx *(ebx+4)) # => eax + 6893 81 7/subop/compare *(eax+0x18) 0/imm32 # Var-register + 6894 0f 84/jump-if-= $populate-mu-function-header:error3/disp32 + 6895 # out->outputs = append(v, out->outputs) + 6896 8d/copy-address *(edi+0x10) 0/r32/eax # Function-outputs + 6897 (append-list Heap *ebx *(ebx+4) *(edi+0x10) *(edi+0x14) %eax) # Function-outputs, Function-outputs + 6898 # + 6899 e9/jump loop/disp32 + 6900 } + 6901 $populate-mu-function-header:done: + 6902 (check-no-tokens-left *(ebp+8)) + 6903 $populate-mu-function-header:end: + 6904 # . reclaim locals + 6905 81 0/subop/add %esp 0x10/imm32 + 6906 # . restore registers + 6907 5f/pop-to-edi + 6908 5b/pop-to-ebx + 6909 5a/pop-to-edx + 6910 59/pop-to-ecx + 6911 58/pop-to-eax + 6912 # . epilogue + 6913 89/<- %esp 5/r32/ebp + 6914 5d/pop-to-ebp + 6915 c3/return + 6916 + 6917 $populate-mu-function-header:error1: + 6918 # error("function header not in form 'fn <name> {'") + 6919 (write-buffered *(ebp+0x14) "function header not in form 'fn <name> [inouts] [-> outputs] {' -- '") + 6920 (flush *(ebp+0x14)) + 6921 (rewind-stream *(ebp+8)) + 6922 (write-stream-data *(ebp+0x14) *(ebp+8)) + 6923 (write-buffered *(ebp+0x14) "'\n") + 6924 (flush *(ebp+0x14)) + 6925 (stop *(ebp+0x18) 1) + 6926 # never gets here + 6927 + 6928 $populate-mu-function-header:error2: + 6929 # error("fn " fn ": function inout '" var "' cannot be in a register") + 6930 (write-buffered *(ebp+0x14) "fn ") + 6931 50/push-eax + 6932 (lookup *edi *(edi+4)) # Function-name Function-name => eax + 6933 (write-buffered *(ebp+0x14) %eax) + 6934 58/pop-to-eax + 6935 (write-buffered *(ebp+0x14) ": function inout '") + 6936 (lookup *eax *(eax+4)) # Var-name Var-name => eax + 6937 (write-buffered *(ebp+0x10) %eax) + 6938 (write-buffered *(ebp+0x14) "' cannot be in a register") + 6939 (flush *(ebp+0x14)) + 6940 (stop *(ebp+0x18) 1) + 6941 # never gets here + 6942 + 6943 $populate-mu-function-header:error3: + 6944 # error("fn " fn ": function output '" var "' must be in a register") + 6945 (write-buffered *(ebp+0x14) "fn ") + 6946 50/push-eax + 6947 (lookup *edi *(edi+4)) # Function-name Function-name => eax + 6948 (write-buffered *(ebp+0x14) %eax) + 6949 58/pop-to-eax + 6950 (write-buffered *(ebp+0x14) ": function output '") + 6951 (lookup *ebx *(ebx+4)) # => eax + 6952 (lookup *eax *(eax+4)) # Var-name Var-name => eax + 6953 (write-buffered *(ebp+0x14) %eax) + 6954 (write-buffered *(ebp+0x14) "' must be in a register, in instruction '") + 6955 (rewind-stream *(ebp+8)) + 6956 (write-stream-data *(ebp+0x14) *(ebp+8)) + 6957 (write-buffered *(ebp+0x14) "'\n") + 6958 (flush *(ebp+0x14)) + 6959 (stop *(ebp+0x18) 1) + 6960 # never gets here + 6961 + 6962 # scenarios considered: + 6963 # ✓ fn foo + 6964 # ✗ fn foo { + 6965 # ✓ fn foo x + 6966 # ✓ fn foo x: int + 6967 # ✓ fn foo x: int -> y/eax: int + 6968 # TODO: + 6969 # disallow outputs of type `(... addr ...)` + 6970 # disallow inputs of type `(... addr ... addr ...)` + 6971 populate-mu-function-signature: # first-line: (addr stream byte), out: (addr function), err: (addr buffered-file), ed: (addr exit-descriptor) + 6972 # pseudocode: + 6973 # var word-slice: slice + 6974 # next-mu-token(first-line, word-slice) + 6975 # assert(word-slice not in '{' '}' '->') + 6976 # out->name = slice-to-string(word-slice) + 6977 # ## inouts + 6978 # while true + 6979 # word-slice = next-mu-token(first-line) + 6980 # if slice-empty?(word-slice) break + 6981 # if (word-slice == '->') break + 6982 # assert(word-slice not in '{' '}') + 6983 # var v: (handle var) = parse-var-with-type(word-slice, first-line) + 6984 # assert(v->register == null) + 6985 # # v->block-depth is implicitly 0 + 6986 # out->inouts = append(v, out->inouts) + 6987 # ## outputs + 6988 # while true + 6989 # word-slice = next-mu-token(first-line) + 6990 # if slice-empty?(word-slice) break + 6991 # assert(word-slice not in '{' '}' '->') + 6992 # var v: (handle var) = parse-var-with-type(word-slice, first-line) + 6993 # assert(v->register != null) + 6994 # out->outputs = append(v, out->outputs) + 6995 # + 6996 # . prologue + 6997 55/push-ebp + 6998 89/<- %ebp 4/r32/esp + 6999 # . save registers + 7000 50/push-eax + 7001 51/push-ecx + 7002 52/push-edx + 7003 53/push-ebx + 7004 57/push-edi + 7005 # edi = out + 7006 8b/-> *(ebp+0xc) 7/r32/edi + 7007 # var word-slice/ecx: slice + 7008 68/push 0/imm32/end + 7009 68/push 0/imm32/start + 7010 89/<- %ecx 4/r32/esp + 7011 # var v/ebx: (handle var) + 7012 68/push 0/imm32 + 7013 68/push 0/imm32 + 7014 89/<- %ebx 4/r32/esp + 7015 # read function name + 7016 (next-mu-token *(ebp+8) %ecx) + 7017 # error checking + 7018 # if (word-slice == '{') abort + 7019 (slice-equal? %ecx "{") # => eax + 7020 3d/compare-eax-and 0/imm32/false + 7021 0f 85/jump-if-!= $populate-mu-function-signature:error1/disp32 + 7022 # if (word-slice == '->') abort + 7023 (slice-equal? %ecx "->") # => eax + 7024 3d/compare-eax-and 0/imm32/false + 7025 0f 85/jump-if-!= $populate-mu-function-signature:error1/disp32 + 7026 # if (word-slice == '}') abort + 7027 (slice-equal? %ecx "}") # => eax + 7028 3d/compare-eax-and 0/imm32/false + 7029 0f 85/jump-if-!= $populate-mu-function-signature:error1/disp32 + 7030 # save function name + 7031 (slice-to-string Heap %ecx %edi) # Function-name + 7032 # save function inouts + 7033 { + 7034 $populate-mu-function-signature:check-for-inout: + 7035 (next-mu-token *(ebp+8) %ecx) + 7036 (slice-empty? %ecx) # => eax + 7037 3d/compare-eax-and 0/imm32/false + 7038 0f 85/jump-if-!= break/disp32 + 7039 # if (word-slice == '->') break + 7040 (slice-equal? %ecx "->") # => eax + 7041 3d/compare-eax-and 0/imm32/false + 7042 0f 85/jump-if-!= break/disp32 + 7043 # if (word-slice == '{') abort + 7044 (slice-equal? %ecx "{") # => eax + 7045 3d/compare-eax-and 0/imm32/false + 7046 0f 85/jump-if-!= $populate-mu-function-signature:error1/disp32 + 7047 # if (word-slice == '}') abort + 7048 (slice-equal? %ecx "}") # => eax + 7049 3d/compare-eax-and 0/imm32/false + 7050 0f 85/jump-if-!= $populate-mu-function-signature:error1/disp32 + 7051 # v = parse-var-with-type(word-slice, first-line) + 7052 (parse-var-with-type %ecx *(ebp+8) %ebx *(ebp+0x10) *(ebp+0x14)) + 7053 # assert(v->register == null) + 7054 # . eax: (addr var) = lookup(v) + 7055 (lookup *ebx *(ebx+4)) # => eax + 7056 81 7/subop/compare *(eax+0x18) 0/imm32 # Var-register + 7057 0f 85/jump-if-!= $populate-mu-function-signature:error2/disp32 + 7058 # v->block-depth is implicitly 0 + 7059 # + 7060 # out->inouts = append(v, out->inouts) + 7061 8d/copy-address *(edi+8) 0/r32/eax # Function-inouts + 7062 (append-list Heap *ebx *(ebx+4) *(edi+8) *(edi+0xc) %eax) # Function-inouts, Function-inouts + 7063 # + 7064 e9/jump loop/disp32 + 7065 } + 7066 # save function outputs + 7067 { + 7068 $populate-mu-function-signature:check-for-out: + 7069 (next-mu-token *(ebp+8) %ecx) + 7070 (slice-empty? %ecx) # => eax + 7071 3d/compare-eax-and 0/imm32/false + 7072 0f 85/jump-if-!= break/disp32 + 7073 # if (word-slice == '{') abort + 7074 (slice-equal? %ecx "{") # => eax + 7075 3d/compare-eax-and 0/imm32/false + 7076 0f 85/jump-if-!= $populate-mu-function-signature:error1/disp32 + 7077 # if (word-slice == '->') abort + 7078 (slice-equal? %ecx "->") # => eax + 7079 3d/compare-eax-and 0/imm32/false + 7080 0f 85/jump-if-!= $populate-mu-function-signature:error1/disp32 + 7081 # if (word-slice == '}') abort + 7082 (slice-equal? %ecx "}") # => eax + 7083 3d/compare-eax-and 0/imm32/false + 7084 0f 85/jump-if-!= $populate-mu-function-signature:error1/disp32 + 7085 # v = parse-var-with-type(word-slice, first-line) + 7086 (parse-var-with-type %ecx *(ebp+8) %ebx *(ebp+0x10) *(ebp+0x14)) + 7087 # assert(var->register != null) + 7088 # . eax: (addr var) = lookup(v) + 7089 (lookup *ebx *(ebx+4)) # => eax + 7090 81 7/subop/compare *(eax+0x18) 0/imm32 # Var-register + 7091 0f 84/jump-if-= $populate-mu-function-signature:error3/disp32 + 7092 # out->outputs = append(v, out->outputs) + 7093 8d/copy-address *(edi+0x10) 0/r32/eax # Function-outputs + 7094 (append-list Heap *ebx *(ebx+4) *(edi+0x10) *(edi+0x14) %eax) # Function-outputs, Function-outputs + 7095 # + 7096 e9/jump loop/disp32 + 7097 } + 7098 $populate-mu-function-signature:done: + 7099 (check-no-tokens-left *(ebp+8)) + 7100 $populate-mu-function-signature:end: + 7101 # . reclaim locals + 7102 81 0/subop/add %esp 0x10/imm32 + 7103 # . restore registers + 7104 5f/pop-to-edi + 7105 5b/pop-to-ebx + 7106 5a/pop-to-edx + 7107 59/pop-to-ecx + 7108 58/pop-to-eax + 7109 # . epilogue + 7110 89/<- %esp 5/r32/ebp + 7111 5d/pop-to-ebp + 7112 c3/return + 7113 + 7114 $populate-mu-function-signature:error1: + 7115 # error("function signature not in form 'fn <name> {'") + 7116 (write-buffered *(ebp+0x10) "function signature not in form 'fn <name> [inouts] [-> outputs] {' -- '") + 7117 (flush *(ebp+0x10)) + 7118 (rewind-stream *(ebp+8)) + 7119 (write-stream-data *(ebp+0x10) *(ebp+8)) + 7120 (write-buffered *(ebp+0x10) "'\n") + 7121 (flush *(ebp+0x10)) + 7122 (stop *(ebp+0x14) 1) + 7123 # never gets here + 7124 + 7125 $populate-mu-function-signature:error2: + 7126 # error("fn " fn ": function inout '" var "' cannot be in a register") + 7127 (write-buffered *(ebp+0x10) "fn ") + 7128 50/push-eax + 7129 (lookup *edi *(edi+4)) # Function-name Function-name => eax + 7130 (write-buffered *(ebp+0x10) %eax) + 7131 58/pop-to-eax + 7132 (write-buffered *(ebp+0x10) ": function inout '") + 7133 (lookup *eax *(eax+4)) # Var-name Var-name => eax + 7134 (write-buffered *(ebp+0x10) %eax) + 7135 (write-buffered *(ebp+0x10) "' cannot be in a register") + 7136 (flush *(ebp+0x10)) + 7137 (stop *(ebp+0x14) 1) + 7138 # never gets here + 7139 + 7140 $populate-mu-function-signature:error3: + 7141 # error("fn " fn ": function output '" var "' must be in a register") + 7142 (write-buffered *(ebp+0x10) "fn ") + 7143 50/push-eax + 7144 (lookup *edi *(edi+4)) # Function-name Function-name => eax + 7145 (write-buffered *(ebp+0x10) %eax) + 7146 58/pop-to-eax + 7147 (write-buffered *(ebp+0x10) ": function output '") + 7148 (lookup *ebx *(ebx+4)) # => eax + 7149 (lookup *eax *(eax+4)) # Var-name Var-name => eax + 7150 (write-buffered *(ebp+0x10) %eax) + 7151 (write-buffered *(ebp+0x10) "' must be in a register, in instruction '") + 7152 (rewind-stream *(ebp+8)) + 7153 (write-stream-data *(ebp+0x10) *(ebp+8)) + 7154 (write-buffered *(ebp+0x10) "'\n") + 7155 (flush *(ebp+0x10)) + 7156 (stop *(ebp+0x14) 1) + 7157 # never gets here + 7158 + 7159 test-function-header-with-arg: + 7160 # . prologue + 7161 55/push-ebp + 7162 89/<- %ebp 4/r32/esp + 7163 # setup + 7164 (clear-stream _test-input-stream) + 7165 (write _test-input-stream "foo n: int {\n") + 7166 # var result/ecx: function + 7167 2b/subtract *Function-size 4/r32/esp + 7168 89/<- %ecx 4/r32/esp + 7169 (zero-out %ecx *Function-size) + 7170 # var vars/ebx: (stack live-var 16) + 7171 81 5/subop/subtract %esp 0xc0/imm32 + 7172 68/push 0xc0/imm32/size + 7173 68/push 0/imm32/top + 7174 89/<- %ebx 4/r32/esp + 7175 # convert + 7176 (populate-mu-function-header _test-input-stream %ecx %ebx Stderr 0) + 7177 # check result->name + 7178 (lookup *ecx *(ecx+4)) # Function-name Function-name => eax + 7179 (check-strings-equal %eax "foo" "F - test-function-header-with-arg/name") + 7180 # var v/edx: (addr var) = result->inouts->value + 7181 (lookup *(ecx+8) *(ecx+0xc)) # Function-inouts Function-inouts => eax + 7182 (lookup *eax *(eax+4)) # List-value List-value => eax + 7183 89/<- %edx 0/r32/eax + 7184 # check v->name + 7185 (lookup *edx *(edx+4)) # Var-name Var-name => eax + 7186 (check-strings-equal %eax "n" "F - test-function-header-with-arg/inout:0") + 7187 # check v->type + 7188 (lookup *(edx+8) *(edx+0xc)) # Var-type Var-type => eax + 7189 (check-ints-equal *eax 1 "F - test-function-header-with-arg/inout:0/type:0") # Type-tree-is-atom + 7190 (check-ints-equal *(eax+4) 1 "F - test-function-header-with-arg/inout:0/type:1") # Type-tree-value + 7191 (check-ints-equal *(eax+0xc) 0 "F - test-function-header-with-arg/inout:0/type:2") # Type-tree-right + 7192 # . epilogue + 7193 89/<- %esp 5/r32/ebp + 7194 5d/pop-to-ebp + 7195 c3/return + 7196 + 7197 test-function-header-with-multiple-args: + 7198 # . prologue + 7199 55/push-ebp + 7200 89/<- %ebp 4/r32/esp + 7201 # setup + 7202 (clear-stream _test-input-stream) + 7203 (write _test-input-stream "foo a: int, b: int c: int {\n") + 7204 # result/ecx: function + 7205 2b/subtract *Function-size 4/r32/esp + 7206 89/<- %ecx 4/r32/esp + 7207 (zero-out %ecx *Function-size) + 7208 # var vars/ebx: (stack live-var 16) + 7209 81 5/subop/subtract %esp 0xc0/imm32 + 7210 68/push 0xc0/imm32/size + 7211 68/push 0/imm32/top + 7212 89/<- %ebx 4/r32/esp + 7213 # convert + 7214 (populate-mu-function-header _test-input-stream %ecx %ebx Stderr 0) + 7215 # check result->name + 7216 (lookup *ecx *(ecx+4)) # Function-name Function-name => eax + 7217 (check-strings-equal %eax "foo" "F - test-function-header-with-multiple-args/name") + 7218 # var inouts/edx: (addr list var) = lookup(result->inouts) + 7219 (lookup *(ecx+8) *(ecx+0xc)) # Function-inouts Function-inouts => eax + 7220 89/<- %edx 0/r32/eax + 7221 $test-function-header-with-multiple-args:inout0: + 7222 # var v/ebx: (addr var) = lookup(inouts->value) + 7223 (lookup *edx *(edx+4)) # List-value List-value => eax + 7224 89/<- %ebx 0/r32/eax + 7225 # check v->name + 7226 (lookup *ebx *(ebx+4)) # Var-name Var-name => eax + 7227 (check-strings-equal %eax "a" "F - test-function-header-with-multiple-args/inout:0") # Var-name + 7228 # check v->type + 7229 (lookup *(ebx+8) *(ebx+0xc)) # Var-type Var-type => eax + 7230 (check-ints-equal *eax 1 "F - test-function-header-with-multiple-args/inout:0/type:0") # Type-tree-is-atom + 7231 (check-ints-equal *(eax+4) 1 "F - test-function-header-with-multiple-args/inout:0/type:1") # Type-tree-value + 7232 (check-ints-equal *(eax+0xc) 0 "F - test-function-header-with-multiple-args/inout:0/type:2") # Type-tree-right + 7233 $test-function-header-with-multiple-args:inout1: + 7234 # inouts = lookup(inouts->next) + 7235 (lookup *(edx+8) *(edx+0xc)) # List-next List-next => eax + 7236 89/<- %edx 0/r32/eax + 7237 # v = lookup(inouts->value) + 7238 (lookup *edx *(edx+4)) # List-value List-value => eax + 7239 89/<- %ebx 0/r32/eax + 7240 # check v->name + 7241 (lookup *ebx *(ebx+4)) # Var-name Var-name => eax + 7242 (check-strings-equal %eax "b" "F - test-function-header-with-multiple-args/inout:1") # Var-name + 7243 # check v->type + 7244 (lookup *(ebx+8) *(ebx+0xc)) # Var-type Var-type => eax + 7245 (check-ints-equal *eax 1 "F - test-function-header-with-multiple-args/inout:1/type:0") # Type-tree-is-atom + 7246 (check-ints-equal *(eax+4) 1 "F - test-function-header-with-multiple-args/inout:1/type:1") # Type-tree-value + 7247 (check-ints-equal *(eax+0xc) 0 "F - test-function-header-with-multiple-args/inout:1/type:2") # Type-tree-right + 7248 $test-function-header-with-multiple-args:inout2: + 7249 # inouts = lookup(inouts->next) + 7250 (lookup *(edx+8) *(edx+0xc)) # List-next List-next => eax + 7251 89/<- %edx 0/r32/eax + 7252 # v = lookup(inouts->value) + 7253 (lookup *edx *(edx+4)) # List-value List-value => eax + 7254 89/<- %ebx 0/r32/eax + 7255 # check v->name + 7256 (lookup *ebx *(ebx+4)) # Var-name Var-name => eax + 7257 (check-strings-equal %eax "c" "F - test-function-header-with-multiple-args/inout:2") # Var-name + 7258 # check v->type + 7259 (lookup *(ebx+8) *(ebx+0xc)) # Var-type Var-type => eax + 7260 (check-ints-equal *eax 1 "F - test-function-header-with-multiple-args/inout:2/type:0") # Type-tree-is-atom + 7261 (check-ints-equal *(eax+4) 1 "F - test-function-header-with-multiple-args/inout:2/type:1") # Type-tree-value + 7262 (check-ints-equal *(eax+0xc) 0 "F - test-function-header-with-multiple-args/inout:2/type:2") # Type-tree-right + 7263 # . epilogue + 7264 89/<- %esp 5/r32/ebp + 7265 5d/pop-to-ebp + 7266 c3/return + 7267 + 7268 test-function-header-with-multiple-args-and-outputs: + 7269 # . prologue + 7270 55/push-ebp + 7271 89/<- %ebp 4/r32/esp + 7272 # setup + 7273 (clear-stream _test-input-stream) + 7274 (write _test-input-stream "foo a: int, b: int, c: int -> x/ecx: int y/edx: int {\n") + 7275 # result/ecx: function + 7276 2b/subtract *Function-size 4/r32/esp + 7277 89/<- %ecx 4/r32/esp + 7278 (zero-out %ecx *Function-size) + 7279 # var vars/ebx: (stack live-var 16) + 7280 81 5/subop/subtract %esp 0xc0/imm32 + 7281 68/push 0xc0/imm32/size + 7282 68/push 0/imm32/top + 7283 89/<- %ebx 4/r32/esp + 7284 # convert + 7285 (populate-mu-function-header _test-input-stream %ecx %ebx Stderr 0) + 7286 # check result->name + 7287 (lookup *ecx *(ecx+4)) # Function-name Function-name => eax + 7288 (check-strings-equal %eax "foo" "F - test-function-header-with-multiple-args-and-outputs/name") + 7289 # var inouts/edx: (addr list var) = lookup(result->inouts) + 7290 (lookup *(ecx+8) *(ecx+0xc)) # Function-inouts Function-inouts => eax + 7291 89/<- %edx 0/r32/eax + 7292 $test-function-header-with-multiple-args-and-outputs:inout0: + 7293 # var v/ebx: (addr var) = lookup(inouts->value) + 7294 (lookup *edx *(edx+4)) # List-value List-value => eax + 7295 89/<- %ebx 0/r32/eax + 7296 # check v->name + 7297 (lookup *ebx *(ebx+4)) # Var-name Var-name => eax + 7298 (check-strings-equal %eax "a" "F - test-function-header-with-multiple-args-and-outputs/inout:0") + 7299 # check v->type + 7300 (lookup *(ebx+8) *(ebx+0xc)) # Var-type Var-type => eax + 7301 (check-ints-equal *eax 1 "F - test-function-header-with-multiple-args-and-outputs/inout:0/type:0") # Type-tree-is-atom + 7302 (check-ints-equal *(eax+4) 1 "F - test-function-header-with-multiple-args-and-outputs/inout:0/type:1") # Type-tree-value + 7303 (check-ints-equal *(eax+0xc) 0 "F - test-function-header-with-multiple-args-and-outputs/inout:0/type:2") # Type-tree-right + 7304 $test-function-header-with-multiple-args-and-outputs:inout1: + 7305 # inouts = lookup(inouts->next) + 7306 (lookup *(edx+8) *(edx+0xc)) # List-next List-next => eax + 7307 89/<- %edx 0/r32/eax + 7308 # v = lookup(inouts->value) + 7309 (lookup *edx *(edx+4)) # List-value List-value => eax + 7310 89/<- %ebx 0/r32/eax + 7311 # check v->name + 7312 (lookup *ebx *(ebx+4)) # Var-name Var-name => eax + 7313 (check-strings-equal %eax "b" "F - test-function-header-with-multiple-args-and-outputs/inout:1") + 7314 # check v->type + 7315 (lookup *(ebx+8) *(ebx+0xc)) # Var-type Var-type => eax + 7316 (check-ints-equal *eax 1 "F - test-function-header-with-multiple-args-and-outputs/inout:1/type:0") # Type-tree-is-atom + 7317 (check-ints-equal *(eax+4) 1 "F - test-function-header-with-multiple-args-and-outputs/inout:1/type:1") # Type-tree-value + 7318 (check-ints-equal *(eax+0xc) 0 "F - test-function-header-with-multiple-args-and-outputs/inout:1/type:2") # Type-tree-right + 7319 $test-function-header-with-multiple-args-and-outputs:inout2: + 7320 # inouts = lookup(inouts->next) + 7321 (lookup *(edx+8) *(edx+0xc)) # List-next List-next => eax + 7322 89/<- %edx 0/r32/eax + 7323 # v = lookup(inouts->value) + 7324 (lookup *edx *(edx+4)) # List-value List-value => eax + 7325 89/<- %ebx 0/r32/eax + 7326 # check v->name + 7327 (lookup *ebx *(ebx+4)) # Var-name Var-name => eax + 7328 (check-strings-equal %eax "c" "F - test-function-header-with-multiple-args-and-outputs/inout:2") + 7329 # check v->type + 7330 (lookup *(ebx+8) *(ebx+0xc)) # Var-type Var-type => eax + 7331 (check-ints-equal *eax 1 "F - test-function-header-with-multiple-args-and-outputs/inout:2/type:0") # Type-tree-is-atom + 7332 (check-ints-equal *(eax+4) 1 "F - test-function-header-with-multiple-args-and-outputs/inout:2/type:1") # Type-tree-value + 7333 (check-ints-equal *(eax+0xc) 0 "F - test-function-header-with-multiple-args-and-outputs/inout:2/type:2") # Type-tree-right + 7334 $test-function-header-with-multiple-args-and-outputs:out0: + 7335 # var outputs/edx: (addr list var) = lookup(result->outputs) + 7336 (lookup *(ecx+0x10) *(ecx+0x14)) # Function-outputs Function-outputs => eax + 7337 89/<- %edx 0/r32/eax + 7338 # v = lookup(outputs->value) + 7339 (lookup *edx *(edx+4)) # List-value List-value => eax + 7340 89/<- %ebx 0/r32/eax + 7341 # check v->name + 7342 (lookup *ebx *(ebx+4)) # Var-name Var-name => eax + 7343 (check-strings-equal %eax "x" "F - test-function-header-with-multiple-args-and-outputs/output:0") + 7344 # check v->register + 7345 (lookup *(ebx+0x18) *(ebx+0x1c)) # Var-register Var-register => eax + 7346 (check-strings-equal %eax "ecx" "F - test-function-header-with-multiple-args-and-outputs/output:0/register") + 7347 # check v->type + 7348 (lookup *(ebx+8) *(ebx+0xc)) # Var-type Var-type => eax + 7349 (check-ints-equal *eax 1 "F - test-function-header-with-multiple-args-and-outputs/output:0/type:0") # Type-tree-is-atom + 7350 (check-ints-equal *(eax+4) 1 "F - test-function-header-with-multiple-args-and-outputs/output:0/type:1") # Type-tree-value + 7351 (check-ints-equal *(eax+0xc) 0 "F - test-function-header-with-multiple-args-and-outputs/output:0/type:2") # Type-tree-right + 7352 $test-function-header-with-multiple-args-and-outputs:out1: + 7353 # outputs = lookup(outputs->next) + 7354 (lookup *(edx+8) *(edx+0xc)) # List-next List-next => eax + 7355 89/<- %edx 0/r32/eax + 7356 # v = lookup(inouts->value) + 7357 (lookup *edx *(edx+4)) # List-value List-value => eax + 7358 89/<- %ebx 0/r32/eax + 7359 # check v->name + 7360 (lookup *ebx *(ebx+4)) # Var-name Var-name => eax + 7361 (check-strings-equal %eax "y" "F - test-function-header-with-multiple-args-and-outputs/output:1") + 7362 # check v->register + 7363 (lookup *(ebx+0x18) *(ebx+0x1c)) # Var-register Var-register => eax + 7364 (check-strings-equal %eax "edx" "F - test-function-header-with-multiple-args-and-outputs/output:1/register") + 7365 # check v->type + 7366 (lookup *(ebx+8) *(ebx+0xc)) # Var-type Var-type => eax + 7367 (check-ints-equal *eax 1 "F - test-function-header-with-multiple-args-and-outputs/output:1/type:0") # Type-tree-is-atom + 7368 (check-ints-equal *(eax+4) 1 "F - test-function-header-with-multiple-args-and-outputs/output:1/type:1") # Type-tree-value + 7369 (check-ints-equal *(eax+0c) 0 "F - test-function-header-with-multiple-args-and-outputs/output:1/type:2") # Type-tree-right + 7370 # . epilogue + 7371 89/<- %esp 5/r32/ebp + 7372 5d/pop-to-ebp + 7373 c3/return + 7374 + 7375 # format for variables with types + 7376 # x: int + 7377 # x: int, + 7378 # x/eax: int + 7379 # x/eax: int, + 7380 # ignores at most one trailing comma + 7381 # WARNING: modifies name + 7382 parse-var-with-type: # name: (addr slice), first-line: (addr stream byte), out: (addr handle var), err: (addr buffered-file), ed: (addr exit-descriptor) + 7383 # pseudocode: + 7384 # var s: slice + 7385 # if (!slice-ends-with(name, ":")) + 7386 # abort + 7387 # --name->end to skip ':' + 7388 # next-token-from-slice(name->start, name->end, '/', s) + 7389 # new-var-from-slice(s, out) + 7390 # ## register + 7391 # next-token-from-slice(s->end, name->end, '/', s) + 7392 # if (!slice-empty?(s)) + 7393 # out->register = slice-to-string(s) + 7394 # ## type + 7395 # var type: (handle type-tree) = parse-type(first-line) + 7396 # out->type = type + 7397 # + 7398 # . prologue + 7399 55/push-ebp + 7400 89/<- %ebp 4/r32/esp + 7401 # . save registers + 7402 50/push-eax + 7403 51/push-ecx + 7404 52/push-edx + 7405 53/push-ebx + 7406 56/push-esi + 7407 57/push-edi + 7408 # esi = name + 7409 8b/-> *(ebp+8) 6/r32/esi + 7410 # if (!slice-ends-with?(name, ":")) abort + 7411 8b/-> *(esi+4) 1/r32/ecx # Slice-end + 7412 49/decrement-ecx + 7413 8a/copy-byte *ecx 1/r32/CL + 7414 81 4/subop/and %ecx 0xff/imm32 + 7415 81 7/subop/compare %ecx 0x3a/imm32/colon + 7416 0f 85/jump-if-!= $parse-var-with-type:abort/disp32 + 7417 # --name->end to skip ':' + 7418 ff 1/subop/decrement *(esi+4) + 7419 # var s/ecx: slice + 7420 68/push 0/imm32/end + 7421 68/push 0/imm32/start + 7422 89/<- %ecx 4/r32/esp + 7423 $parse-var-with-type:parse-name: + 7424 (next-token-from-slice *esi *(esi+4) 0x2f %ecx) # Slice-start, Slice-end, '/' + 7425 $parse-var-with-type:create-var: + 7426 # new-var-from-slice(s, out) + 7427 (new-var-from-slice Heap %ecx *(ebp+0x10)) + 7428 # save out->register + 7429 $parse-var-with-type:save-register: + 7430 # . var out-addr/edi: (addr var) = lookup(*out) + 7431 8b/-> *(ebp+0x10) 7/r32/edi + 7432 (lookup *edi *(edi+4)) # => eax + 7433 89/<- %edi 0/r32/eax + 7434 # . s = next-token(...) + 7435 (next-token-from-slice *(ecx+4) *(esi+4) 0x2f %ecx) # s->end, name->end, '/' + 7436 # . if (!slice-empty?(s)) out->register = slice-to-string(s) + 7437 { + 7438 $parse-var-with-type:write-register: + 7439 (slice-empty? %ecx) # => eax + 7440 3d/compare-eax-and 0/imm32/false + 7441 75/jump-if-!= break/disp8 + 7442 # out->register = slice-to-string(s) + 7443 8d/copy-address *(edi+0x18) 0/r32/eax # Var-register + 7444 (slice-to-string Heap %ecx %eax) + 7445 } + 7446 $parse-var-with-type:save-type: + 7447 8d/copy-address *(edi+8) 0/r32/eax # Var-type + 7448 (parse-type Heap *(ebp+0xc) %eax *(ebp+0x14) *(ebp+0x18)) + 7449 $parse-var-with-type:end: + 7450 # . reclaim locals + 7451 81 0/subop/add %esp 8/imm32 + 7452 # . restore registers + 7453 5f/pop-to-edi + 7454 5e/pop-to-esi + 7455 5b/pop-to-ebx + 7456 5a/pop-to-edx + 7457 59/pop-to-ecx + 7458 58/pop-to-eax + 7459 # . epilogue + 7460 89/<- %esp 5/r32/ebp + 7461 5d/pop-to-ebp + 7462 c3/return + 7463 + 7464 $parse-var-with-type:abort: + 7465 # error("var should have form 'name: type' in '" line "'\n") + 7466 (write-buffered *(ebp+0x14) "var should have form 'name: type' in '") + 7467 (flush *(ebp+0x14)) + 7468 (rewind-stream *(ebp+0xc)) + 7469 (write-stream-data *(ebp+0x14) *(ebp+0xc)) + 7470 (write-buffered *(ebp+0x14) "'\n") + 7471 (flush *(ebp+0x14)) + 7472 (stop *(ebp+0x18) 1) + 7473 # never gets here + 7474 + 7475 parse-type: # ad: (addr allocation-descriptor), in: (addr stream byte), out: (addr handle type-tree), err: (addr buffered-file), ed: (addr exit-descriptor) + 7476 # pseudocode: + 7477 # var s: slice = next-mu-token(in) + 7478 # assert s != "" + 7479 # assert s != "->" + 7480 # assert s != "{" + 7481 # assert s != "}" + 7482 # if s == ")" + 7483 # return + 7484 # out = allocate(Type-tree) + 7485 # if s != "(" + 7486 # HACK: if s is an int, parse and return it + 7487 # out->is-atom? = true + 7488 # if (s[0] == "_") + 7489 # out->value = type-parameter + 7490 # out->parameter-name = slice-to-string(ad, s) + 7491 # else + 7492 # out->value = pos-or-insert-slice(Type-id, s) + 7493 # return + 7494 # out->left = parse-type(ad, in) + 7495 # out->right = parse-type-tree(ad, in) + 7496 # + 7497 # . prologue + 7498 55/push-ebp + 7499 89/<- %ebp 4/r32/esp + 7500 # . save registers + 7501 50/push-eax + 7502 51/push-ecx + 7503 52/push-edx + 7504 # clear out + 7505 (zero-out *(ebp+0x10) *Handle-size) + 7506 # var s/ecx: slice + 7507 68/push 0/imm32 + 7508 68/push 0/imm32 + 7509 89/<- %ecx 4/r32/esp + 7510 # s = next-mu-token(in) + 7511 (next-mu-token *(ebp+0xc) %ecx) + 7512 #? (write-buffered Stderr "tok: ") + 7513 #? (write-slice-buffered Stderr %ecx) + 7514 #? (write-buffered Stderr "$\n") + 7515 #? (flush Stderr) + 7516 # assert s != "" + 7517 (slice-equal? %ecx "") # => eax + 7518 3d/compare-eax-and 0/imm32/false + 7519 0f 85/jump-if-!= $parse-type:abort/disp32 + 7520 # assert s != "{" + 7521 (slice-equal? %ecx "{") # => eax + 7522 3d/compare-eax-and 0/imm32/false + 7523 0f 85/jump-if-!= $parse-type:abort/disp32 + 7524 # assert s != "}" + 7525 (slice-equal? %ecx "}") # => eax + 7526 3d/compare-eax-and 0/imm32/false + 7527 0f 85/jump-if-!= $parse-type:abort/disp32 + 7528 # assert s != "->" + 7529 (slice-equal? %ecx "->") # => eax + 7530 3d/compare-eax-and 0/imm32/false + 7531 0f 85/jump-if-!= $parse-type:abort/disp32 + 7532 # if (s == ")") return + 7533 (slice-equal? %ecx ")") # => eax + 7534 3d/compare-eax-and 0/imm32/false + 7535 0f 85/jump-if-!= $parse-type:end/disp32 + 7536 # out = new tree + 7537 (allocate *(ebp+8) *Type-tree-size *(ebp+0x10)) + 7538 # var out-addr/edx: (addr type-tree) = lookup(*out) + 7539 8b/-> *(ebp+0x10) 2/r32/edx + 7540 (lookup *edx *(edx+4)) # => eax + 7541 89/<- %edx 0/r32/eax + 7542 { + 7543 # if (s != "(") break + 7544 (slice-equal? %ecx "(") # => eax + 7545 3d/compare-eax-and 0/imm32/false + 7546 0f 85/jump-if-!= break/disp32 + 7547 # if s is a number, store it in the type's size field + 7548 { + 7549 $parse-type:check-for-int: + 7550 # var tmp/eax: byte = *s->slice + 7551 8b/-> *ecx 0/r32/eax + 7552 8a/copy-byte *eax 0/r32/AL + 7553 81 4/subop/and %eax 0xff/imm32 + 7554 # TODO: raise an error on `var x: (array int a)` + 7555 (is-decimal-digit? %eax) # => eax + 7556 3d/compare-eax-and 0/imm32/false + 7557 74/jump-if-= break/disp8 + 7558 # + 7559 (is-hex-int? %ecx) # => eax + 7560 3d/compare-eax-and 0/imm32/false + 7561 74/jump-if-= break/disp8 + 7562 $parse-type:int: + 7563 (check-mu-hex-int %ecx *(ebp+0x14) *(ebp+0x18)) + 7564 (parse-hex-int-from-slice %ecx) # => eax + 7565 c7 0/subop/copy *(edx+4) 9/imm32/type-id-array-capacity # Type-tree-value + 7566 89/<- *(edx+8) 0/r32/eax # Type-tree-value-size + 7567 e9/jump $parse-type:end/disp32 + 7568 } + 7569 $parse-type:atom: + 7570 # out->is-atom? = true + 7571 c7 0/subop/copy *edx 1/imm32/true # Type-tree-is-atom + 7572 { + 7573 $parse-type:check-for-type-parameter: + 7574 # var tmp/eax: byte = *s->slice + 7575 8b/-> *ecx 0/r32/eax + 7576 8a/copy-byte *eax 0/r32/AL + 7577 81 4/subop/and %eax 0xff/imm32 + 7578 # if (tmp != '_') break + 7579 3d/compare-eax-and 0x5f/imm32/_ + 7580 75/jump-if-!= break/disp8 + 7581 $parse-type:type-parameter: + 7582 # out->value = type-parameter + 7583 c7 0/subop/copy *(edx+4) 0xa/imm32/type-parameter # Type-tree-value + 7584 # out->parameter-name = slice-to-string(ad, s) + 7585 8d/copy-address *(edx+8) 0/r32/eax # Type-tree-parameter-name + 7586 (slice-to-string *(ebp+8) %ecx %eax) + 7587 e9/jump $parse-type:end/disp32 + 7588 } + 7589 $parse-type:non-type-parameter: + 7590 # out->value = pos-or-insert-slice(Type-id, s) + 7591 (pos-or-insert-slice Type-id %ecx) # => eax + 7592 89/<- *(edx+4) 0/r32/eax # Type-tree-value + 7593 e9/jump $parse-type:end/disp32 + 7594 } + 7595 $parse-type:non-atom: + 7596 # otherwise s == "(" + 7597 # out->left = parse-type(ad, in) + 7598 8d/copy-address *(edx+4) 0/r32/eax # Type-tree-left + 7599 (parse-type *(ebp+8) *(ebp+0xc) %eax *(ebp+0x14) *(ebp+0x18)) + 7600 # out->right = parse-type-tree(ad, in) + 7601 8d/copy-address *(edx+0xc) 0/r32/eax # Type-tree-right + 7602 (parse-type-tree *(ebp+8) *(ebp+0xc) %eax *(ebp+0x14) *(ebp+0x18)) + 7603 $parse-type:end: + 7604 # . reclaim locals + 7605 81 0/subop/add %esp 8/imm32 + 7606 # . restore registers + 7607 5a/pop-to-edx + 7608 59/pop-to-ecx + 7609 58/pop-to-eax + 7610 # . epilogue + 7611 89/<- %esp 5/r32/ebp + 7612 5d/pop-to-ebp + 7613 c3/return + 7614 + 7615 $parse-type:abort: + 7616 # error("unexpected token when parsing type: '" s "'\n") + 7617 (write-buffered *(ebp+0x14) "unexpected token when parsing type: '") + 7618 (write-slice-buffered *(ebp+0x14) %ecx) + 7619 (write-buffered *(ebp+0x14) "'\n") + 7620 (flush *(ebp+0x14)) + 7621 (stop *(ebp+0x18) 1) + 7622 # never gets here + 7623 + 7624 parse-type-tree: # ad: (addr allocation-descriptor), in: (addr stream byte), out: (addr handle type-tree), err: (addr buffered-file), ed: (addr exit-descriptor) + 7625 # pseudocode: + 7626 # var tmp: (handle type-tree) = parse-type(ad, in) + 7627 # if tmp == 0 + 7628 # return 0 + 7629 # out = allocate(Type-tree) + 7630 # out->left = tmp + 7631 # out->right = parse-type-tree(ad, in) + 7632 # + 7633 # . prologue + 7634 55/push-ebp + 7635 89/<- %ebp 4/r32/esp + 7636 # . save registers + 7637 50/push-eax + 7638 51/push-ecx + 7639 52/push-edx + 7640 # + 7641 (zero-out *(ebp+0x10) *Handle-size) + 7642 # var tmp/ecx: (handle type-tree) + 7643 68/push 0/imm32 + 7644 68/push 0/imm32 + 7645 89/<- %ecx 4/r32/esp + 7646 # tmp = parse-type(ad, in) + 7647 (parse-type *(ebp+8) *(ebp+0xc) %ecx *(ebp+0x14) *(ebp+0x18)) + 7648 # if (tmp == 0) return + 7649 81 7/subop/compare *ecx 0/imm32 + 7650 74/jump-if-= $parse-type-tree:end/disp8 + 7651 # out = new tree + 7652 (allocate *(ebp+8) *Type-tree-size *(ebp+0x10)) + 7653 # var out-addr/edx: (addr tree) = lookup(*out) + 7654 8b/-> *(ebp+0x10) 2/r32/edx + 7655 (lookup *edx *(edx+4)) # => eax + 7656 89/<- %edx 0/r32/eax + 7657 # out->left = tmp + 7658 8b/-> *ecx 0/r32/eax + 7659 89/<- *(edx+4) 0/r32/eax # Type-tree-left + 7660 8b/-> *(ecx+4) 0/r32/eax + 7661 89/<- *(edx+8) 0/r32/eax # Type-tree-left + 7662 # out->right = parse-type-tree(ad, in) + 7663 8d/copy-address *(edx+0xc) 0/r32/eax # Type-tree-right + 7664 (parse-type-tree *(ebp+8) *(ebp+0xc) %eax *(ebp+0x14) *(ebp+0x18)) + 7665 $parse-type-tree:end: + 7666 # . reclaim locals + 7667 81 0/subop/add %esp 8/imm32 + 7668 # . restore registers + 7669 5a/pop-to-edx + 7670 59/pop-to-ecx + 7671 58/pop-to-eax + 7672 # . epilogue + 7673 89/<- %esp 5/r32/ebp + 7674 5d/pop-to-ebp + 7675 c3/return + 7676 + 7677 next-mu-token: # in: (addr stream byte), out: (addr slice) + 7678 # pseudocode: + 7679 # start: + 7680 # skip-chars-matching-whitespace(in) + 7681 # if in->read >= in->write # end of in + 7682 # out = {0, 0} + 7683 # return + 7684 # out->start = &in->data[in->read] + 7685 # var curr-byte/eax: byte = in->data[in->read] + 7686 # if curr->byte == ',' # comment token + 7687 # ++in->read + 7688 # goto start + 7689 # if curr-byte == '#' # comment + 7690 # goto done # treat as eof + 7691 # if curr-byte == '"' # string literal + 7692 # skip-string(in) + 7693 # goto done # no metadata + 7694 # if curr-byte == '(' 7695 # ++in->read 7696 # goto done - 7697 # # read a word - 7698 # while true - 7699 # if in->read >= in->write - 7700 # break - 7701 # curr-byte = in->data[in->read] - 7702 # if curr-byte == ' ' + 7697 # if curr-byte == ')' + 7698 # ++in->read + 7699 # goto done + 7700 # # read a word + 7701 # while true + 7702 # if in->read >= in->write 7703 # break - 7704 # if curr-byte == '\r' - 7705 # break - 7706 # if curr-byte == '\n' - 7707 # break - 7708 # if curr-byte == '(' - 7709 # break - 7710 # if curr-byte == ')' - 7711 # break - 7712 # if curr-byte == ',' - 7713 # break - 7714 # ++in->read - 7715 # done: - 7716 # out->end = &in->data[in->read] - 7717 # - 7718 # . prologue - 7719 55/push-ebp - 7720 89/<- %ebp 4/r32/esp - 7721 # . save registers - 7722 50/push-eax - 7723 51/push-ecx - 7724 56/push-esi - 7725 57/push-edi - 7726 # esi = in - 7727 8b/-> *(ebp+8) 6/r32/esi - 7728 # edi = out - 7729 8b/-> *(ebp+0xc) 7/r32/edi - 7730 $next-mu-token:start: - 7731 (skip-chars-matching-whitespace %esi) - 7732 $next-mu-token:check0: - 7733 # if (in->read >= in->write) return out = {0, 0} - 7734 # . ecx = in->read - 7735 8b/-> *(esi+4) 1/r32/ecx - 7736 # . if (ecx >= in->write) return out = {0, 0} - 7737 3b/compare<- *esi 1/r32/ecx - 7738 c7 0/subop/copy *edi 0/imm32 - 7739 c7 0/subop/copy *(edi+4) 0/imm32 - 7740 0f 8d/jump-if->= $next-mu-token:end/disp32 - 7741 # out->start = &in->data[in->read] - 7742 8d/copy-address *(esi+ecx+0xc) 0/r32/eax - 7743 89/<- *edi 0/r32/eax - 7744 # var curr-byte/eax: byte = in->data[in->read] - 7745 31/xor-with %eax 0/r32/eax - 7746 8a/copy-byte *(esi+ecx+0xc) 0/r32/AL - 7747 { - 7748 $next-mu-token:check-for-comma: - 7749 # if (curr-byte != ',') break - 7750 3d/compare-eax-and 0x2c/imm32/comma - 7751 75/jump-if-!= break/disp8 - 7752 # ++in->read - 7753 ff 0/subop/increment *(esi+4) - 7754 # restart - 7755 e9/jump $next-mu-token:start/disp32 - 7756 } - 7757 { - 7758 $next-mu-token:check-for-comment: - 7759 # if (curr-byte != '#') break - 7760 3d/compare-eax-and 0x23/imm32/pound - 7761 75/jump-if-!= break/disp8 - 7762 # return eof - 7763 e9/jump $next-mu-token:done/disp32 - 7764 } - 7765 { - 7766 $next-mu-token:check-for-string-literal: - 7767 # if (curr-byte != '"') break - 7768 3d/compare-eax-and 0x22/imm32/dquote - 7769 75/jump-if-!= break/disp8 - 7770 (skip-string %esi) - 7771 # return - 7772 e9/jump $next-mu-token:done/disp32 - 7773 } - 7774 { - 7775 $next-mu-token:check-for-open-paren: - 7776 # if (curr-byte != '(') break - 7777 3d/compare-eax-and 0x28/imm32/open-paren - 7778 75/jump-if-!= break/disp8 - 7779 # ++in->read - 7780 ff 0/subop/increment *(esi+4) - 7781 # return - 7782 e9/jump $next-mu-token:done/disp32 - 7783 } - 7784 { - 7785 $next-mu-token:check-for-close-paren: - 7786 # if (curr-byte != ')') break - 7787 3d/compare-eax-and 0x29/imm32/close-paren - 7788 75/jump-if-!= break/disp8 - 7789 # ++in->read - 7790 ff 0/subop/increment *(esi+4) - 7791 # return - 7792 e9/jump $next-mu-token:done/disp32 - 7793 } - 7794 { - 7795 $next-mu-token:regular-word-without-metadata: - 7796 # if (in->read >= in->write) break - 7797 # . ecx = in->read - 7798 8b/-> *(esi+4) 1/r32/ecx - 7799 # . if (ecx >= in->write) break - 7800 3b/compare<- *esi 1/r32/ecx - 7801 7d/jump-if->= break/disp8 - 7802 # var c/eax: byte = in->data[in->read] - 7803 31/xor-with %eax 0/r32/eax - 7804 8a/copy-byte *(esi+ecx+0xc) 0/r32/AL - 7805 # if (c == ' ') break - 7806 3d/compare-eax-and 0x20/imm32/space - 7807 74/jump-if-= break/disp8 - 7808 # if (c == '\r') break - 7809 3d/compare-eax-and 0xd/imm32/carriage-return + 7704 # curr-byte = in->data[in->read] + 7705 # if curr-byte == ' ' + 7706 # break + 7707 # if curr-byte == '\r' + 7708 # break + 7709 # if curr-byte == '\n' + 7710 # break + 7711 # if curr-byte == '(' + 7712 # break + 7713 # if curr-byte == ')' + 7714 # break + 7715 # if curr-byte == ',' + 7716 # break + 7717 # ++in->read + 7718 # done: + 7719 # out->end = &in->data[in->read] + 7720 # + 7721 # . prologue + 7722 55/push-ebp + 7723 89/<- %ebp 4/r32/esp + 7724 # . save registers + 7725 50/push-eax + 7726 51/push-ecx + 7727 56/push-esi + 7728 57/push-edi + 7729 # esi = in + 7730 8b/-> *(ebp+8) 6/r32/esi + 7731 # edi = out + 7732 8b/-> *(ebp+0xc) 7/r32/edi + 7733 $next-mu-token:start: + 7734 (skip-chars-matching-whitespace %esi) + 7735 $next-mu-token:check0: + 7736 # if (in->read >= in->write) return out = {0, 0} + 7737 # . ecx = in->read + 7738 8b/-> *(esi+4) 1/r32/ecx + 7739 # . if (ecx >= in->write) return out = {0, 0} + 7740 3b/compare<- *esi 1/r32/ecx + 7741 c7 0/subop/copy *edi 0/imm32 + 7742 c7 0/subop/copy *(edi+4) 0/imm32 + 7743 0f 8d/jump-if->= $next-mu-token:end/disp32 + 7744 # out->start = &in->data[in->read] + 7745 8d/copy-address *(esi+ecx+0xc) 0/r32/eax + 7746 89/<- *edi 0/r32/eax + 7747 # var curr-byte/eax: byte = in->data[in->read] + 7748 31/xor-with %eax 0/r32/eax + 7749 8a/copy-byte *(esi+ecx+0xc) 0/r32/AL + 7750 { + 7751 $next-mu-token:check-for-comma: + 7752 # if (curr-byte != ',') break + 7753 3d/compare-eax-and 0x2c/imm32/comma + 7754 75/jump-if-!= break/disp8 + 7755 # ++in->read + 7756 ff 0/subop/increment *(esi+4) + 7757 # restart + 7758 e9/jump $next-mu-token:start/disp32 + 7759 } + 7760 { + 7761 $next-mu-token:check-for-comment: + 7762 # if (curr-byte != '#') break + 7763 3d/compare-eax-and 0x23/imm32/pound + 7764 75/jump-if-!= break/disp8 + 7765 # return eof + 7766 e9/jump $next-mu-token:done/disp32 + 7767 } + 7768 { + 7769 $next-mu-token:check-for-string-literal: + 7770 # if (curr-byte != '"') break + 7771 3d/compare-eax-and 0x22/imm32/dquote + 7772 75/jump-if-!= break/disp8 + 7773 (skip-string %esi) + 7774 # return + 7775 e9/jump $next-mu-token:done/disp32 + 7776 } + 7777 { + 7778 $next-mu-token:check-for-open-paren: + 7779 # if (curr-byte != '(') break + 7780 3d/compare-eax-and 0x28/imm32/open-paren + 7781 75/jump-if-!= break/disp8 + 7782 # ++in->read + 7783 ff 0/subop/increment *(esi+4) + 7784 # return + 7785 e9/jump $next-mu-token:done/disp32 + 7786 } + 7787 { + 7788 $next-mu-token:check-for-close-paren: + 7789 # if (curr-byte != ')') break + 7790 3d/compare-eax-and 0x29/imm32/close-paren + 7791 75/jump-if-!= break/disp8 + 7792 # ++in->read + 7793 ff 0/subop/increment *(esi+4) + 7794 # return + 7795 e9/jump $next-mu-token:done/disp32 + 7796 } + 7797 { + 7798 $next-mu-token:regular-word-without-metadata: + 7799 # if (in->read >= in->write) break + 7800 # . ecx = in->read + 7801 8b/-> *(esi+4) 1/r32/ecx + 7802 # . if (ecx >= in->write) break + 7803 3b/compare<- *esi 1/r32/ecx + 7804 7d/jump-if->= break/disp8 + 7805 # var c/eax: byte = in->data[in->read] + 7806 31/xor-with %eax 0/r32/eax + 7807 8a/copy-byte *(esi+ecx+0xc) 0/r32/AL + 7808 # if (c == ' ') break + 7809 3d/compare-eax-and 0x20/imm32/space 7810 74/jump-if-= break/disp8 - 7811 # if (c == '\n') break - 7812 3d/compare-eax-and 0xa/imm32/newline + 7811 # if (c == '\r') break + 7812 3d/compare-eax-and 0xd/imm32/carriage-return 7813 74/jump-if-= break/disp8 - 7814 # if (c == '(') break - 7815 3d/compare-eax-and 0x28/imm32/open-paren - 7816 0f 84/jump-if-= break/disp32 - 7817 # if (c == ')') break - 7818 3d/compare-eax-and 0x29/imm32/close-paren + 7814 # if (c == '\n') break + 7815 3d/compare-eax-and 0xa/imm32/newline + 7816 74/jump-if-= break/disp8 + 7817 # if (c == '(') break + 7818 3d/compare-eax-and 0x28/imm32/open-paren 7819 0f 84/jump-if-= break/disp32 - 7820 # if (c == ',') break - 7821 3d/compare-eax-and 0x2c/imm32/comma + 7820 # if (c == ')') break + 7821 3d/compare-eax-and 0x29/imm32/close-paren 7822 0f 84/jump-if-= break/disp32 - 7823 # ++in->read - 7824 ff 0/subop/increment *(esi+4) - 7825 # - 7826 e9/jump loop/disp32 - 7827 } - 7828 $next-mu-token:done: - 7829 # out->end = &in->data[in->read] - 7830 8b/-> *(esi+4) 1/r32/ecx - 7831 8d/copy-address *(esi+ecx+0xc) 0/r32/eax - 7832 89/<- *(edi+4) 0/r32/eax - 7833 $next-mu-token:end: - 7834 # . restore registers - 7835 5f/pop-to-edi - 7836 5e/pop-to-esi - 7837 59/pop-to-ecx - 7838 58/pop-to-eax - 7839 # . epilogue - 7840 89/<- %esp 5/r32/ebp - 7841 5d/pop-to-ebp - 7842 c3/return - 7843 - 7844 pos-or-insert-slice: # arr: (addr stream (addr array byte)), s: (addr slice) -> index/eax: int - 7845 # . prologue - 7846 55/push-ebp - 7847 89/<- %ebp 4/r32/esp - 7848 # if (pos-slice(arr, s) != -1) return it - 7849 (pos-slice *(ebp+8) *(ebp+0xc)) # => eax - 7850 3d/compare-eax-and -1/imm32 - 7851 75/jump-if-!= $pos-or-insert-slice:end/disp8 - 7852 $pos-or-insert-slice:insert: - 7853 # var s2/eax: (handle array byte) - 7854 68/push 0/imm32 - 7855 68/push 0/imm32 - 7856 89/<- %eax 4/r32/esp - 7857 (slice-to-string Heap *(ebp+0xc) %eax) - 7858 # throw away alloc-id - 7859 (lookup *eax *(eax+4)) # => eax - 7860 (write-int *(ebp+8) %eax) - 7861 (pos-slice *(ebp+8) *(ebp+0xc)) # => eax - 7862 $pos-or-insert-slice:end: - 7863 # . reclaim locals - 7864 81 0/subop/add %esp 8/imm32 - 7865 # . epilogue - 7866 89/<- %esp 5/r32/ebp - 7867 5d/pop-to-ebp - 7868 c3/return - 7869 - 7870 # return the index in an array of strings matching 's', -1 if not found - 7871 # index is denominated in elements, not bytes - 7872 pos-slice: # arr: (addr stream (addr array byte)), s: (addr slice) -> index/eax: int - 7873 # . prologue - 7874 55/push-ebp - 7875 89/<- %ebp 4/r32/esp - 7876 # . save registers - 7877 51/push-ecx - 7878 52/push-edx - 7879 53/push-ebx - 7880 56/push-esi - 7881 #? (write-buffered Stderr "pos-slice: ") - 7882 #? (write-slice-buffered Stderr *(ebp+0xc)) - 7883 #? (write-buffered Stderr "\n") - 7884 #? (flush Stderr) - 7885 # esi = arr - 7886 8b/-> *(ebp+8) 6/r32/esi - 7887 # var index/ecx: int = 0 - 7888 b9/copy-to-ecx 0/imm32 - 7889 # var curr/edx: (addr (addr array byte)) = arr->data - 7890 8d/copy-address *(esi+0xc) 2/r32/edx - 7891 # var max/ebx: (addr (addr array byte)) = &arr->data[arr->write] - 7892 8b/-> *esi 3/r32/ebx - 7893 8d/copy-address *(esi+ebx+0xc) 3/r32/ebx - 7894 { - 7895 #? (write-buffered Stderr " ") - 7896 #? (write-int32-hex-buffered Stderr %ecx) - 7897 #? (write-buffered Stderr "\n") - 7898 #? (flush Stderr) - 7899 # if (curr >= max) return -1 - 7900 39/compare %edx 3/r32/ebx - 7901 b8/copy-to-eax -1/imm32 - 7902 73/jump-if-addr>= $pos-slice:end/disp8 - 7903 # if (slice-equal?(s, *curr)) break - 7904 (slice-equal? *(ebp+0xc) *edx) # => eax - 7905 3d/compare-eax-and 0/imm32/false - 7906 75/jump-if-!= break/disp8 - 7907 # ++index - 7908 41/increment-ecx - 7909 # curr += 4 - 7910 81 0/subop/add %edx 4/imm32 - 7911 # - 7912 eb/jump loop/disp8 - 7913 } - 7914 # return index - 7915 89/<- %eax 1/r32/ecx - 7916 $pos-slice:end: - 7917 #? (write-buffered Stderr "=> ") - 7918 #? (write-int32-hex-buffered Stderr %eax) - 7919 #? (write-buffered Stderr "\n") - 7920 # . restore registers - 7921 5e/pop-to-esi - 7922 5b/pop-to-ebx - 7923 5a/pop-to-edx - 7924 59/pop-to-ecx - 7925 # . epilogue - 7926 89/<- %esp 5/r32/ebp - 7927 5d/pop-to-ebp - 7928 c3/return - 7929 - 7930 test-parse-var-with-type: - 7931 # . prologue - 7932 55/push-ebp - 7933 89/<- %ebp 4/r32/esp - 7934 # (eax..ecx) = "x:" - 7935 b8/copy-to-eax "x:"/imm32 - 7936 8b/-> *eax 1/r32/ecx - 7937 8d/copy-address *(eax+ecx+4) 1/r32/ecx - 7938 05/add-to-eax 4/imm32 - 7939 # var slice/ecx: slice = {eax, ecx} - 7940 51/push-ecx - 7941 50/push-eax - 7942 89/<- %ecx 4/r32/esp - 7943 # _test-input-stream contains "int" - 7944 (clear-stream _test-input-stream) - 7945 (write _test-input-stream "int") - 7946 # var v/edx: (handle var) - 7947 68/push 0/imm32 - 7948 68/push 0/imm32 - 7949 89/<- %edx 4/r32/esp - 7950 # - 7951 (parse-var-with-type %ecx _test-input-stream %edx Stderr 0) - 7952 # var v-addr/edx: (addr var) = lookup(v) - 7953 (lookup *edx *(edx+4)) # => eax - 7954 89/<- %edx 0/r32/eax - 7955 # check v-addr->name - 7956 (lookup *edx *(edx+4)) # Var-name Var-name => eax - 7957 (check-strings-equal %eax "x" "F - test-parse-var-with-type/name") - 7958 # check v-addr->type - 7959 (lookup *(edx+8) *(edx+0xc)) # Var-type Var-type => eax - 7960 (check-ints-equal *eax 1 "F - test-parse-var-with-type/type:0") # Type-tree-is-atom - 7961 (check-ints-equal *(eax+4) 1 "F - test-parse-var-with-type/type:1") # Type-tree-value - 7962 (check-ints-equal *(eax+0xc) 0 "F - test-parse-var-with-type/type:2") # Type-tree-right - 7963 # . epilogue - 7964 89/<- %esp 5/r32/ebp - 7965 5d/pop-to-ebp - 7966 c3/return - 7967 - 7968 test-parse-var-with-type-and-register: - 7969 # . prologue - 7970 55/push-ebp - 7971 89/<- %ebp 4/r32/esp - 7972 # (eax..ecx) = "x/eax:" - 7973 b8/copy-to-eax "x/eax:"/imm32 - 7974 8b/-> *eax 1/r32/ecx - 7975 8d/copy-address *(eax+ecx+4) 1/r32/ecx - 7976 05/add-to-eax 4/imm32 - 7977 # var slice/ecx: slice = {eax, ecx} - 7978 51/push-ecx - 7979 50/push-eax - 7980 89/<- %ecx 4/r32/esp - 7981 # _test-input-stream contains "int" - 7982 (clear-stream _test-input-stream) - 7983 (write _test-input-stream "int") - 7984 # var v/edx: (handle var) - 7985 68/push 0/imm32 - 7986 68/push 0/imm32 - 7987 89/<- %edx 4/r32/esp - 7988 # - 7989 (parse-var-with-type %ecx _test-input-stream %edx Stderr 0) - 7990 # var v-addr/edx: (addr var) = lookup(v) - 7991 (lookup *edx *(edx+4)) # => eax - 7992 89/<- %edx 0/r32/eax - 7993 # check v-addr->name - 7994 (lookup *edx *(edx+4)) # Var-name Var-name => eax - 7995 (check-strings-equal %eax "x" "F - test-parse-var-with-type-and-register/name") - 7996 # check v-addr->register - 7997 (lookup *(edx+0x18) *(edx+0x1c)) # Var-register Var-register => eax - 7998 (check-strings-equal %eax "eax" "F - test-parse-var-with-type-and-register/register") - 7999 # check v-addr->type - 8000 (lookup *(edx+8) *(edx+0xc)) # Var-type Var-type => eax - 8001 (check-ints-equal *eax 1 "F - test-parse-var-with-type-and-register/type:0") # Type-tree-is-atom - 8002 (check-ints-equal *(eax+4) 1 "F - test-parse-var-with-type-and-register/type:1") # Type-tree-left - 8003 (check-ints-equal *(eax+0xc) 0 "F - test-parse-var-with-type-and-register/type:2") # Type-tree-right - 8004 # . epilogue - 8005 89/<- %esp 5/r32/ebp - 8006 5d/pop-to-ebp - 8007 c3/return - 8008 - 8009 test-parse-var-with-trailing-characters: - 8010 # . prologue - 8011 55/push-ebp - 8012 89/<- %ebp 4/r32/esp - 8013 # (eax..ecx) = "x:" - 8014 b8/copy-to-eax "x:"/imm32 - 8015 8b/-> *eax 1/r32/ecx - 8016 8d/copy-address *(eax+ecx+4) 1/r32/ecx - 8017 05/add-to-eax 4/imm32 - 8018 # var slice/ecx: slice = {eax, ecx} - 8019 51/push-ecx - 8020 50/push-eax - 8021 89/<- %ecx 4/r32/esp - 8022 # _test-input-stream contains "int," - 8023 (clear-stream _test-input-stream) - 8024 (write _test-input-stream "int,") - 8025 # var v/edx: (handle var) - 8026 68/push 0/imm32 - 8027 68/push 0/imm32 - 8028 89/<- %edx 4/r32/esp - 8029 # - 8030 (parse-var-with-type %ecx _test-input-stream %edx Stderr 0) - 8031 # var v-addr/edx: (addr var) = lookup(v) - 8032 (lookup *edx *(edx+4)) # => eax - 8033 89/<- %edx 0/r32/eax - 8034 # check v-addr->name - 8035 (lookup *edx *(edx+4)) # Var-name Var-name => eax - 8036 (check-strings-equal %eax "x" "F - test-parse-var-with-trailing-characters/name") - 8037 # check v-addr->register - 8038 (check-ints-equal *(edx+0x18) 0 "F - test-parse-var-with-trailing-characters/register") # Var-register - 8039 # check v-addr->type - 8040 (lookup *(edx+8) *(edx+0xc)) # Var-type Var-type => eax - 8041 (check-ints-equal *eax 1 "F - test-parse-var-with-trailing-characters/type:0") # Type-tree-is-atom - 8042 (check-ints-equal *(eax+4) 1 "F - test-parse-var-with-trailing-characters/type:1") # Type-tree-left - 8043 (check-ints-equal *(eax+0xc) 0 "F - test-parse-var-with-trailing-characters/type:1") # Type-tree-right - 8044 # . epilogue - 8045 89/<- %esp 5/r32/ebp - 8046 5d/pop-to-ebp - 8047 c3/return - 8048 - 8049 test-parse-var-with-register-and-trailing-characters: - 8050 # . prologue - 8051 55/push-ebp - 8052 89/<- %ebp 4/r32/esp - 8053 # (eax..ecx) = "x/eax:" - 8054 b8/copy-to-eax "x/eax:"/imm32 - 8055 8b/-> *eax 1/r32/ecx - 8056 8d/copy-address *(eax+ecx+4) 1/r32/ecx - 8057 05/add-to-eax 4/imm32 - 8058 # var slice/ecx: slice = {eax, ecx} - 8059 51/push-ecx - 8060 50/push-eax - 8061 89/<- %ecx 4/r32/esp - 8062 # _test-input-stream contains "int," - 8063 (clear-stream _test-input-stream) - 8064 (write _test-input-stream "int,") - 8065 # var v/edx: (handle var) - 8066 68/push 0/imm32 - 8067 68/push 0/imm32 - 8068 89/<- %edx 4/r32/esp - 8069 # - 8070 (parse-var-with-type %ecx _test-input-stream %edx Stderr 0) - 8071 # var v-addr/edx: (addr var) = lookup(v) - 8072 (lookup *edx *(edx+4)) # => eax - 8073 89/<- %edx 0/r32/eax - 8074 # check v-addr->name - 8075 (lookup *edx *(edx+4)) # Var-name Var-name => eax - 8076 (check-strings-equal %eax "x" "F - test-parse-var-with-register-and-trailing-characters/name") - 8077 # check v-addr->register - 8078 (lookup *(edx+0x18) *(edx+0x1c)) # Var-register Var-register => eax - 8079 (check-strings-equal %eax "eax" "F - test-parse-var-with-register-and-trailing-characters/register") - 8080 # check v-addr->type - 8081 (lookup *(edx+8) *(edx+0xc)) # Var-type Var-type => eax - 8082 (check-ints-equal *eax 1 "F - test-parse-var-with-register-and-trailing-characters/type:0") # Type-tree-is-atom - 8083 (check-ints-equal *(eax+4) 1 "F - test-parse-var-with-register-and-trailing-characters/type:1") # Type-tree-left - 8084 (check-ints-equal *(eax+0xc) 0 "F - test-parse-var-with-register-and-trailing-characters/type:2") # Type-tree-right - 8085 # . epilogue - 8086 89/<- %esp 5/r32/ebp - 8087 5d/pop-to-ebp - 8088 c3/return - 8089 - 8090 test-parse-var-with-compound-type: - 8091 # . prologue - 8092 55/push-ebp - 8093 89/<- %ebp 4/r32/esp - 8094 # (eax..ecx) = "x:" - 8095 b8/copy-to-eax "x:"/imm32 - 8096 8b/-> *eax 1/r32/ecx - 8097 8d/copy-address *(eax+ecx+4) 1/r32/ecx - 8098 05/add-to-eax 4/imm32 - 8099 # var slice/ecx: slice = {eax, ecx} - 8100 51/push-ecx - 8101 50/push-eax - 8102 89/<- %ecx 4/r32/esp - 8103 # _test-input-stream contains "(addr int)" - 8104 (clear-stream _test-input-stream) - 8105 (write _test-input-stream "(addr int)") - 8106 # var v/edx: (handle var) - 8107 68/push 0/imm32 - 8108 68/push 0/imm32 - 8109 89/<- %edx 4/r32/esp - 8110 # - 8111 (parse-var-with-type %ecx _test-input-stream %edx Stderr 0) - 8112 # var v-addr/edx: (addr var) = lookup(v) - 8113 (lookup *edx *(edx+4)) # => eax - 8114 89/<- %edx 0/r32/eax - 8115 # check v-addr->name - 8116 (lookup *edx *(edx+4)) # Var-name Var-name => eax - 8117 (check-strings-equal %eax "x" "F - test-parse-var-with-compound-type/name") - 8118 # check v-addr->register - 8119 (check-ints-equal *(edx+0x18) 0 "F - test-parse-var-with-compound-type/register") # Var-register - 8120 # - check v-addr->type - 8121 # var type/edx: (addr type-tree) = var->type - 8122 (lookup *(edx+8) *(edx+0xc)) # Var-type Var-type => eax - 8123 89/<- %edx 0/r32/eax - 8124 # type is a non-atom - 8125 (check-ints-equal *edx 0 "F - test-parse-var-with-compound-type/type:0") # Type-tree-is-atom - 8126 # type->left == atom(addr) - 8127 (lookup *(edx+4) *(edx+8)) # Type-tree-left Type-tree-left => eax - 8128 (check-ints-equal *eax 1 "F - test-parse-var-with-compound-type/type:1") # Type-tree-is-atom - 8129 (check-ints-equal *(eax+4) 2 "F - test-parse-var-with-compound-type/type:2") # Type-tree-value - 8130 # type->right->left == atom(int) - 8131 (lookup *(edx+0xc) *(edx+0x10)) # Type-tree-right Type-tree-right => eax - 8132 (lookup *(eax+4) *(eax+8)) # Type-tree-left Type-tree-left => eax - 8133 (check-ints-equal *eax 1 "F - test-parse-var-with-compound-type/type:3") # Type-tree-is-atom - 8134 (check-ints-equal *(eax+4) 1 "F - test-parse-var-with-compound-type/type:4") # Type-tree-value - 8135 # type->right->right == null - 8136 (check-ints-equal *(eax+0xc) 0 "F - test-parse-var-with-compound-type/type:5") # Type-tree-right - 8137 # . epilogue - 8138 89/<- %esp 5/r32/ebp - 8139 5d/pop-to-ebp - 8140 c3/return - 8141 - 8142 # identifier starts with a letter or '$' or '_' - 8143 # no constraints at the moment on later letters - 8144 # all we really want to do so far is exclude '{', '}' and '->' - 8145 is-identifier?: # in: (addr slice) -> result/eax: boolean - 8146 # . prologue - 8147 55/push-ebp - 8148 89/<- %ebp 4/r32/esp - 8149 # if (slice-empty?(in)) return false - 8150 (slice-empty? *(ebp+8)) # => eax - 8151 3d/compare-eax-and 0/imm32/false - 8152 75/jump-if-!= $is-identifier?:false/disp8 - 8153 # var c/eax: byte = *in->start - 8154 8b/-> *(ebp+8) 0/r32/eax - 8155 8b/-> *eax 0/r32/eax - 8156 8a/copy-byte *eax 0/r32/AL - 8157 81 4/subop/and %eax 0xff/imm32 - 8158 # if (c == '$') return true - 8159 3d/compare-eax-and 0x24/imm32/$ - 8160 74/jump-if-= $is-identifier?:true/disp8 - 8161 # if (c == '_') return true - 8162 3d/compare-eax-and 0x5f/imm32/_ + 7823 # if (c == ',') break + 7824 3d/compare-eax-and 0x2c/imm32/comma + 7825 0f 84/jump-if-= break/disp32 + 7826 # ++in->read + 7827 ff 0/subop/increment *(esi+4) + 7828 # + 7829 e9/jump loop/disp32 + 7830 } + 7831 $next-mu-token:done: + 7832 # out->end = &in->data[in->read] + 7833 8b/-> *(esi+4) 1/r32/ecx + 7834 8d/copy-address *(esi+ecx+0xc) 0/r32/eax + 7835 89/<- *(edi+4) 0/r32/eax + 7836 $next-mu-token:end: + 7837 # . restore registers + 7838 5f/pop-to-edi + 7839 5e/pop-to-esi + 7840 59/pop-to-ecx + 7841 58/pop-to-eax + 7842 # . epilogue + 7843 89/<- %esp 5/r32/ebp + 7844 5d/pop-to-ebp + 7845 c3/return + 7846 + 7847 pos-or-insert-slice: # arr: (addr stream (addr array byte)), s: (addr slice) -> index/eax: int + 7848 # . prologue + 7849 55/push-ebp + 7850 89/<- %ebp 4/r32/esp + 7851 # if (pos-slice(arr, s) != -1) return it + 7852 (pos-slice *(ebp+8) *(ebp+0xc)) # => eax + 7853 3d/compare-eax-and -1/imm32 + 7854 75/jump-if-!= $pos-or-insert-slice:end/disp8 + 7855 $pos-or-insert-slice:insert: + 7856 # var s2/eax: (handle array byte) + 7857 68/push 0/imm32 + 7858 68/push 0/imm32 + 7859 89/<- %eax 4/r32/esp + 7860 (slice-to-string Heap *(ebp+0xc) %eax) + 7861 # throw away alloc-id + 7862 (lookup *eax *(eax+4)) # => eax + 7863 (write-int *(ebp+8) %eax) + 7864 (pos-slice *(ebp+8) *(ebp+0xc)) # => eax + 7865 $pos-or-insert-slice:end: + 7866 # . reclaim locals + 7867 81 0/subop/add %esp 8/imm32 + 7868 # . epilogue + 7869 89/<- %esp 5/r32/ebp + 7870 5d/pop-to-ebp + 7871 c3/return + 7872 + 7873 # return the index in an array of strings matching 's', -1 if not found + 7874 # index is denominated in elements, not bytes + 7875 pos-slice: # arr: (addr stream (addr array byte)), s: (addr slice) -> index/eax: int + 7876 # . prologue + 7877 55/push-ebp + 7878 89/<- %ebp 4/r32/esp + 7879 # . save registers + 7880 51/push-ecx + 7881 52/push-edx + 7882 53/push-ebx + 7883 56/push-esi + 7884 #? (write-buffered Stderr "pos-slice: ") + 7885 #? (write-slice-buffered Stderr *(ebp+0xc)) + 7886 #? (write-buffered Stderr "\n") + 7887 #? (flush Stderr) + 7888 # esi = arr + 7889 8b/-> *(ebp+8) 6/r32/esi + 7890 # var index/ecx: int = 0 + 7891 b9/copy-to-ecx 0/imm32 + 7892 # var curr/edx: (addr (addr array byte)) = arr->data + 7893 8d/copy-address *(esi+0xc) 2/r32/edx + 7894 # var max/ebx: (addr (addr array byte)) = &arr->data[arr->write] + 7895 8b/-> *esi 3/r32/ebx + 7896 8d/copy-address *(esi+ebx+0xc) 3/r32/ebx + 7897 { + 7898 #? (write-buffered Stderr " ") + 7899 #? (write-int32-hex-buffered Stderr %ecx) + 7900 #? (write-buffered Stderr "\n") + 7901 #? (flush Stderr) + 7902 # if (curr >= max) return -1 + 7903 39/compare %edx 3/r32/ebx + 7904 b8/copy-to-eax -1/imm32 + 7905 73/jump-if-addr>= $pos-slice:end/disp8 + 7906 # if (slice-equal?(s, *curr)) break + 7907 (slice-equal? *(ebp+0xc) *edx) # => eax + 7908 3d/compare-eax-and 0/imm32/false + 7909 75/jump-if-!= break/disp8 + 7910 # ++index + 7911 41/increment-ecx + 7912 # curr += 4 + 7913 81 0/subop/add %edx 4/imm32 + 7914 # + 7915 eb/jump loop/disp8 + 7916 } + 7917 # return index + 7918 89/<- %eax 1/r32/ecx + 7919 $pos-slice:end: + 7920 #? (write-buffered Stderr "=> ") + 7921 #? (write-int32-hex-buffered Stderr %eax) + 7922 #? (write-buffered Stderr "\n") + 7923 # . restore registers + 7924 5e/pop-to-esi + 7925 5b/pop-to-ebx + 7926 5a/pop-to-edx + 7927 59/pop-to-ecx + 7928 # . epilogue + 7929 89/<- %esp 5/r32/ebp + 7930 5d/pop-to-ebp + 7931 c3/return + 7932 + 7933 test-parse-var-with-type: + 7934 # . prologue + 7935 55/push-ebp + 7936 89/<- %ebp 4/r32/esp + 7937 # (eax..ecx) = "x:" + 7938 b8/copy-to-eax "x:"/imm32 + 7939 8b/-> *eax 1/r32/ecx + 7940 8d/copy-address *(eax+ecx+4) 1/r32/ecx + 7941 05/add-to-eax 4/imm32 + 7942 # var slice/ecx: slice = {eax, ecx} + 7943 51/push-ecx + 7944 50/push-eax + 7945 89/<- %ecx 4/r32/esp + 7946 # _test-input-stream contains "int" + 7947 (clear-stream _test-input-stream) + 7948 (write _test-input-stream "int") + 7949 # var v/edx: (handle var) + 7950 68/push 0/imm32 + 7951 68/push 0/imm32 + 7952 89/<- %edx 4/r32/esp + 7953 # + 7954 (parse-var-with-type %ecx _test-input-stream %edx Stderr 0) + 7955 # var v-addr/edx: (addr var) = lookup(v) + 7956 (lookup *edx *(edx+4)) # => eax + 7957 89/<- %edx 0/r32/eax + 7958 # check v-addr->name + 7959 (lookup *edx *(edx+4)) # Var-name Var-name => eax + 7960 (check-strings-equal %eax "x" "F - test-parse-var-with-type/name") + 7961 # check v-addr->type + 7962 (lookup *(edx+8) *(edx+0xc)) # Var-type Var-type => eax + 7963 (check-ints-equal *eax 1 "F - test-parse-var-with-type/type:0") # Type-tree-is-atom + 7964 (check-ints-equal *(eax+4) 1 "F - test-parse-var-with-type/type:1") # Type-tree-value + 7965 (check-ints-equal *(eax+0xc) 0 "F - test-parse-var-with-type/type:2") # Type-tree-right + 7966 # . epilogue + 7967 89/<- %esp 5/r32/ebp + 7968 5d/pop-to-ebp + 7969 c3/return + 7970 + 7971 test-parse-var-with-type-and-register: + 7972 # . prologue + 7973 55/push-ebp + 7974 89/<- %ebp 4/r32/esp + 7975 # (eax..ecx) = "x/eax:" + 7976 b8/copy-to-eax "x/eax:"/imm32 + 7977 8b/-> *eax 1/r32/ecx + 7978 8d/copy-address *(eax+ecx+4) 1/r32/ecx + 7979 05/add-to-eax 4/imm32 + 7980 # var slice/ecx: slice = {eax, ecx} + 7981 51/push-ecx + 7982 50/push-eax + 7983 89/<- %ecx 4/r32/esp + 7984 # _test-input-stream contains "int" + 7985 (clear-stream _test-input-stream) + 7986 (write _test-input-stream "int") + 7987 # var v/edx: (handle var) + 7988 68/push 0/imm32 + 7989 68/push 0/imm32 + 7990 89/<- %edx 4/r32/esp + 7991 # + 7992 (parse-var-with-type %ecx _test-input-stream %edx Stderr 0) + 7993 # var v-addr/edx: (addr var) = lookup(v) + 7994 (lookup *edx *(edx+4)) # => eax + 7995 89/<- %edx 0/r32/eax + 7996 # check v-addr->name + 7997 (lookup *edx *(edx+4)) # Var-name Var-name => eax + 7998 (check-strings-equal %eax "x" "F - test-parse-var-with-type-and-register/name") + 7999 # check v-addr->register + 8000 (lookup *(edx+0x18) *(edx+0x1c)) # Var-register Var-register => eax + 8001 (check-strings-equal %eax "eax" "F - test-parse-var-with-type-and-register/register") + 8002 # check v-addr->type + 8003 (lookup *(edx+8) *(edx+0xc)) # Var-type Var-type => eax + 8004 (check-ints-equal *eax 1 "F - test-parse-var-with-type-and-register/type:0") # Type-tree-is-atom + 8005 (check-ints-equal *(eax+4) 1 "F - test-parse-var-with-type-and-register/type:1") # Type-tree-left + 8006 (check-ints-equal *(eax+0xc) 0 "F - test-parse-var-with-type-and-register/type:2") # Type-tree-right + 8007 # . epilogue + 8008 89/<- %esp 5/r32/ebp + 8009 5d/pop-to-ebp + 8010 c3/return + 8011 + 8012 test-parse-var-with-trailing-characters: + 8013 # . prologue + 8014 55/push-ebp + 8015 89/<- %ebp 4/r32/esp + 8016 # (eax..ecx) = "x:" + 8017 b8/copy-to-eax "x:"/imm32 + 8018 8b/-> *eax 1/r32/ecx + 8019 8d/copy-address *(eax+ecx+4) 1/r32/ecx + 8020 05/add-to-eax 4/imm32 + 8021 # var slice/ecx: slice = {eax, ecx} + 8022 51/push-ecx + 8023 50/push-eax + 8024 89/<- %ecx 4/r32/esp + 8025 # _test-input-stream contains "int," + 8026 (clear-stream _test-input-stream) + 8027 (write _test-input-stream "int,") + 8028 # var v/edx: (handle var) + 8029 68/push 0/imm32 + 8030 68/push 0/imm32 + 8031 89/<- %edx 4/r32/esp + 8032 # + 8033 (parse-var-with-type %ecx _test-input-stream %edx Stderr 0) + 8034 # var v-addr/edx: (addr var) = lookup(v) + 8035 (lookup *edx *(edx+4)) # => eax + 8036 89/<- %edx 0/r32/eax + 8037 # check v-addr->name + 8038 (lookup *edx *(edx+4)) # Var-name Var-name => eax + 8039 (check-strings-equal %eax "x" "F - test-parse-var-with-trailing-characters/name") + 8040 # check v-addr->register + 8041 (check-ints-equal *(edx+0x18) 0 "F - test-parse-var-with-trailing-characters/register") # Var-register + 8042 # check v-addr->type + 8043 (lookup *(edx+8) *(edx+0xc)) # Var-type Var-type => eax + 8044 (check-ints-equal *eax 1 "F - test-parse-var-with-trailing-characters/type:0") # Type-tree-is-atom + 8045 (check-ints-equal *(eax+4) 1 "F - test-parse-var-with-trailing-characters/type:1") # Type-tree-left + 8046 (check-ints-equal *(eax+0xc) 0 "F - test-parse-var-with-trailing-characters/type:1") # Type-tree-right + 8047 # . epilogue + 8048 89/<- %esp 5/r32/ebp + 8049 5d/pop-to-ebp + 8050 c3/return + 8051 + 8052 test-parse-var-with-register-and-trailing-characters: + 8053 # . prologue + 8054 55/push-ebp + 8055 89/<- %ebp 4/r32/esp + 8056 # (eax..ecx) = "x/eax:" + 8057 b8/copy-to-eax "x/eax:"/imm32 + 8058 8b/-> *eax 1/r32/ecx + 8059 8d/copy-address *(eax+ecx+4) 1/r32/ecx + 8060 05/add-to-eax 4/imm32 + 8061 # var slice/ecx: slice = {eax, ecx} + 8062 51/push-ecx + 8063 50/push-eax + 8064 89/<- %ecx 4/r32/esp + 8065 # _test-input-stream contains "int," + 8066 (clear-stream _test-input-stream) + 8067 (write _test-input-stream "int,") + 8068 # var v/edx: (handle var) + 8069 68/push 0/imm32 + 8070 68/push 0/imm32 + 8071 89/<- %edx 4/r32/esp + 8072 # + 8073 (parse-var-with-type %ecx _test-input-stream %edx Stderr 0) + 8074 # var v-addr/edx: (addr var) = lookup(v) + 8075 (lookup *edx *(edx+4)) # => eax + 8076 89/<- %edx 0/r32/eax + 8077 # check v-addr->name + 8078 (lookup *edx *(edx+4)) # Var-name Var-name => eax + 8079 (check-strings-equal %eax "x" "F - test-parse-var-with-register-and-trailing-characters/name") + 8080 # check v-addr->register + 8081 (lookup *(edx+0x18) *(edx+0x1c)) # Var-register Var-register => eax + 8082 (check-strings-equal %eax "eax" "F - test-parse-var-with-register-and-trailing-characters/register") + 8083 # check v-addr->type + 8084 (lookup *(edx+8) *(edx+0xc)) # Var-type Var-type => eax + 8085 (check-ints-equal *eax 1 "F - test-parse-var-with-register-and-trailing-characters/type:0") # Type-tree-is-atom + 8086 (check-ints-equal *(eax+4) 1 "F - test-parse-var-with-register-and-trailing-characters/type:1") # Type-tree-left + 8087 (check-ints-equal *(eax+0xc) 0 "F - test-parse-var-with-register-and-trailing-characters/type:2") # Type-tree-right + 8088 # . epilogue + 8089 89/<- %esp 5/r32/ebp + 8090 5d/pop-to-ebp + 8091 c3/return + 8092 + 8093 test-parse-var-with-compound-type: + 8094 # . prologue + 8095 55/push-ebp + 8096 89/<- %ebp 4/r32/esp + 8097 # (eax..ecx) = "x:" + 8098 b8/copy-to-eax "x:"/imm32 + 8099 8b/-> *eax 1/r32/ecx + 8100 8d/copy-address *(eax+ecx+4) 1/r32/ecx + 8101 05/add-to-eax 4/imm32 + 8102 # var slice/ecx: slice = {eax, ecx} + 8103 51/push-ecx + 8104 50/push-eax + 8105 89/<- %ecx 4/r32/esp + 8106 # _test-input-stream contains "(addr int)" + 8107 (clear-stream _test-input-stream) + 8108 (write _test-input-stream "(addr int)") + 8109 # var v/edx: (handle var) + 8110 68/push 0/imm32 + 8111 68/push 0/imm32 + 8112 89/<- %edx 4/r32/esp + 8113 # + 8114 (parse-var-with-type %ecx _test-input-stream %edx Stderr 0) + 8115 # var v-addr/edx: (addr var) = lookup(v) + 8116 (lookup *edx *(edx+4)) # => eax + 8117 89/<- %edx 0/r32/eax + 8118 # check v-addr->name + 8119 (lookup *edx *(edx+4)) # Var-name Var-name => eax + 8120 (check-strings-equal %eax "x" "F - test-parse-var-with-compound-type/name") + 8121 # check v-addr->register + 8122 (check-ints-equal *(edx+0x18) 0 "F - test-parse-var-with-compound-type/register") # Var-register + 8123 # - check v-addr->type + 8124 # var type/edx: (addr type-tree) = var->type + 8125 (lookup *(edx+8) *(edx+0xc)) # Var-type Var-type => eax + 8126 89/<- %edx 0/r32/eax + 8127 # type is a non-atom + 8128 (check-ints-equal *edx 0 "F - test-parse-var-with-compound-type/type:0") # Type-tree-is-atom + 8129 # type->left == atom(addr) + 8130 (lookup *(edx+4) *(edx+8)) # Type-tree-left Type-tree-left => eax + 8131 (check-ints-equal *eax 1 "F - test-parse-var-with-compound-type/type:1") # Type-tree-is-atom + 8132 (check-ints-equal *(eax+4) 2 "F - test-parse-var-with-compound-type/type:2") # Type-tree-value + 8133 # type->right->left == atom(int) + 8134 (lookup *(edx+0xc) *(edx+0x10)) # Type-tree-right Type-tree-right => eax + 8135 (lookup *(eax+4) *(eax+8)) # Type-tree-left Type-tree-left => eax + 8136 (check-ints-equal *eax 1 "F - test-parse-var-with-compound-type/type:3") # Type-tree-is-atom + 8137 (check-ints-equal *(eax+4) 1 "F - test-parse-var-with-compound-type/type:4") # Type-tree-value + 8138 # type->right->right == null + 8139 (check-ints-equal *(eax+0xc) 0 "F - test-parse-var-with-compound-type/type:5") # Type-tree-right + 8140 # . epilogue + 8141 89/<- %esp 5/r32/ebp + 8142 5d/pop-to-ebp + 8143 c3/return + 8144 + 8145 # identifier starts with a letter or '$' or '_' + 8146 # no constraints at the moment on later letters + 8147 # all we really want to do so far is exclude '{', '}' and '->' + 8148 is-identifier?: # in: (addr slice) -> result/eax: boolean + 8149 # . prologue + 8150 55/push-ebp + 8151 89/<- %ebp 4/r32/esp + 8152 # if (slice-empty?(in)) return false + 8153 (slice-empty? *(ebp+8)) # => eax + 8154 3d/compare-eax-and 0/imm32/false + 8155 75/jump-if-!= $is-identifier?:false/disp8 + 8156 # var c/eax: byte = *in->start + 8157 8b/-> *(ebp+8) 0/r32/eax + 8158 8b/-> *eax 0/r32/eax + 8159 8a/copy-byte *eax 0/r32/AL + 8160 81 4/subop/and %eax 0xff/imm32 + 8161 # if (c == '$') return true + 8162 3d/compare-eax-and 0x24/imm32/$ 8163 74/jump-if-= $is-identifier?:true/disp8 - 8164 # drop case - 8165 25/and-eax-with 0x5f/imm32 - 8166 # if (c < 'A') return false - 8167 3d/compare-eax-and 0x41/imm32/A - 8168 7c/jump-if-< $is-identifier?:false/disp8 - 8169 # if (c > 'Z') return false - 8170 3d/compare-eax-and 0x5a/imm32/Z - 8171 7f/jump-if-> $is-identifier?:false/disp8 - 8172 # otherwise return true - 8173 $is-identifier?:true: - 8174 b8/copy-to-eax 1/imm32/true - 8175 eb/jump $is-identifier?:end/disp8 - 8176 $is-identifier?:false: - 8177 b8/copy-to-eax 0/imm32/false - 8178 $is-identifier?:end: - 8179 # . epilogue - 8180 89/<- %esp 5/r32/ebp - 8181 5d/pop-to-ebp - 8182 c3/return - 8183 - 8184 test-is-identifier-dollar: - 8185 # . prologue - 8186 55/push-ebp - 8187 89/<- %ebp 4/r32/esp - 8188 # (eax..ecx) = "$a" - 8189 b8/copy-to-eax "$a"/imm32 - 8190 8b/-> *eax 1/r32/ecx - 8191 8d/copy-address *(eax+ecx+4) 1/r32/ecx - 8192 05/add-to-eax 4/imm32 - 8193 # var slice/ecx: slice = {eax, ecx} - 8194 51/push-ecx - 8195 50/push-eax - 8196 89/<- %ecx 4/r32/esp - 8197 # - 8198 (is-identifier? %ecx) - 8199 (check-ints-equal %eax 1 "F - test-is-identifier-dollar") - 8200 # . epilogue - 8201 89/<- %esp 5/r32/ebp - 8202 5d/pop-to-ebp - 8203 c3/return - 8204 - 8205 test-is-identifier-underscore: - 8206 # . prologue - 8207 55/push-ebp - 8208 89/<- %ebp 4/r32/esp - 8209 # (eax..ecx) = "_a" - 8210 b8/copy-to-eax "_a"/imm32 - 8211 8b/-> *eax 1/r32/ecx - 8212 8d/copy-address *(eax+ecx+4) 1/r32/ecx - 8213 05/add-to-eax 4/imm32 - 8214 # var slice/ecx: slice = {eax, ecx} - 8215 51/push-ecx - 8216 50/push-eax - 8217 89/<- %ecx 4/r32/esp - 8218 # - 8219 (is-identifier? %ecx) - 8220 (check-ints-equal %eax 1 "F - test-is-identifier-underscore") - 8221 # . epilogue - 8222 89/<- %esp 5/r32/ebp - 8223 5d/pop-to-ebp - 8224 c3/return - 8225 - 8226 test-is-identifier-a: - 8227 # . prologue - 8228 55/push-ebp - 8229 89/<- %ebp 4/r32/esp - 8230 # (eax..ecx) = "a$" - 8231 b8/copy-to-eax "a$"/imm32 - 8232 8b/-> *eax 1/r32/ecx - 8233 8d/copy-address *(eax+ecx+4) 1/r32/ecx - 8234 05/add-to-eax 4/imm32 - 8235 # var slice/ecx: slice = {eax, ecx} - 8236 51/push-ecx - 8237 50/push-eax - 8238 89/<- %ecx 4/r32/esp - 8239 # - 8240 (is-identifier? %ecx) - 8241 (check-ints-equal %eax 1 "F - test-is-identifier-a") - 8242 # . epilogue - 8243 89/<- %esp 5/r32/ebp - 8244 5d/pop-to-ebp - 8245 c3/return - 8246 - 8247 test-is-identifier-z: - 8248 # . prologue - 8249 55/push-ebp - 8250 89/<- %ebp 4/r32/esp - 8251 # (eax..ecx) = "z$" - 8252 b8/copy-to-eax "z$"/imm32 - 8253 8b/-> *eax 1/r32/ecx - 8254 8d/copy-address *(eax+ecx+4) 1/r32/ecx - 8255 05/add-to-eax 4/imm32 - 8256 # var slice/ecx: slice = {eax, ecx} - 8257 51/push-ecx - 8258 50/push-eax - 8259 89/<- %ecx 4/r32/esp - 8260 # - 8261 (is-identifier? %ecx) - 8262 (check-ints-equal %eax 1 "F - test-is-identifier-z") - 8263 # . epilogue - 8264 89/<- %esp 5/r32/ebp - 8265 5d/pop-to-ebp - 8266 c3/return - 8267 - 8268 test-is-identifier-A: - 8269 # . prologue - 8270 55/push-ebp - 8271 89/<- %ebp 4/r32/esp - 8272 # (eax..ecx) = "A$" - 8273 b8/copy-to-eax "A$"/imm32 - 8274 8b/-> *eax 1/r32/ecx - 8275 8d/copy-address *(eax+ecx+4) 1/r32/ecx - 8276 05/add-to-eax 4/imm32 - 8277 # var slice/ecx: slice = {eax, ecx} - 8278 51/push-ecx - 8279 50/push-eax - 8280 89/<- %ecx 4/r32/esp - 8281 # - 8282 (is-identifier? %ecx) - 8283 (check-ints-equal %eax 1 "F - test-is-identifier-A") - 8284 # . epilogue - 8285 89/<- %esp 5/r32/ebp - 8286 5d/pop-to-ebp - 8287 c3/return - 8288 - 8289 test-is-identifier-Z: - 8290 # . prologue - 8291 55/push-ebp - 8292 89/<- %ebp 4/r32/esp - 8293 # (eax..ecx) = "Z$" - 8294 b8/copy-to-eax "Z$"/imm32 - 8295 8b/-> *eax 1/r32/ecx - 8296 8d/copy-address *(eax+ecx+4) 1/r32/ecx - 8297 05/add-to-eax 4/imm32 - 8298 # var slice/ecx: slice = {eax, ecx} - 8299 51/push-ecx - 8300 50/push-eax - 8301 89/<- %ecx 4/r32/esp - 8302 # - 8303 (is-identifier? %ecx) - 8304 (check-ints-equal %eax 1 "F - test-is-identifier-Z") - 8305 # . epilogue - 8306 89/<- %esp 5/r32/ebp - 8307 5d/pop-to-ebp - 8308 c3/return - 8309 - 8310 test-is-identifier-at: - 8311 # character before 'A' is invalid - 8312 # . prologue - 8313 55/push-ebp - 8314 89/<- %ebp 4/r32/esp - 8315 # (eax..ecx) = "@a" - 8316 b8/copy-to-eax "@a"/imm32 - 8317 8b/-> *eax 1/r32/ecx - 8318 8d/copy-address *(eax+ecx+4) 1/r32/ecx - 8319 05/add-to-eax 4/imm32 - 8320 # var slice/ecx: slice = {eax, ecx} - 8321 51/push-ecx - 8322 50/push-eax - 8323 89/<- %ecx 4/r32/esp - 8324 # - 8325 (is-identifier? %ecx) - 8326 (check-ints-equal %eax 0 "F - test-is-identifier-@") - 8327 # . epilogue - 8328 89/<- %esp 5/r32/ebp - 8329 5d/pop-to-ebp - 8330 c3/return - 8331 - 8332 test-is-identifier-square-bracket: - 8333 # character after 'Z' is invalid - 8334 # . prologue - 8335 55/push-ebp - 8336 89/<- %ebp 4/r32/esp - 8337 # (eax..ecx) = "[a" - 8338 b8/copy-to-eax "[a"/imm32 - 8339 8b/-> *eax 1/r32/ecx - 8340 8d/copy-address *(eax+ecx+4) 1/r32/ecx - 8341 05/add-to-eax 4/imm32 - 8342 # var slice/ecx: slice = {eax, ecx} - 8343 51/push-ecx - 8344 50/push-eax - 8345 89/<- %ecx 4/r32/esp - 8346 # - 8347 (is-identifier? %ecx) - 8348 (check-ints-equal %eax 0 "F - test-is-identifier-@") - 8349 # . epilogue - 8350 89/<- %esp 5/r32/ebp - 8351 5d/pop-to-ebp - 8352 c3/return - 8353 - 8354 test-is-identifier-backtick: - 8355 # character before 'a' is invalid - 8356 # . prologue - 8357 55/push-ebp - 8358 89/<- %ebp 4/r32/esp - 8359 # (eax..ecx) = "`a" - 8360 b8/copy-to-eax "`a"/imm32 - 8361 8b/-> *eax 1/r32/ecx - 8362 8d/copy-address *(eax+ecx+4) 1/r32/ecx - 8363 05/add-to-eax 4/imm32 - 8364 # var slice/ecx: slice = {eax, ecx} - 8365 51/push-ecx - 8366 50/push-eax - 8367 89/<- %ecx 4/r32/esp - 8368 # - 8369 (is-identifier? %ecx) - 8370 (check-ints-equal %eax 0 "F - test-is-identifier-backtick") - 8371 # . epilogue - 8372 89/<- %esp 5/r32/ebp - 8373 5d/pop-to-ebp - 8374 c3/return - 8375 - 8376 test-is-identifier-curly-brace-open: - 8377 # character after 'z' is invalid; also used for blocks - 8378 # . prologue - 8379 55/push-ebp - 8380 89/<- %ebp 4/r32/esp - 8381 # (eax..ecx) = "{a" - 8382 b8/copy-to-eax "{a"/imm32 - 8383 8b/-> *eax 1/r32/ecx - 8384 8d/copy-address *(eax+ecx+4) 1/r32/ecx - 8385 05/add-to-eax 4/imm32 - 8386 # var slice/ecx: slice = {eax, ecx} - 8387 51/push-ecx - 8388 50/push-eax - 8389 89/<- %ecx 4/r32/esp - 8390 # - 8391 (is-identifier? %ecx) - 8392 (check-ints-equal %eax 0 "F - test-is-identifier-curly-brace-open") - 8393 # . epilogue - 8394 89/<- %esp 5/r32/ebp - 8395 5d/pop-to-ebp - 8396 c3/return - 8397 - 8398 test-is-identifier-curly-brace-close: - 8399 # . prologue - 8400 55/push-ebp - 8401 89/<- %ebp 4/r32/esp - 8402 # (eax..ecx) = "}a" - 8403 b8/copy-to-eax "}a"/imm32 - 8404 8b/-> *eax 1/r32/ecx - 8405 8d/copy-address *(eax+ecx+4) 1/r32/ecx - 8406 05/add-to-eax 4/imm32 - 8407 # var slice/ecx: slice = {eax, ecx} - 8408 51/push-ecx - 8409 50/push-eax - 8410 89/<- %ecx 4/r32/esp - 8411 # - 8412 (is-identifier? %ecx) - 8413 (check-ints-equal %eax 0 "F - test-is-identifier-curly-brace-close") - 8414 # . epilogue - 8415 89/<- %esp 5/r32/ebp - 8416 5d/pop-to-ebp - 8417 c3/return - 8418 - 8419 test-is-identifier-hyphen: - 8420 # disallow leading '-' since '->' has special meaning - 8421 # . prologue - 8422 55/push-ebp - 8423 89/<- %ebp 4/r32/esp - 8424 # (eax..ecx) = "-a" - 8425 b8/copy-to-eax "-a"/imm32 - 8426 8b/-> *eax 1/r32/ecx - 8427 8d/copy-address *(eax+ecx+4) 1/r32/ecx - 8428 05/add-to-eax 4/imm32 - 8429 # var slice/ecx: slice = {eax, ecx} - 8430 51/push-ecx - 8431 50/push-eax - 8432 89/<- %ecx 4/r32/esp - 8433 # - 8434 (is-identifier? %ecx) - 8435 (check-ints-equal %eax 0 "F - test-is-identifier-hyphen") - 8436 # . epilogue - 8437 89/<- %esp 5/r32/ebp - 8438 5d/pop-to-ebp - 8439 c3/return - 8440 - 8441 populate-mu-function-body: # in: (addr buffered-file), out: (addr function), vars: (addr stack live-var), err: (addr buffered-file), ed: (addr exit-descriptor) - 8442 # . prologue - 8443 55/push-ebp - 8444 89/<- %ebp 4/r32/esp - 8445 # . save registers - 8446 50/push-eax - 8447 56/push-esi - 8448 57/push-edi - 8449 # esi = in - 8450 8b/-> *(ebp+8) 6/r32/esi - 8451 # edi = out - 8452 8b/-> *(ebp+0xc) 7/r32/edi - 8453 # initialize some global state - 8454 c7 0/subop/copy *Curr-block-depth 1/imm32 - 8455 # parse-mu-block(in, vars, out, out->body) - 8456 8d/copy-address *(edi+0x18) 0/r32/eax # Function-body - 8457 (parse-mu-block %esi *(ebp+0x10) %edi %eax *(ebp+0x14) *(ebp+0x18)) - 8458 $populate-mu-function-body:end: - 8459 # . restore registers - 8460 5f/pop-to-edi - 8461 5e/pop-to-esi - 8462 58/pop-to-eax - 8463 # . epilogue - 8464 89/<- %esp 5/r32/ebp - 8465 5d/pop-to-ebp - 8466 c3/return - 8467 - 8468 # parses a block, assuming that the leading '{' has already been read by the caller - 8469 parse-mu-block: # in: (addr buffered-file), vars: (addr stack live-var), fn: (addr function), out: (addr handle block), err: (addr buffered-file), ed: (addr exit-descriptor) - 8470 # pseudocode: - 8471 # var line: (stream byte 512) - 8472 # var word-slice: slice - 8473 # allocate(Heap, Stmt-size, out) - 8474 # var out-addr: (addr block) = lookup(*out) - 8475 # out-addr->tag = 0/block - 8476 # out-addr->var = some unique name - 8477 # push(vars, {out-addr->var, false}) - 8478 # while true # line loop - 8479 # clear-stream(line) - 8480 # read-line-buffered(in, line) - 8481 # if (line->write == 0) break # end of file - 8482 # word-slice = next-mu-token(line) - 8483 # if slice-empty?(word-slice) # end of line - 8484 # continue - 8485 # else if slice-starts-with?(word-slice, "#") - 8486 # continue - 8487 # else if slice-equal?(word-slice, "{") - 8488 # assert(no-tokens-in(line)) - 8489 # block = parse-mu-block(in, vars, fn) - 8490 # append-to-block(out-addr, block) - 8491 # else if slice-equal?(word-slice, "}") - 8492 # break - 8493 # else if slice-ends-with?(word-slice, ":") - 8494 # # TODO: error-check the rest of 'line' - 8495 # --word-slice->end to skip ':' - 8496 # named-block = parse-mu-named-block(word-slice, in, vars, fn) - 8497 # append-to-block(out-addr, named-block) - 8498 # else if slice-equal?(word-slice, "var") - 8499 # var-def = parse-mu-var-def(line, vars, fn) - 8500 # append-to-block(out-addr, var-def) - 8501 # else - 8502 # stmt = parse-mu-stmt(line, vars, fn) - 8503 # append-to-block(out-addr, stmt) - 8504 # pop(vars) - 8505 # - 8506 # . prologue - 8507 55/push-ebp - 8508 89/<- %ebp 4/r32/esp - 8509 # . save registers - 8510 50/push-eax - 8511 51/push-ecx - 8512 52/push-edx - 8513 53/push-ebx - 8514 57/push-edi - 8515 # var line/ecx: (stream byte 512) - 8516 81 5/subop/subtract %esp 0x200/imm32 - 8517 68/push 0x200/imm32/size - 8518 68/push 0/imm32/read - 8519 68/push 0/imm32/write - 8520 89/<- %ecx 4/r32/esp - 8521 # var word-slice/edx: slice - 8522 68/push 0/imm32/end - 8523 68/push 0/imm32/start - 8524 89/<- %edx 4/r32/esp - 8525 # allocate into out - 8526 (allocate Heap *Stmt-size *(ebp+0x14)) - 8527 # var out-addr/edi: (addr block) = lookup(*out) - 8528 8b/-> *(ebp+0x14) 7/r32/edi - 8529 (lookup *edi *(edi+4)) # => eax - 8530 89/<- %edi 0/r32/eax - 8531 # out-addr->tag is 0 (block) by default - 8532 # set out-addr->var - 8533 8d/copy-address *(edi+0xc) 0/r32/eax # Block-var - 8534 (new-block-name *(ebp+0x10) %eax) - 8535 # push(vars, out-addr->var) - 8536 (push *(ebp+0xc) *(edi+0xc)) # Block-var - 8537 (push *(ebp+0xc) *(edi+0x10)) # Block-var - 8538 (push *(ebp+0xc) 0) # false - 8539 # increment *Curr-block-depth - 8540 ff 0/subop/increment *Curr-block-depth - 8541 { - 8542 $parse-mu-block:line-loop: - 8543 # line = read-line-buffered(in) - 8544 (clear-stream %ecx) - 8545 (read-line-buffered *(ebp+8) %ecx) - 8546 #? (write-buffered Stderr "line: ") - 8547 #? (write-stream-data Stderr %ecx) - 8548 #? #? (write-buffered Stderr Newline) # line has its own newline - 8549 #? (flush Stderr) - 8550 #? (rewind-stream %ecx) - 8551 # if (line->write == 0) break - 8552 81 7/subop/compare *ecx 0/imm32 - 8553 0f 84/jump-if-= break/disp32 - 8554 #? (write-buffered Stderr "vars:\n") - 8555 #? (dump-vars *(ebp+0xc)) - 8556 # word-slice = next-mu-token(line) - 8557 (next-mu-token %ecx %edx) - 8558 #? (write-buffered Stderr "word: ") - 8559 #? (write-slice-buffered Stderr %edx) - 8560 #? (write-buffered Stderr Newline) - 8561 #? (flush Stderr) - 8562 # if slice-empty?(word-slice) continue - 8563 (slice-empty? %edx) - 8564 3d/compare-eax-and 0/imm32/false - 8565 0f 85/jump-if-!= loop/disp32 - 8566 # if (slice-starts-with?(word-slice, '#') continue - 8567 # . eax = *word-slice->start - 8568 8b/-> *edx 0/r32/eax - 8569 8a/copy-byte *eax 0/r32/AL - 8570 81 4/subop/and %eax 0xff/imm32 - 8571 # . if (eax == '#') continue - 8572 3d/compare-eax-and 0x23/imm32/hash - 8573 0f 84/jump-if-= loop/disp32 - 8574 # if slice-equal?(word-slice, "{") - 8575 { - 8576 $parse-mu-block:check-for-block: - 8577 (slice-equal? %edx "{") - 8578 3d/compare-eax-and 0/imm32/false - 8579 74/jump-if-= break/disp8 - 8580 (check-no-tokens-left %ecx) - 8581 # parse new block and append - 8582 # . var tmp/eax: (handle block) - 8583 68/push 0/imm32 - 8584 68/push 0/imm32 - 8585 89/<- %eax 4/r32/esp - 8586 # . - 8587 (parse-mu-block *(ebp+8) *(ebp+0xc) *(ebp+0x10) %eax *(ebp+0x18) *(ebp+0x1c)) - 8588 (append-to-block Heap %edi *eax *(eax+4)) - 8589 # . reclaim tmp - 8590 81 0/subop/add %esp 8/imm32 - 8591 # . - 8592 e9/jump $parse-mu-block:line-loop/disp32 - 8593 } - 8594 # if slice-equal?(word-slice, "}") break - 8595 $parse-mu-block:check-for-end: - 8596 (slice-equal? %edx "}") - 8597 3d/compare-eax-and 0/imm32/false - 8598 0f 85/jump-if-!= break/disp32 - 8599 # if slice-ends-with?(word-slice, ":") parse named block and append - 8600 { - 8601 $parse-mu-block:check-for-named-block: - 8602 # . eax = *(word-slice->end-1) - 8603 8b/-> *(edx+4) 0/r32/eax - 8604 48/decrement-eax - 8605 8a/copy-byte *eax 0/r32/AL - 8606 81 4/subop/and %eax 0xff/imm32 - 8607 # . if (eax != ':') break - 8608 3d/compare-eax-and 0x3a/imm32/colon - 8609 0f 85/jump-if-!= break/disp32 - 8610 # TODO: error-check the rest of 'line' - 8611 # - 8612 # skip ':' - 8613 ff 1/subop/decrement *(edx+4) # Slice-end - 8614 # var tmp/eax: (handle block) - 8615 68/push 0/imm32 - 8616 68/push 0/imm32 - 8617 89/<- %eax 4/r32/esp - 8618 # - 8619 (parse-mu-named-block %edx *(ebp+8) *(ebp+0xc) *(ebp+0x10) %eax *(ebp+0x18) *(ebp+0x1c)) - 8620 (append-to-block Heap %edi *eax *(eax+4)) - 8621 # reclaim tmp - 8622 81 0/subop/add %esp 8/imm32 - 8623 # - 8624 e9/jump $parse-mu-block:line-loop/disp32 - 8625 } - 8626 # if slice-equal?(word-slice, "var") - 8627 { - 8628 $parse-mu-block:check-for-var: - 8629 (slice-equal? %edx "var") - 8630 3d/compare-eax-and 0/imm32/false - 8631 74/jump-if-= break/disp8 - 8632 # var tmp/eax: (handle block) - 8633 68/push 0/imm32 - 8634 68/push 0/imm32 - 8635 89/<- %eax 4/r32/esp - 8636 # - 8637 (parse-mu-var-def %ecx *(ebp+0xc) %eax *(ebp+0x10) *(ebp+0x18) *(ebp+0x1c)) - 8638 (append-to-block Heap %edi *eax *(eax+4)) - 8639 # reclaim tmp - 8640 81 0/subop/add %esp 8/imm32 - 8641 # - 8642 e9/jump $parse-mu-block:line-loop/disp32 - 8643 } - 8644 $parse-mu-block:regular-stmt: - 8645 # otherwise - 8646 # var tmp/eax: (handle block) - 8647 68/push 0/imm32 - 8648 68/push 0/imm32 - 8649 89/<- %eax 4/r32/esp - 8650 # - 8651 (parse-mu-stmt %ecx *(ebp+0xc) *(ebp+0x10) %eax *(ebp+0x18) *(ebp+0x1c)) - 8652 (append-to-block Heap %edi *eax *(eax+4)) - 8653 # reclaim tmp - 8654 81 0/subop/add %esp 8/imm32 - 8655 # - 8656 e9/jump loop/disp32 - 8657 } # end line loop - 8658 (clean-up-blocks *(ebp+0xc) *Curr-block-depth *(ebp+0x10)) - 8659 # decrement *Curr-block-depth - 8660 ff 1/subop/decrement *Curr-block-depth - 8661 # pop(vars) - 8662 (pop *(ebp+0xc)) # => eax - 8663 (pop *(ebp+0xc)) # => eax - 8664 (pop *(ebp+0xc)) # => eax - 8665 $parse-mu-block:end: - 8666 # . reclaim locals - 8667 81 0/subop/add %esp 0x214/imm32 - 8668 # . restore registers - 8669 5f/pop-to-edi - 8670 5b/pop-to-ebx - 8671 5a/pop-to-edx - 8672 59/pop-to-ecx - 8673 58/pop-to-eax - 8674 # . epilogue - 8675 89/<- %esp 5/r32/ebp - 8676 5d/pop-to-ebp - 8677 c3/return - 8678 - 8679 $parse-mu-block:abort: - 8680 # error("'{' or '}' should be on its own line, but got '") - 8681 (write-buffered *(ebp+0x18) "'{' or '}' should be on its own line, but got '") - 8682 (rewind-stream %ecx) - 8683 (write-stream-data *(ebp+0x18) %ecx) - 8684 (write-buffered *(ebp+0x18) "'\n") - 8685 (flush *(ebp+0x18)) - 8686 (stop *(ebp+0x1c) 1) - 8687 # never gets here - 8688 - 8689 new-block-name: # fn: (addr function), out: (addr handle var) - 8690 # . prologue - 8691 55/push-ebp - 8692 89/<- %ebp 4/r32/esp - 8693 # . save registers - 8694 50/push-eax - 8695 51/push-ecx - 8696 52/push-edx - 8697 # var n/ecx: int = len(fn->name) + 10 for an int + 2 for '$:' - 8698 8b/-> *(ebp+8) 0/r32/eax - 8699 (lookup *eax *(eax+4)) # Function-name Function-name => eax - 8700 8b/-> *eax 0/r32/eax # String-size - 8701 05/add-to-eax 0xd/imm32 # 10 + 2 for '$:' - 8702 89/<- %ecx 0/r32/eax - 8703 # var name/edx: (stream byte n) - 8704 29/subtract-from %esp 1/r32/ecx - 8705 ff 6/subop/push %ecx - 8706 68/push 0/imm32/read - 8707 68/push 0/imm32/write - 8708 89/<- %edx 4/r32/esp - 8709 (clear-stream %edx) - 8710 # eax = fn->name - 8711 8b/-> *(ebp+8) 0/r32/eax - 8712 (lookup *eax *(eax+4)) # Function-name Function-name => eax - 8713 # construct result using Next-block-index (and increment it) - 8714 (write %edx "$") - 8715 (write %edx %eax) - 8716 (write %edx ":") - 8717 (write-int32-hex %edx *Next-block-index) - 8718 ff 0/subop/increment *Next-block-index - 8719 # var s/eax: slice = {name->data, name->data + name->write} (clobbering edx) - 8720 # . eax = name->write - 8721 8b/-> *edx 0/r32/eax - 8722 # . edx = name->data - 8723 8d/copy-address *(edx+0xc) 2/r32/edx - 8724 # . eax = name->write + name->data - 8725 01/add-to %eax 2/r32/edx - 8726 # . push {edx, eax} - 8727 ff 6/subop/push %eax - 8728 ff 6/subop/push %edx - 8729 89/<- %eax 4/r32/esp - 8730 # out = new literal(s) - 8731 (new-literal Heap %eax *(ebp+0xc)) - 8732 #? 8b/-> *(ebp+0xc) 0/r32/eax - 8733 #? (write-buffered Stderr "type allocid in caller after new-literal: ") - 8734 #? (write-int32-hex-buffered Stderr *(eax+8)) - 8735 #? (write-buffered Stderr " for var ") - 8736 #? (write-int32-hex-buffered Stderr %eax) - 8737 #? (write-buffered Stderr Newline) - 8738 #? (flush Stderr) - 8739 $new-block-name:end: - 8740 # . reclaim locals - 8741 81 0/subop/add %ecx 0xc/imm32 # name.{read/write/len} - 8742 81 0/subop/add %ecx 8/imm32 # slice - 8743 01/add-to %esp 1/r32/ecx - 8744 # . restore registers - 8745 5a/pop-to-edx - 8746 59/pop-to-ecx - 8747 58/pop-to-eax - 8748 # . epilogue - 8749 89/<- %esp 5/r32/ebp - 8750 5d/pop-to-ebp - 8751 c3/return - 8752 - 8753 check-no-tokens-left: # line: (addr stream byte) - 8754 # . prologue - 8755 55/push-ebp - 8756 89/<- %ebp 4/r32/esp - 8757 # . save registers - 8758 50/push-eax - 8759 51/push-ecx - 8760 # var s/ecx: slice - 8761 68/push 0/imm32/end - 8762 68/push 0/imm32/start - 8763 89/<- %ecx 4/r32/esp - 8764 # - 8765 (next-mu-token *(ebp+8) %ecx) - 8766 # if slice-empty?(s) return - 8767 (slice-empty? %ecx) - 8768 3d/compare-eax-and 0/imm32/false - 8769 75/jump-if-!= $check-no-tokens-left:end/disp8 - 8770 # if (slice-starts-with?(s, '#') return - 8771 # . eax = *s->start - 8772 8b/-> *edx 0/r32/eax - 8773 8a/copy-byte *eax 0/r32/AL - 8774 81 4/subop/and %eax 0xff/imm32 - 8775 # . if (eax == '#') continue - 8776 3d/compare-eax-and 0x23/imm32/hash - 8777 74/jump-if-= $check-no-tokens-left:end/disp8 - 8778 # abort - 8779 (write-buffered Stderr "'{' or '}' should be on its own line, but got '") - 8780 (rewind-stream %ecx) - 8781 (write-stream 2 %ecx) - 8782 (write-buffered Stderr "'\n") - 8783 (flush Stderr) - 8784 # . syscall(exit, 1) - 8785 bb/copy-to-ebx 1/imm32 - 8786 e8/call syscall_exit/disp32 - 8787 # never gets here - 8788 $check-no-tokens-left:end: - 8789 # . reclaim locals - 8790 81 0/subop/add %esp 8/imm32 - 8791 # . restore registers - 8792 59/pop-to-ecx - 8793 58/pop-to-eax - 8794 # . epilogue - 8795 89/<- %esp 5/r32/ebp - 8796 5d/pop-to-ebp - 8797 c3/return - 8798 - 8799 parse-mu-named-block: # name: (addr slice), in: (addr buffered-file), vars: (addr stack live-var), fn: (addr function), out: (addr handle stmt), err: (addr buffered-file), ed: (addr exit-descriptor) - 8800 # pseudocode: - 8801 # var v: (handle var) - 8802 # new-literal(name, v) - 8803 # push(vars, {v, false}) - 8804 # parse-mu-block(in, vars, fn, out) - 8805 # pop(vars) - 8806 # out->tag = block - 8807 # out->var = v - 8808 # - 8809 # . prologue - 8810 55/push-ebp - 8811 89/<- %ebp 4/r32/esp - 8812 # . save registers - 8813 50/push-eax - 8814 51/push-ecx - 8815 57/push-edi - 8816 # var v/ecx: (handle var) - 8817 68/push 0/imm32 - 8818 68/push 0/imm32 - 8819 89/<- %ecx 4/r32/esp - 8820 # - 8821 (new-literal Heap *(ebp+8) %ecx) - 8822 # push(vars, v) - 8823 (push *(ebp+0x10) *ecx) - 8824 (push *(ebp+0x10) *(ecx+4)) - 8825 (push *(ebp+0x10) 0) # false - 8826 # - 8827 (parse-mu-block *(ebp+0xc) *(ebp+0x10) *(ebp+0x14) *(ebp+0x18) *(ebp+0x1c) *(ebp+0x20)) - 8828 # pop v off vars - 8829 (pop *(ebp+0x10)) # => eax - 8830 (pop *(ebp+0x10)) # => eax - 8831 (pop *(ebp+0x10)) # => eax - 8832 # var out-addr/edi: (addr stmt) = lookup(*out) - 8833 8b/-> *(ebp+0x18) 7/r32/edi - 8834 (lookup *edi *(edi+4)) # => eax - 8835 89/<- %edi 0/r32/eax - 8836 # out-addr->tag = named-block - 8837 c7 0/subop/copy *edi 0/imm32/block # Stmt-tag - 8838 # out-addr->var = v - 8839 8b/-> *ecx 0/r32/eax - 8840 89/<- *(edi+0xc) 0/r32/eax # Block-var - 8841 8b/-> *(ecx+4) 0/r32/eax - 8842 89/<- *(edi+0x10) 0/r32/eax # Block-var - 8843 $parse-mu-named-block:end: - 8844 # . reclaim locals - 8845 81 0/subop/add %esp 8/imm32 - 8846 # . restore registers - 8847 5f/pop-to-edi - 8848 59/pop-to-ecx - 8849 58/pop-to-eax - 8850 # . epilogue - 8851 89/<- %esp 5/r32/ebp - 8852 5d/pop-to-ebp - 8853 c3/return - 8854 - 8855 parse-mu-var-def: # line: (addr stream byte), vars: (addr stack live-var), out: (addr handle stmt), fn: (addr function), err: (addr buffered-file), ed: (addr exit-descriptor) - 8856 # . prologue - 8857 55/push-ebp - 8858 89/<- %ebp 4/r32/esp - 8859 # . save registers - 8860 50/push-eax - 8861 51/push-ecx - 8862 52/push-edx - 8863 53/push-ebx - 8864 57/push-edi - 8865 # edi = out - 8866 8b/-> *(ebp+0x10) 7/r32/edi - 8867 # var word-slice/ecx: slice - 8868 68/push 0/imm32/end - 8869 68/push 0/imm32/start - 8870 89/<- %ecx 4/r32/esp - 8871 # var v/edx: (handle var) - 8872 68/push 0/imm32 - 8873 68/push 0/imm32 - 8874 89/<- %edx 4/r32/esp - 8875 # v = parse-var-with-type(next-mu-token(line)) - 8876 (next-mu-token *(ebp+8) %ecx) - 8877 (parse-var-with-type %ecx *(ebp+8) %edx *(ebp+0x18) *(ebp+0x1c)) - 8878 # var v-addr/eax: (addr var) - 8879 (lookup *edx *(edx+4)) # => eax - 8880 # v->block-depth = *Curr-block-depth - 8881 8b/-> *Curr-block-depth 3/r32/ebx - 8882 89/<- *(eax+0x10) 3/r32/ebx # Var-block-depth - 8883 # either v has no register and there's no more to this line - 8884 8b/-> *(eax+0x18) 0/r32/eax # Var-register - 8885 3d/compare-eax-and 0/imm32 - 8886 { - 8887 75/jump-if-!= break/disp8 - 8888 # TODO: disallow vars of type 'byte' on the stack - 8889 # ensure that there's nothing else on this line - 8890 (next-mu-token *(ebp+8) %ecx) - 8891 (slice-empty? %ecx) # => eax - 8892 3d/compare-eax-and 0/imm32/false - 8893 0f 84/jump-if-= $parse-mu-var-def:error2/disp32 - 8894 # - 8895 (new-var-def Heap *edx *(edx+4) %edi) - 8896 e9/jump $parse-mu-var-def:update-vars/disp32 - 8897 } - 8898 # or v has a register and there's more to this line - 8899 { - 8900 0f 84/jump-if-= break/disp32 - 8901 # TODO: disallow vars of type 'byte' in registers 'esi' or 'edi' - 8902 # TODO: vars of type 'byte' should only be initialized by clearing to 0 - 8903 # ensure that the next word is '<-' - 8904 (next-mu-token *(ebp+8) %ecx) - 8905 (slice-equal? %ecx "<-") # => eax - 8906 3d/compare-eax-and 0/imm32/false - 8907 0f 84/jump-if-= $parse-mu-var-def:error1/disp32 - 8908 # - 8909 (new-reg-var-def Heap *edx *(edx+4) %edi) - 8910 (lookup *edi *(edi+4)) # => eax - 8911 (add-operation-and-inputs-to-stmt %eax *(ebp+8) *(ebp+0xc) *(ebp+0x14) *(ebp+0x18) *(ebp+0x1c)) - 8912 } - 8913 $parse-mu-var-def:update-vars: - 8914 # push 'v' at end of function - 8915 (push *(ebp+0xc) *edx) - 8916 (push *(ebp+0xc) *(edx+4)) - 8917 (push *(ebp+0xc) 0) # Live-var-register-spilled is unused during parsing - 8918 $parse-mu-var-def:end: - 8919 # . reclaim locals - 8920 81 0/subop/add %esp 0x10/imm32 - 8921 # . restore registers - 8922 5f/pop-to-edi - 8923 5b/pop-to-ebx - 8924 5a/pop-to-edx - 8925 59/pop-to-ecx - 8926 58/pop-to-eax - 8927 # . epilogue - 8928 89/<- %esp 5/r32/ebp - 8929 5d/pop-to-ebp - 8930 c3/return - 8931 - 8932 $parse-mu-var-def:error1: - 8933 (rewind-stream *(ebp+8)) - 8934 # error("register variable requires a valid instruction to initialize but got '" line "'\n") - 8935 (write-buffered *(ebp+0x18) "register variable requires a valid instruction to initialize but got '") - 8936 (flush *(ebp+0x18)) - 8937 (write-stream-data *(ebp+0x18) *(ebp+8)) - 8938 (write-buffered *(ebp+0x18) "'\n") + 8164 # if (c == '_') return true + 8165 3d/compare-eax-and 0x5f/imm32/_ + 8166 74/jump-if-= $is-identifier?:true/disp8 + 8167 # drop case + 8168 25/and-eax-with 0x5f/imm32 + 8169 # if (c < 'A') return false + 8170 3d/compare-eax-and 0x41/imm32/A + 8171 7c/jump-if-< $is-identifier?:false/disp8 + 8172 # if (c > 'Z') return false + 8173 3d/compare-eax-and 0x5a/imm32/Z + 8174 7f/jump-if-> $is-identifier?:false/disp8 + 8175 # otherwise return true + 8176 $is-identifier?:true: + 8177 b8/copy-to-eax 1/imm32/true + 8178 eb/jump $is-identifier?:end/disp8 + 8179 $is-identifier?:false: + 8180 b8/copy-to-eax 0/imm32/false + 8181 $is-identifier?:end: + 8182 # . epilogue + 8183 89/<- %esp 5/r32/ebp + 8184 5d/pop-to-ebp + 8185 c3/return + 8186 + 8187 test-is-identifier-dollar: + 8188 # . prologue + 8189 55/push-ebp + 8190 89/<- %ebp 4/r32/esp + 8191 # (eax..ecx) = "$a" + 8192 b8/copy-to-eax "$a"/imm32 + 8193 8b/-> *eax 1/r32/ecx + 8194 8d/copy-address *(eax+ecx+4) 1/r32/ecx + 8195 05/add-to-eax 4/imm32 + 8196 # var slice/ecx: slice = {eax, ecx} + 8197 51/push-ecx + 8198 50/push-eax + 8199 89/<- %ecx 4/r32/esp + 8200 # + 8201 (is-identifier? %ecx) + 8202 (check-ints-equal %eax 1 "F - test-is-identifier-dollar") + 8203 # . epilogue + 8204 89/<- %esp 5/r32/ebp + 8205 5d/pop-to-ebp + 8206 c3/return + 8207 + 8208 test-is-identifier-underscore: + 8209 # . prologue + 8210 55/push-ebp + 8211 89/<- %ebp 4/r32/esp + 8212 # (eax..ecx) = "_a" + 8213 b8/copy-to-eax "_a"/imm32 + 8214 8b/-> *eax 1/r32/ecx + 8215 8d/copy-address *(eax+ecx+4) 1/r32/ecx + 8216 05/add-to-eax 4/imm32 + 8217 # var slice/ecx: slice = {eax, ecx} + 8218 51/push-ecx + 8219 50/push-eax + 8220 89/<- %ecx 4/r32/esp + 8221 # + 8222 (is-identifier? %ecx) + 8223 (check-ints-equal %eax 1 "F - test-is-identifier-underscore") + 8224 # . epilogue + 8225 89/<- %esp 5/r32/ebp + 8226 5d/pop-to-ebp + 8227 c3/return + 8228 + 8229 test-is-identifier-a: + 8230 # . prologue + 8231 55/push-ebp + 8232 89/<- %ebp 4/r32/esp + 8233 # (eax..ecx) = "a$" + 8234 b8/copy-to-eax "a$"/imm32 + 8235 8b/-> *eax 1/r32/ecx + 8236 8d/copy-address *(eax+ecx+4) 1/r32/ecx + 8237 05/add-to-eax 4/imm32 + 8238 # var slice/ecx: slice = {eax, ecx} + 8239 51/push-ecx + 8240 50/push-eax + 8241 89/<- %ecx 4/r32/esp + 8242 # + 8243 (is-identifier? %ecx) + 8244 (check-ints-equal %eax 1 "F - test-is-identifier-a") + 8245 # . epilogue + 8246 89/<- %esp 5/r32/ebp + 8247 5d/pop-to-ebp + 8248 c3/return + 8249 + 8250 test-is-identifier-z: + 8251 # . prologue + 8252 55/push-ebp + 8253 89/<- %ebp 4/r32/esp + 8254 # (eax..ecx) = "z$" + 8255 b8/copy-to-eax "z$"/imm32 + 8256 8b/-> *eax 1/r32/ecx + 8257 8d/copy-address *(eax+ecx+4) 1/r32/ecx + 8258 05/add-to-eax 4/imm32 + 8259 # var slice/ecx: slice = {eax, ecx} + 8260 51/push-ecx + 8261 50/push-eax + 8262 89/<- %ecx 4/r32/esp + 8263 # + 8264 (is-identifier? %ecx) + 8265 (check-ints-equal %eax 1 "F - test-is-identifier-z") + 8266 # . epilogue + 8267 89/<- %esp 5/r32/ebp + 8268 5d/pop-to-ebp + 8269 c3/return + 8270 + 8271 test-is-identifier-A: + 8272 # . prologue + 8273 55/push-ebp + 8274 89/<- %ebp 4/r32/esp + 8275 # (eax..ecx) = "A$" + 8276 b8/copy-to-eax "A$"/imm32 + 8277 8b/-> *eax 1/r32/ecx + 8278 8d/copy-address *(eax+ecx+4) 1/r32/ecx + 8279 05/add-to-eax 4/imm32 + 8280 # var slice/ecx: slice = {eax, ecx} + 8281 51/push-ecx + 8282 50/push-eax + 8283 89/<- %ecx 4/r32/esp + 8284 # + 8285 (is-identifier? %ecx) + 8286 (check-ints-equal %eax 1 "F - test-is-identifier-A") + 8287 # . epilogue + 8288 89/<- %esp 5/r32/ebp + 8289 5d/pop-to-ebp + 8290 c3/return + 8291 + 8292 test-is-identifier-Z: + 8293 # . prologue + 8294 55/push-ebp + 8295 89/<- %ebp 4/r32/esp + 8296 # (eax..ecx) = "Z$" + 8297 b8/copy-to-eax "Z$"/imm32 + 8298 8b/-> *eax 1/r32/ecx + 8299 8d/copy-address *(eax+ecx+4) 1/r32/ecx + 8300 05/add-to-eax 4/imm32 + 8301 # var slice/ecx: slice = {eax, ecx} + 8302 51/push-ecx + 8303 50/push-eax + 8304 89/<- %ecx 4/r32/esp + 8305 # + 8306 (is-identifier? %ecx) + 8307 (check-ints-equal %eax 1 "F - test-is-identifier-Z") + 8308 # . epilogue + 8309 89/<- %esp 5/r32/ebp + 8310 5d/pop-to-ebp + 8311 c3/return + 8312 + 8313 test-is-identifier-at: + 8314 # character before 'A' is invalid + 8315 # . prologue + 8316 55/push-ebp + 8317 89/<- %ebp 4/r32/esp + 8318 # (eax..ecx) = "@a" + 8319 b8/copy-to-eax "@a"/imm32 + 8320 8b/-> *eax 1/r32/ecx + 8321 8d/copy-address *(eax+ecx+4) 1/r32/ecx + 8322 05/add-to-eax 4/imm32 + 8323 # var slice/ecx: slice = {eax, ecx} + 8324 51/push-ecx + 8325 50/push-eax + 8326 89/<- %ecx 4/r32/esp + 8327 # + 8328 (is-identifier? %ecx) + 8329 (check-ints-equal %eax 0 "F - test-is-identifier-@") + 8330 # . epilogue + 8331 89/<- %esp 5/r32/ebp + 8332 5d/pop-to-ebp + 8333 c3/return + 8334 + 8335 test-is-identifier-square-bracket: + 8336 # character after 'Z' is invalid + 8337 # . prologue + 8338 55/push-ebp + 8339 89/<- %ebp 4/r32/esp + 8340 # (eax..ecx) = "[a" + 8341 b8/copy-to-eax "[a"/imm32 + 8342 8b/-> *eax 1/r32/ecx + 8343 8d/copy-address *(eax+ecx+4) 1/r32/ecx + 8344 05/add-to-eax 4/imm32 + 8345 # var slice/ecx: slice = {eax, ecx} + 8346 51/push-ecx + 8347 50/push-eax + 8348 89/<- %ecx 4/r32/esp + 8349 # + 8350 (is-identifier? %ecx) + 8351 (check-ints-equal %eax 0 "F - test-is-identifier-@") + 8352 # . epilogue + 8353 89/<- %esp 5/r32/ebp + 8354 5d/pop-to-ebp + 8355 c3/return + 8356 + 8357 test-is-identifier-backtick: + 8358 # character before 'a' is invalid + 8359 # . prologue + 8360 55/push-ebp + 8361 89/<- %ebp 4/r32/esp + 8362 # (eax..ecx) = "`a" + 8363 b8/copy-to-eax "`a"/imm32 + 8364 8b/-> *eax 1/r32/ecx + 8365 8d/copy-address *(eax+ecx+4) 1/r32/ecx + 8366 05/add-to-eax 4/imm32 + 8367 # var slice/ecx: slice = {eax, ecx} + 8368 51/push-ecx + 8369 50/push-eax + 8370 89/<- %ecx 4/r32/esp + 8371 # + 8372 (is-identifier? %ecx) + 8373 (check-ints-equal %eax 0 "F - test-is-identifier-backtick") + 8374 # . epilogue + 8375 89/<- %esp 5/r32/ebp + 8376 5d/pop-to-ebp + 8377 c3/return + 8378 + 8379 test-is-identifier-curly-brace-open: + 8380 # character after 'z' is invalid; also used for blocks + 8381 # . prologue + 8382 55/push-ebp + 8383 89/<- %ebp 4/r32/esp + 8384 # (eax..ecx) = "{a" + 8385 b8/copy-to-eax "{a"/imm32 + 8386 8b/-> *eax 1/r32/ecx + 8387 8d/copy-address *(eax+ecx+4) 1/r32/ecx + 8388 05/add-to-eax 4/imm32 + 8389 # var slice/ecx: slice = {eax, ecx} + 8390 51/push-ecx + 8391 50/push-eax + 8392 89/<- %ecx 4/r32/esp + 8393 # + 8394 (is-identifier? %ecx) + 8395 (check-ints-equal %eax 0 "F - test-is-identifier-curly-brace-open") + 8396 # . epilogue + 8397 89/<- %esp 5/r32/ebp + 8398 5d/pop-to-ebp + 8399 c3/return + 8400 + 8401 test-is-identifier-curly-brace-close: + 8402 # . prologue + 8403 55/push-ebp + 8404 89/<- %ebp 4/r32/esp + 8405 # (eax..ecx) = "}a" + 8406 b8/copy-to-eax "}a"/imm32 + 8407 8b/-> *eax 1/r32/ecx + 8408 8d/copy-address *(eax+ecx+4) 1/r32/ecx + 8409 05/add-to-eax 4/imm32 + 8410 # var slice/ecx: slice = {eax, ecx} + 8411 51/push-ecx + 8412 50/push-eax + 8413 89/<- %ecx 4/r32/esp + 8414 # + 8415 (is-identifier? %ecx) + 8416 (check-ints-equal %eax 0 "F - test-is-identifier-curly-brace-close") + 8417 # . epilogue + 8418 89/<- %esp 5/r32/ebp + 8419 5d/pop-to-ebp + 8420 c3/return + 8421 + 8422 test-is-identifier-hyphen: + 8423 # disallow leading '-' since '->' has special meaning + 8424 # . prologue + 8425 55/push-ebp + 8426 89/<- %ebp 4/r32/esp + 8427 # (eax..ecx) = "-a" + 8428 b8/copy-to-eax "-a"/imm32 + 8429 8b/-> *eax 1/r32/ecx + 8430 8d/copy-address *(eax+ecx+4) 1/r32/ecx + 8431 05/add-to-eax 4/imm32 + 8432 # var slice/ecx: slice = {eax, ecx} + 8433 51/push-ecx + 8434 50/push-eax + 8435 89/<- %ecx 4/r32/esp + 8436 # + 8437 (is-identifier? %ecx) + 8438 (check-ints-equal %eax 0 "F - test-is-identifier-hyphen") + 8439 # . epilogue + 8440 89/<- %esp 5/r32/ebp + 8441 5d/pop-to-ebp + 8442 c3/return + 8443 + 8444 populate-mu-function-body: # in: (addr buffered-file), out: (addr function), vars: (addr stack live-var), err: (addr buffered-file), ed: (addr exit-descriptor) + 8445 # . prologue + 8446 55/push-ebp + 8447 89/<- %ebp 4/r32/esp + 8448 # . save registers + 8449 50/push-eax + 8450 56/push-esi + 8451 57/push-edi + 8452 # esi = in + 8453 8b/-> *(ebp+8) 6/r32/esi + 8454 # edi = out + 8455 8b/-> *(ebp+0xc) 7/r32/edi + 8456 # initialize some global state + 8457 c7 0/subop/copy *Curr-block-depth 1/imm32 + 8458 # parse-mu-block(in, vars, out, out->body) + 8459 8d/copy-address *(edi+0x18) 0/r32/eax # Function-body + 8460 (parse-mu-block %esi *(ebp+0x10) %edi %eax *(ebp+0x14) *(ebp+0x18)) + 8461 $populate-mu-function-body:end: + 8462 # . restore registers + 8463 5f/pop-to-edi + 8464 5e/pop-to-esi + 8465 58/pop-to-eax + 8466 # . epilogue + 8467 89/<- %esp 5/r32/ebp + 8468 5d/pop-to-ebp + 8469 c3/return + 8470 + 8471 # parses a block, assuming that the leading '{' has already been read by the caller + 8472 parse-mu-block: # in: (addr buffered-file), vars: (addr stack live-var), fn: (addr function), out: (addr handle block), err: (addr buffered-file), ed: (addr exit-descriptor) + 8473 # pseudocode: + 8474 # var line: (stream byte 512) + 8475 # var word-slice: slice + 8476 # allocate(Heap, Stmt-size, out) + 8477 # var out-addr: (addr block) = lookup(*out) + 8478 # out-addr->tag = 0/block + 8479 # out-addr->var = some unique name + 8480 # push(vars, {out-addr->var, false}) + 8481 # while true # line loop + 8482 # clear-stream(line) + 8483 # read-line-buffered(in, line) + 8484 # if (line->write == 0) break # end of file + 8485 # word-slice = next-mu-token(line) + 8486 # if slice-empty?(word-slice) # end of line + 8487 # continue + 8488 # else if slice-starts-with?(word-slice, "#") + 8489 # continue + 8490 # else if slice-equal?(word-slice, "{") + 8491 # assert(no-tokens-in(line)) + 8492 # block = parse-mu-block(in, vars, fn) + 8493 # append-to-block(out-addr, block) + 8494 # else if slice-equal?(word-slice, "}") + 8495 # break + 8496 # else if slice-ends-with?(word-slice, ":") + 8497 # # TODO: error-check the rest of 'line' + 8498 # --word-slice->end to skip ':' + 8499 # named-block = parse-mu-named-block(word-slice, in, vars, fn) + 8500 # append-to-block(out-addr, named-block) + 8501 # else if slice-equal?(word-slice, "var") + 8502 # var-def = parse-mu-var-def(line, vars, fn) + 8503 # append-to-block(out-addr, var-def) + 8504 # else + 8505 # stmt = parse-mu-stmt(line, vars, fn) + 8506 # append-to-block(out-addr, stmt) + 8507 # pop(vars) + 8508 # + 8509 # . prologue + 8510 55/push-ebp + 8511 89/<- %ebp 4/r32/esp + 8512 # . save registers + 8513 50/push-eax + 8514 51/push-ecx + 8515 52/push-edx + 8516 53/push-ebx + 8517 57/push-edi + 8518 # var line/ecx: (stream byte 512) + 8519 81 5/subop/subtract %esp 0x200/imm32 + 8520 68/push 0x200/imm32/size + 8521 68/push 0/imm32/read + 8522 68/push 0/imm32/write + 8523 89/<- %ecx 4/r32/esp + 8524 # var word-slice/edx: slice + 8525 68/push 0/imm32/end + 8526 68/push 0/imm32/start + 8527 89/<- %edx 4/r32/esp + 8528 # allocate into out + 8529 (allocate Heap *Stmt-size *(ebp+0x14)) + 8530 # var out-addr/edi: (addr block) = lookup(*out) + 8531 8b/-> *(ebp+0x14) 7/r32/edi + 8532 (lookup *edi *(edi+4)) # => eax + 8533 89/<- %edi 0/r32/eax + 8534 # out-addr->tag is 0 (block) by default + 8535 # set out-addr->var + 8536 8d/copy-address *(edi+0xc) 0/r32/eax # Block-var + 8537 (new-block-name *(ebp+0x10) %eax) + 8538 # push(vars, out-addr->var) + 8539 (push *(ebp+0xc) *(edi+0xc)) # Block-var + 8540 (push *(ebp+0xc) *(edi+0x10)) # Block-var + 8541 (push *(ebp+0xc) 0) # false + 8542 # increment *Curr-block-depth + 8543 ff 0/subop/increment *Curr-block-depth + 8544 { + 8545 $parse-mu-block:line-loop: + 8546 # line = read-line-buffered(in) + 8547 (clear-stream %ecx) + 8548 (read-line-buffered *(ebp+8) %ecx) + 8549 #? (write-buffered Stderr "line: ") + 8550 #? (write-stream-data Stderr %ecx) + 8551 #? #? (write-buffered Stderr Newline) # line has its own newline + 8552 #? (flush Stderr) + 8553 #? (rewind-stream %ecx) + 8554 # if (line->write == 0) break + 8555 81 7/subop/compare *ecx 0/imm32 + 8556 0f 84/jump-if-= break/disp32 + 8557 #? (write-buffered Stderr "vars:\n") + 8558 #? (dump-vars *(ebp+0xc)) + 8559 # word-slice = next-mu-token(line) + 8560 (next-mu-token %ecx %edx) + 8561 #? (write-buffered Stderr "word: ") + 8562 #? (write-slice-buffered Stderr %edx) + 8563 #? (write-buffered Stderr Newline) + 8564 #? (flush Stderr) + 8565 # if slice-empty?(word-slice) continue + 8566 (slice-empty? %edx) + 8567 3d/compare-eax-and 0/imm32/false + 8568 0f 85/jump-if-!= loop/disp32 + 8569 # if (slice-starts-with?(word-slice, '#') continue + 8570 # . eax = *word-slice->start + 8571 8b/-> *edx 0/r32/eax + 8572 8a/copy-byte *eax 0/r32/AL + 8573 81 4/subop/and %eax 0xff/imm32 + 8574 # . if (eax == '#') continue + 8575 3d/compare-eax-and 0x23/imm32/hash + 8576 0f 84/jump-if-= loop/disp32 + 8577 # if slice-equal?(word-slice, "{") + 8578 { + 8579 $parse-mu-block:check-for-block: + 8580 (slice-equal? %edx "{") + 8581 3d/compare-eax-and 0/imm32/false + 8582 74/jump-if-= break/disp8 + 8583 (check-no-tokens-left %ecx) + 8584 # parse new block and append + 8585 # . var tmp/eax: (handle block) + 8586 68/push 0/imm32 + 8587 68/push 0/imm32 + 8588 89/<- %eax 4/r32/esp + 8589 # . + 8590 (parse-mu-block *(ebp+8) *(ebp+0xc) *(ebp+0x10) %eax *(ebp+0x18) *(ebp+0x1c)) + 8591 (append-to-block Heap %edi *eax *(eax+4)) + 8592 # . reclaim tmp + 8593 81 0/subop/add %esp 8/imm32 + 8594 # . + 8595 e9/jump $parse-mu-block:line-loop/disp32 + 8596 } + 8597 # if slice-equal?(word-slice, "}") break + 8598 $parse-mu-block:check-for-end: + 8599 (slice-equal? %edx "}") + 8600 3d/compare-eax-and 0/imm32/false + 8601 0f 85/jump-if-!= break/disp32 + 8602 # if slice-ends-with?(word-slice, ":") parse named block and append + 8603 { + 8604 $parse-mu-block:check-for-named-block: + 8605 # . eax = *(word-slice->end-1) + 8606 8b/-> *(edx+4) 0/r32/eax + 8607 48/decrement-eax + 8608 8a/copy-byte *eax 0/r32/AL + 8609 81 4/subop/and %eax 0xff/imm32 + 8610 # . if (eax != ':') break + 8611 3d/compare-eax-and 0x3a/imm32/colon + 8612 0f 85/jump-if-!= break/disp32 + 8613 # TODO: error-check the rest of 'line' + 8614 # + 8615 # skip ':' + 8616 ff 1/subop/decrement *(edx+4) # Slice-end + 8617 # var tmp/eax: (handle block) + 8618 68/push 0/imm32 + 8619 68/push 0/imm32 + 8620 89/<- %eax 4/r32/esp + 8621 # + 8622 (parse-mu-named-block %edx *(ebp+8) *(ebp+0xc) *(ebp+0x10) %eax *(ebp+0x18) *(ebp+0x1c)) + 8623 (append-to-block Heap %edi *eax *(eax+4)) + 8624 # reclaim tmp + 8625 81 0/subop/add %esp 8/imm32 + 8626 # + 8627 e9/jump $parse-mu-block:line-loop/disp32 + 8628 } + 8629 # if slice-equal?(word-slice, "var") + 8630 { + 8631 $parse-mu-block:check-for-var: + 8632 (slice-equal? %edx "var") + 8633 3d/compare-eax-and 0/imm32/false + 8634 74/jump-if-= break/disp8 + 8635 # var tmp/eax: (handle block) + 8636 68/push 0/imm32 + 8637 68/push 0/imm32 + 8638 89/<- %eax 4/r32/esp + 8639 # + 8640 (parse-mu-var-def %ecx *(ebp+0xc) %eax *(ebp+0x10) *(ebp+0x18) *(ebp+0x1c)) + 8641 (append-to-block Heap %edi *eax *(eax+4)) + 8642 # reclaim tmp + 8643 81 0/subop/add %esp 8/imm32 + 8644 # + 8645 e9/jump $parse-mu-block:line-loop/disp32 + 8646 } + 8647 $parse-mu-block:regular-stmt: + 8648 # otherwise + 8649 # var tmp/eax: (handle block) + 8650 68/push 0/imm32 + 8651 68/push 0/imm32 + 8652 89/<- %eax 4/r32/esp + 8653 # + 8654 (parse-mu-stmt %ecx *(ebp+0xc) *(ebp+0x10) %eax *(ebp+0x18) *(ebp+0x1c)) + 8655 (append-to-block Heap %edi *eax *(eax+4)) + 8656 # reclaim tmp + 8657 81 0/subop/add %esp 8/imm32 + 8658 # + 8659 e9/jump loop/disp32 + 8660 } # end line loop + 8661 (clean-up-blocks *(ebp+0xc) *Curr-block-depth *(ebp+0x10)) + 8662 # decrement *Curr-block-depth + 8663 ff 1/subop/decrement *Curr-block-depth + 8664 # pop(vars) + 8665 (pop *(ebp+0xc)) # => eax + 8666 (pop *(ebp+0xc)) # => eax + 8667 (pop *(ebp+0xc)) # => eax + 8668 $parse-mu-block:end: + 8669 # . reclaim locals + 8670 81 0/subop/add %esp 0x214/imm32 + 8671 # . restore registers + 8672 5f/pop-to-edi + 8673 5b/pop-to-ebx + 8674 5a/pop-to-edx + 8675 59/pop-to-ecx + 8676 58/pop-to-eax + 8677 # . epilogue + 8678 89/<- %esp 5/r32/ebp + 8679 5d/pop-to-ebp + 8680 c3/return + 8681 + 8682 $parse-mu-block:abort: + 8683 # error("'{' or '}' should be on its own line, but got '") + 8684 (write-buffered *(ebp+0x18) "'{' or '}' should be on its own line, but got '") + 8685 (rewind-stream %ecx) + 8686 (write-stream-data *(ebp+0x18) %ecx) + 8687 (write-buffered *(ebp+0x18) "'\n") + 8688 (flush *(ebp+0x18)) + 8689 (stop *(ebp+0x1c) 1) + 8690 # never gets here + 8691 + 8692 new-block-name: # fn: (addr function), out: (addr handle var) + 8693 # . prologue + 8694 55/push-ebp + 8695 89/<- %ebp 4/r32/esp + 8696 # . save registers + 8697 50/push-eax + 8698 51/push-ecx + 8699 52/push-edx + 8700 # var n/ecx: int = len(fn->name) + 10 for an int + 2 for '$:' + 8701 8b/-> *(ebp+8) 0/r32/eax + 8702 (lookup *eax *(eax+4)) # Function-name Function-name => eax + 8703 8b/-> *eax 0/r32/eax # String-size + 8704 05/add-to-eax 0xd/imm32 # 10 + 2 for '$:' + 8705 89/<- %ecx 0/r32/eax + 8706 # var name/edx: (stream byte n) + 8707 29/subtract-from %esp 1/r32/ecx + 8708 ff 6/subop/push %ecx + 8709 68/push 0/imm32/read + 8710 68/push 0/imm32/write + 8711 89/<- %edx 4/r32/esp + 8712 (clear-stream %edx) + 8713 # eax = fn->name + 8714 8b/-> *(ebp+8) 0/r32/eax + 8715 (lookup *eax *(eax+4)) # Function-name Function-name => eax + 8716 # construct result using Next-block-index (and increment it) + 8717 (write %edx "$") + 8718 (write %edx %eax) + 8719 (write %edx ":") + 8720 (write-int32-hex %edx *Next-block-index) + 8721 ff 0/subop/increment *Next-block-index + 8722 # var s/eax: slice = {name->data, name->data + name->write} (clobbering edx) + 8723 # . eax = name->write + 8724 8b/-> *edx 0/r32/eax + 8725 # . edx = name->data + 8726 8d/copy-address *(edx+0xc) 2/r32/edx + 8727 # . eax = name->write + name->data + 8728 01/add-to %eax 2/r32/edx + 8729 # . push {edx, eax} + 8730 ff 6/subop/push %eax + 8731 ff 6/subop/push %edx + 8732 89/<- %eax 4/r32/esp + 8733 # out = new literal(s) + 8734 (new-literal Heap %eax *(ebp+0xc)) + 8735 #? 8b/-> *(ebp+0xc) 0/r32/eax + 8736 #? (write-buffered Stderr "type allocid in caller after new-literal: ") + 8737 #? (write-int32-hex-buffered Stderr *(eax+8)) + 8738 #? (write-buffered Stderr " for var ") + 8739 #? (write-int32-hex-buffered Stderr %eax) + 8740 #? (write-buffered Stderr Newline) + 8741 #? (flush Stderr) + 8742 $new-block-name:end: + 8743 # . reclaim locals + 8744 81 0/subop/add %ecx 0xc/imm32 # name.{read/write/len} + 8745 81 0/subop/add %ecx 8/imm32 # slice + 8746 01/add-to %esp 1/r32/ecx + 8747 # . restore registers + 8748 5a/pop-to-edx + 8749 59/pop-to-ecx + 8750 58/pop-to-eax + 8751 # . epilogue + 8752 89/<- %esp 5/r32/ebp + 8753 5d/pop-to-ebp + 8754 c3/return + 8755 + 8756 check-no-tokens-left: # line: (addr stream byte) + 8757 # . prologue + 8758 55/push-ebp + 8759 89/<- %ebp 4/r32/esp + 8760 # . save registers + 8761 50/push-eax + 8762 51/push-ecx + 8763 # var s/ecx: slice + 8764 68/push 0/imm32/end + 8765 68/push 0/imm32/start + 8766 89/<- %ecx 4/r32/esp + 8767 # + 8768 (next-mu-token *(ebp+8) %ecx) + 8769 # if slice-empty?(s) return + 8770 (slice-empty? %ecx) + 8771 3d/compare-eax-and 0/imm32/false + 8772 75/jump-if-!= $check-no-tokens-left:end/disp8 + 8773 # if (slice-starts-with?(s, '#') return + 8774 # . eax = *s->start + 8775 8b/-> *edx 0/r32/eax + 8776 8a/copy-byte *eax 0/r32/AL + 8777 81 4/subop/and %eax 0xff/imm32 + 8778 # . if (eax == '#') continue + 8779 3d/compare-eax-and 0x23/imm32/hash + 8780 74/jump-if-= $check-no-tokens-left:end/disp8 + 8781 # abort + 8782 (write-buffered Stderr "'{' or '}' should be on its own line, but got '") + 8783 (rewind-stream %ecx) + 8784 (write-stream 2 %ecx) + 8785 (write-buffered Stderr "'\n") + 8786 (flush Stderr) + 8787 # . syscall(exit, 1) + 8788 bb/copy-to-ebx 1/imm32 + 8789 e8/call syscall_exit/disp32 + 8790 # never gets here + 8791 $check-no-tokens-left:end: + 8792 # . reclaim locals + 8793 81 0/subop/add %esp 8/imm32 + 8794 # . restore registers + 8795 59/pop-to-ecx + 8796 58/pop-to-eax + 8797 # . epilogue + 8798 89/<- %esp 5/r32/ebp + 8799 5d/pop-to-ebp + 8800 c3/return + 8801 + 8802 parse-mu-named-block: # name: (addr slice), in: (addr buffered-file), vars: (addr stack live-var), fn: (addr function), out: (addr handle stmt), err: (addr buffered-file), ed: (addr exit-descriptor) + 8803 # pseudocode: + 8804 # var v: (handle var) + 8805 # new-literal(name, v) + 8806 # push(vars, {v, false}) + 8807 # parse-mu-block(in, vars, fn, out) + 8808 # pop(vars) + 8809 # out->tag = block + 8810 # out->var = v + 8811 # + 8812 # . prologue + 8813 55/push-ebp + 8814 89/<- %ebp 4/r32/esp + 8815 # . save registers + 8816 50/push-eax + 8817 51/push-ecx + 8818 57/push-edi + 8819 # var v/ecx: (handle var) + 8820 68/push 0/imm32 + 8821 68/push 0/imm32 + 8822 89/<- %ecx 4/r32/esp + 8823 # + 8824 (new-literal Heap *(ebp+8) %ecx) + 8825 # push(vars, v) + 8826 (push *(ebp+0x10) *ecx) + 8827 (push *(ebp+0x10) *(ecx+4)) + 8828 (push *(ebp+0x10) 0) # false + 8829 # + 8830 (parse-mu-block *(ebp+0xc) *(ebp+0x10) *(ebp+0x14) *(ebp+0x18) *(ebp+0x1c) *(ebp+0x20)) + 8831 # pop v off vars + 8832 (pop *(ebp+0x10)) # => eax + 8833 (pop *(ebp+0x10)) # => eax + 8834 (pop *(ebp+0x10)) # => eax + 8835 # var out-addr/edi: (addr stmt) = lookup(*out) + 8836 8b/-> *(ebp+0x18) 7/r32/edi + 8837 (lookup *edi *(edi+4)) # => eax + 8838 89/<- %edi 0/r32/eax + 8839 # out-addr->tag = named-block + 8840 c7 0/subop/copy *edi 0/imm32/block # Stmt-tag + 8841 # out-addr->var = v + 8842 8b/-> *ecx 0/r32/eax + 8843 89/<- *(edi+0xc) 0/r32/eax # Block-var + 8844 8b/-> *(ecx+4) 0/r32/eax + 8845 89/<- *(edi+0x10) 0/r32/eax # Block-var + 8846 $parse-mu-named-block:end: + 8847 # . reclaim locals + 8848 81 0/subop/add %esp 8/imm32 + 8849 # . restore registers + 8850 5f/pop-to-edi + 8851 59/pop-to-ecx + 8852 58/pop-to-eax + 8853 # . epilogue + 8854 89/<- %esp 5/r32/ebp + 8855 5d/pop-to-ebp + 8856 c3/return + 8857 + 8858 parse-mu-var-def: # line: (addr stream byte), vars: (addr stack live-var), out: (addr handle stmt), fn: (addr function), err: (addr buffered-file), ed: (addr exit-descriptor) + 8859 # . prologue + 8860 55/push-ebp + 8861 89/<- %ebp 4/r32/esp + 8862 # . save registers + 8863 50/push-eax + 8864 51/push-ecx + 8865 52/push-edx + 8866 53/push-ebx + 8867 57/push-edi + 8868 # edi = out + 8869 8b/-> *(ebp+0x10) 7/r32/edi + 8870 # var word-slice/ecx: slice + 8871 68/push 0/imm32/end + 8872 68/push 0/imm32/start + 8873 89/<- %ecx 4/r32/esp + 8874 # var v/edx: (handle var) + 8875 68/push 0/imm32 + 8876 68/push 0/imm32 + 8877 89/<- %edx 4/r32/esp + 8878 # v = parse-var-with-type(next-mu-token(line)) + 8879 (next-mu-token *(ebp+8) %ecx) + 8880 (parse-var-with-type %ecx *(ebp+8) %edx *(ebp+0x18) *(ebp+0x1c)) + 8881 # var v-addr/eax: (addr var) + 8882 (lookup *edx *(edx+4)) # => eax + 8883 # v->block-depth = *Curr-block-depth + 8884 8b/-> *Curr-block-depth 3/r32/ebx + 8885 89/<- *(eax+0x10) 3/r32/ebx # Var-block-depth + 8886 # either v has no register and there's no more to this line + 8887 8b/-> *(eax+0x18) 0/r32/eax # Var-register + 8888 3d/compare-eax-and 0/imm32 + 8889 { + 8890 75/jump-if-!= break/disp8 + 8891 # TODO: disallow vars of type 'byte' on the stack + 8892 # ensure that there's nothing else on this line + 8893 (next-mu-token *(ebp+8) %ecx) + 8894 (slice-empty? %ecx) # => eax + 8895 3d/compare-eax-and 0/imm32/false + 8896 0f 84/jump-if-= $parse-mu-var-def:error2/disp32 + 8897 # + 8898 (new-var-def Heap *edx *(edx+4) %edi) + 8899 e9/jump $parse-mu-var-def:update-vars/disp32 + 8900 } + 8901 # or v has a register and there's more to this line + 8902 { + 8903 0f 84/jump-if-= break/disp32 + 8904 # TODO: disallow vars of type 'byte' in registers 'esi' or 'edi' + 8905 # TODO: vars of type 'byte' should only be initialized by clearing to 0 + 8906 # ensure that the next word is '<-' + 8907 (next-mu-token *(ebp+8) %ecx) + 8908 (slice-equal? %ecx "<-") # => eax + 8909 3d/compare-eax-and 0/imm32/false + 8910 0f 84/jump-if-= $parse-mu-var-def:error1/disp32 + 8911 # + 8912 (new-reg-var-def Heap *edx *(edx+4) %edi) + 8913 (lookup *edi *(edi+4)) # => eax + 8914 (add-operation-and-inputs-to-stmt %eax *(ebp+8) *(ebp+0xc) *(ebp+0x14) *(ebp+0x18) *(ebp+0x1c)) + 8915 } + 8916 $parse-mu-var-def:update-vars: + 8917 # push 'v' at end of function + 8918 (push *(ebp+0xc) *edx) + 8919 (push *(ebp+0xc) *(edx+4)) + 8920 (push *(ebp+0xc) 0) # Live-var-register-spilled is unused during parsing + 8921 $parse-mu-var-def:end: + 8922 # . reclaim locals + 8923 81 0/subop/add %esp 0x10/imm32 + 8924 # . restore registers + 8925 5f/pop-to-edi + 8926 5b/pop-to-ebx + 8927 5a/pop-to-edx + 8928 59/pop-to-ecx + 8929 58/pop-to-eax + 8930 # . epilogue + 8931 89/<- %esp 5/r32/ebp + 8932 5d/pop-to-ebp + 8933 c3/return + 8934 + 8935 $parse-mu-var-def:error1: + 8936 (rewind-stream *(ebp+8)) + 8937 # error("register variable requires a valid instruction to initialize but got '" line "'\n") + 8938 (write-buffered *(ebp+0x18) "register variable requires a valid instruction to initialize but got '") 8939 (flush *(ebp+0x18)) - 8940 (stop *(ebp+0x1c) 1) - 8941 # never gets here - 8942 - 8943 $parse-mu-var-def:error2: - 8944 (rewind-stream *(ebp+8)) - 8945 # error("fn " fn ": var " var ": variables on the stack can't take an initializer\n") - 8946 (write-buffered *(ebp+0x18) "fn ") - 8947 8b/-> *(ebp+0x14) 0/r32/eax - 8948 (lookup *eax *(eax+4)) # Function-name Function-name => eax - 8949 (write-buffered *(ebp+0x18) %eax) - 8950 (write-buffered *(ebp+0x18) ": var ") - 8951 # var v-addr/eax: (addr var) = lookup(v) - 8952 (lookup *edx *(edx+4)) # => eax - 8953 (lookup *eax *(eax+4)) # Var-name Var-name => eax - 8954 (write-buffered *(ebp+0x18) %eax) - 8955 (write-buffered *(ebp+0x18) ": variables on the stack can't take an initializer\n") - 8956 (flush *(ebp+0x18)) - 8957 (stop *(ebp+0x1c) 1) - 8958 # never gets here - 8959 - 8960 test-parse-mu-var-def: - 8961 # 'var n: int' - 8962 # . prologue - 8963 55/push-ebp - 8964 89/<- %ebp 4/r32/esp - 8965 # setup - 8966 (clear-stream _test-input-stream) - 8967 (write _test-input-stream "n: int\n") # caller has consumed the 'var' - 8968 c7 0/subop/copy *Curr-block-depth 1/imm32 - 8969 # var out/esi: (handle stmt) - 8970 68/push 0/imm32 - 8971 68/push 0/imm32 - 8972 89/<- %esi 4/r32/esp - 8973 # var vars/ecx: (stack (addr var) 16) - 8974 81 5/subop/subtract %esp 0xc0/imm32 - 8975 68/push 0xc0/imm32/size - 8976 68/push 0/imm32/top - 8977 89/<- %ecx 4/r32/esp - 8978 (clear-stack %ecx) - 8979 # convert - 8980 (parse-mu-var-def _test-input-stream %ecx %esi 0 Stderr 0) - 8981 # var out-addr/esi: (addr stmt) - 8982 (lookup *esi *(esi+4)) # => eax - 8983 89/<- %esi 0/r32/eax - 8984 # - 8985 (check-ints-equal *esi 2 "F - test-parse-mu-var-def/tag") # Stmt-tag is var-def - 8986 # var v/ecx: (addr var) = lookup(out->var) - 8987 (lookup *(esi+4) *(esi+8)) # Vardef-var Vardef-var => eax - 8988 89/<- %ecx 0/r32/eax - 8989 # v->name - 8990 (lookup *ecx *(ecx+4)) # Var-name Var-name => eax - 8991 (check-strings-equal %eax "n" "F - test-parse-mu-var-def/var-name") - 8992 # v->register - 8993 (check-ints-equal *(ecx+0x18) 0 "F - test-parse-mu-var-def/var-register") # Var-register - 8994 # v->block-depth - 8995 (check-ints-equal *(ecx+0x10) 1 "F - test-parse-mu-var-def/output-block-depth") # Var-block-depth - 8996 # v->type == int - 8997 (lookup *(ecx+8) *(ecx+0xc)) # Var-type Var-type => eax - 8998 (check-ints-equal *eax 1 "F - test-parse-mu-var-def/var-type:0") # Type-tree-is-atom - 8999 (check-ints-equal *(eax+4) 1 "F - test-parse-mu-var-def/var-type:1") # Type-tree-value - 9000 (check-ints-equal *(eax+0xc) 0 "F - test-parse-mu-var-def/var-type:2") # Type-tree-right - 9001 # . epilogue - 9002 89/<- %esp 5/r32/ebp - 9003 5d/pop-to-ebp - 9004 c3/return - 9005 - 9006 test-parse-mu-reg-var-def: - 9007 # 'var n/eax: int <- copy 0' - 9008 # . prologue - 9009 55/push-ebp - 9010 89/<- %ebp 4/r32/esp - 9011 # setup - 9012 (clear-stream _test-input-stream) - 9013 (write _test-input-stream "n/eax: int <- copy 0\n") # caller has consumed the 'var' - 9014 c7 0/subop/copy *Curr-block-depth 1/imm32 - 9015 # var out/esi: (handle stmt) - 9016 68/push 0/imm32 - 9017 68/push 0/imm32 - 9018 89/<- %esi 4/r32/esp - 9019 # var vars/ecx: (stack (addr var) 16) - 9020 81 5/subop/subtract %esp 0xc0/imm32 - 9021 68/push 0xc0/imm32/size - 9022 68/push 0/imm32/top - 9023 89/<- %ecx 4/r32/esp - 9024 (clear-stack %ecx) - 9025 # convert - 9026 (parse-mu-var-def _test-input-stream %ecx %esi 0 Stderr 0) - 9027 # var out-addr/esi: (addr stmt) - 9028 (lookup *esi *(esi+4)) # => eax - 9029 89/<- %esi 0/r32/eax - 9030 # - 9031 (check-ints-equal *esi 3 "F - test-parse-mu-reg-var-def/tag") # Stmt-tag is reg-var-def - 9032 # var v/ecx: (addr var) = lookup(out->outputs->value) - 9033 # . eax: (addr stmt-var) = lookup(out->outputs) - 9034 (lookup *(esi+0x14) *(esi+0x18)) # Regvardef-outputs Regvardef-outputs => eax - 9035 # . - 9036 (check-ints-equal *(eax+8) 0 "F - test-parse-mu-reg-var-def/single-output") # Stmt-var-next - 9037 # . eax: (addr var) = lookup(eax->value) - 9038 (lookup *eax *(eax+4)) # Stmt-var-value Stmt-var-value => eax - 9039 # . ecx = eax - 9040 89/<- %ecx 0/r32/eax - 9041 # v->name - 9042 (lookup *ecx *(ecx+4)) # Var-name Var-name => eax - 9043 (check-strings-equal %eax "n" "F - test-parse-mu-reg-var-def/output-name") # Var-name - 9044 # v->register - 9045 (lookup *(ecx+0x18) *(ecx+0x1c)) # Var-register Var-register => eax - 9046 (check-strings-equal %eax "eax" "F - test-parse-mu-reg-var-def/output-register") - 9047 # v->block-depth - 9048 (check-ints-equal *(ecx+0x10) 1 "F - test-parse-mu-reg-var-def/output-block-depth") # Var-block-depth - 9049 # v->type == int - 9050 (lookup *(ecx+8) *(ecx+0xc)) # Var-type Var-type => eax - 9051 (check-ints-equal *eax 1 "F - test-parse-mu-reg-var-def/output-type:0") # Type-tree-is-atom - 9052 (check-ints-equal *(eax+4) 1 "F - test-parse-mu-reg-var-def/output-type:1") # Type-tree-value - 9053 (check-ints-equal *(eax+0xc) 0 "F - test-parse-mu-reg-var-def/output-type:2") # Type-tree-right - 9054 # . epilogue - 9055 89/<- %esp 5/r32/ebp - 9056 5d/pop-to-ebp - 9057 c3/return - 9058 - 9059 parse-mu-stmt: # line: (addr stream byte), vars: (addr stack live-var), fn: (addr function), out: (addr handle stmt), err: (addr buffered-file), ed: (addr exit-descriptor) - 9060 # Carefully push any outputs on the vars stack _after_ reading the inputs - 9061 # that may conflict with them. - 9062 # - 9063 # The only situation in which outputs are pushed here (when it's not a - 9064 # 'var' vardef stmt), and so can possibly conflict with inputs, is if the - 9065 # output is a function output. - 9066 # - 9067 # pseudocode: - 9068 # var name: slice - 9069 # allocate(Heap, Stmt-size, out) - 9070 # var out-addr: (addr stmt) = lookup(*out) - 9071 # out-addr->tag = stmt - 9072 # if stmt-has-outputs?(line) - 9073 # while true - 9074 # name = next-mu-token(line) - 9075 # if (name == '<-') break - 9076 # assert(is-identifier?(name)) - 9077 # var v: (handle var) = lookup-var-or-find-in-fn-outputs(name, vars, fn) - 9078 # out-addr->outputs = append(v, out-addr->outputs) - 9079 # add-operation-and-inputs-to-stmt(out-addr, line, vars) - 9080 # for output in stmt->outputs: - 9081 # maybe-define-var(output, vars) - 9082 # - 9083 # . prologue - 9084 55/push-ebp - 9085 89/<- %ebp 4/r32/esp - 9086 # . save registers - 9087 50/push-eax - 9088 51/push-ecx - 9089 52/push-edx - 9090 53/push-ebx - 9091 57/push-edi - 9092 # var name/ecx: slice - 9093 68/push 0/imm32/end - 9094 68/push 0/imm32/start - 9095 89/<- %ecx 4/r32/esp - 9096 # var is-deref?/edx: boolean = false - 9097 ba/copy-to-edx 0/imm32/false - 9098 # var v: (handle var) - 9099 68/push 0/imm32 - 9100 68/push 0/imm32 - 9101 89/<- %ebx 4/r32/esp - 9102 # - 9103 (allocate Heap *Stmt-size *(ebp+0x14)) - 9104 # var out-addr/edi: (addr stmt) = lookup(*out) - 9105 8b/-> *(ebp+0x14) 7/r32/edi - 9106 (lookup *edi *(edi+4)) # => eax - 9107 89/<- %edi 0/r32/eax - 9108 # out-addr->tag = 1/stmt - 9109 c7 0/subop/copy *edi 1/imm32/stmt1 # Stmt-tag - 9110 { - 9111 (stmt-has-outputs? *(ebp+8)) - 9112 3d/compare-eax-and 0/imm32/false - 9113 0f 84/jump-if-= break/disp32 - 9114 { - 9115 $parse-mu-stmt:read-outputs: - 9116 # name = next-mu-token(line) - 9117 (next-mu-token *(ebp+8) %ecx) - 9118 # if slice-empty?(word-slice) break - 9119 (slice-empty? %ecx) # => eax - 9120 3d/compare-eax-and 0/imm32/false - 9121 0f 85/jump-if-!= break/disp32 - 9122 # if (name == "<-") break - 9123 (slice-equal? %ecx "<-") # => eax - 9124 3d/compare-eax-and 0/imm32/false - 9125 0f 85/jump-if-!= break/disp32 - 9126 # is-deref? = false - 9127 ba/copy-to-edx 0/imm32/false - 9128 # if (slice-starts-with?(name, '*')) ++name->start and set is-deref? - 9129 8b/-> *ecx 0/r32/eax # Slice-start - 9130 8a/copy-byte *eax 0/r32/AL - 9131 81 4/subop/and %eax 0xff/imm32 - 9132 3d/compare-eax-and 0x2a/imm32/asterisk - 9133 { - 9134 75/jump-if-!= break/disp8 - 9135 ff 0/subop/increment *ecx - 9136 ba/copy-to-edx 1/imm32/true - 9137 } - 9138 # assert(is-identifier?(name)) - 9139 (is-identifier? %ecx) # => eax - 9140 3d/compare-eax-and 0/imm32/false - 9141 0f 84/jump-if-= $parse-mu-stmt:abort/disp32 - 9142 # - 9143 (lookup-var-or-find-in-fn-outputs %ecx *(ebp+0xc) *(ebp+0x10) %ebx *(ebp+0x18) *(ebp+0x1c)) - 9144 8d/copy-address *(edi+0x14) 0/r32/eax # Stmt1-outputs - 9145 (append-stmt-var Heap *ebx *(ebx+4) *(edi+0x14) *(edi+0x18) %edx %eax) # Stmt1-outputs - 9146 # - 9147 e9/jump loop/disp32 - 9148 } - 9149 } - 9150 (add-operation-and-inputs-to-stmt %edi *(ebp+8) *(ebp+0xc) *(ebp+0x10) *(ebp+0x18) *(ebp+0x1c)) - 9151 $parse-mu-stmt:define-outputs: - 9152 # var output/edi: (addr stmt-var) = lookup(out-addr->outputs) - 9153 (lookup *(edi+0x14) *(edi+0x18)) # Stmt1-outputs Stmt1-outputs => eax - 9154 89/<- %edi 0/r32/eax - 9155 { - 9156 $parse-mu-stmt:define-outputs-loop: - 9157 # if (output == null) break - 9158 81 7/subop/compare %edi 0/imm32 - 9159 74/jump-if-= break/disp8 - 9160 # - 9161 (maybe-define-var *edi *(edi+4) *(ebp+0xc)) # if output is a deref, then it's already been defined, - 9162 # and must be in vars. This call will be a no-op, but safe. - 9163 # output = output->next - 9164 (lookup *(edi+8) *(edi+0xc)) # Stmt-var-next Stmt-var-next => eax - 9165 89/<- %edi 0/r32/eax - 9166 # - 9167 eb/jump loop/disp8 - 9168 } - 9169 $parse-mu-stmt:end: - 9170 # . reclaim locals - 9171 81 0/subop/add %esp 0x10/imm32 - 9172 # . restore registers - 9173 5f/pop-to-edi - 9174 5b/pop-to-ebx - 9175 5a/pop-to-edx - 9176 59/pop-to-ecx - 9177 58/pop-to-eax - 9178 # . epilogue - 9179 89/<- %esp 5/r32/ebp - 9180 5d/pop-to-ebp - 9181 c3/return - 9182 - 9183 $parse-mu-stmt:abort: - 9184 # error("invalid identifier '" name "'\n") - 9185 (write-buffered *(ebp+0x18) "invalid identifier '") - 9186 (write-slice-buffered *(ebp+0x18) %ecx) - 9187 (write-buffered *(ebp+0x18) "'\n") - 9188 (flush *(ebp+0x18)) - 9189 (stop *(ebp+0x1c) 1) - 9190 # never gets here - 9191 - 9192 add-operation-and-inputs-to-stmt: # stmt: (addr stmt), line: (addr stream byte), vars: (addr stack live-var), fn: (addr function), err: (addr buffered-file), ed: (addr exit-descriptor) - 9193 # pseudocode: - 9194 # stmt->name = slice-to-string(next-mu-token(line)) - 9195 # while true - 9196 # name = next-mu-token(line) - 9197 # v = lookup-var-or-literal(name) - 9198 # stmt->inouts = append(v, stmt->inouts) - 9199 # - 9200 # . prologue - 9201 55/push-ebp - 9202 89/<- %ebp 4/r32/esp - 9203 # . save registers - 9204 50/push-eax - 9205 51/push-ecx - 9206 52/push-edx - 9207 53/push-ebx - 9208 56/push-esi - 9209 57/push-edi - 9210 # edi = stmt - 9211 8b/-> *(ebp+8) 7/r32/edi - 9212 # var name/ecx: slice - 9213 68/push 0/imm32/end - 9214 68/push 0/imm32/start - 9215 89/<- %ecx 4/r32/esp - 9216 # var is-deref?/edx: boolean = false - 9217 ba/copy-to-edx 0/imm32/false - 9218 # var v/esi: (handle var) - 9219 68/push 0/imm32 - 9220 68/push 0/imm32 - 9221 89/<- %esi 4/r32/esp - 9222 $add-operation-and-inputs-to-stmt:read-operation: - 9223 (next-mu-token *(ebp+0xc) %ecx) - 9224 8d/copy-address *(edi+4) 0/r32/eax # Stmt1-operation or Regvardef-operationStmt1-operation or Regvardef-operation - 9225 (slice-to-string Heap %ecx %eax) - 9226 # var is-get?/ebx: boolean = (name == "get") - 9227 (slice-equal? %ecx "get") # => eax - 9228 89/<- %ebx 0/r32/eax - 9229 { - 9230 $add-operation-and-inputs-to-stmt:read-inouts: - 9231 # name = next-mu-token(line) - 9232 (next-mu-token *(ebp+0xc) %ecx) - 9233 # if slice-empty?(word-slice) break - 9234 (slice-empty? %ecx) # => eax - 9235 3d/compare-eax-and 0/imm32/false - 9236 0f 85/jump-if-!= break/disp32 - 9237 # if (name == "<-") abort - 9238 (slice-equal? %ecx "<-") - 9239 3d/compare-eax-and 0/imm32/false - 9240 0f 85/jump-if-!= $add-operation-and-inputs-to-stmt:abort/disp32 - 9241 # if (is-get? && second operand) lookup or create offset - 9242 { - 9243 81 7/subop/compare %ebx 0/imm32/false - 9244 74/jump-if-= break/disp8 - 9245 (lookup *(edi+0xc) *(edi+0x10)) # Stmt1-inouts Stmt1-inouts => eax - 9246 3d/compare-eax-and 0/imm32 + 8940 (write-stream-data *(ebp+0x18) *(ebp+8)) + 8941 (write-buffered *(ebp+0x18) "'\n") + 8942 (flush *(ebp+0x18)) + 8943 (stop *(ebp+0x1c) 1) + 8944 # never gets here + 8945 + 8946 $parse-mu-var-def:error2: + 8947 (rewind-stream *(ebp+8)) + 8948 # error("fn " fn ": var " var ": variables on the stack can't take an initializer\n") + 8949 (write-buffered *(ebp+0x18) "fn ") + 8950 8b/-> *(ebp+0x14) 0/r32/eax + 8951 (lookup *eax *(eax+4)) # Function-name Function-name => eax + 8952 (write-buffered *(ebp+0x18) %eax) + 8953 (write-buffered *(ebp+0x18) ": var ") + 8954 # var v-addr/eax: (addr var) = lookup(v) + 8955 (lookup *edx *(edx+4)) # => eax + 8956 (lookup *eax *(eax+4)) # Var-name Var-name => eax + 8957 (write-buffered *(ebp+0x18) %eax) + 8958 (write-buffered *(ebp+0x18) ": variables on the stack can't take an initializer\n") + 8959 (flush *(ebp+0x18)) + 8960 (stop *(ebp+0x1c) 1) + 8961 # never gets here + 8962 + 8963 test-parse-mu-var-def: + 8964 # 'var n: int' + 8965 # . prologue + 8966 55/push-ebp + 8967 89/<- %ebp 4/r32/esp + 8968 # setup + 8969 (clear-stream _test-input-stream) + 8970 (write _test-input-stream "n: int\n") # caller has consumed the 'var' + 8971 c7 0/subop/copy *Curr-block-depth 1/imm32 + 8972 # var out/esi: (handle stmt) + 8973 68/push 0/imm32 + 8974 68/push 0/imm32 + 8975 89/<- %esi 4/r32/esp + 8976 # var vars/ecx: (stack (addr var) 16) + 8977 81 5/subop/subtract %esp 0xc0/imm32 + 8978 68/push 0xc0/imm32/size + 8979 68/push 0/imm32/top + 8980 89/<- %ecx 4/r32/esp + 8981 (clear-stack %ecx) + 8982 # convert + 8983 (parse-mu-var-def _test-input-stream %ecx %esi 0 Stderr 0) + 8984 # var out-addr/esi: (addr stmt) + 8985 (lookup *esi *(esi+4)) # => eax + 8986 89/<- %esi 0/r32/eax + 8987 # + 8988 (check-ints-equal *esi 2 "F - test-parse-mu-var-def/tag") # Stmt-tag is var-def + 8989 # var v/ecx: (addr var) = lookup(out->var) + 8990 (lookup *(esi+4) *(esi+8)) # Vardef-var Vardef-var => eax + 8991 89/<- %ecx 0/r32/eax + 8992 # v->name + 8993 (lookup *ecx *(ecx+4)) # Var-name Var-name => eax + 8994 (check-strings-equal %eax "n" "F - test-parse-mu-var-def/var-name") + 8995 # v->register + 8996 (check-ints-equal *(ecx+0x18) 0 "F - test-parse-mu-var-def/var-register") # Var-register + 8997 # v->block-depth + 8998 (check-ints-equal *(ecx+0x10) 1 "F - test-parse-mu-var-def/output-block-depth") # Var-block-depth + 8999 # v->type == int + 9000 (lookup *(ecx+8) *(ecx+0xc)) # Var-type Var-type => eax + 9001 (check-ints-equal *eax 1 "F - test-parse-mu-var-def/var-type:0") # Type-tree-is-atom + 9002 (check-ints-equal *(eax+4) 1 "F - test-parse-mu-var-def/var-type:1") # Type-tree-value + 9003 (check-ints-equal *(eax+0xc) 0 "F - test-parse-mu-var-def/var-type:2") # Type-tree-right + 9004 # . epilogue + 9005 89/<- %esp 5/r32/ebp + 9006 5d/pop-to-ebp + 9007 c3/return + 9008 + 9009 test-parse-mu-reg-var-def: + 9010 # 'var n/eax: int <- copy 0' + 9011 # . prologue + 9012 55/push-ebp + 9013 89/<- %ebp 4/r32/esp + 9014 # setup + 9015 (clear-stream _test-input-stream) + 9016 (write _test-input-stream "n/eax: int <- copy 0\n") # caller has consumed the 'var' + 9017 c7 0/subop/copy *Curr-block-depth 1/imm32 + 9018 # var out/esi: (handle stmt) + 9019 68/push 0/imm32 + 9020 68/push 0/imm32 + 9021 89/<- %esi 4/r32/esp + 9022 # var vars/ecx: (stack (addr var) 16) + 9023 81 5/subop/subtract %esp 0xc0/imm32 + 9024 68/push 0xc0/imm32/size + 9025 68/push 0/imm32/top + 9026 89/<- %ecx 4/r32/esp + 9027 (clear-stack %ecx) + 9028 # convert + 9029 (parse-mu-var-def _test-input-stream %ecx %esi 0 Stderr 0) + 9030 # var out-addr/esi: (addr stmt) + 9031 (lookup *esi *(esi+4)) # => eax + 9032 89/<- %esi 0/r32/eax + 9033 # + 9034 (check-ints-equal *esi 3 "F - test-parse-mu-reg-var-def/tag") # Stmt-tag is reg-var-def + 9035 # var v/ecx: (addr var) = lookup(out->outputs->value) + 9036 # . eax: (addr stmt-var) = lookup(out->outputs) + 9037 (lookup *(esi+0x14) *(esi+0x18)) # Regvardef-outputs Regvardef-outputs => eax + 9038 # . + 9039 (check-ints-equal *(eax+8) 0 "F - test-parse-mu-reg-var-def/single-output") # Stmt-var-next + 9040 # . eax: (addr var) = lookup(eax->value) + 9041 (lookup *eax *(eax+4)) # Stmt-var-value Stmt-var-value => eax + 9042 # . ecx = eax + 9043 89/<- %ecx 0/r32/eax + 9044 # v->name + 9045 (lookup *ecx *(ecx+4)) # Var-name Var-name => eax + 9046 (check-strings-equal %eax "n" "F - test-parse-mu-reg-var-def/output-name") # Var-name + 9047 # v->register + 9048 (lookup *(ecx+0x18) *(ecx+0x1c)) # Var-register Var-register => eax + 9049 (check-strings-equal %eax "eax" "F - test-parse-mu-reg-var-def/output-register") + 9050 # v->block-depth + 9051 (check-ints-equal *(ecx+0x10) 1 "F - test-parse-mu-reg-var-def/output-block-depth") # Var-block-depth + 9052 # v->type == int + 9053 (lookup *(ecx+8) *(ecx+0xc)) # Var-type Var-type => eax + 9054 (check-ints-equal *eax 1 "F - test-parse-mu-reg-var-def/output-type:0") # Type-tree-is-atom + 9055 (check-ints-equal *(eax+4) 1 "F - test-parse-mu-reg-var-def/output-type:1") # Type-tree-value + 9056 (check-ints-equal *(eax+0xc) 0 "F - test-parse-mu-reg-var-def/output-type:2") # Type-tree-right + 9057 # . epilogue + 9058 89/<- %esp 5/r32/ebp + 9059 5d/pop-to-ebp + 9060 c3/return + 9061 + 9062 parse-mu-stmt: # line: (addr stream byte), vars: (addr stack live-var), fn: (addr function), out: (addr handle stmt), err: (addr buffered-file), ed: (addr exit-descriptor) + 9063 # Carefully push any outputs on the vars stack _after_ reading the inputs + 9064 # that may conflict with them. + 9065 # + 9066 # The only situation in which outputs are pushed here (when it's not a + 9067 # 'var' vardef stmt), and so can possibly conflict with inputs, is if the + 9068 # output is a function output. + 9069 # + 9070 # pseudocode: + 9071 # var name: slice + 9072 # allocate(Heap, Stmt-size, out) + 9073 # var out-addr: (addr stmt) = lookup(*out) + 9074 # out-addr->tag = stmt + 9075 # if stmt-has-outputs?(line) + 9076 # while true + 9077 # name = next-mu-token(line) + 9078 # if (name == '<-') break + 9079 # assert(is-identifier?(name)) + 9080 # var v: (handle var) = lookup-var-or-find-in-fn-outputs(name, vars, fn) + 9081 # out-addr->outputs = append(v, out-addr->outputs) + 9082 # add-operation-and-inputs-to-stmt(out-addr, line, vars) + 9083 # for output in stmt->outputs: + 9084 # maybe-define-var(output, vars) + 9085 # + 9086 # . prologue + 9087 55/push-ebp + 9088 89/<- %ebp 4/r32/esp + 9089 # . save registers + 9090 50/push-eax + 9091 51/push-ecx + 9092 52/push-edx + 9093 53/push-ebx + 9094 57/push-edi + 9095 # var name/ecx: slice + 9096 68/push 0/imm32/end + 9097 68/push 0/imm32/start + 9098 89/<- %ecx 4/r32/esp + 9099 # var is-deref?/edx: boolean = false + 9100 ba/copy-to-edx 0/imm32/false + 9101 # var v: (handle var) + 9102 68/push 0/imm32 + 9103 68/push 0/imm32 + 9104 89/<- %ebx 4/r32/esp + 9105 # + 9106 (allocate Heap *Stmt-size *(ebp+0x14)) + 9107 # var out-addr/edi: (addr stmt) = lookup(*out) + 9108 8b/-> *(ebp+0x14) 7/r32/edi + 9109 (lookup *edi *(edi+4)) # => eax + 9110 89/<- %edi 0/r32/eax + 9111 # out-addr->tag = 1/stmt + 9112 c7 0/subop/copy *edi 1/imm32/stmt1 # Stmt-tag + 9113 { + 9114 (stmt-has-outputs? *(ebp+8)) + 9115 3d/compare-eax-and 0/imm32/false + 9116 0f 84/jump-if-= break/disp32 + 9117 { + 9118 $parse-mu-stmt:read-outputs: + 9119 # name = next-mu-token(line) + 9120 (next-mu-token *(ebp+8) %ecx) + 9121 # if slice-empty?(word-slice) break + 9122 (slice-empty? %ecx) # => eax + 9123 3d/compare-eax-and 0/imm32/false + 9124 0f 85/jump-if-!= break/disp32 + 9125 # if (name == "<-") break + 9126 (slice-equal? %ecx "<-") # => eax + 9127 3d/compare-eax-and 0/imm32/false + 9128 0f 85/jump-if-!= break/disp32 + 9129 # is-deref? = false + 9130 ba/copy-to-edx 0/imm32/false + 9131 # if (slice-starts-with?(name, '*')) ++name->start and set is-deref? + 9132 8b/-> *ecx 0/r32/eax # Slice-start + 9133 8a/copy-byte *eax 0/r32/AL + 9134 81 4/subop/and %eax 0xff/imm32 + 9135 3d/compare-eax-and 0x2a/imm32/asterisk + 9136 { + 9137 75/jump-if-!= break/disp8 + 9138 ff 0/subop/increment *ecx + 9139 ba/copy-to-edx 1/imm32/true + 9140 } + 9141 # assert(is-identifier?(name)) + 9142 (is-identifier? %ecx) # => eax + 9143 3d/compare-eax-and 0/imm32/false + 9144 0f 84/jump-if-= $parse-mu-stmt:abort/disp32 + 9145 # + 9146 (lookup-var-or-find-in-fn-outputs %ecx *(ebp+0xc) *(ebp+0x10) %ebx *(ebp+0x18) *(ebp+0x1c)) + 9147 8d/copy-address *(edi+0x14) 0/r32/eax # Stmt1-outputs + 9148 (append-stmt-var Heap *ebx *(ebx+4) *(edi+0x14) *(edi+0x18) %edx %eax) # Stmt1-outputs + 9149 # + 9150 e9/jump loop/disp32 + 9151 } + 9152 } + 9153 (add-operation-and-inputs-to-stmt %edi *(ebp+8) *(ebp+0xc) *(ebp+0x10) *(ebp+0x18) *(ebp+0x1c)) + 9154 $parse-mu-stmt:define-outputs: + 9155 # var output/edi: (addr stmt-var) = lookup(out-addr->outputs) + 9156 (lookup *(edi+0x14) *(edi+0x18)) # Stmt1-outputs Stmt1-outputs => eax + 9157 89/<- %edi 0/r32/eax + 9158 { + 9159 $parse-mu-stmt:define-outputs-loop: + 9160 # if (output == null) break + 9161 81 7/subop/compare %edi 0/imm32 + 9162 74/jump-if-= break/disp8 + 9163 # + 9164 (maybe-define-var *edi *(edi+4) *(ebp+0xc)) # if output is a deref, then it's already been defined, + 9165 # and must be in vars. This call will be a no-op, but safe. + 9166 # output = output->next + 9167 (lookup *(edi+8) *(edi+0xc)) # Stmt-var-next Stmt-var-next => eax + 9168 89/<- %edi 0/r32/eax + 9169 # + 9170 eb/jump loop/disp8 + 9171 } + 9172 $parse-mu-stmt:end: + 9173 # . reclaim locals + 9174 81 0/subop/add %esp 0x10/imm32 + 9175 # . restore registers + 9176 5f/pop-to-edi + 9177 5b/pop-to-ebx + 9178 5a/pop-to-edx + 9179 59/pop-to-ecx + 9180 58/pop-to-eax + 9181 # . epilogue + 9182 89/<- %esp 5/r32/ebp + 9183 5d/pop-to-ebp + 9184 c3/return + 9185 + 9186 $parse-mu-stmt:abort: + 9187 # error("invalid identifier '" name "'\n") + 9188 (write-buffered *(ebp+0x18) "invalid identifier '") + 9189 (write-slice-buffered *(ebp+0x18) %ecx) + 9190 (write-buffered *(ebp+0x18) "'\n") + 9191 (flush *(ebp+0x18)) + 9192 (stop *(ebp+0x1c) 1) + 9193 # never gets here + 9194 + 9195 add-operation-and-inputs-to-stmt: # stmt: (addr stmt), line: (addr stream byte), vars: (addr stack live-var), fn: (addr function), err: (addr buffered-file), ed: (addr exit-descriptor) + 9196 # pseudocode: + 9197 # stmt->name = slice-to-string(next-mu-token(line)) + 9198 # while true + 9199 # name = next-mu-token(line) + 9200 # v = lookup-var-or-literal(name) + 9201 # stmt->inouts = append(v, stmt->inouts) + 9202 # + 9203 # . prologue + 9204 55/push-ebp + 9205 89/<- %ebp 4/r32/esp + 9206 # . save registers + 9207 50/push-eax + 9208 51/push-ecx + 9209 52/push-edx + 9210 53/push-ebx + 9211 56/push-esi + 9212 57/push-edi + 9213 # edi = stmt + 9214 8b/-> *(ebp+8) 7/r32/edi + 9215 # var name/ecx: slice + 9216 68/push 0/imm32/end + 9217 68/push 0/imm32/start + 9218 89/<- %ecx 4/r32/esp + 9219 # var is-deref?/edx: boolean = false + 9220 ba/copy-to-edx 0/imm32/false + 9221 # var v/esi: (handle var) + 9222 68/push 0/imm32 + 9223 68/push 0/imm32 + 9224 89/<- %esi 4/r32/esp + 9225 $add-operation-and-inputs-to-stmt:read-operation: + 9226 (next-mu-token *(ebp+0xc) %ecx) + 9227 8d/copy-address *(edi+4) 0/r32/eax # Stmt1-operation or Regvardef-operationStmt1-operation or Regvardef-operation + 9228 (slice-to-string Heap %ecx %eax) + 9229 # var is-get?/ebx: boolean = (name == "get") + 9230 (slice-equal? %ecx "get") # => eax + 9231 89/<- %ebx 0/r32/eax + 9232 { + 9233 $add-operation-and-inputs-to-stmt:read-inouts: + 9234 # name = next-mu-token(line) + 9235 (next-mu-token *(ebp+0xc) %ecx) + 9236 # if slice-empty?(word-slice) break + 9237 (slice-empty? %ecx) # => eax + 9238 3d/compare-eax-and 0/imm32/false + 9239 0f 85/jump-if-!= break/disp32 + 9240 # if (name == "<-") abort + 9241 (slice-equal? %ecx "<-") + 9242 3d/compare-eax-and 0/imm32/false + 9243 0f 85/jump-if-!= $add-operation-and-inputs-to-stmt:abort/disp32 + 9244 # if (is-get? && second operand) lookup or create offset + 9245 { + 9246 81 7/subop/compare %ebx 0/imm32/false 9247 74/jump-if-= break/disp8 - 9248 (lookup-or-create-constant %eax %ecx %esi) - 9249 #? (lookup *esi *(esi+4)) - 9250 #? (write-buffered Stderr "creating new output var ") - 9251 #? (write-int32-hex-buffered Stderr %eax) - 9252 #? (write-buffered Stderr " for field called ") - 9253 #? (write-slice-buffered Stderr %ecx) - 9254 #? (write-buffered Stderr "; var name ") - 9255 #? (lookup *eax *(eax+4)) # Var-name - 9256 #? (write-buffered Stderr %eax) - 9257 #? (write-buffered Stderr Newline) - 9258 #? (flush Stderr) - 9259 e9/jump $add-operation-and-inputs-to-stmt:save-var/disp32 - 9260 } - 9261 # is-deref? = false - 9262 ba/copy-to-edx 0/imm32/false - 9263 # if (slice-starts-with?(name, '*')) ++name->start and set is-deref? - 9264 8b/-> *ecx 0/r32/eax # Slice-start - 9265 8a/copy-byte *eax 0/r32/AL - 9266 81 4/subop/and %eax 0xff/imm32 - 9267 3d/compare-eax-and 0x2a/imm32/asterisk - 9268 { - 9269 75/jump-if-!= break/disp8 - 9270 $add-operation-and-inputs-to-stmt:inout-is-deref: - 9271 ff 0/subop/increment *ecx - 9272 ba/copy-to-edx 1/imm32/true - 9273 } - 9274 (lookup-var-or-literal %ecx *(ebp+0x10) %esi *(ebp+0x14) *(ebp+0x18) *(ebp+0x1c)) - 9275 $add-operation-and-inputs-to-stmt:save-var: - 9276 8d/copy-address *(edi+0xc) 0/r32/eax - 9277 (append-stmt-var Heap *esi *(esi+4) *(edi+0xc) *(edi+0x10) %edx %eax) # Stmt1-inouts or Regvardef-inouts - 9278 # - 9279 e9/jump loop/disp32 - 9280 } - 9281 $add-operation-and-inputs-to-stmt:end: - 9282 # . reclaim locals - 9283 81 0/subop/add %esp 0x10/imm32 - 9284 # . restore registers - 9285 5f/pop-to-edi - 9286 5e/pop-to-esi - 9287 5b/pop-to-ebx - 9288 5a/pop-to-edx - 9289 59/pop-to-ecx - 9290 58/pop-to-eax - 9291 # . epilogue - 9292 89/<- %esp 5/r32/ebp - 9293 5d/pop-to-ebp - 9294 c3/return - 9295 - 9296 $add-operation-and-inputs-to-stmt:abort: - 9297 # error("fn ___: invalid identifier in '" line "'\n") - 9298 (write-buffered *(ebp+0x18) "fn ") - 9299 8b/-> *(ebp+0x14) 0/r32/eax - 9300 (lookup *eax *(eax+4)) # Function-name Function-name => eax - 9301 (write-buffered *(ebp+0x18) %eax) - 9302 (rewind-stream *(ebp+0xc)) - 9303 (write-buffered *(ebp+0x18) ": invalid identifier in '") - 9304 (write-stream-data *(ebp+0x18) *(ebp+0xc)) - 9305 (write-buffered *(ebp+0x18) "'\n") - 9306 (flush *(ebp+0x18)) - 9307 (stop *(ebp+0x1c) 1) - 9308 # never gets here - 9309 - 9310 stmt-has-outputs?: # line: (addr stream byte) -> result/eax: boolean - 9311 # . prologue - 9312 55/push-ebp - 9313 89/<- %ebp 4/r32/esp - 9314 # . save registers - 9315 51/push-ecx - 9316 # var word-slice/ecx: slice - 9317 68/push 0/imm32/end - 9318 68/push 0/imm32/start - 9319 89/<- %ecx 4/r32/esp - 9320 # result = false - 9321 b8/copy-to-eax 0/imm32/false - 9322 (rewind-stream *(ebp+8)) - 9323 { - 9324 (next-mu-token *(ebp+8) %ecx) - 9325 # if slice-empty?(word-slice) break - 9326 (slice-empty? %ecx) - 9327 3d/compare-eax-and 0/imm32/false - 9328 b8/copy-to-eax 0/imm32/false/result # restore result (if we're here it's still false) - 9329 0f 85/jump-if-!= break/disp32 - 9330 # if slice-starts-with?(word-slice, '#') break - 9331 # . eax = *word-slice->start - 9332 8b/-> *ecx 0/r32/eax - 9333 8a/copy-byte *eax 0/r32/AL - 9334 81 4/subop/and %eax 0xff/imm32 - 9335 # . if (eax == '#') break - 9336 3d/compare-eax-and 0x23/imm32/hash - 9337 b8/copy-to-eax 0/imm32/false/result # restore result (if we're here it's still false) - 9338 0f 84/jump-if-= break/disp32 - 9339 # if slice-equal?(word-slice, '<-') return true - 9340 (slice-equal? %ecx "<-") - 9341 3d/compare-eax-and 0/imm32/false - 9342 74/jump-if-= loop/disp8 - 9343 b8/copy-to-eax 1/imm32/true - 9344 } - 9345 $stmt-has-outputs:end: - 9346 (rewind-stream *(ebp+8)) - 9347 # . reclaim locals - 9348 81 0/subop/add %esp 8/imm32 - 9349 # . restore registers - 9350 59/pop-to-ecx - 9351 # . epilogue - 9352 89/<- %esp 5/r32/ebp - 9353 5d/pop-to-ebp - 9354 c3/return - 9355 - 9356 # if 'name' starts with a digit, create a new literal var for it - 9357 # otherwise return first 'name' from the top (back) of 'vars' and abort if not found - 9358 lookup-var-or-literal: # name: (addr slice), vars: (addr stack live-var), out: (addr handle var), fn: (addr function), err: (addr buffered-file), ed: (addr exit-descriptor) - 9359 # . prologue - 9360 55/push-ebp - 9361 89/<- %ebp 4/r32/esp - 9362 # . save registers - 9363 50/push-eax - 9364 51/push-ecx - 9365 56/push-esi - 9366 # esi = name - 9367 8b/-> *(ebp+8) 6/r32/esi - 9368 # if slice-empty?(name) abort - 9369 (slice-empty? %esi) # => eax - 9370 3d/compare-eax-and 0/imm32/false - 9371 0f 85/jump-if-!= $lookup-var-or-literal:abort/disp32 - 9372 # var c/ecx: byte = *name->start - 9373 8b/-> *esi 1/r32/ecx - 9374 8a/copy-byte *ecx 1/r32/CL - 9375 81 4/subop/and %ecx 0xff/imm32 - 9376 # if is-decimal-digit?(c) return new var(name) - 9377 { - 9378 (is-decimal-digit? %ecx) # => eax - 9379 3d/compare-eax-and 0/imm32/false - 9380 74/jump-if-= break/disp8 - 9381 $lookup-var-or-literal:literal: - 9382 (new-literal-integer Heap %esi *(ebp+0x10) *(ebp+0x14) *(ebp+0x18) *(ebp+0x1c)) - 9383 eb/jump $lookup-var-or-literal:end/disp8 - 9384 } - 9385 # else if (c == '"') return new var(name) - 9386 { - 9387 81 7/subop/compare %ecx 0x22/imm32/dquote - 9388 75/jump-if-!= break/disp8 - 9389 $lookup-var-or-literal:literal-string: - 9390 (new-literal Heap %esi *(ebp+0x10)) - 9391 eb/jump $lookup-var-or-literal:end/disp8 - 9392 } - 9393 # otherwise return lookup-var(name, vars) - 9394 { - 9395 $lookup-var-or-literal:var: - 9396 (lookup-var %esi *(ebp+0xc) *(ebp+0x10) *(ebp+0x14) *(ebp+0x18) *(ebp+0x1c)) - 9397 } - 9398 $lookup-var-or-literal:end: - 9399 # . restore registers - 9400 5e/pop-to-esi - 9401 59/pop-to-ecx - 9402 58/pop-to-eax - 9403 # . epilogue - 9404 89/<- %esp 5/r32/ebp - 9405 5d/pop-to-ebp - 9406 c3/return - 9407 - 9408 $lookup-var-or-literal:abort: - 9409 (write-buffered *(ebp+0x18) "fn ") - 9410 8b/-> *(ebp+0x14) 0/r32/eax - 9411 (lookup *eax *(eax+4)) # Function-name Function-name => eax - 9412 (write-buffered *(ebp+0x18) %eax) - 9413 (write-buffered *(ebp+0x18) ": empty variable!") - 9414 (flush *(ebp+0x18)) - 9415 (stop *(ebp+0x1c) 1) - 9416 # never gets here - 9417 - 9418 # return first 'name' from the top (back) of 'vars' and abort if not found - 9419 lookup-var: # name: (addr slice), vars: (addr stack live-var), out: (addr handle var), fn: (addr function), err: (addr buffered-file), ed: (addr exit-descriptor) - 9420 # . prologue - 9421 55/push-ebp - 9422 89/<- %ebp 4/r32/esp - 9423 # . save registers - 9424 50/push-eax - 9425 # - 9426 (lookup-var-helper *(ebp+8) *(ebp+0xc) *(ebp+0x10) *(ebp+0x14) *(ebp+0x18) *(ebp+0x1c)) - 9427 # if (*out == 0) abort - 9428 8b/-> *(ebp+0x10) 0/r32/eax - 9429 81 7/subop/compare *eax 0/imm32 - 9430 74/jump-if-= $lookup-var:abort/disp8 - 9431 $lookup-var:end: - 9432 # . restore registers - 9433 58/pop-to-eax - 9434 # . epilogue - 9435 89/<- %esp 5/r32/ebp - 9436 5d/pop-to-ebp - 9437 c3/return - 9438 - 9439 $lookup-var:abort: - 9440 (write-buffered *(ebp+0x18) "fn ") - 9441 8b/-> *(ebp+0x14) 0/r32/eax - 9442 (lookup *eax *(eax+4)) # Function-name Function-name => eax - 9443 (write-buffered *(ebp+0x18) %eax) - 9444 (write-buffered *(ebp+0x18) ": unknown variable '") - 9445 (write-slice-buffered *(ebp+0x18) *(ebp+8)) - 9446 (write-buffered *(ebp+0x18) "'\n") - 9447 (flush *(ebp+0x18)) - 9448 (stop *(ebp+0x1c) 1) - 9449 # never gets here - 9450 - 9451 # return first 'name' from the top (back) of 'vars', and 0/null if not found - 9452 # ensure that 'name' if in a register is the topmost variable in that register - 9453 lookup-var-helper: # name: (addr slice), vars: (addr stack live-var), out: (addr handle var), fn: (addr function), err: (addr buffered-file), ed: (addr exit-descriptor) - 9454 # pseudocode: - 9455 # var curr: (addr handle var) = &vars->data[vars->top - 12] - 9456 # var min = vars->data - 9457 # while curr >= min - 9458 # var v: (handle var) = *curr - 9459 # if v->name == name - 9460 # return - 9461 # curr -= 12 - 9462 # - 9463 # . prologue - 9464 55/push-ebp - 9465 89/<- %ebp 4/r32/esp - 9466 # . save registers - 9467 50/push-eax - 9468 51/push-ecx - 9469 52/push-edx - 9470 53/push-ebx - 9471 56/push-esi - 9472 57/push-edi - 9473 # clear out - 9474 (zero-out *(ebp+0x10) *Handle-size) - 9475 # esi = vars - 9476 8b/-> *(ebp+0xc) 6/r32/esi - 9477 # ebx = vars->top - 9478 8b/-> *esi 3/r32/ebx - 9479 # if (vars->top > vars->size) abort - 9480 3b/compare<- *(esi+4) 0/r32/eax - 9481 0f 8f/jump-if-> $lookup-var-helper:error1/disp32 - 9482 # var min/edx: (addr handle var) = vars->data - 9483 8d/copy-address *(esi+8) 2/r32/edx - 9484 # var curr/ebx: (addr handle var) = &vars->data[vars->top - 12] - 9485 8d/copy-address *(esi+ebx-4) 3/r32/ebx # vars + 8 + vars->type - 12 - 9486 # var var-in-reg/edi: 8 addrs - 9487 68/push 0/imm32 - 9488 68/push 0/imm32 - 9489 68/push 0/imm32 + 9248 (lookup *(edi+0xc) *(edi+0x10)) # Stmt1-inouts Stmt1-inouts => eax + 9249 3d/compare-eax-and 0/imm32 + 9250 74/jump-if-= break/disp8 + 9251 (lookup-or-create-constant %eax %ecx %esi) + 9252 #? (lookup *esi *(esi+4)) + 9253 #? (write-buffered Stderr "creating new output var ") + 9254 #? (write-int32-hex-buffered Stderr %eax) + 9255 #? (write-buffered Stderr " for field called ") + 9256 #? (write-slice-buffered Stderr %ecx) + 9257 #? (write-buffered Stderr "; var name ") + 9258 #? (lookup *eax *(eax+4)) # Var-name + 9259 #? (write-buffered Stderr %eax) + 9260 #? (write-buffered Stderr Newline) + 9261 #? (flush Stderr) + 9262 e9/jump $add-operation-and-inputs-to-stmt:save-var/disp32 + 9263 } + 9264 # is-deref? = false + 9265 ba/copy-to-edx 0/imm32/false + 9266 # if (slice-starts-with?(name, '*')) ++name->start and set is-deref? + 9267 8b/-> *ecx 0/r32/eax # Slice-start + 9268 8a/copy-byte *eax 0/r32/AL + 9269 81 4/subop/and %eax 0xff/imm32 + 9270 3d/compare-eax-and 0x2a/imm32/asterisk + 9271 { + 9272 75/jump-if-!= break/disp8 + 9273 $add-operation-and-inputs-to-stmt:inout-is-deref: + 9274 ff 0/subop/increment *ecx + 9275 ba/copy-to-edx 1/imm32/true + 9276 } + 9277 (lookup-var-or-literal %ecx *(ebp+0x10) %esi *(ebp+0x14) *(ebp+0x18) *(ebp+0x1c)) + 9278 $add-operation-and-inputs-to-stmt:save-var: + 9279 8d/copy-address *(edi+0xc) 0/r32/eax + 9280 (append-stmt-var Heap *esi *(esi+4) *(edi+0xc) *(edi+0x10) %edx %eax) # Stmt1-inouts or Regvardef-inouts + 9281 # + 9282 e9/jump loop/disp32 + 9283 } + 9284 $add-operation-and-inputs-to-stmt:end: + 9285 # . reclaim locals + 9286 81 0/subop/add %esp 0x10/imm32 + 9287 # . restore registers + 9288 5f/pop-to-edi + 9289 5e/pop-to-esi + 9290 5b/pop-to-ebx + 9291 5a/pop-to-edx + 9292 59/pop-to-ecx + 9293 58/pop-to-eax + 9294 # . epilogue + 9295 89/<- %esp 5/r32/ebp + 9296 5d/pop-to-ebp + 9297 c3/return + 9298 + 9299 $add-operation-and-inputs-to-stmt:abort: + 9300 # error("fn ___: invalid identifier in '" line "'\n") + 9301 (write-buffered *(ebp+0x18) "fn ") + 9302 8b/-> *(ebp+0x14) 0/r32/eax + 9303 (lookup *eax *(eax+4)) # Function-name Function-name => eax + 9304 (write-buffered *(ebp+0x18) %eax) + 9305 (rewind-stream *(ebp+0xc)) + 9306 (write-buffered *(ebp+0x18) ": invalid identifier in '") + 9307 (write-stream-data *(ebp+0x18) *(ebp+0xc)) + 9308 (write-buffered *(ebp+0x18) "'\n") + 9309 (flush *(ebp+0x18)) + 9310 (stop *(ebp+0x1c) 1) + 9311 # never gets here + 9312 + 9313 stmt-has-outputs?: # line: (addr stream byte) -> result/eax: boolean + 9314 # . prologue + 9315 55/push-ebp + 9316 89/<- %ebp 4/r32/esp + 9317 # . save registers + 9318 51/push-ecx + 9319 # var word-slice/ecx: slice + 9320 68/push 0/imm32/end + 9321 68/push 0/imm32/start + 9322 89/<- %ecx 4/r32/esp + 9323 # result = false + 9324 b8/copy-to-eax 0/imm32/false + 9325 (rewind-stream *(ebp+8)) + 9326 { + 9327 (next-mu-token *(ebp+8) %ecx) + 9328 # if slice-empty?(word-slice) break + 9329 (slice-empty? %ecx) + 9330 3d/compare-eax-and 0/imm32/false + 9331 b8/copy-to-eax 0/imm32/false/result # restore result (if we're here it's still false) + 9332 0f 85/jump-if-!= break/disp32 + 9333 # if slice-starts-with?(word-slice, '#') break + 9334 # . eax = *word-slice->start + 9335 8b/-> *ecx 0/r32/eax + 9336 8a/copy-byte *eax 0/r32/AL + 9337 81 4/subop/and %eax 0xff/imm32 + 9338 # . if (eax == '#') break + 9339 3d/compare-eax-and 0x23/imm32/hash + 9340 b8/copy-to-eax 0/imm32/false/result # restore result (if we're here it's still false) + 9341 0f 84/jump-if-= break/disp32 + 9342 # if slice-equal?(word-slice, '<-') return true + 9343 (slice-equal? %ecx "<-") + 9344 3d/compare-eax-and 0/imm32/false + 9345 74/jump-if-= loop/disp8 + 9346 b8/copy-to-eax 1/imm32/true + 9347 } + 9348 $stmt-has-outputs:end: + 9349 (rewind-stream *(ebp+8)) + 9350 # . reclaim locals + 9351 81 0/subop/add %esp 8/imm32 + 9352 # . restore registers + 9353 59/pop-to-ecx + 9354 # . epilogue + 9355 89/<- %esp 5/r32/ebp + 9356 5d/pop-to-ebp + 9357 c3/return + 9358 + 9359 # if 'name' starts with a digit, create a new literal var for it + 9360 # otherwise return first 'name' from the top (back) of 'vars' and abort if not found + 9361 lookup-var-or-literal: # name: (addr slice), vars: (addr stack live-var), out: (addr handle var), fn: (addr function), err: (addr buffered-file), ed: (addr exit-descriptor) + 9362 # . prologue + 9363 55/push-ebp + 9364 89/<- %ebp 4/r32/esp + 9365 # . save registers + 9366 50/push-eax + 9367 51/push-ecx + 9368 56/push-esi + 9369 # esi = name + 9370 8b/-> *(ebp+8) 6/r32/esi + 9371 # if slice-empty?(name) abort + 9372 (slice-empty? %esi) # => eax + 9373 3d/compare-eax-and 0/imm32/false + 9374 0f 85/jump-if-!= $lookup-var-or-literal:abort/disp32 + 9375 # var c/ecx: byte = *name->start + 9376 8b/-> *esi 1/r32/ecx + 9377 8a/copy-byte *ecx 1/r32/CL + 9378 81 4/subop/and %ecx 0xff/imm32 + 9379 # if is-decimal-digit?(c) return new var(name) + 9380 { + 9381 (is-decimal-digit? %ecx) # => eax + 9382 3d/compare-eax-and 0/imm32/false + 9383 74/jump-if-= break/disp8 + 9384 $lookup-var-or-literal:literal: + 9385 (new-literal-integer Heap %esi *(ebp+0x10) *(ebp+0x14) *(ebp+0x18) *(ebp+0x1c)) + 9386 eb/jump $lookup-var-or-literal:end/disp8 + 9387 } + 9388 # else if (c == '"') return new var(name) + 9389 { + 9390 81 7/subop/compare %ecx 0x22/imm32/dquote + 9391 75/jump-if-!= break/disp8 + 9392 $lookup-var-or-literal:literal-string: + 9393 (new-literal Heap %esi *(ebp+0x10)) + 9394 eb/jump $lookup-var-or-literal:end/disp8 + 9395 } + 9396 # otherwise return lookup-var(name, vars) + 9397 { + 9398 $lookup-var-or-literal:var: + 9399 (lookup-var %esi *(ebp+0xc) *(ebp+0x10) *(ebp+0x14) *(ebp+0x18) *(ebp+0x1c)) + 9400 } + 9401 $lookup-var-or-literal:end: + 9402 # . restore registers + 9403 5e/pop-to-esi + 9404 59/pop-to-ecx + 9405 58/pop-to-eax + 9406 # . epilogue + 9407 89/<- %esp 5/r32/ebp + 9408 5d/pop-to-ebp + 9409 c3/return + 9410 + 9411 $lookup-var-or-literal:abort: + 9412 (write-buffered *(ebp+0x18) "fn ") + 9413 8b/-> *(ebp+0x14) 0/r32/eax + 9414 (lookup *eax *(eax+4)) # Function-name Function-name => eax + 9415 (write-buffered *(ebp+0x18) %eax) + 9416 (write-buffered *(ebp+0x18) ": empty variable!") + 9417 (flush *(ebp+0x18)) + 9418 (stop *(ebp+0x1c) 1) + 9419 # never gets here + 9420 + 9421 # return first 'name' from the top (back) of 'vars' and abort if not found + 9422 lookup-var: # name: (addr slice), vars: (addr stack live-var), out: (addr handle var), fn: (addr function), err: (addr buffered-file), ed: (addr exit-descriptor) + 9423 # . prologue + 9424 55/push-ebp + 9425 89/<- %ebp 4/r32/esp + 9426 # . save registers + 9427 50/push-eax + 9428 # + 9429 (lookup-var-helper *(ebp+8) *(ebp+0xc) *(ebp+0x10) *(ebp+0x14) *(ebp+0x18) *(ebp+0x1c)) + 9430 # if (*out == 0) abort + 9431 8b/-> *(ebp+0x10) 0/r32/eax + 9432 81 7/subop/compare *eax 0/imm32 + 9433 74/jump-if-= $lookup-var:abort/disp8 + 9434 $lookup-var:end: + 9435 # . restore registers + 9436 58/pop-to-eax + 9437 # . epilogue + 9438 89/<- %esp 5/r32/ebp + 9439 5d/pop-to-ebp + 9440 c3/return + 9441 + 9442 $lookup-var:abort: + 9443 (write-buffered *(ebp+0x18) "fn ") + 9444 8b/-> *(ebp+0x14) 0/r32/eax + 9445 (lookup *eax *(eax+4)) # Function-name Function-name => eax + 9446 (write-buffered *(ebp+0x18) %eax) + 9447 (write-buffered *(ebp+0x18) ": unknown variable '") + 9448 (write-slice-buffered *(ebp+0x18) *(ebp+8)) + 9449 (write-buffered *(ebp+0x18) "'\n") + 9450 (flush *(ebp+0x18)) + 9451 (stop *(ebp+0x1c) 1) + 9452 # never gets here + 9453 + 9454 # return first 'name' from the top (back) of 'vars', and 0/null if not found + 9455 # ensure that 'name' if in a register is the topmost variable in that register + 9456 lookup-var-helper: # name: (addr slice), vars: (addr stack live-var), out: (addr handle var), fn: (addr function), err: (addr buffered-file), ed: (addr exit-descriptor) + 9457 # pseudocode: + 9458 # var curr: (addr handle var) = &vars->data[vars->top - 12] + 9459 # var min = vars->data + 9460 # while curr >= min + 9461 # var v: (handle var) = *curr + 9462 # if v->name == name + 9463 # return + 9464 # curr -= 12 + 9465 # + 9466 # . prologue + 9467 55/push-ebp + 9468 89/<- %ebp 4/r32/esp + 9469 # . save registers + 9470 50/push-eax + 9471 51/push-ecx + 9472 52/push-edx + 9473 53/push-ebx + 9474 56/push-esi + 9475 57/push-edi + 9476 # clear out + 9477 (zero-out *(ebp+0x10) *Handle-size) + 9478 # esi = vars + 9479 8b/-> *(ebp+0xc) 6/r32/esi + 9480 # ebx = vars->top + 9481 8b/-> *esi 3/r32/ebx + 9482 # if (vars->top > vars->size) abort + 9483 3b/compare<- *(esi+4) 0/r32/eax + 9484 0f 8f/jump-if-> $lookup-var-helper:error1/disp32 + 9485 # var min/edx: (addr handle var) = vars->data + 9486 8d/copy-address *(esi+8) 2/r32/edx + 9487 # var curr/ebx: (addr handle var) = &vars->data[vars->top - 12] + 9488 8d/copy-address *(esi+ebx-4) 3/r32/ebx # vars + 8 + vars->type - 12 + 9489 # var var-in-reg/edi: 8 addrs 9490 68/push 0/imm32 9491 68/push 0/imm32 9492 68/push 0/imm32 9493 68/push 0/imm32 9494 68/push 0/imm32 - 9495 89/<- %edi 4/r32/esp - 9496 { - 9497 $lookup-var-helper:loop: - 9498 # if (curr < min) return - 9499 39/compare %ebx 2/r32/edx - 9500 0f 82/jump-if-addr< break/disp32 - 9501 # var v/ecx: (addr var) = lookup(*curr) - 9502 (lookup *ebx *(ebx+4)) # => eax - 9503 89/<- %ecx 0/r32/eax - 9504 # var vn/eax: (addr array byte) = lookup(v->name) - 9505 (lookup *ecx *(ecx+4)) # Var-name Var-name => eax - 9506 # if (vn == name) return curr - 9507 (slice-equal? *(ebp+8) %eax) # => eax - 9508 3d/compare-eax-and 0/imm32/false - 9509 { - 9510 74/jump-if-= break/disp8 - 9511 $lookup-var-helper:found: - 9512 # var vr/eax: (addr array byte) = lookup(v->register) - 9513 (lookup *(ecx+0x18) *(ecx+0x1c)) # Var-register Var-register => eax - 9514 3d/compare-eax-and 0/imm32 - 9515 { - 9516 74/jump-if-= break/disp8 - 9517 $lookup-var-helper:found-register: - 9518 # var reg/eax: int = get(Registers, vr) - 9519 (get Mu-registers %eax 0xc "Mu-registers") # => eax - 9520 8b/-> *eax 0/r32/eax - 9521 # if (var-in-reg[reg]) error - 9522 8b/-> *(edi+eax<<2) 0/r32/eax - 9523 3d/compare-eax-and 0/imm32 - 9524 0f 85/jump-if-!= $lookup-var-helper:error2/disp32 - 9525 } - 9526 $lookup-var-helper:return: - 9527 # esi = out - 9528 8b/-> *(ebp+0x10) 6/r32/esi - 9529 # *out = *curr - 9530 8b/-> *ebx 0/r32/eax - 9531 89/<- *esi 0/r32/eax - 9532 8b/-> *(ebx+4) 0/r32/eax - 9533 89/<- *(esi+4) 0/r32/eax - 9534 # return - 9535 eb/jump $lookup-var-helper:end/disp8 - 9536 } - 9537 # 'name' not yet found; update var-in-reg if v in register - 9538 # . var vr/eax: (addr array byte) = lookup(v->register) - 9539 (lookup *(ecx+0x18) *(ecx+0x1c)) # Var-register Var-register => eax - 9540 # . if (var == 0) continue - 9541 3d/compare-eax-and 0/imm32 - 9542 74/jump-if-= $lookup-var-helper:continue/disp8 - 9543 # . var reg/eax: int = get(Registers, vr) - 9544 (get Mu-registers %eax 0xc "Mu-registers") # => eax - 9545 8b/-> *eax 0/r32/eax - 9546 # . if (var-in-reg[reg] == 0) var-in-reg[reg] = v - 9547 81 7/subop/compare *(edi+eax<<2) 0/imm32 - 9548 75/jump-if-!= $lookup-var-helper:continue/disp8 - 9549 89/<- *(edi+eax<<2) 1/r32/ecx - 9550 $lookup-var-helper:continue: - 9551 # curr -= 12 - 9552 81 5/subop/subtract %ebx 0xc/imm32 - 9553 e9/jump loop/disp32 - 9554 } - 9555 $lookup-var-helper:end: - 9556 # . reclaim locals - 9557 81 0/subop/add %esp 0x20/imm32 - 9558 # . restore registers - 9559 5f/pop-to-edi - 9560 5e/pop-to-esi - 9561 5b/pop-to-ebx - 9562 5a/pop-to-edx - 9563 59/pop-to-ecx - 9564 58/pop-to-eax - 9565 # . epilogue - 9566 89/<- %esp 5/r32/ebp - 9567 5d/pop-to-ebp - 9568 c3/return - 9569 - 9570 $lookup-var-helper:error1: - 9571 (write-buffered *(ebp+0x18) "fn ") - 9572 8b/-> *(ebp+0x14) 0/r32/eax - 9573 (lookup *eax *(eax+4)) # Function-name Function-name => eax - 9574 (write-buffered *(ebp+0x18) %eax) - 9575 (write-buffered *(ebp+0x18) ": malformed stack when looking up '") - 9576 (write-slice-buffered *(ebp+0x18) *(ebp+8)) - 9577 (write-buffered *(ebp+0x18) "'\n") - 9578 (flush *(ebp+0x18)) - 9579 (stop *(ebp+0x1c) 1) - 9580 # never gets here - 9581 - 9582 $lookup-var-helper:error2: - 9583 # eax contains the conflicting var at this point - 9584 (write-buffered *(ebp+0x18) "fn ") - 9585 50/push-eax - 9586 8b/-> *(ebp+0x14) 0/r32/eax - 9587 (lookup *eax *(eax+4)) # Function-name Function-name => eax - 9588 (write-buffered *(ebp+0x18) %eax) - 9589 58/pop-eax - 9590 (write-buffered *(ebp+0x18) ": register ") - 9591 50/push-eax - 9592 (lookup *(eax+0x18) *(eax+0x1c)) # Var-register Var-register => eax - 9593 (write-buffered *(ebp+0x18) %eax) - 9594 58/pop-to-eax - 9595 (write-buffered *(ebp+0x18) " reads var '") - 9596 (write-slice-buffered *(ebp+0x18) *(ebp+8)) - 9597 (write-buffered *(ebp+0x18) "' after writing var '") - 9598 (lookup *eax *(eax+4)) # Var-name Var-name => eax - 9599 (write-buffered *(ebp+0x18) %eax) - 9600 (write-buffered *(ebp+0x18) "'\n") - 9601 (flush *(ebp+0x18)) - 9602 (stop *(ebp+0x1c) 1) - 9603 # never gets here - 9604 - 9605 dump-vars: # vars: (addr stack live-var) - 9606 # pseudocode: - 9607 # var curr: (addr handle var) = &vars->data[vars->top - 12] - 9608 # var min = vars->data - 9609 # while curr >= min - 9610 # var v: (handle var) = *curr - 9611 # print v - 9612 # curr -= 12 - 9613 # - 9614 # . prologue - 9615 55/push-ebp - 9616 89/<- %ebp 4/r32/esp - 9617 # . save registers - 9618 52/push-edx - 9619 53/push-ebx - 9620 56/push-esi - 9621 # esi = vars - 9622 8b/-> *(ebp+8) 6/r32/esi - 9623 # ebx = vars->top - 9624 8b/-> *esi 3/r32/ebx - 9625 # var min/edx: (addr handle var) = vars->data - 9626 8d/copy-address *(esi+8) 2/r32/edx - 9627 # var curr/ebx: (addr handle var) = &vars->data[vars->top - 12] - 9628 8d/copy-address *(esi+ebx-4) 3/r32/ebx # vars + 8 + vars->type - 12 - 9629 { - 9630 $dump-vars:loop: - 9631 # if (curr < min) return - 9632 39/compare %ebx 2/r32/edx - 9633 0f 82/jump-if-addr< break/disp32 - 9634 # - 9635 (write-buffered Stderr " var@") - 9636 (dump-var 2 %ebx) - 9637 # curr -= 12 - 9638 81 5/subop/subtract %ebx 0xc/imm32 - 9639 e9/jump loop/disp32 - 9640 } - 9641 $dump-vars:end: - 9642 # . restore registers - 9643 5e/pop-to-esi - 9644 5b/pop-to-ebx - 9645 5a/pop-to-edx - 9646 # . epilogue - 9647 89/<- %esp 5/r32/ebp - 9648 5d/pop-to-ebp - 9649 c3/return - 9650 - 9651 == data - 9652 # Like Registers, but no esp or ebp - 9653 Mu-registers: # (addr stream {(handle array byte), int}) - 9654 # a table is a stream - 9655 0x48/imm32/write - 9656 0/imm32/read - 9657 0x48/imm32/length - 9658 # data - 9659 # it is perfectly ok to use fake alloc-ids -- as long as you never try to reclaim them - 9660 0x11/imm32/alloc-id $Mu-register-eax/imm32 0/imm32 - 9661 0x11/imm32/alloc-id $Mu-register-ecx/imm32 1/imm32 - 9662 0x11/imm32/alloc-id $Mu-register-edx/imm32 2/imm32 - 9663 0x11/imm32/alloc-id $Mu-register-ebx/imm32 3/imm32 - 9664 0x11/imm32/alloc-id $Mu-register-esi/imm32 6/imm32 - 9665 0x11/imm32/alloc-id $Mu-register-edi/imm32 7/imm32 - 9666 - 9667 $Mu-register-eax: - 9668 0x11/imm32/alloc-id - 9669 3/imm32/size - 9670 0x65/e 0x61/a 0x78/x - 9671 - 9672 $Mu-register-ecx: - 9673 0x11/imm32/alloc-id - 9674 3/imm32/size - 9675 0x65/e 0x63/c 0x78/x - 9676 - 9677 $Mu-register-edx: - 9678 0x11/imm32/alloc-id - 9679 3/imm32/size - 9680 0x65/e 0x64/d 0x78/x - 9681 - 9682 $Mu-register-ebx: - 9683 0x11/imm32/alloc-id - 9684 3/imm32/size - 9685 0x65/e 0x62/b 0x78/x - 9686 - 9687 $Mu-register-esi: - 9688 0x11/imm32/alloc-id - 9689 3/imm32/size - 9690 0x65/e 0x73/s 0x69/i - 9691 - 9692 $Mu-register-edi: - 9693 0x11/imm32/alloc-id - 9694 3/imm32/size - 9695 0x65/e 0x64/d 0x69/i - 9696 - 9697 == code - 9698 - 9699 # return first 'name' from the top (back) of 'vars' and create a new var for a fn output if not found - 9700 lookup-var-or-find-in-fn-outputs: # name: (addr slice), vars: (addr stack live-var), fn: (addr function), out: (addr handle var), err: (addr buffered-file), ed: (addr exit-descriptor) - 9701 # . prologue - 9702 55/push-ebp - 9703 89/<- %ebp 4/r32/esp - 9704 # . save registers - 9705 50/push-eax - 9706 # - 9707 (lookup-var-helper *(ebp+8) *(ebp+0xc) *(ebp+0x14) *(ebp+0x10) *(ebp+0x18) *(ebp+0x1c)) # arg order slightly different; 'fn' is deemphasized - 9708 { - 9709 # if (out != 0) return - 9710 8b/-> *(ebp+0x14) 0/r32/eax - 9711 81 7/subop/compare *eax 0/imm32 - 9712 75/jump-if-!= break/disp8 - 9713 # if name is one of fn's outputs, return it - 9714 (find-in-function-outputs *(ebp+0x10) *(ebp+8) *(ebp+0x14)) - 9715 8b/-> *(ebp+0x14) 0/r32/eax - 9716 81 7/subop/compare *eax 0/imm32 - 9717 # otherwise abort - 9718 0f 84/jump-if-= $lookup-or-define-var:abort/disp32 - 9719 } - 9720 $lookup-or-define-var:end: - 9721 # . restore registers - 9722 58/pop-to-eax - 9723 # . epilogue - 9724 89/<- %esp 5/r32/ebp - 9725 5d/pop-to-ebp - 9726 c3/return - 9727 - 9728 $lookup-or-define-var:abort: - 9729 (write-buffered *(ebp+0x18) "unknown variable '") - 9730 (write-slice-buffered *(ebp+0x18) *(ebp+8)) - 9731 (write-buffered *(ebp+0x18) "'\n") - 9732 (flush *(ebp+0x18)) - 9733 (stop *(ebp+0x1c) 1) - 9734 # never gets here - 9735 - 9736 find-in-function-outputs: # fn: (addr function), name: (addr slice), out: (addr handle var) - 9737 # . prologue - 9738 55/push-ebp - 9739 89/<- %ebp 4/r32/esp - 9740 # . save registers - 9741 50/push-eax - 9742 51/push-ecx - 9743 # var curr/ecx: (addr list var) = lookup(fn->outputs) - 9744 8b/-> *(ebp+8) 1/r32/ecx - 9745 (lookup *(ecx+0x10) *(ecx+0x14)) # Function-outputs Function-outputs => eax - 9746 89/<- %ecx 0/r32/eax - 9747 # while curr != null - 9748 { - 9749 81 7/subop/compare %ecx 0/imm32 - 9750 74/jump-if-= break/disp8 - 9751 # var v/eax: (addr var) = lookup(curr->value) - 9752 (lookup *ecx *(ecx+4)) # List-value List-value => eax - 9753 # var s/eax: (addr array byte) = lookup(v->name) - 9754 (lookup *eax *(eax+4)) # Var-name Var-name => eax - 9755 # if (s == name) return curr->value - 9756 (slice-equal? *(ebp+0xc) %eax) # => eax - 9757 3d/compare-eax-and 0/imm32/false - 9758 { - 9759 74/jump-if-= break/disp8 - 9760 # var edi = out - 9761 57/push-edi - 9762 8b/-> *(ebp+0x10) 7/r32/edi - 9763 # *out = curr->value - 9764 8b/-> *ecx 0/r32/eax - 9765 89/<- *edi 0/r32/eax - 9766 8b/-> *(ecx+4) 0/r32/eax - 9767 89/<- *(edi+4) 0/r32/eax - 9768 # - 9769 5f/pop-to-edi - 9770 eb/jump $find-in-function-outputs:end/disp8 - 9771 } - 9772 # curr = curr->next - 9773 (lookup *(ecx+8) *(ecx+0xc)) # List-next List-next => eax - 9774 89/<- %ecx 0/r32/eax - 9775 # - 9776 eb/jump loop/disp8 - 9777 } - 9778 b8/copy-to-eax 0/imm32 - 9779 $find-in-function-outputs:end: - 9780 # . restore registers - 9781 59/pop-to-ecx - 9782 58/pop-to-eax - 9783 # . epilogue - 9784 89/<- %esp 5/r32/ebp - 9785 5d/pop-to-ebp - 9786 c3/return - 9787 - 9788 # push 'out' to 'vars' if not already there; it's assumed to be a fn output - 9789 maybe-define-var: # out: (handle var), vars: (addr stack live-var) - 9790 # . prologue - 9791 55/push-ebp - 9792 89/<- %ebp 4/r32/esp - 9793 # . save registers - 9794 50/push-eax - 9795 # var out-addr/eax: (addr var) - 9796 (lookup *(ebp+8) *(ebp+0xc)) # => eax - 9797 # - 9798 (binding-exists? %eax *(ebp+0x10)) # => eax - 9799 3d/compare-eax-and 0/imm32/false - 9800 75/jump-if-!= $maybe-define-var:end/disp8 - 9801 # otherwise update vars - 9802 (push *(ebp+0x10) *(ebp+8)) - 9803 (push *(ebp+0x10) *(ebp+0xc)) - 9804 (push *(ebp+0x10) 0) # 'out' is always a fn output; never spill it - 9805 $maybe-define-var:end: - 9806 # . restore registers - 9807 58/pop-to-eax - 9808 # . epilogue - 9809 89/<- %esp 5/r32/ebp - 9810 5d/pop-to-ebp - 9811 c3/return - 9812 - 9813 # simpler version of lookup-var-helper - 9814 binding-exists?: # target: (addr var), vars: (addr stack live-var) -> result/eax: boolean - 9815 # pseudocode: - 9816 # var curr: (addr handle var) = &vars->data[vars->top - 12] - 9817 # var min = vars->data - 9818 # while curr >= min - 9819 # var v: (handle var) = *curr - 9820 # if v->name == target->name - 9821 # return true - 9822 # curr -= 12 - 9823 # return false - 9824 # - 9825 # . prologue - 9826 55/push-ebp - 9827 89/<- %ebp 4/r32/esp - 9828 # . save registers - 9829 51/push-ecx - 9830 52/push-edx - 9831 56/push-esi - 9832 # var target-name/ecx: (addr array byte) = lookup(target->name) - 9833 8b/-> *(ebp+8) 0/r32/eax - 9834 (lookup *eax *(eax+4)) # Var-name Var-name => eax - 9835 89/<- %ecx 0/r32/eax - 9836 # esi = vars - 9837 8b/-> *(ebp+0xc) 6/r32/esi - 9838 # eax = vars->top - 9839 8b/-> *esi 0/r32/eax - 9840 # var min/edx: (addr handle var) = vars->data - 9841 8d/copy-address *(esi+8) 2/r32/edx - 9842 # var curr/esi: (addr handle var) = &vars->data[vars->top - 12] - 9843 8d/copy-address *(esi+eax-4) 6/r32/esi # vars + 8 + vars->type - 12 - 9844 { - 9845 $binding-exists?:loop: - 9846 # if (curr < min) return - 9847 39/compare %esi 2/r32/edx - 9848 0f 82/jump-if-addr< break/disp32 - 9849 # var v/eax: (addr var) = lookup(*curr) - 9850 (lookup *esi *(esi+4)) # => eax - 9851 # var vn/eax: (addr array byte) = lookup(v->name) - 9852 (lookup *eax *(eax+4)) # Var-name Var-name => eax - 9853 # if (vn == target-name) return true - 9854 (string-equal? %ecx %eax) # => eax - 9855 3d/compare-eax-and 0/imm32/false - 9856 75/jump-if-!= $binding-exists?:end/disp8 # eax already contains true - 9857 # curr -= 12 - 9858 81 5/subop/subtract %esi 0xc/imm32 - 9859 e9/jump loop/disp32 - 9860 } - 9861 b8/copy-to-eax 0/imm32/false - 9862 $binding-exists?:end: - 9863 # . restore registers - 9864 5e/pop-to-esi - 9865 5a/pop-to-edx - 9866 59/pop-to-ecx - 9867 # . epilogue - 9868 89/<- %esp 5/r32/ebp - 9869 5d/pop-to-ebp - 9870 c3/return - 9871 - 9872 test-parse-mu-stmt: - 9873 # . prologue - 9874 55/push-ebp - 9875 89/<- %ebp 4/r32/esp - 9876 # setup - 9877 (clear-stream _test-input-stream) - 9878 (write _test-input-stream "increment n\n") - 9879 # var vars/ecx: (stack (addr var) 16) - 9880 81 5/subop/subtract %esp 0xc0/imm32 - 9881 68/push 0xc0/imm32/size - 9882 68/push 0/imm32/top - 9883 89/<- %ecx 4/r32/esp - 9884 (clear-stack %ecx) - 9885 # var v/edx: (handle var) - 9886 68/push 0/imm32 - 9887 68/push 0/imm32 - 9888 89/<- %edx 4/r32/esp - 9889 # var s/eax: (handle array byte) + 9495 68/push 0/imm32 + 9496 68/push 0/imm32 + 9497 68/push 0/imm32 + 9498 89/<- %edi 4/r32/esp + 9499 { + 9500 $lookup-var-helper:loop: + 9501 # if (curr < min) return + 9502 39/compare %ebx 2/r32/edx + 9503 0f 82/jump-if-addr< break/disp32 + 9504 # var v/ecx: (addr var) = lookup(*curr) + 9505 (lookup *ebx *(ebx+4)) # => eax + 9506 89/<- %ecx 0/r32/eax + 9507 # var vn/eax: (addr array byte) = lookup(v->name) + 9508 (lookup *ecx *(ecx+4)) # Var-name Var-name => eax + 9509 # if (vn == name) return curr + 9510 (slice-equal? *(ebp+8) %eax) # => eax + 9511 3d/compare-eax-and 0/imm32/false + 9512 { + 9513 74/jump-if-= break/disp8 + 9514 $lookup-var-helper:found: + 9515 # var vr/eax: (addr array byte) = lookup(v->register) + 9516 (lookup *(ecx+0x18) *(ecx+0x1c)) # Var-register Var-register => eax + 9517 3d/compare-eax-and 0/imm32 + 9518 { + 9519 74/jump-if-= break/disp8 + 9520 $lookup-var-helper:found-register: + 9521 # var reg/eax: int = get(Registers, vr) + 9522 (get Mu-registers %eax 0xc "Mu-registers") # => eax + 9523 8b/-> *eax 0/r32/eax + 9524 # if (var-in-reg[reg]) error + 9525 8b/-> *(edi+eax<<2) 0/r32/eax + 9526 3d/compare-eax-and 0/imm32 + 9527 0f 85/jump-if-!= $lookup-var-helper:error2/disp32 + 9528 } + 9529 $lookup-var-helper:return: + 9530 # esi = out + 9531 8b/-> *(ebp+0x10) 6/r32/esi + 9532 # *out = *curr + 9533 8b/-> *ebx 0/r32/eax + 9534 89/<- *esi 0/r32/eax + 9535 8b/-> *(ebx+4) 0/r32/eax + 9536 89/<- *(esi+4) 0/r32/eax + 9537 # return + 9538 eb/jump $lookup-var-helper:end/disp8 + 9539 } + 9540 # 'name' not yet found; update var-in-reg if v in register + 9541 # . var vr/eax: (addr array byte) = lookup(v->register) + 9542 (lookup *(ecx+0x18) *(ecx+0x1c)) # Var-register Var-register => eax + 9543 # . if (var == 0) continue + 9544 3d/compare-eax-and 0/imm32 + 9545 74/jump-if-= $lookup-var-helper:continue/disp8 + 9546 # . var reg/eax: int = get(Registers, vr) + 9547 (get Mu-registers %eax 0xc "Mu-registers") # => eax + 9548 8b/-> *eax 0/r32/eax + 9549 # . if (var-in-reg[reg] == 0) var-in-reg[reg] = v + 9550 81 7/subop/compare *(edi+eax<<2) 0/imm32 + 9551 75/jump-if-!= $lookup-var-helper:continue/disp8 + 9552 89/<- *(edi+eax<<2) 1/r32/ecx + 9553 $lookup-var-helper:continue: + 9554 # curr -= 12 + 9555 81 5/subop/subtract %ebx 0xc/imm32 + 9556 e9/jump loop/disp32 + 9557 } + 9558 $lookup-var-helper:end: + 9559 # . reclaim locals + 9560 81 0/subop/add %esp 0x20/imm32 + 9561 # . restore registers + 9562 5f/pop-to-edi + 9563 5e/pop-to-esi + 9564 5b/pop-to-ebx + 9565 5a/pop-to-edx + 9566 59/pop-to-ecx + 9567 58/pop-to-eax + 9568 # . epilogue + 9569 89/<- %esp 5/r32/ebp + 9570 5d/pop-to-ebp + 9571 c3/return + 9572 + 9573 $lookup-var-helper:error1: + 9574 (write-buffered *(ebp+0x18) "fn ") + 9575 8b/-> *(ebp+0x14) 0/r32/eax + 9576 (lookup *eax *(eax+4)) # Function-name Function-name => eax + 9577 (write-buffered *(ebp+0x18) %eax) + 9578 (write-buffered *(ebp+0x18) ": malformed stack when looking up '") + 9579 (write-slice-buffered *(ebp+0x18) *(ebp+8)) + 9580 (write-buffered *(ebp+0x18) "'\n") + 9581 (flush *(ebp+0x18)) + 9582 (stop *(ebp+0x1c) 1) + 9583 # never gets here + 9584 + 9585 $lookup-var-helper:error2: + 9586 # eax contains the conflicting var at this point + 9587 (write-buffered *(ebp+0x18) "fn ") + 9588 50/push-eax + 9589 8b/-> *(ebp+0x14) 0/r32/eax + 9590 (lookup *eax *(eax+4)) # Function-name Function-name => eax + 9591 (write-buffered *(ebp+0x18) %eax) + 9592 58/pop-eax + 9593 (write-buffered *(ebp+0x18) ": register ") + 9594 50/push-eax + 9595 (lookup *(eax+0x18) *(eax+0x1c)) # Var-register Var-register => eax + 9596 (write-buffered *(ebp+0x18) %eax) + 9597 58/pop-to-eax + 9598 (write-buffered *(ebp+0x18) " reads var '") + 9599 (write-slice-buffered *(ebp+0x18) *(ebp+8)) + 9600 (write-buffered *(ebp+0x18) "' after writing var '") + 9601 (lookup *eax *(eax+4)) # Var-name Var-name => eax + 9602 (write-buffered *(ebp+0x18) %eax) + 9603 (write-buffered *(ebp+0x18) "'\n") + 9604 (flush *(ebp+0x18)) + 9605 (stop *(ebp+0x1c) 1) + 9606 # never gets here + 9607 + 9608 dump-vars: # vars: (addr stack live-var) + 9609 # pseudocode: + 9610 # var curr: (addr handle var) = &vars->data[vars->top - 12] + 9611 # var min = vars->data + 9612 # while curr >= min + 9613 # var v: (handle var) = *curr + 9614 # print v + 9615 # curr -= 12 + 9616 # + 9617 # . prologue + 9618 55/push-ebp + 9619 89/<- %ebp 4/r32/esp + 9620 # . save registers + 9621 52/push-edx + 9622 53/push-ebx + 9623 56/push-esi + 9624 # esi = vars + 9625 8b/-> *(ebp+8) 6/r32/esi + 9626 # ebx = vars->top + 9627 8b/-> *esi 3/r32/ebx + 9628 # var min/edx: (addr handle var) = vars->data + 9629 8d/copy-address *(esi+8) 2/r32/edx + 9630 # var curr/ebx: (addr handle var) = &vars->data[vars->top - 12] + 9631 8d/copy-address *(esi+ebx-4) 3/r32/ebx # vars + 8 + vars->type - 12 + 9632 { + 9633 $dump-vars:loop: + 9634 # if (curr < min) return + 9635 39/compare %ebx 2/r32/edx + 9636 0f 82/jump-if-addr< break/disp32 + 9637 # + 9638 (write-buffered Stderr " var@") + 9639 (dump-var 2 %ebx) + 9640 # curr -= 12 + 9641 81 5/subop/subtract %ebx 0xc/imm32 + 9642 e9/jump loop/disp32 + 9643 } + 9644 $dump-vars:end: + 9645 # . restore registers + 9646 5e/pop-to-esi + 9647 5b/pop-to-ebx + 9648 5a/pop-to-edx + 9649 # . epilogue + 9650 89/<- %esp 5/r32/ebp + 9651 5d/pop-to-ebp + 9652 c3/return + 9653 + 9654 == data + 9655 # Like Registers, but no esp or ebp + 9656 Mu-registers: # (addr stream {(handle array byte), int}) + 9657 # a table is a stream + 9658 0x48/imm32/write + 9659 0/imm32/read + 9660 0x48/imm32/length + 9661 # data + 9662 # it is perfectly ok to use fake alloc-ids -- as long as you never try to reclaim them + 9663 0x11/imm32/alloc-id $Mu-register-eax/imm32 0/imm32 + 9664 0x11/imm32/alloc-id $Mu-register-ecx/imm32 1/imm32 + 9665 0x11/imm32/alloc-id $Mu-register-edx/imm32 2/imm32 + 9666 0x11/imm32/alloc-id $Mu-register-ebx/imm32 3/imm32 + 9667 0x11/imm32/alloc-id $Mu-register-esi/imm32 6/imm32 + 9668 0x11/imm32/alloc-id $Mu-register-edi/imm32 7/imm32 + 9669 + 9670 $Mu-register-eax: + 9671 0x11/imm32/alloc-id + 9672 3/imm32/size + 9673 0x65/e 0x61/a 0x78/x + 9674 + 9675 $Mu-register-ecx: + 9676 0x11/imm32/alloc-id + 9677 3/imm32/size + 9678 0x65/e 0x63/c 0x78/x + 9679 + 9680 $Mu-register-edx: + 9681 0x11/imm32/alloc-id + 9682 3/imm32/size + 9683 0x65/e 0x64/d 0x78/x + 9684 + 9685 $Mu-register-ebx: + 9686 0x11/imm32/alloc-id + 9687 3/imm32/size + 9688 0x65/e 0x62/b 0x78/x + 9689 + 9690 $Mu-register-esi: + 9691 0x11/imm32/alloc-id + 9692 3/imm32/size + 9693 0x65/e 0x73/s 0x69/i + 9694 + 9695 $Mu-register-edi: + 9696 0x11/imm32/alloc-id + 9697 3/imm32/size + 9698 0x65/e 0x64/d 0x69/i + 9699 + 9700 == code + 9701 + 9702 # return first 'name' from the top (back) of 'vars' and create a new var for a fn output if not found + 9703 lookup-var-or-find-in-fn-outputs: # name: (addr slice), vars: (addr stack live-var), fn: (addr function), out: (addr handle var), err: (addr buffered-file), ed: (addr exit-descriptor) + 9704 # . prologue + 9705 55/push-ebp + 9706 89/<- %ebp 4/r32/esp + 9707 # . save registers + 9708 50/push-eax + 9709 # + 9710 (lookup-var-helper *(ebp+8) *(ebp+0xc) *(ebp+0x14) *(ebp+0x10) *(ebp+0x18) *(ebp+0x1c)) # arg order slightly different; 'fn' is deemphasized + 9711 { + 9712 # if (out != 0) return + 9713 8b/-> *(ebp+0x14) 0/r32/eax + 9714 81 7/subop/compare *eax 0/imm32 + 9715 75/jump-if-!= break/disp8 + 9716 # if name is one of fn's outputs, return it + 9717 (find-in-function-outputs *(ebp+0x10) *(ebp+8) *(ebp+0x14)) + 9718 8b/-> *(ebp+0x14) 0/r32/eax + 9719 81 7/subop/compare *eax 0/imm32 + 9720 # otherwise abort + 9721 0f 84/jump-if-= $lookup-or-define-var:abort/disp32 + 9722 } + 9723 $lookup-or-define-var:end: + 9724 # . restore registers + 9725 58/pop-to-eax + 9726 # . epilogue + 9727 89/<- %esp 5/r32/ebp + 9728 5d/pop-to-ebp + 9729 c3/return + 9730 + 9731 $lookup-or-define-var:abort: + 9732 (write-buffered *(ebp+0x18) "unknown variable '") + 9733 (write-slice-buffered *(ebp+0x18) *(ebp+8)) + 9734 (write-buffered *(ebp+0x18) "'\n") + 9735 (flush *(ebp+0x18)) + 9736 (stop *(ebp+0x1c) 1) + 9737 # never gets here + 9738 + 9739 find-in-function-outputs: # fn: (addr function), name: (addr slice), out: (addr handle var) + 9740 # . prologue + 9741 55/push-ebp + 9742 89/<- %ebp 4/r32/esp + 9743 # . save registers + 9744 50/push-eax + 9745 51/push-ecx + 9746 # var curr/ecx: (addr list var) = lookup(fn->outputs) + 9747 8b/-> *(ebp+8) 1/r32/ecx + 9748 (lookup *(ecx+0x10) *(ecx+0x14)) # Function-outputs Function-outputs => eax + 9749 89/<- %ecx 0/r32/eax + 9750 # while curr != null + 9751 { + 9752 81 7/subop/compare %ecx 0/imm32 + 9753 74/jump-if-= break/disp8 + 9754 # var v/eax: (addr var) = lookup(curr->value) + 9755 (lookup *ecx *(ecx+4)) # List-value List-value => eax + 9756 # var s/eax: (addr array byte) = lookup(v->name) + 9757 (lookup *eax *(eax+4)) # Var-name Var-name => eax + 9758 # if (s == name) return curr->value + 9759 (slice-equal? *(ebp+0xc) %eax) # => eax + 9760 3d/compare-eax-and 0/imm32/false + 9761 { + 9762 74/jump-if-= break/disp8 + 9763 # var edi = out + 9764 57/push-edi + 9765 8b/-> *(ebp+0x10) 7/r32/edi + 9766 # *out = curr->value + 9767 8b/-> *ecx 0/r32/eax + 9768 89/<- *edi 0/r32/eax + 9769 8b/-> *(ecx+4) 0/r32/eax + 9770 89/<- *(edi+4) 0/r32/eax + 9771 # + 9772 5f/pop-to-edi + 9773 eb/jump $find-in-function-outputs:end/disp8 + 9774 } + 9775 # curr = curr->next + 9776 (lookup *(ecx+8) *(ecx+0xc)) # List-next List-next => eax + 9777 89/<- %ecx 0/r32/eax + 9778 # + 9779 eb/jump loop/disp8 + 9780 } + 9781 b8/copy-to-eax 0/imm32 + 9782 $find-in-function-outputs:end: + 9783 # . restore registers + 9784 59/pop-to-ecx + 9785 58/pop-to-eax + 9786 # . epilogue + 9787 89/<- %esp 5/r32/ebp + 9788 5d/pop-to-ebp + 9789 c3/return + 9790 + 9791 # push 'out' to 'vars' if not already there; it's assumed to be a fn output + 9792 maybe-define-var: # out: (handle var), vars: (addr stack live-var) + 9793 # . prologue + 9794 55/push-ebp + 9795 89/<- %ebp 4/r32/esp + 9796 # . save registers + 9797 50/push-eax + 9798 # var out-addr/eax: (addr var) + 9799 (lookup *(ebp+8) *(ebp+0xc)) # => eax + 9800 # + 9801 (binding-exists? %eax *(ebp+0x10)) # => eax + 9802 3d/compare-eax-and 0/imm32/false + 9803 75/jump-if-!= $maybe-define-var:end/disp8 + 9804 # otherwise update vars + 9805 (push *(ebp+0x10) *(ebp+8)) + 9806 (push *(ebp+0x10) *(ebp+0xc)) + 9807 (push *(ebp+0x10) 0) # 'out' is always a fn output; never spill it + 9808 $maybe-define-var:end: + 9809 # . restore registers + 9810 58/pop-to-eax + 9811 # . epilogue + 9812 89/<- %esp 5/r32/ebp + 9813 5d/pop-to-ebp + 9814 c3/return + 9815 + 9816 # simpler version of lookup-var-helper + 9817 binding-exists?: # target: (addr var), vars: (addr stack live-var) -> result/eax: boolean + 9818 # pseudocode: + 9819 # var curr: (addr handle var) = &vars->data[vars->top - 12] + 9820 # var min = vars->data + 9821 # while curr >= min + 9822 # var v: (handle var) = *curr + 9823 # if v->name == target->name + 9824 # return true + 9825 # curr -= 12 + 9826 # return false + 9827 # + 9828 # . prologue + 9829 55/push-ebp + 9830 89/<- %ebp 4/r32/esp + 9831 # . save registers + 9832 51/push-ecx + 9833 52/push-edx + 9834 56/push-esi + 9835 # var target-name/ecx: (addr array byte) = lookup(target->name) + 9836 8b/-> *(ebp+8) 0/r32/eax + 9837 (lookup *eax *(eax+4)) # Var-name Var-name => eax + 9838 89/<- %ecx 0/r32/eax + 9839 # esi = vars + 9840 8b/-> *(ebp+0xc) 6/r32/esi + 9841 # eax = vars->top + 9842 8b/-> *esi 0/r32/eax + 9843 # var min/edx: (addr handle var) = vars->data + 9844 8d/copy-address *(esi+8) 2/r32/edx + 9845 # var curr/esi: (addr handle var) = &vars->data[vars->top - 12] + 9846 8d/copy-address *(esi+eax-4) 6/r32/esi # vars + 8 + vars->type - 12 + 9847 { + 9848 $binding-exists?:loop: + 9849 # if (curr < min) return + 9850 39/compare %esi 2/r32/edx + 9851 0f 82/jump-if-addr< break/disp32 + 9852 # var v/eax: (addr var) = lookup(*curr) + 9853 (lookup *esi *(esi+4)) # => eax + 9854 # var vn/eax: (addr array byte) = lookup(v->name) + 9855 (lookup *eax *(eax+4)) # Var-name Var-name => eax + 9856 # if (vn == target-name) return true + 9857 (string-equal? %ecx %eax) # => eax + 9858 3d/compare-eax-and 0/imm32/false + 9859 75/jump-if-!= $binding-exists?:end/disp8 # eax already contains true + 9860 # curr -= 12 + 9861 81 5/subop/subtract %esi 0xc/imm32 + 9862 e9/jump loop/disp32 + 9863 } + 9864 b8/copy-to-eax 0/imm32/false + 9865 $binding-exists?:end: + 9866 # . restore registers + 9867 5e/pop-to-esi + 9868 5a/pop-to-edx + 9869 59/pop-to-ecx + 9870 # . epilogue + 9871 89/<- %esp 5/r32/ebp + 9872 5d/pop-to-ebp + 9873 c3/return + 9874 + 9875 test-parse-mu-stmt: + 9876 # . prologue + 9877 55/push-ebp + 9878 89/<- %ebp 4/r32/esp + 9879 # setup + 9880 (clear-stream _test-input-stream) + 9881 (write _test-input-stream "increment n\n") + 9882 # var vars/ecx: (stack (addr var) 16) + 9883 81 5/subop/subtract %esp 0xc0/imm32 + 9884 68/push 0xc0/imm32/size + 9885 68/push 0/imm32/top + 9886 89/<- %ecx 4/r32/esp + 9887 (clear-stack %ecx) + 9888 # var v/edx: (handle var) + 9889 68/push 0/imm32 9890 68/push 0/imm32 - 9891 68/push 0/imm32 - 9892 89/<- %eax 4/r32/esp - 9893 # v = new var("n") - 9894 (copy-array Heap "n" %eax) - 9895 (new-var Heap *eax *(eax+4) %edx) - 9896 # - 9897 (push %ecx *edx) - 9898 (push %ecx *(edx+4)) - 9899 (push %ecx 0) - 9900 # var out/eax: (handle stmt) - 9901 68/push 0/imm32 - 9902 68/push 0/imm32 - 9903 89/<- %eax 4/r32/esp - 9904 # convert - 9905 (parse-mu-stmt _test-input-stream %ecx 0 %eax Stderr 0) - 9906 # var out-addr/edx: (addr stmt) = lookup(*out) - 9907 (lookup *eax *(eax+4)) # => eax - 9908 89/<- %edx 0/r32/eax - 9909 # out->tag - 9910 (check-ints-equal *edx 1 "F - test-parse-mu-stmt/tag") # Stmt-tag is Stmt1 - 9911 # out->operation - 9912 (lookup *(edx+4) *(edx+8)) # Stmt1-operation Stmt1-operation => eax - 9913 (check-strings-equal %eax "increment" "F - test-parse-mu-stmt/name") # Stmt1-operation - 9914 # out->inouts->value->name - 9915 # . eax = out->inouts - 9916 (lookup *(edx+0xc) *(edx+0x10)) # Stmt1-inouts Stmt1-inouts => eax - 9917 # . eax = out->inouts->value - 9918 (lookup *eax *(eax+4)) # Stmt-var-value Stmt-var-value => eax - 9919 # . eax = out->inouts->value->name - 9920 (lookup *eax *(eax+4)) # Var-name Var-name => eax - 9921 # . - 9922 (check-strings-equal %eax "n" "F - test-parse-mu-stmt/inout:0") - 9923 # . epilogue - 9924 89/<- %esp 5/r32/ebp - 9925 5d/pop-to-ebp - 9926 c3/return - 9927 - 9928 test-parse-mu-stmt-with-comma: - 9929 # . prologue - 9930 55/push-ebp - 9931 89/<- %ebp 4/r32/esp - 9932 # setup - 9933 (clear-stream _test-input-stream) - 9934 (write _test-input-stream "copy-to n, 3\n") - 9935 # var vars/ecx: (stack (addr var) 16) - 9936 81 5/subop/subtract %esp 0xc0/imm32 - 9937 68/push 0xc0/imm32/size - 9938 68/push 0/imm32/top - 9939 89/<- %ecx 4/r32/esp - 9940 (clear-stack %ecx) - 9941 # var v/edx: (handle var) - 9942 68/push 0/imm32 - 9943 68/push 0/imm32 - 9944 89/<- %edx 4/r32/esp - 9945 # var s/eax: (handle array byte) + 9891 89/<- %edx 4/r32/esp + 9892 # var s/eax: (handle array byte) + 9893 68/push 0/imm32 + 9894 68/push 0/imm32 + 9895 89/<- %eax 4/r32/esp + 9896 # v = new var("n") + 9897 (copy-array Heap "n" %eax) + 9898 (new-var Heap *eax *(eax+4) %edx) + 9899 # + 9900 (push %ecx *edx) + 9901 (push %ecx *(edx+4)) + 9902 (push %ecx 0) + 9903 # var out/eax: (handle stmt) + 9904 68/push 0/imm32 + 9905 68/push 0/imm32 + 9906 89/<- %eax 4/r32/esp + 9907 # convert + 9908 (parse-mu-stmt _test-input-stream %ecx 0 %eax Stderr 0) + 9909 # var out-addr/edx: (addr stmt) = lookup(*out) + 9910 (lookup *eax *(eax+4)) # => eax + 9911 89/<- %edx 0/r32/eax + 9912 # out->tag + 9913 (check-ints-equal *edx 1 "F - test-parse-mu-stmt/tag") # Stmt-tag is Stmt1 + 9914 # out->operation + 9915 (lookup *(edx+4) *(edx+8)) # Stmt1-operation Stmt1-operation => eax + 9916 (check-strings-equal %eax "increment" "F - test-parse-mu-stmt/name") # Stmt1-operation + 9917 # out->inouts->value->name + 9918 # . eax = out->inouts + 9919 (lookup *(edx+0xc) *(edx+0x10)) # Stmt1-inouts Stmt1-inouts => eax + 9920 # . eax = out->inouts->value + 9921 (lookup *eax *(eax+4)) # Stmt-var-value Stmt-var-value => eax + 9922 # . eax = out->inouts->value->name + 9923 (lookup *eax *(eax+4)) # Var-name Var-name => eax + 9924 # . + 9925 (check-strings-equal %eax "n" "F - test-parse-mu-stmt/inout:0") + 9926 # . epilogue + 9927 89/<- %esp 5/r32/ebp + 9928 5d/pop-to-ebp + 9929 c3/return + 9930 + 9931 test-parse-mu-stmt-with-comma: + 9932 # . prologue + 9933 55/push-ebp + 9934 89/<- %ebp 4/r32/esp + 9935 # setup + 9936 (clear-stream _test-input-stream) + 9937 (write _test-input-stream "copy-to n, 3\n") + 9938 # var vars/ecx: (stack (addr var) 16) + 9939 81 5/subop/subtract %esp 0xc0/imm32 + 9940 68/push 0xc0/imm32/size + 9941 68/push 0/imm32/top + 9942 89/<- %ecx 4/r32/esp + 9943 (clear-stack %ecx) + 9944 # var v/edx: (handle var) + 9945 68/push 0/imm32 9946 68/push 0/imm32 - 9947 68/push 0/imm32 - 9948 89/<- %eax 4/r32/esp - 9949 # v = new var("n") - 9950 (copy-array Heap "n" %eax) - 9951 (new-var Heap *eax *(eax+4) %edx) - 9952 # - 9953 (push %ecx *edx) - 9954 (push %ecx *(edx+4)) - 9955 (push %ecx 0) - 9956 # var out/eax: (handle stmt) - 9957 68/push 0/imm32 - 9958 68/push 0/imm32 - 9959 89/<- %eax 4/r32/esp - 9960 # convert - 9961 (parse-mu-stmt _test-input-stream %ecx 0 %eax Stderr 0) - 9962 # var out-addr/edx: (addr stmt) = lookup(*out) - 9963 (lookup *eax *(eax+4)) # => eax - 9964 89/<- %edx 0/r32/eax - 9965 # out->tag - 9966 (check-ints-equal *edx 1 "F - test-parse-mu-stmt-with-comma/tag") # Stmt-tag is Stmt1 - 9967 # out->operation - 9968 (lookup *(edx+4) *(edx+8)) # Stmt1-operation Stmt1-operation => eax - 9969 (check-strings-equal %eax "copy-to" "F - test-parse-mu-stmt-with-comma/name") # Stmt1-operation - 9970 # out->inouts->value->name - 9971 # . eax = out->inouts - 9972 (lookup *(edx+0xc) *(edx+0x10)) # Stmt1-inouts Stmt1-inouts => eax - 9973 # . eax = out->inouts->value - 9974 (lookup *eax *(eax+4)) # Stmt-var-value Stmt-var-value => eax - 9975 # . eax = out->inouts->value->name - 9976 (lookup *eax *(eax+4)) # Var-name Var-name => eax - 9977 # . - 9978 (check-strings-equal %eax "n" "F - test-parse-mu-stmt-with-comma/inout:0") - 9979 # . epilogue - 9980 89/<- %esp 5/r32/ebp - 9981 5d/pop-to-ebp - 9982 c3/return - 9983 - 9984 new-var: # ad: (addr allocation-descriptor), name: (handle array byte), out: (addr handle var) - 9985 # . prologue - 9986 55/push-ebp - 9987 89/<- %ebp 4/r32/esp - 9988 # . save registers - 9989 50/push-eax - 9990 51/push-ecx - 9991 # ecx = out - 9992 8b/-> *(ebp+0x14) 1/r32/ecx - 9993 # - 9994 (allocate *(ebp+8) *Var-size %ecx) - 9995 # var out-addr/eax: (addr var) - 9996 (lookup *ecx *(ecx+4)) # => eax - 9997 # out-addr->name = name - 9998 8b/-> *(ebp+0xc) 1/r32/ecx - 9999 89/<- *eax 1/r32/ecx # Var-name -10000 8b/-> *(ebp+0x10) 1/r32/ecx -10001 89/<- *(eax+4) 1/r32/ecx # Var-name -10002 #? (write-buffered Stderr "var ") -10003 #? (lookup *(ebp+0xc) *(ebp+0x10)) -10004 #? (write-buffered Stderr %eax) -10005 #? (write-buffered Stderr " at ") -10006 #? 8b/-> *(ebp+0x14) 1/r32/ecx -10007 #? (lookup *ecx *(ecx+4)) # => eax -10008 #? (write-int32-hex-buffered Stderr %eax) -10009 #? (write-buffered Stderr Newline) -10010 #? (flush Stderr) -10011 $new-var:end: -10012 # . restore registers -10013 59/pop-to-ecx -10014 58/pop-to-eax -10015 # . epilogue -10016 89/<- %esp 5/r32/ebp -10017 5d/pop-to-ebp -10018 c3/return -10019 -10020 new-literal-integer: # ad: (addr allocation-descriptor), name: (addr slice), out: (addr handle var), fn: (addr function), err: (addr buffered-file), ed: (addr exit-descriptor) -10021 # . prologue -10022 55/push-ebp -10023 89/<- %ebp 4/r32/esp -10024 # . save registers -10025 50/push-eax -10026 51/push-ecx -10027 # if (!is-hex-int?(name)) abort -10028 (is-hex-int? *(ebp+0xc)) # => eax -10029 3d/compare-eax-and 0/imm32/false -10030 0f 84/jump-if-= $new-literal-integer:abort/disp32 -10031 # a little more error-checking -10032 (check-mu-hex-int *(ebp+0xc) *(ebp+0x18) *(ebp+0x1c)) -10033 # out = new var(s) -10034 (new-var-from-slice *(ebp+8) *(ebp+0xc) *(ebp+0x10)) -10035 # var out-addr/ecx: (addr var) = lookup(*out) -10036 8b/-> *(ebp+0x10) 0/r32/eax -10037 (lookup *eax *(eax+4)) # => eax -10038 89/<- %ecx 0/r32/eax -10039 # out-addr->block-depth = *Curr-block-depth -10040 8b/-> *Curr-block-depth 0/r32/eax -10041 89/<- *(ecx+0x10) 0/r32/eax # Var-block-depth -10042 # out-addr->type = new tree() -10043 8d/copy-address *(ecx+8) 0/r32/eax # Var-type -10044 (allocate *(ebp+8) *Type-tree-size %eax) -10045 (lookup *(ecx+8) *(ecx+0xc)) # Var-type Var-type => eax -10046 c7 0/subop/copy *eax 1/imm32/true # Type-tree-is-atom -10047 # nothing else to do; default type is 'literal' -10048 $new-literal-integer:end: -10049 # . reclaim locals -10050 81 0/subop/add %esp 8/imm32 -10051 # . restore registers -10052 59/pop-to-ecx -10053 58/pop-to-eax -10054 # . epilogue -10055 89/<- %esp 5/r32/ebp -10056 5d/pop-to-ebp -10057 c3/return -10058 -10059 $new-literal-integer:abort: -10060 (write-buffered *(ebp+0x18) "fn ") -10061 8b/-> *(ebp+0x14) 0/r32/eax -10062 (lookup *eax *(eax+4)) # Function-name Function-name => eax -10063 (write-buffered *(ebp+0x18) %eax) -10064 (write-buffered *(ebp+0x18) ": variable '") -10065 (write-slice-buffered *(ebp+0x18) *(ebp+0xc)) -10066 (write-buffered *(ebp+0x18) "' cannot begin with a digit (or do you have a typo in a number?)\n") -10067 (flush *(ebp+0x18)) -10068 (stop *(ebp+0x1c) 1) -10069 # never gets here -10070 -10071 # precondition: name is a valid hex integer; require a '0x' prefix -10072 check-mu-hex-int: # name: (addr slice), err: (addr buffered-file), ed: (addr exit-descriptor) -10073 # . prologue -10074 55/push-ebp -10075 89/<- %ebp 4/r32/esp -10076 # . save registers -10077 50/push-eax -10078 51/push-ecx -10079 52/push-edx -10080 # -10081 8b/-> *(ebp+8) 1/r32/ecx -10082 # var start/ecx: (addr byte) = name->start -10083 8b/-> *(ecx+4) 2/r32/edx -10084 # var end/ecx: (addr byte) = name->end -10085 8b/-> *ecx 1/r32/ecx -10086 # var len/eax: int = name->end - name->start -10087 89/<- %eax 2/r32/edx -10088 29/subtract-from %eax 1/r32/ecx -10089 # if (len <= 1) return -10090 3d/compare-eax-with 1/imm32 -10091 0f 8e/jump-if-<= $check-mu-hex-int:end/disp32 -10092 $check-mu-hex-int:length->-1: -10093 # if slice-starts-with?("0x") return -10094 (slice-starts-with? *(ebp+8) "0x") # => eax -10095 3d/compare-eax-with 0/imm32/false -10096 75/jump-if-!= $check-mu-hex-int:end/disp8 -10097 $check-mu-hex-int:abort: -10098 # otherwise abort -10099 (write-buffered *(ebp+0xc) "literal integers are always hex in Mu; either start '") -10100 (write-slice-buffered *(ebp+0xc) *(ebp+8)) -10101 (write-buffered *(ebp+0xc) "' with a '0x' to be unambiguous, or convert it to decimal.\n") -10102 (flush *(ebp+0xc)) -10103 (stop *(ebp+0x10) 1) -10104 $check-mu-hex-int:end: -10105 # . restore registers -10106 5a/pop-to-edx -10107 59/pop-to-ecx -10108 58/pop-to-eax -10109 # . epilogue -10110 89/<- %esp 5/r32/ebp -10111 5d/pop-to-ebp -10112 c3/return -10113 -10114 new-literal: # ad: (addr allocation-descriptor), name: (addr slice), out: (addr handle var) -10115 # . prologue -10116 55/push-ebp -10117 89/<- %ebp 4/r32/esp -10118 # . save registers -10119 50/push-eax -10120 51/push-ecx -10121 # var s/ecx: (handle array byte) -10122 68/push 0/imm32 -10123 68/push 0/imm32 -10124 89/<- %ecx 4/r32/esp -10125 # s = slice-to-string(name) -10126 (slice-to-string Heap *(ebp+0xc) %ecx) -10127 # allocate to out -10128 (new-var *(ebp+8) *ecx *(ecx+4) *(ebp+0x10)) -10129 # var out-addr/ecx: (addr var) = lookup(*out) -10130 8b/-> *(ebp+0x10) 1/r32/ecx -10131 (lookup *ecx *(ecx+4)) # => eax -10132 89/<- %ecx 0/r32/eax -10133 # out-addr->block-depth = *Curr-block-depth -10134 8b/-> *Curr-block-depth 0/r32/eax -10135 89/<- *(ecx+0x10) 0/r32/eax # Var-block-depth -10136 # out-addr->type/eax = new type -10137 8d/copy-address *(ecx+8) 0/r32/eax # Var-type -10138 (allocate *(ebp+8) *Type-tree-size %eax) -10139 (lookup *(ecx+8) *(ecx+0xc)) # Var-type Var-type => eax -10140 # nothing else to do; default type is 'literal' -10141 c7 0/subop/copy *eax 1/imm32/true # Type-tree-is-atom -10142 $new-literal:end: -10143 # . reclaim locals -10144 81 0/subop/add %esp 8/imm32 -10145 # . restore registers -10146 59/pop-to-ecx -10147 58/pop-to-eax -10148 # . epilogue -10149 89/<- %esp 5/r32/ebp -10150 5d/pop-to-ebp -10151 c3/return -10152 -10153 new-var-from-slice: # ad: (addr allocation-descriptor), name: (addr slice), out: (addr handle var) -10154 # . prologue -10155 55/push-ebp -10156 89/<- %ebp 4/r32/esp -10157 # . save registers -10158 51/push-ecx -10159 # var tmp/ecx: (handle array byte) -10160 68/push 0/imm32 -10161 68/push 0/imm32 -10162 89/<- %ecx 4/r32/esp -10163 # tmp = slice-to-string(name) -10164 (slice-to-string Heap *(ebp+0xc) %ecx) -10165 # out = new-var(tmp) -10166 (new-var *(ebp+8) *ecx *(ecx+4) *(ebp+0x10)) -10167 $new-var-from-slice:end: -10168 # . reclaim locals -10169 81 0/subop/add %esp 8/imm32 -10170 # . restore registers -10171 59/pop-to-ecx -10172 # . epilogue -10173 89/<- %esp 5/r32/ebp -10174 5d/pop-to-ebp -10175 c3/return -10176 -10177 new-var-def: # ad: (addr allocation-descriptor), var: (handle var), out: (addr handle stmt) -10178 # . prologue -10179 55/push-ebp -10180 89/<- %ebp 4/r32/esp -10181 # . save registers -10182 50/push-eax -10183 51/push-ecx -10184 # -10185 (allocate *(ebp+8) *Stmt-size *(ebp+0x14)) -10186 # var out-addr/eax: (addr stmt) = lookup(*out) -10187 8b/-> *(ebp+0x14) 0/r32/eax -10188 (lookup *eax *(eax+4)) # => eax -10189 # out-addr->tag = stmt -10190 c7 0/subop/copy *eax 2/imm32/tag/var-on-stack # Stmt-tag -10191 # result->var = var -10192 8b/-> *(ebp+0xc) 1/r32/ecx -10193 89/<- *(eax+4) 1/r32/ecx # Vardef-var -10194 8b/-> *(ebp+0x10) 1/r32/ecx -10195 89/<- *(eax+8) 1/r32/ecx # Vardef-var -10196 $new-var-def:end: -10197 # . restore registers -10198 59/pop-to-ecx -10199 58/pop-to-eax -10200 # . epilogue -10201 89/<- %esp 5/r32/ebp -10202 5d/pop-to-ebp -10203 c3/return -10204 -10205 new-reg-var-def: # ad: (addr allocation-descriptor), var: (handle var), out: (addr handle stmt) -10206 # . prologue -10207 55/push-ebp -10208 89/<- %ebp 4/r32/esp -10209 # . save registers -10210 50/push-eax -10211 # eax = out -10212 8b/-> *(ebp+0x14) 0/r32/eax -10213 # -10214 (allocate *(ebp+8) *Stmt-size %eax) -10215 # var out-addr/eax: (addr stmt) = lookup(*out) -10216 (lookup *eax *(eax+4)) # => eax -10217 # set tag -10218 c7 0/subop/copy *eax 3/imm32/tag/var-in-register # Stmt-tag -10219 # set output -10220 8d/copy-address *(eax+0x14) 0/r32/eax # Regvardef-outputs -10221 (append-stmt-var Heap *(ebp+0xc) *(ebp+0x10) 0 0 0 %eax) -10222 $new-reg-var-def:end: -10223 # . restore registers -10224 58/pop-to-eax -10225 # . epilogue -10226 89/<- %esp 5/r32/ebp -10227 5d/pop-to-ebp -10228 c3/return -10229 -10230 append-list: # ad: (addr allocation-descriptor), value: (handle _type), list: (handle list _type), out: (addr handle list _type) -10231 # . prologue -10232 55/push-ebp -10233 89/<- %ebp 4/r32/esp -10234 # . save registers -10235 50/push-eax -10236 51/push-ecx -10237 57/push-edi -10238 # edi = out -10239 8b/-> *(ebp+0x1c) 7/r32/edi -10240 # *out = new list -10241 (allocate *(ebp+8) *List-size %edi) -10242 # var out-addr/edi: (addr list _type) = lookup(*out) -10243 (lookup *edi *(edi+4)) # => eax -10244 89/<- %edi 0/r32/eax -10245 # out-addr->value = value -10246 8b/-> *(ebp+0xc) 0/r32/eax -10247 89/<- *edi 0/r32/eax # List-value -10248 8b/-> *(ebp+0x10) 0/r32/eax -10249 89/<- *(edi+4) 0/r32/eax # List-value -10250 # if (list == null) return -10251 81 7/subop/compare *(ebp+0x14) 0/imm32 -10252 74/jump-if-= $append-list:end/disp8 -10253 # otherwise append -10254 $append-list:non-empty-list: -10255 # var curr/eax: (addr list _type) = lookup(list) -10256 (lookup *(ebp+0x14) *(ebp+0x18)) # => eax -10257 # while (curr->next != null) curr = curr->next -10258 { -10259 81 7/subop/compare *(eax+8) 0/imm32 # List-next -10260 74/jump-if-= break/disp8 -10261 # curr = lookup(curr->next) -10262 (lookup *(eax+8) *(eax+0xc)) # List-next, List-next => eax -10263 # -10264 eb/jump loop/disp8 -10265 } -10266 # edi = out -10267 8b/-> *(ebp+0x1c) 7/r32/edi -10268 # curr->next = out -10269 8b/-> *edi 1/r32/ecx -10270 89/<- *(eax+8) 1/r32/ecx # List-next -10271 8b/-> *(edi+4) 1/r32/ecx -10272 89/<- *(eax+0xc) 1/r32/ecx # List-next -10273 # out = list -10274 8b/-> *(ebp+0x14) 1/r32/ecx -10275 89/<- *edi 1/r32/ecx -10276 8b/-> *(ebp+0x18) 1/r32/ecx -10277 89/<- *(edi+4) 1/r32/ecx -10278 $append-list:end: -10279 # . restore registers -10280 5f/pop-to-edi -10281 59/pop-to-ecx -10282 58/pop-to-eax -10283 # . epilogue -10284 89/<- %esp 5/r32/ebp -10285 5d/pop-to-ebp -10286 c3/return -10287 -10288 append-stmt-var: # ad: (addr allocation-descriptor), v: (handle var), vars: (handle stmt-var), is-deref?: boolean, out: (addr handle stmt-var) -10289 # . prologue -10290 55/push-ebp -10291 89/<- %ebp 4/r32/esp -10292 # . save registers -10293 50/push-eax -10294 51/push-ecx -10295 57/push-edi -10296 # edi = out -10297 8b/-> *(ebp+0x20) 7/r32/edi -10298 # out = new stmt-var -10299 (allocate *(ebp+8) *Stmt-var-size %edi) -10300 # var out-addr/ecx: (addr stmt-var) = lookup(*out) -10301 (lookup *edi *(edi+4)) # => eax -10302 89/<- %ecx 0/r32/eax -10303 # out-addr->value = v -10304 8b/-> *(ebp+0xc) 0/r32/eax -10305 89/<- *ecx 0/r32/eax # Stmt-var-value -10306 8b/-> *(ebp+0x10) 0/r32/eax -10307 89/<- *(ecx+4) 0/r32/eax # Stmt-var-value -10308 # out-addr->is-deref? = is-deref? -10309 8b/-> *(ebp+0x1c) 0/r32/eax -10310 89/<- *(ecx+0x10) 0/r32/eax # Stmt-var-is-deref -10311 # if (vars == null) return result -10312 81 7/subop/compare *(ebp+0x14) 0/imm32/null -10313 74/jump-if-= $append-stmt-var:end/disp8 -10314 # otherwise append -10315 # var curr/eax: (addr stmt-var) = lookup(vars) -10316 (lookup *(ebp+0x14) *(ebp+0x18)) # => eax -10317 # while (curr->next != null) curr = curr->next -10318 { -10319 81 7/subop/compare *(eax+8) 0/imm32 # Stmt-var-next -10320 74/jump-if-= break/disp8 -10321 # curr = lookup(curr->next) -10322 (lookup *(eax+8) *(eax+0xc)) # Stmt-var-next, Stmt-var-next => eax -10323 # -10324 eb/jump loop/disp8 -10325 } -10326 # curr->next = out -10327 8b/-> *edi 1/r32/ecx -10328 89/<- *(eax+8) 1/r32/ecx # Stmt-var-next -10329 8b/-> *(edi+4) 1/r32/ecx -10330 89/<- *(eax+0xc) 1/r32/ecx # Stmt-var-next -10331 # out = vars -10332 8b/-> *(ebp+0x14) 1/r32/ecx -10333 89/<- *edi 1/r32/ecx -10334 8b/-> *(ebp+0x18) 1/r32/ecx -10335 89/<- *(edi+4) 1/r32/ecx -10336 $append-stmt-var:end: -10337 # . restore registers -10338 5f/pop-to-edi -10339 59/pop-to-ecx -10340 58/pop-to-eax -10341 # . epilogue -10342 89/<- %esp 5/r32/ebp -10343 5d/pop-to-ebp -10344 c3/return -10345 -10346 append-to-block: # ad: (addr allocation-descriptor), block: (addr block), x: (handle stmt) -10347 # . prologue -10348 55/push-ebp -10349 89/<- %ebp 4/r32/esp -10350 # . save registers -10351 50/push-eax -10352 56/push-esi -10353 # esi = block -10354 8b/-> *(ebp+0xc) 6/r32/esi -10355 # block->stmts = append(x, block->stmts) -10356 8d/copy-address *(esi+4) 0/r32/eax # Block-stmts -10357 (append-list *(ebp+8) *(ebp+0x10) *(ebp+0x14) *(esi+4) *(esi+8) %eax) # ad, x, x, Block-stmts, Block-stmts -10358 $append-to-block:end: -10359 # . restore registers -10360 5e/pop-to-esi -10361 58/pop-to-eax -10362 # . epilogue -10363 89/<- %esp 5/r32/ebp -10364 5d/pop-to-ebp -10365 c3/return -10366 -10367 ## Parsing types -10368 # We need to create metadata on user-defined types, and we need to use this -10369 # metadata as we parse instructions. -10370 # However, we also want to allow types to be used before their definitions. -10371 # This means we can't ever assume any type data structures exist. -10372 -10373 lookup-or-create-constant: # container: (addr stmt-var), field-name: (addr slice), out: (addr handle var) -10374 # . prologue -10375 55/push-ebp -10376 89/<- %ebp 4/r32/esp -10377 # . save registers -10378 50/push-eax -10379 56/push-esi -10380 # var container-type/esi: type-id -10381 (container-type *(ebp+8)) # => eax -10382 89/<- %esi 0/r32/eax -10383 # var tmp/eax: (handle typeinfo) = find-or-create-typeinfo(container-type) -10384 68/push 0/imm32 -10385 68/push 0/imm32 -10386 89/<- %eax 4/r32/esp -10387 (find-or-create-typeinfo %esi %eax) -10388 # var tmp-addr/eax: (addr typeinfo) = lookup(tmp) -10389 (lookup *eax *(eax+4)) # => eax -10390 # result = find-or-create-typeinfo-output-var(typeinfo, field-name) -10391 #? (write-buffered Stderr "constant: ") -10392 #? (write-slice-buffered Stderr *(ebp+0xc)) -10393 #? (write-buffered Stderr Newline) -10394 #? (flush Stderr) -10395 (find-or-create-typeinfo-output-var %eax *(ebp+0xc) *(ebp+0x10)) -10396 #? 8b/-> *(ebp+0x10) 0/r32/eax -10397 #? (write-buffered Stderr "@") -10398 #? (lookup *eax *(eax+4)) -10399 #? (write-int32-hex-buffered Stderr %eax) -10400 #? (lookup *eax *(eax+4)) -10401 #? (write-buffered Stderr %eax) -10402 #? (write-buffered Stderr Newline) -10403 #? (flush Stderr) -10404 #? (write-buffered Stderr "offset: ") -10405 #? 8b/-> *(eax+0x14) 0/r32/eax -10406 #? (write-int32-hex-buffered Stderr %eax) -10407 #? (write-buffered Stderr Newline) -10408 #? (flush Stderr) -10409 $lookup-or-create-constant:end: -10410 # . reclaim locals -10411 81 0/subop/add %esp 8/imm32 -10412 # . restore registers -10413 5e/pop-to-esi -10414 58/pop-to-eax -10415 # . epilogue -10416 89/<- %esp 5/r32/ebp -10417 5d/pop-to-ebp -10418 c3/return -10419 -10420 # if addr var: -10421 # container->var->type->right->left->value -10422 # otherwise -10423 # container->var->type->value -10424 container-type: # container: (addr stmt-var) -> result/eax: type-id -10425 # . prologue -10426 55/push-ebp -10427 89/<- %ebp 4/r32/esp -10428 # -10429 8b/-> *(ebp+8) 0/r32/eax -10430 (lookup *eax *(eax+4)) # Stmt-var-value Stmt-var-value => eax -10431 (lookup *(eax+8) *(eax+0xc)) # Var-type Var-type => eax -10432 { -10433 81 7/subop/compare *(eax+8) 0/imm32 # Type-tree-right -10434 74/jump-if-= break/disp8 -10435 (lookup *(eax+0xc) *(eax+0x10)) # Type-tree-right Type-tree-right => eax -10436 (lookup *(eax+4) *(eax+8)) # Type-tree-left Type-tree-left => eax -10437 } -10438 8b/-> *(eax+4) 0/r32/eax # Type-tree-value -10439 $container-type:end: -10440 # . epilogue -10441 89/<- %esp 5/r32/ebp -10442 5d/pop-to-ebp -10443 c3/return -10444 -10445 is-container?: # t: type-id -> result/eax: boolean -10446 # . prologue -10447 55/push-ebp -10448 89/<- %ebp 4/r32/esp -10449 # -10450 8b/-> *(ebp+8) 0/r32/eax -10451 c1/shift 4/subop/left %eax 2/imm8 -10452 3b/compare 0/r32/eax *Primitive-type-ids -10453 0f 9d/set-if->= %al -10454 81 4/subop/and %eax 0xff/imm32 -10455 $is-container?:end: -10456 # . epilogue -10457 89/<- %esp 5/r32/ebp -10458 5d/pop-to-ebp -10459 c3/return -10460 -10461 find-or-create-typeinfo: # t: type-id, out: (addr handle typeinfo) -10462 # . prologue -10463 55/push-ebp -10464 89/<- %ebp 4/r32/esp -10465 # . save registers -10466 50/push-eax -10467 51/push-ecx -10468 52/push-edx -10469 57/push-edi -10470 # edi = out -10471 8b/-> *(ebp+0xc) 7/r32/edi -10472 # var fields/ecx: (handle table (handle array byte) (handle typeinfo-entry)) -10473 68/push 0/imm32 -10474 68/push 0/imm32 -10475 89/<- %ecx 4/r32/esp -10476 # find-typeinfo(t, out) -10477 (find-typeinfo *(ebp+8) %edi) -10478 { -10479 # if (*out != 0) break -10480 81 7/subop/compare *edi 0/imm32 -10481 0f 85/jump-if-!= break/disp32 -10482 $find-or-create-typeinfo:create: -10483 # *out = allocate -10484 (allocate Heap *Typeinfo-size %edi) -10485 # var tmp/eax: (addr typeinfo) = lookup(*out) -10486 (lookup *edi *(edi+4)) # => eax -10487 #? (write-buffered Stderr "created typeinfo at ") -10488 #? (write-int32-hex-buffered Stderr %eax) -10489 #? (write-buffered Stderr " for type-id ") -10490 #? (write-int32-hex-buffered Stderr *(ebp+8)) -10491 #? (write-buffered Stderr Newline) -10492 #? (flush Stderr) -10493 # tmp->id = t -10494 8b/-> *(ebp+8) 2/r32/edx -10495 89/<- *eax 2/r32/edx # Typeinfo-id -10496 # tmp->fields = new table -10497 # . fields = new table -10498 (new-stream Heap 0x40 *Typeinfo-fields-row-size %ecx) -10499 # . tmp->fields = fields -10500 8b/-> *ecx 2/r32/edx -10501 89/<- *(eax+4) 2/r32/edx # Typeinfo-fields -10502 8b/-> *(ecx+4) 2/r32/edx -10503 89/<- *(eax+8) 2/r32/edx # Typeinfo-fields -10504 # tmp->next = Program->types -10505 8b/-> *_Program-types 1/r32/ecx -10506 89/<- *(eax+0x10) 1/r32/ecx # Typeinfo-next -10507 8b/-> *_Program-types->payload 1/r32/ecx -10508 89/<- *(eax+0x14) 1/r32/ecx # Typeinfo-next -10509 # Program->types = out -10510 8b/-> *edi 1/r32/ecx -10511 89/<- *_Program-types 1/r32/ecx -10512 8b/-> *(edi+4) 1/r32/ecx -10513 89/<- *_Program-types->payload 1/r32/ecx -10514 } -10515 $find-or-create-typeinfo:end: -10516 # . reclaim locals -10517 81 0/subop/add %esp 8/imm32 -10518 # . restore registers -10519 5f/pop-to-edi -10520 5a/pop-to-edx -10521 59/pop-to-ecx -10522 58/pop-to-eax -10523 # . epilogue -10524 89/<- %esp 5/r32/ebp -10525 5d/pop-to-ebp -10526 c3/return -10527 -10528 find-typeinfo: # t: type-id, out: (addr handle typeinfo) -10529 # . prologue -10530 55/push-ebp -10531 89/<- %ebp 4/r32/esp -10532 # . save registers -10533 50/push-eax -10534 51/push-ecx -10535 52/push-edx -10536 57/push-edi -10537 # ecx = t -10538 8b/-> *(ebp+8) 1/r32/ecx -10539 # edi = out -10540 8b/-> *(ebp+0xc) 7/r32/edi -10541 # *out = Program->types -10542 8b/-> *_Program-types 0/r32/eax -10543 89/<- *edi 0/r32/eax -10544 8b/-> *_Program-types->payload 0/r32/eax -10545 89/<- *(edi+4) 0/r32/eax -10546 { -10547 $find-typeinfo:loop: -10548 # if (*out == 0) break -10549 81 7/subop/compare *edi 0/imm32 -10550 74/jump-if-= break/disp8 -10551 $find-typeinfo:check: -10552 # var tmp/eax: (addr typeinfo) = lookup(*out) -10553 (lookup *edi *(edi+4)) # => eax -10554 # if (tmp->id == t) break -10555 39/compare *eax 1/r32/ecx # Typeinfo-id -10556 74/jump-if-= break/disp8 -10557 $find-typeinfo:continue: -10558 # *out = tmp->next -10559 8b/-> *(eax+0x10) 2/r32/edx # Typeinfo-next -10560 89/<- *edi 2/r32/edx -10561 8b/-> *(eax+0x14) 2/r32/edx # Typeinfo-next -10562 89/<- *(edi+4) 2/r32/edx -10563 # -10564 eb/jump loop/disp8 -10565 } -10566 $find-typeinfo:end: -10567 # . restore registers -10568 5f/pop-to-edi -10569 5a/pop-to-edx -10570 59/pop-to-ecx -10571 58/pop-to-eax -10572 # . epilogue -10573 89/<- %esp 5/r32/ebp -10574 5d/pop-to-ebp -10575 c3/return -10576 -10577 find-or-create-typeinfo-output-var: # T: (addr typeinfo), f: (addr slice), out: (addr handle var) -10578 # . prologue -10579 55/push-ebp -10580 89/<- %ebp 4/r32/esp -10581 # . save registers -10582 50/push-eax -10583 52/push-edx -10584 57/push-edi -10585 # var dest/edi: (handle typeinfo-entry) -10586 68/push 0/imm32 -10587 68/push 0/imm32 -10588 89/<- %edi 4/r32/esp -10589 # find-or-create-typeinfo-fields(T, f, dest) -10590 (find-or-create-typeinfo-fields *(ebp+8) *(ebp+0xc) %edi) -10591 # var dest-addr/edi: (addr typeinfo-entry) = lookup(dest) -10592 (lookup *edi *(edi+4)) # => eax -10593 89/<- %edi 0/r32/eax -10594 # if dest-addr->output-var doesn't exist, create it -10595 { -10596 81 7/subop/compare *(edi+0xc) 0/imm32 # Typeinfo-entry-output-var -10597 0f 85/jump-if-!= break/disp32 -10598 # dest-addr->output-var = new var(dummy name, type, -1 offset) -10599 # . var name/eax: (handle array byte) = "field" -10600 68/push 0/imm32 -10601 68/push 0/imm32 -10602 89/<- %eax 4/r32/esp -10603 (slice-to-string Heap *(ebp+0xc) %eax) -10604 # . new var -10605 8d/copy-address *(edi+0xc) 2/r32/edx -10606 (new-var Heap *eax *(eax+4) %edx) -10607 # . reclaim name -10608 81 0/subop/add %esp 8/imm32 -10609 # var result/edx: (addr var) = lookup(dest-addr->output-var) -10610 (lookup *(edi+0xc) *(edi+0x10)) # => eax -10611 89/<- %edx 0/r32/eax -10612 # result->type = new constant type -10613 8d/copy-address *(edx+8) 0/r32/eax # Var-type -10614 (allocate Heap *Type-tree-size %eax) -10615 (lookup *(edx+8) *(edx+0xc)) # => eax -10616 c7 0/subop/copy *eax 1/imm32/true # Type-tree-is-atom -10617 c7 0/subop/copy *(eax+4) 6/imm32/constant # Type-tree-value -10618 c7 0/subop/copy *(eax+8) 0/imm32 # Type-tree-left -10619 c7 0/subop/copy *(eax+0xc) 0/imm32 # Type-tree-right -10620 c7 0/subop/copy *(eax+0x10) 0/imm32 # Type-tree-right -10621 # result->offset isn't filled out yet -10622 c7 0/subop/copy *(edx+0x14) -1/imm32/uninitialized # Var-offset -10623 } -10624 # out = dest-addr->output-var -10625 8b/-> *(ebp+0x10) 2/r32/edx -10626 8b/-> *(edi+0xc) 0/r32/eax # Typeinfo-entry-output-var -10627 89/<- *edx 0/r32/eax -10628 8b/-> *(edi+0x10) 0/r32/eax # Typeinfo-entry-output-var -10629 89/<- *(edx+4) 0/r32/eax -10630 $find-or-create-typeinfo-output-var:end: -10631 # . reclaim locals -10632 81 0/subop/add %esp 8/imm32 -10633 # . restore registers -10634 5f/pop-to-edi -10635 5a/pop-to-edx -10636 58/pop-to-eax -10637 # . epilogue -10638 89/<- %esp 5/r32/ebp -10639 5d/pop-to-ebp -10640 c3/return -10641 -10642 find-or-create-typeinfo-fields: # T: (addr typeinfo), f: (addr slice), out: (addr handle typeinfo-entry) -10643 # . prologue -10644 55/push-ebp -10645 89/<- %ebp 4/r32/esp -10646 # . save registers -10647 50/push-eax -10648 56/push-esi -10649 57/push-edi -10650 # eax = lookup(T->fields) -10651 8b/-> *(ebp+8) 0/r32/eax -10652 (lookup *(eax+4) *(eax+8)) # Typeinfo-fields Typeinfo-fields => eax -10653 # edi = out -10654 8b/-> *(ebp+0x10) 7/r32/edi -10655 # var src/esi: (addr handle typeinfo-entry) = get-or-insert-slice(T->fields, f) -10656 (get-or-insert-slice %eax *(ebp+0xc) *Typeinfo-fields-row-size Heap) # => eax -10657 89/<- %esi 0/r32/eax -10658 # if src doesn't exist, allocate it -10659 { -10660 81 7/subop/compare *esi 0/imm32 -10661 75/jump-if-!= break/disp8 -10662 (allocate Heap *Typeinfo-entry-size %esi) -10663 #? (write-buffered Stderr "handle at ") -10664 #? (write-int32-hex-buffered Stderr %esi) -10665 #? (write-buffered Stderr ": ") -10666 #? (write-int32-hex-buffered Stderr *esi) -10667 #? (write-buffered Stderr " ") -10668 #? (write-int32-hex-buffered Stderr *(esi+4)) -10669 #? (write-buffered Stderr Newline) -10670 #? (flush Stderr) -10671 #? (lookup *esi *(esi+4)) -10672 #? (write-buffered Stderr "created typeinfo fields at ") -10673 #? (write-int32-hex-buffered Stderr %esi) -10674 #? (write-buffered Stderr " for ") -10675 #? (write-int32-hex-buffered Stderr *(ebp+8)) -10676 #? (write-buffered Stderr Newline) -10677 #? (flush Stderr) -10678 } -10679 # *out = src -10680 # . *edi = *src -10681 8b/-> *esi 0/r32/eax -10682 89/<- *edi 0/r32/eax -10683 8b/-> *(esi+4) 0/r32/eax -10684 89/<- *(edi+4) 0/r32/eax -10685 $find-or-create-typeinfo-fields:end: -10686 # . restore registers -10687 5f/pop-to-edi -10688 5e/pop-to-esi -10689 58/pop-to-eax -10690 # . epilogue -10691 89/<- %esp 5/r32/ebp -10692 5d/pop-to-ebp -10693 c3/return -10694 -10695 populate-mu-type: # in: (addr stream byte), t: (addr typeinfo), err: (addr buffered-file), ed: (addr exit-descriptor) -10696 # pseudocode: -10697 # var line: (stream byte 512) -10698 # curr-index = 0 -10699 # while true -10700 # clear-stream(line) -10701 # read-line-buffered(in, line) -10702 # if line->write == 0 -10703 # abort -10704 # word-slice = next-mu-token(line) -10705 # if slice-empty?(word-slice) # end of line -10706 # continue -10707 # if slice-equal?(word-slice, "}") -10708 # break -10709 # var v: (handle var) = parse-var-with-type(word-slice, line) -10710 # var r: (handle typeinfo-fields) = find-or-create-typeinfo-fields(t, word-slice/v->name) -10711 # TODO: ensure that r->first is null -10712 # r->index = curr-index -10713 # curr-index++ -10714 # r->input-var = v -10715 # if r->output-var == 0 -10716 # r->output-var = new literal -10717 # TODO: ensure nothing else in line -10718 # t->total-size-in-bytes = -2 (not yet initialized) -10719 # -10720 # . prologue -10721 55/push-ebp -10722 89/<- %ebp 4/r32/esp -10723 # var curr-index: int at *(ebp-4) -10724 68/push 0/imm32 -10725 # . save registers -10726 50/push-eax -10727 51/push-ecx -10728 52/push-edx -10729 53/push-ebx -10730 56/push-esi -10731 57/push-edi -10732 # edi = t -10733 8b/-> *(ebp+0xc) 7/r32/edi -10734 # var line/ecx: (stream byte 512) -10735 81 5/subop/subtract %esp 0x200/imm32 -10736 68/push 0x200/imm32/size -10737 68/push 0/imm32/read -10738 68/push 0/imm32/write -10739 89/<- %ecx 4/r32/esp -10740 # var word-slice/edx: slice -10741 68/push 0/imm32/end -10742 68/push 0/imm32/start -10743 89/<- %edx 4/r32/esp -10744 # var v/esi: (handle var) -10745 68/push 0/imm32 -10746 68/push 0/imm32 -10747 89/<- %esi 4/r32/esp -10748 # var r/ebx: (handle typeinfo-entry) + 9947 89/<- %edx 4/r32/esp + 9948 # var s/eax: (handle array byte) + 9949 68/push 0/imm32 + 9950 68/push 0/imm32 + 9951 89/<- %eax 4/r32/esp + 9952 # v = new var("n") + 9953 (copy-array Heap "n" %eax) + 9954 (new-var Heap *eax *(eax+4) %edx) + 9955 # + 9956 (push %ecx *edx) + 9957 (push %ecx *(edx+4)) + 9958 (push %ecx 0) + 9959 # var out/eax: (handle stmt) + 9960 68/push 0/imm32 + 9961 68/push 0/imm32 + 9962 89/<- %eax 4/r32/esp + 9963 # convert + 9964 (parse-mu-stmt _test-input-stream %ecx 0 %eax Stderr 0) + 9965 # var out-addr/edx: (addr stmt) = lookup(*out) + 9966 (lookup *eax *(eax+4)) # => eax + 9967 89/<- %edx 0/r32/eax + 9968 # out->tag + 9969 (check-ints-equal *edx 1 "F - test-parse-mu-stmt-with-comma/tag") # Stmt-tag is Stmt1 + 9970 # out->operation + 9971 (lookup *(edx+4) *(edx+8)) # Stmt1-operation Stmt1-operation => eax + 9972 (check-strings-equal %eax "copy-to" "F - test-parse-mu-stmt-with-comma/name") # Stmt1-operation + 9973 # out->inouts->value->name + 9974 # . eax = out->inouts + 9975 (lookup *(edx+0xc) *(edx+0x10)) # Stmt1-inouts Stmt1-inouts => eax + 9976 # . eax = out->inouts->value + 9977 (lookup *eax *(eax+4)) # Stmt-var-value Stmt-var-value => eax + 9978 # . eax = out->inouts->value->name + 9979 (lookup *eax *(eax+4)) # Var-name Var-name => eax + 9980 # . + 9981 (check-strings-equal %eax "n" "F - test-parse-mu-stmt-with-comma/inout:0") + 9982 # . epilogue + 9983 89/<- %esp 5/r32/ebp + 9984 5d/pop-to-ebp + 9985 c3/return + 9986 + 9987 new-var: # ad: (addr allocation-descriptor), name: (handle array byte), out: (addr handle var) + 9988 # . prologue + 9989 55/push-ebp + 9990 89/<- %ebp 4/r32/esp + 9991 # . save registers + 9992 50/push-eax + 9993 51/push-ecx + 9994 # ecx = out + 9995 8b/-> *(ebp+0x14) 1/r32/ecx + 9996 # + 9997 (allocate *(ebp+8) *Var-size %ecx) + 9998 # var out-addr/eax: (addr var) + 9999 (lookup *ecx *(ecx+4)) # => eax +10000 # out-addr->name = name +10001 8b/-> *(ebp+0xc) 1/r32/ecx +10002 89/<- *eax 1/r32/ecx # Var-name +10003 8b/-> *(ebp+0x10) 1/r32/ecx +10004 89/<- *(eax+4) 1/r32/ecx # Var-name +10005 #? (write-buffered Stderr "var ") +10006 #? (lookup *(ebp+0xc) *(ebp+0x10)) +10007 #? (write-buffered Stderr %eax) +10008 #? (write-buffered Stderr " at ") +10009 #? 8b/-> *(ebp+0x14) 1/r32/ecx +10010 #? (lookup *ecx *(ecx+4)) # => eax +10011 #? (write-int32-hex-buffered Stderr %eax) +10012 #? (write-buffered Stderr Newline) +10013 #? (flush Stderr) +10014 $new-var:end: +10015 # . restore registers +10016 59/pop-to-ecx +10017 58/pop-to-eax +10018 # . epilogue +10019 89/<- %esp 5/r32/ebp +10020 5d/pop-to-ebp +10021 c3/return +10022 +10023 new-literal-integer: # ad: (addr allocation-descriptor), name: (addr slice), out: (addr handle var), fn: (addr function), err: (addr buffered-file), ed: (addr exit-descriptor) +10024 # . prologue +10025 55/push-ebp +10026 89/<- %ebp 4/r32/esp +10027 # . save registers +10028 50/push-eax +10029 51/push-ecx +10030 # if (!is-hex-int?(name)) abort +10031 (is-hex-int? *(ebp+0xc)) # => eax +10032 3d/compare-eax-and 0/imm32/false +10033 0f 84/jump-if-= $new-literal-integer:abort/disp32 +10034 # a little more error-checking +10035 (check-mu-hex-int *(ebp+0xc) *(ebp+0x18) *(ebp+0x1c)) +10036 # out = new var(s) +10037 (new-var-from-slice *(ebp+8) *(ebp+0xc) *(ebp+0x10)) +10038 # var out-addr/ecx: (addr var) = lookup(*out) +10039 8b/-> *(ebp+0x10) 0/r32/eax +10040 (lookup *eax *(eax+4)) # => eax +10041 89/<- %ecx 0/r32/eax +10042 # out-addr->block-depth = *Curr-block-depth +10043 8b/-> *Curr-block-depth 0/r32/eax +10044 89/<- *(ecx+0x10) 0/r32/eax # Var-block-depth +10045 # out-addr->type = new tree() +10046 8d/copy-address *(ecx+8) 0/r32/eax # Var-type +10047 (allocate *(ebp+8) *Type-tree-size %eax) +10048 (lookup *(ecx+8) *(ecx+0xc)) # Var-type Var-type => eax +10049 c7 0/subop/copy *eax 1/imm32/true # Type-tree-is-atom +10050 # nothing else to do; default type is 'literal' +10051 $new-literal-integer:end: +10052 # . reclaim locals +10053 81 0/subop/add %esp 8/imm32 +10054 # . restore registers +10055 59/pop-to-ecx +10056 58/pop-to-eax +10057 # . epilogue +10058 89/<- %esp 5/r32/ebp +10059 5d/pop-to-ebp +10060 c3/return +10061 +10062 $new-literal-integer:abort: +10063 (write-buffered *(ebp+0x18) "fn ") +10064 8b/-> *(ebp+0x14) 0/r32/eax +10065 (lookup *eax *(eax+4)) # Function-name Function-name => eax +10066 (write-buffered *(ebp+0x18) %eax) +10067 (write-buffered *(ebp+0x18) ": variable '") +10068 (write-slice-buffered *(ebp+0x18) *(ebp+0xc)) +10069 (write-buffered *(ebp+0x18) "' cannot begin with a digit (or do you have a typo in a number?)\n") +10070 (flush *(ebp+0x18)) +10071 (stop *(ebp+0x1c) 1) +10072 # never gets here +10073 +10074 # precondition: name is a valid hex integer; require a '0x' prefix +10075 check-mu-hex-int: # name: (addr slice), err: (addr buffered-file), ed: (addr exit-descriptor) +10076 # . prologue +10077 55/push-ebp +10078 89/<- %ebp 4/r32/esp +10079 # . save registers +10080 50/push-eax +10081 51/push-ecx +10082 52/push-edx +10083 # +10084 8b/-> *(ebp+8) 1/r32/ecx +10085 # var start/ecx: (addr byte) = name->start +10086 8b/-> *(ecx+4) 2/r32/edx +10087 # var end/ecx: (addr byte) = name->end +10088 8b/-> *ecx 1/r32/ecx +10089 # var len/eax: int = name->end - name->start +10090 89/<- %eax 2/r32/edx +10091 29/subtract-from %eax 1/r32/ecx +10092 # if (len <= 1) return +10093 3d/compare-eax-with 1/imm32 +10094 0f 8e/jump-if-<= $check-mu-hex-int:end/disp32 +10095 $check-mu-hex-int:length->-1: +10096 # if slice-starts-with?("0x") return +10097 (slice-starts-with? *(ebp+8) "0x") # => eax +10098 3d/compare-eax-with 0/imm32/false +10099 75/jump-if-!= $check-mu-hex-int:end/disp8 +10100 $check-mu-hex-int:abort: +10101 # otherwise abort +10102 (write-buffered *(ebp+0xc) "literal integers are always hex in Mu; either start '") +10103 (write-slice-buffered *(ebp+0xc) *(ebp+8)) +10104 (write-buffered *(ebp+0xc) "' with a '0x' to be unambiguous, or convert it to decimal.\n") +10105 (flush *(ebp+0xc)) +10106 (stop *(ebp+0x10) 1) +10107 $check-mu-hex-int:end: +10108 # . restore registers +10109 5a/pop-to-edx +10110 59/pop-to-ecx +10111 58/pop-to-eax +10112 # . epilogue +10113 89/<- %esp 5/r32/ebp +10114 5d/pop-to-ebp +10115 c3/return +10116 +10117 new-literal: # ad: (addr allocation-descriptor), name: (addr slice), out: (addr handle var) +10118 # . prologue +10119 55/push-ebp +10120 89/<- %ebp 4/r32/esp +10121 # . save registers +10122 50/push-eax +10123 51/push-ecx +10124 # var s/ecx: (handle array byte) +10125 68/push 0/imm32 +10126 68/push 0/imm32 +10127 89/<- %ecx 4/r32/esp +10128 # s = slice-to-string(name) +10129 (slice-to-string Heap *(ebp+0xc) %ecx) +10130 # allocate to out +10131 (new-var *(ebp+8) *ecx *(ecx+4) *(ebp+0x10)) +10132 # var out-addr/ecx: (addr var) = lookup(*out) +10133 8b/-> *(ebp+0x10) 1/r32/ecx +10134 (lookup *ecx *(ecx+4)) # => eax +10135 89/<- %ecx 0/r32/eax +10136 # out-addr->block-depth = *Curr-block-depth +10137 8b/-> *Curr-block-depth 0/r32/eax +10138 89/<- *(ecx+0x10) 0/r32/eax # Var-block-depth +10139 # out-addr->type/eax = new type +10140 8d/copy-address *(ecx+8) 0/r32/eax # Var-type +10141 (allocate *(ebp+8) *Type-tree-size %eax) +10142 (lookup *(ecx+8) *(ecx+0xc)) # Var-type Var-type => eax +10143 # nothing else to do; default type is 'literal' +10144 c7 0/subop/copy *eax 1/imm32/true # Type-tree-is-atom +10145 $new-literal:end: +10146 # . reclaim locals +10147 81 0/subop/add %esp 8/imm32 +10148 # . restore registers +10149 59/pop-to-ecx +10150 58/pop-to-eax +10151 # . epilogue +10152 89/<- %esp 5/r32/ebp +10153 5d/pop-to-ebp +10154 c3/return +10155 +10156 new-var-from-slice: # ad: (addr allocation-descriptor), name: (addr slice), out: (addr handle var) +10157 # . prologue +10158 55/push-ebp +10159 89/<- %ebp 4/r32/esp +10160 # . save registers +10161 51/push-ecx +10162 # var tmp/ecx: (handle array byte) +10163 68/push 0/imm32 +10164 68/push 0/imm32 +10165 89/<- %ecx 4/r32/esp +10166 # tmp = slice-to-string(name) +10167 (slice-to-string Heap *(ebp+0xc) %ecx) +10168 # out = new-var(tmp) +10169 (new-var *(ebp+8) *ecx *(ecx+4) *(ebp+0x10)) +10170 $new-var-from-slice:end: +10171 # . reclaim locals +10172 81 0/subop/add %esp 8/imm32 +10173 # . restore registers +10174 59/pop-to-ecx +10175 # . epilogue +10176 89/<- %esp 5/r32/ebp +10177 5d/pop-to-ebp +10178 c3/return +10179 +10180 new-var-def: # ad: (addr allocation-descriptor), var: (handle var), out: (addr handle stmt) +10181 # . prologue +10182 55/push-ebp +10183 89/<- %ebp 4/r32/esp +10184 # . save registers +10185 50/push-eax +10186 51/push-ecx +10187 # +10188 (allocate *(ebp+8) *Stmt-size *(ebp+0x14)) +10189 # var out-addr/eax: (addr stmt) = lookup(*out) +10190 8b/-> *(ebp+0x14) 0/r32/eax +10191 (lookup *eax *(eax+4)) # => eax +10192 # out-addr->tag = stmt +10193 c7 0/subop/copy *eax 2/imm32/tag/var-on-stack # Stmt-tag +10194 # result->var = var +10195 8b/-> *(ebp+0xc) 1/r32/ecx +10196 89/<- *(eax+4) 1/r32/ecx # Vardef-var +10197 8b/-> *(ebp+0x10) 1/r32/ecx +10198 89/<- *(eax+8) 1/r32/ecx # Vardef-var +10199 $new-var-def:end: +10200 # . restore registers +10201 59/pop-to-ecx +10202 58/pop-to-eax +10203 # . epilogue +10204 89/<- %esp 5/r32/ebp +10205 5d/pop-to-ebp +10206 c3/return +10207 +10208 new-reg-var-def: # ad: (addr allocation-descriptor), var: (handle var), out: (addr handle stmt) +10209 # . prologue +10210 55/push-ebp +10211 89/<- %ebp 4/r32/esp +10212 # . save registers +10213 50/push-eax +10214 # eax = out +10215 8b/-> *(ebp+0x14) 0/r32/eax +10216 # +10217 (allocate *(ebp+8) *Stmt-size %eax) +10218 # var out-addr/eax: (addr stmt) = lookup(*out) +10219 (lookup *eax *(eax+4)) # => eax +10220 # set tag +10221 c7 0/subop/copy *eax 3/imm32/tag/var-in-register # Stmt-tag +10222 # set output +10223 8d/copy-address *(eax+0x14) 0/r32/eax # Regvardef-outputs +10224 (append-stmt-var Heap *(ebp+0xc) *(ebp+0x10) 0 0 0 %eax) +10225 $new-reg-var-def:end: +10226 # . restore registers +10227 58/pop-to-eax +10228 # . epilogue +10229 89/<- %esp 5/r32/ebp +10230 5d/pop-to-ebp +10231 c3/return +10232 +10233 append-list: # ad: (addr allocation-descriptor), value: (handle _type), list: (handle list _type), out: (addr handle list _type) +10234 # . prologue +10235 55/push-ebp +10236 89/<- %ebp 4/r32/esp +10237 # . save registers +10238 50/push-eax +10239 51/push-ecx +10240 57/push-edi +10241 # edi = out +10242 8b/-> *(ebp+0x1c) 7/r32/edi +10243 # *out = new list +10244 (allocate *(ebp+8) *List-size %edi) +10245 # var out-addr/edi: (addr list _type) = lookup(*out) +10246 (lookup *edi *(edi+4)) # => eax +10247 89/<- %edi 0/r32/eax +10248 # out-addr->value = value +10249 8b/-> *(ebp+0xc) 0/r32/eax +10250 89/<- *edi 0/r32/eax # List-value +10251 8b/-> *(ebp+0x10) 0/r32/eax +10252 89/<- *(edi+4) 0/r32/eax # List-value +10253 # if (list == null) return +10254 81 7/subop/compare *(ebp+0x14) 0/imm32 +10255 74/jump-if-= $append-list:end/disp8 +10256 # otherwise append +10257 $append-list:non-empty-list: +10258 # var curr/eax: (addr list _type) = lookup(list) +10259 (lookup *(ebp+0x14) *(ebp+0x18)) # => eax +10260 # while (curr->next != null) curr = curr->next +10261 { +10262 81 7/subop/compare *(eax+8) 0/imm32 # List-next +10263 74/jump-if-= break/disp8 +10264 # curr = lookup(curr->next) +10265 (lookup *(eax+8) *(eax+0xc)) # List-next, List-next => eax +10266 # +10267 eb/jump loop/disp8 +10268 } +10269 # edi = out +10270 8b/-> *(ebp+0x1c) 7/r32/edi +10271 # curr->next = out +10272 8b/-> *edi 1/r32/ecx +10273 89/<- *(eax+8) 1/r32/ecx # List-next +10274 8b/-> *(edi+4) 1/r32/ecx +10275 89/<- *(eax+0xc) 1/r32/ecx # List-next +10276 # out = list +10277 8b/-> *(ebp+0x14) 1/r32/ecx +10278 89/<- *edi 1/r32/ecx +10279 8b/-> *(ebp+0x18) 1/r32/ecx +10280 89/<- *(edi+4) 1/r32/ecx +10281 $append-list:end: +10282 # . restore registers +10283 5f/pop-to-edi +10284 59/pop-to-ecx +10285 58/pop-to-eax +10286 # . epilogue +10287 89/<- %esp 5/r32/ebp +10288 5d/pop-to-ebp +10289 c3/return +10290 +10291 append-stmt-var: # ad: (addr allocation-descriptor), v: (handle var), vars: (handle stmt-var), is-deref?: boolean, out: (addr handle stmt-var) +10292 # . prologue +10293 55/push-ebp +10294 89/<- %ebp 4/r32/esp +10295 # . save registers +10296 50/push-eax +10297 51/push-ecx +10298 57/push-edi +10299 # edi = out +10300 8b/-> *(ebp+0x20) 7/r32/edi +10301 # out = new stmt-var +10302 (allocate *(ebp+8) *Stmt-var-size %edi) +10303 # var out-addr/ecx: (addr stmt-var) = lookup(*out) +10304 (lookup *edi *(edi+4)) # => eax +10305 89/<- %ecx 0/r32/eax +10306 # out-addr->value = v +10307 8b/-> *(ebp+0xc) 0/r32/eax +10308 89/<- *ecx 0/r32/eax # Stmt-var-value +10309 8b/-> *(ebp+0x10) 0/r32/eax +10310 89/<- *(ecx+4) 0/r32/eax # Stmt-var-value +10311 # out-addr->is-deref? = is-deref? +10312 8b/-> *(ebp+0x1c) 0/r32/eax +10313 89/<- *(ecx+0x10) 0/r32/eax # Stmt-var-is-deref +10314 # if (vars == null) return result +10315 81 7/subop/compare *(ebp+0x14) 0/imm32/null +10316 74/jump-if-= $append-stmt-var:end/disp8 +10317 # otherwise append +10318 # var curr/eax: (addr stmt-var) = lookup(vars) +10319 (lookup *(ebp+0x14) *(ebp+0x18)) # => eax +10320 # while (curr->next != null) curr = curr->next +10321 { +10322 81 7/subop/compare *(eax+8) 0/imm32 # Stmt-var-next +10323 74/jump-if-= break/disp8 +10324 # curr = lookup(curr->next) +10325 (lookup *(eax+8) *(eax+0xc)) # Stmt-var-next, Stmt-var-next => eax +10326 # +10327 eb/jump loop/disp8 +10328 } +10329 # curr->next = out +10330 8b/-> *edi 1/r32/ecx +10331 89/<- *(eax+8) 1/r32/ecx # Stmt-var-next +10332 8b/-> *(edi+4) 1/r32/ecx +10333 89/<- *(eax+0xc) 1/r32/ecx # Stmt-var-next +10334 # out = vars +10335 8b/-> *(ebp+0x14) 1/r32/ecx +10336 89/<- *edi 1/r32/ecx +10337 8b/-> *(ebp+0x18) 1/r32/ecx +10338 89/<- *(edi+4) 1/r32/ecx +10339 $append-stmt-var:end: +10340 # . restore registers +10341 5f/pop-to-edi +10342 59/pop-to-ecx +10343 58/pop-to-eax +10344 # . epilogue +10345 89/<- %esp 5/r32/ebp +10346 5d/pop-to-ebp +10347 c3/return +10348 +10349 append-to-block: # ad: (addr allocation-descriptor), block: (addr block), x: (handle stmt) +10350 # . prologue +10351 55/push-ebp +10352 89/<- %ebp 4/r32/esp +10353 # . save registers +10354 50/push-eax +10355 56/push-esi +10356 # esi = block +10357 8b/-> *(ebp+0xc) 6/r32/esi +10358 # block->stmts = append(x, block->stmts) +10359 8d/copy-address *(esi+4) 0/r32/eax # Block-stmts +10360 (append-list *(ebp+8) *(ebp+0x10) *(ebp+0x14) *(esi+4) *(esi+8) %eax) # ad, x, x, Block-stmts, Block-stmts +10361 $append-to-block:end: +10362 # . restore registers +10363 5e/pop-to-esi +10364 58/pop-to-eax +10365 # . epilogue +10366 89/<- %esp 5/r32/ebp +10367 5d/pop-to-ebp +10368 c3/return +10369 +10370 ## Parsing types +10371 # We need to create metadata on user-defined types, and we need to use this +10372 # metadata as we parse instructions. +10373 # However, we also want to allow types to be used before their definitions. +10374 # This means we can't ever assume any type data structures exist. +10375 +10376 lookup-or-create-constant: # container: (addr stmt-var), field-name: (addr slice), out: (addr handle var) +10377 # . prologue +10378 55/push-ebp +10379 89/<- %ebp 4/r32/esp +10380 # . save registers +10381 50/push-eax +10382 56/push-esi +10383 # var container-type/esi: type-id +10384 (container-type *(ebp+8)) # => eax +10385 89/<- %esi 0/r32/eax +10386 # var tmp/eax: (handle typeinfo) = find-or-create-typeinfo(container-type) +10387 68/push 0/imm32 +10388 68/push 0/imm32 +10389 89/<- %eax 4/r32/esp +10390 (find-or-create-typeinfo %esi %eax) +10391 # var tmp-addr/eax: (addr typeinfo) = lookup(tmp) +10392 (lookup *eax *(eax+4)) # => eax +10393 # result = find-or-create-typeinfo-output-var(typeinfo, field-name) +10394 #? (write-buffered Stderr "constant: ") +10395 #? (write-slice-buffered Stderr *(ebp+0xc)) +10396 #? (write-buffered Stderr Newline) +10397 #? (flush Stderr) +10398 (find-or-create-typeinfo-output-var %eax *(ebp+0xc) *(ebp+0x10)) +10399 #? 8b/-> *(ebp+0x10) 0/r32/eax +10400 #? (write-buffered Stderr "@") +10401 #? (lookup *eax *(eax+4)) +10402 #? (write-int32-hex-buffered Stderr %eax) +10403 #? (lookup *eax *(eax+4)) +10404 #? (write-buffered Stderr %eax) +10405 #? (write-buffered Stderr Newline) +10406 #? (flush Stderr) +10407 #? (write-buffered Stderr "offset: ") +10408 #? 8b/-> *(eax+0x14) 0/r32/eax +10409 #? (write-int32-hex-buffered Stderr %eax) +10410 #? (write-buffered Stderr Newline) +10411 #? (flush Stderr) +10412 $lookup-or-create-constant:end: +10413 # . reclaim locals +10414 81 0/subop/add %esp 8/imm32 +10415 # . restore registers +10416 5e/pop-to-esi +10417 58/pop-to-eax +10418 # . epilogue +10419 89/<- %esp 5/r32/ebp +10420 5d/pop-to-ebp +10421 c3/return +10422 +10423 # if addr var: +10424 # container->var->type->right->left->value +10425 # otherwise +10426 # container->var->type->value +10427 container-type: # container: (addr stmt-var) -> result/eax: type-id +10428 # . prologue +10429 55/push-ebp +10430 89/<- %ebp 4/r32/esp +10431 # +10432 8b/-> *(ebp+8) 0/r32/eax +10433 (lookup *eax *(eax+4)) # Stmt-var-value Stmt-var-value => eax +10434 (lookup *(eax+8) *(eax+0xc)) # Var-type Var-type => eax +10435 { +10436 81 7/subop/compare *(eax+8) 0/imm32 # Type-tree-right +10437 74/jump-if-= break/disp8 +10438 (lookup *(eax+0xc) *(eax+0x10)) # Type-tree-right Type-tree-right => eax +10439 (lookup *(eax+4) *(eax+8)) # Type-tree-left Type-tree-left => eax +10440 } +10441 8b/-> *(eax+4) 0/r32/eax # Type-tree-value +10442 $container-type:end: +10443 # . epilogue +10444 89/<- %esp 5/r32/ebp +10445 5d/pop-to-ebp +10446 c3/return +10447 +10448 is-container?: # t: type-id -> result/eax: boolean +10449 # . prologue +10450 55/push-ebp +10451 89/<- %ebp 4/r32/esp +10452 # +10453 8b/-> *(ebp+8) 0/r32/eax +10454 c1/shift 4/subop/left %eax 2/imm8 +10455 3b/compare 0/r32/eax *Primitive-type-ids +10456 0f 9d/set-if->= %al +10457 81 4/subop/and %eax 0xff/imm32 +10458 $is-container?:end: +10459 # . epilogue +10460 89/<- %esp 5/r32/ebp +10461 5d/pop-to-ebp +10462 c3/return +10463 +10464 find-or-create-typeinfo: # t: type-id, out: (addr handle typeinfo) +10465 # . prologue +10466 55/push-ebp +10467 89/<- %ebp 4/r32/esp +10468 # . save registers +10469 50/push-eax +10470 51/push-ecx +10471 52/push-edx +10472 57/push-edi +10473 # edi = out +10474 8b/-> *(ebp+0xc) 7/r32/edi +10475 # var fields/ecx: (handle table (handle array byte) (handle typeinfo-entry)) +10476 68/push 0/imm32 +10477 68/push 0/imm32 +10478 89/<- %ecx 4/r32/esp +10479 # find-typeinfo(t, out) +10480 (find-typeinfo *(ebp+8) %edi) +10481 { +10482 # if (*out != 0) break +10483 81 7/subop/compare *edi 0/imm32 +10484 0f 85/jump-if-!= break/disp32 +10485 $find-or-create-typeinfo:create: +10486 # *out = allocate +10487 (allocate Heap *Typeinfo-size %edi) +10488 # var tmp/eax: (addr typeinfo) = lookup(*out) +10489 (lookup *edi *(edi+4)) # => eax +10490 #? (write-buffered Stderr "created typeinfo at ") +10491 #? (write-int32-hex-buffered Stderr %eax) +10492 #? (write-buffered Stderr " for type-id ") +10493 #? (write-int32-hex-buffered Stderr *(ebp+8)) +10494 #? (write-buffered Stderr Newline) +10495 #? (flush Stderr) +10496 # tmp->id = t +10497 8b/-> *(ebp+8) 2/r32/edx +10498 89/<- *eax 2/r32/edx # Typeinfo-id +10499 # tmp->fields = new table +10500 # . fields = new table +10501 (new-stream Heap 0x40 *Typeinfo-fields-row-size %ecx) +10502 # . tmp->fields = fields +10503 8b/-> *ecx 2/r32/edx +10504 89/<- *(eax+4) 2/r32/edx # Typeinfo-fields +10505 8b/-> *(ecx+4) 2/r32/edx +10506 89/<- *(eax+8) 2/r32/edx # Typeinfo-fields +10507 # tmp->next = Program->types +10508 8b/-> *_Program-types 1/r32/ecx +10509 89/<- *(eax+0x10) 1/r32/ecx # Typeinfo-next +10510 8b/-> *_Program-types->payload 1/r32/ecx +10511 89/<- *(eax+0x14) 1/r32/ecx # Typeinfo-next +10512 # Program->types = out +10513 8b/-> *edi 1/r32/ecx +10514 89/<- *_Program-types 1/r32/ecx +10515 8b/-> *(edi+4) 1/r32/ecx +10516 89/<- *_Program-types->payload 1/r32/ecx +10517 } +10518 $find-or-create-typeinfo:end: +10519 # . reclaim locals +10520 81 0/subop/add %esp 8/imm32 +10521 # . restore registers +10522 5f/pop-to-edi +10523 5a/pop-to-edx +10524 59/pop-to-ecx +10525 58/pop-to-eax +10526 # . epilogue +10527 89/<- %esp 5/r32/ebp +10528 5d/pop-to-ebp +10529 c3/return +10530 +10531 find-typeinfo: # t: type-id, out: (addr handle typeinfo) +10532 # . prologue +10533 55/push-ebp +10534 89/<- %ebp 4/r32/esp +10535 # . save registers +10536 50/push-eax +10537 51/push-ecx +10538 52/push-edx +10539 57/push-edi +10540 # ecx = t +10541 8b/-> *(ebp+8) 1/r32/ecx +10542 # edi = out +10543 8b/-> *(ebp+0xc) 7/r32/edi +10544 # *out = Program->types +10545 8b/-> *_Program-types 0/r32/eax +10546 89/<- *edi 0/r32/eax +10547 8b/-> *_Program-types->payload 0/r32/eax +10548 89/<- *(edi+4) 0/r32/eax +10549 { +10550 $find-typeinfo:loop: +10551 # if (*out == 0) break +10552 81 7/subop/compare *edi 0/imm32 +10553 74/jump-if-= break/disp8 +10554 $find-typeinfo:check: +10555 # var tmp/eax: (addr typeinfo) = lookup(*out) +10556 (lookup *edi *(edi+4)) # => eax +10557 # if (tmp->id == t) break +10558 39/compare *eax 1/r32/ecx # Typeinfo-id +10559 74/jump-if-= break/disp8 +10560 $find-typeinfo:continue: +10561 # *out = tmp->next +10562 8b/-> *(eax+0x10) 2/r32/edx # Typeinfo-next +10563 89/<- *edi 2/r32/edx +10564 8b/-> *(eax+0x14) 2/r32/edx # Typeinfo-next +10565 89/<- *(edi+4) 2/r32/edx +10566 # +10567 eb/jump loop/disp8 +10568 } +10569 $find-typeinfo:end: +10570 # . restore registers +10571 5f/pop-to-edi +10572 5a/pop-to-edx +10573 59/pop-to-ecx +10574 58/pop-to-eax +10575 # . epilogue +10576 89/<- %esp 5/r32/ebp +10577 5d/pop-to-ebp +10578 c3/return +10579 +10580 find-or-create-typeinfo-output-var: # T: (addr typeinfo), f: (addr slice), out: (addr handle var) +10581 # . prologue +10582 55/push-ebp +10583 89/<- %ebp 4/r32/esp +10584 # . save registers +10585 50/push-eax +10586 52/push-edx +10587 57/push-edi +10588 # var dest/edi: (handle typeinfo-entry) +10589 68/push 0/imm32 +10590 68/push 0/imm32 +10591 89/<- %edi 4/r32/esp +10592 # find-or-create-typeinfo-fields(T, f, dest) +10593 (find-or-create-typeinfo-fields *(ebp+8) *(ebp+0xc) %edi) +10594 # var dest-addr/edi: (addr typeinfo-entry) = lookup(dest) +10595 (lookup *edi *(edi+4)) # => eax +10596 89/<- %edi 0/r32/eax +10597 # if dest-addr->output-var doesn't exist, create it +10598 { +10599 81 7/subop/compare *(edi+0xc) 0/imm32 # Typeinfo-entry-output-var +10600 0f 85/jump-if-!= break/disp32 +10601 # dest-addr->output-var = new var(dummy name, type, -1 offset) +10602 # . var name/eax: (handle array byte) = "field" +10603 68/push 0/imm32 +10604 68/push 0/imm32 +10605 89/<- %eax 4/r32/esp +10606 (slice-to-string Heap *(ebp+0xc) %eax) +10607 # . new var +10608 8d/copy-address *(edi+0xc) 2/r32/edx +10609 (new-var Heap *eax *(eax+4) %edx) +10610 # . reclaim name +10611 81 0/subop/add %esp 8/imm32 +10612 # var result/edx: (addr var) = lookup(dest-addr->output-var) +10613 (lookup *(edi+0xc) *(edi+0x10)) # => eax +10614 89/<- %edx 0/r32/eax +10615 # result->type = new constant type +10616 8d/copy-address *(edx+8) 0/r32/eax # Var-type +10617 (allocate Heap *Type-tree-size %eax) +10618 (lookup *(edx+8) *(edx+0xc)) # => eax +10619 c7 0/subop/copy *eax 1/imm32/true # Type-tree-is-atom +10620 c7 0/subop/copy *(eax+4) 6/imm32/constant # Type-tree-value +10621 c7 0/subop/copy *(eax+8) 0/imm32 # Type-tree-left +10622 c7 0/subop/copy *(eax+0xc) 0/imm32 # Type-tree-right +10623 c7 0/subop/copy *(eax+0x10) 0/imm32 # Type-tree-right +10624 # result->offset isn't filled out yet +10625 c7 0/subop/copy *(edx+0x14) -1/imm32/uninitialized # Var-offset +10626 } +10627 # out = dest-addr->output-var +10628 8b/-> *(ebp+0x10) 2/r32/edx +10629 8b/-> *(edi+0xc) 0/r32/eax # Typeinfo-entry-output-var +10630 89/<- *edx 0/r32/eax +10631 8b/-> *(edi+0x10) 0/r32/eax # Typeinfo-entry-output-var +10632 89/<- *(edx+4) 0/r32/eax +10633 $find-or-create-typeinfo-output-var:end: +10634 # . reclaim locals +10635 81 0/subop/add %esp 8/imm32 +10636 # . restore registers +10637 5f/pop-to-edi +10638 5a/pop-to-edx +10639 58/pop-to-eax +10640 # . epilogue +10641 89/<- %esp 5/r32/ebp +10642 5d/pop-to-ebp +10643 c3/return +10644 +10645 find-or-create-typeinfo-fields: # T: (addr typeinfo), f: (addr slice), out: (addr handle typeinfo-entry) +10646 # . prologue +10647 55/push-ebp +10648 89/<- %ebp 4/r32/esp +10649 # . save registers +10650 50/push-eax +10651 56/push-esi +10652 57/push-edi +10653 # eax = lookup(T->fields) +10654 8b/-> *(ebp+8) 0/r32/eax +10655 (lookup *(eax+4) *(eax+8)) # Typeinfo-fields Typeinfo-fields => eax +10656 # edi = out +10657 8b/-> *(ebp+0x10) 7/r32/edi +10658 # var src/esi: (addr handle typeinfo-entry) = get-or-insert-slice(T->fields, f) +10659 (get-or-insert-slice %eax *(ebp+0xc) *Typeinfo-fields-row-size Heap) # => eax +10660 89/<- %esi 0/r32/eax +10661 # if src doesn't exist, allocate it +10662 { +10663 81 7/subop/compare *esi 0/imm32 +10664 75/jump-if-!= break/disp8 +10665 (allocate Heap *Typeinfo-entry-size %esi) +10666 #? (write-buffered Stderr "handle at ") +10667 #? (write-int32-hex-buffered Stderr %esi) +10668 #? (write-buffered Stderr ": ") +10669 #? (write-int32-hex-buffered Stderr *esi) +10670 #? (write-buffered Stderr " ") +10671 #? (write-int32-hex-buffered Stderr *(esi+4)) +10672 #? (write-buffered Stderr Newline) +10673 #? (flush Stderr) +10674 #? (lookup *esi *(esi+4)) +10675 #? (write-buffered Stderr "created typeinfo fields at ") +10676 #? (write-int32-hex-buffered Stderr %esi) +10677 #? (write-buffered Stderr " for ") +10678 #? (write-int32-hex-buffered Stderr *(ebp+8)) +10679 #? (write-buffered Stderr Newline) +10680 #? (flush Stderr) +10681 } +10682 # *out = src +10683 # . *edi = *src +10684 8b/-> *esi 0/r32/eax +10685 89/<- *edi 0/r32/eax +10686 8b/-> *(esi+4) 0/r32/eax +10687 89/<- *(edi+4) 0/r32/eax +10688 $find-or-create-typeinfo-fields:end: +10689 # . restore registers +10690 5f/pop-to-edi +10691 5e/pop-to-esi +10692 58/pop-to-eax +10693 # . epilogue +10694 89/<- %esp 5/r32/ebp +10695 5d/pop-to-ebp +10696 c3/return +10697 +10698 populate-mu-type: # in: (addr stream byte), t: (addr typeinfo), err: (addr buffered-file), ed: (addr exit-descriptor) +10699 # pseudocode: +10700 # var line: (stream byte 512) +10701 # curr-index = 0 +10702 # while true +10703 # clear-stream(line) +10704 # read-line-buffered(in, line) +10705 # if line->write == 0 +10706 # abort +10707 # word-slice = next-mu-token(line) +10708 # if slice-empty?(word-slice) # end of line +10709 # continue +10710 # if slice-equal?(word-slice, "}") +10711 # break +10712 # var v: (handle var) = parse-var-with-type(word-slice, line) +10713 # var r: (handle typeinfo-fields) = find-or-create-typeinfo-fields(t, word-slice/v->name) +10714 # TODO: ensure that r->first is null +10715 # r->index = curr-index +10716 # curr-index++ +10717 # r->input-var = v +10718 # if r->output-var == 0 +10719 # r->output-var = new literal +10720 # TODO: ensure nothing else in line +10721 # t->total-size-in-bytes = -2 (not yet initialized) +10722 # +10723 # . prologue +10724 55/push-ebp +10725 89/<- %ebp 4/r32/esp +10726 # var curr-index: int at *(ebp-4) +10727 68/push 0/imm32 +10728 # . save registers +10729 50/push-eax +10730 51/push-ecx +10731 52/push-edx +10732 53/push-ebx +10733 56/push-esi +10734 57/push-edi +10735 # edi = t +10736 8b/-> *(ebp+0xc) 7/r32/edi +10737 # var line/ecx: (stream byte 512) +10738 81 5/subop/subtract %esp 0x200/imm32 +10739 68/push 0x200/imm32/size +10740 68/push 0/imm32/read +10741 68/push 0/imm32/write +10742 89/<- %ecx 4/r32/esp +10743 # var word-slice/edx: slice +10744 68/push 0/imm32/end +10745 68/push 0/imm32/start +10746 89/<- %edx 4/r32/esp +10747 # var v/esi: (handle var) +10748 68/push 0/imm32 10749 68/push 0/imm32 -10750 68/push 0/imm32 -10751 89/<- %ebx 4/r32/esp -10752 { -10753 $populate-mu-type:line-loop: -10754 (clear-stream %ecx) -10755 (read-line-buffered *(ebp+8) %ecx) -10756 # if (line->write == 0) abort -10757 81 7/subop/compare *ecx 0/imm32 -10758 0f 84/jump-if-= $populate-mu-type:error1/disp32 -10759 +-- 6 lines: #? # dump line --------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- -10765 (next-mu-token %ecx %edx) -10766 # if slice-empty?(word-slice) continue -10767 (slice-empty? %edx) # => eax -10768 3d/compare-eax-and 0/imm32 -10769 0f 85/jump-if-!= loop/disp32 -10770 # if slice-equal?(word-slice, "}") break -10771 (slice-equal? %edx "}") -10772 3d/compare-eax-and 0/imm32 -10773 0f 85/jump-if-!= break/disp32 -10774 $populate-mu-type:parse-element: -10775 # v = parse-var-with-type(word-slice, first-line) -10776 # must do this first to strip the trailing ':' from word-slice before -10777 # using it in find-or-create-typeinfo-fields below -10778 # TODO: clean up that mutation in parse-var-with-type -10779 (parse-var-with-type %edx %ecx %esi *(ebp+0x10) *(ebp+0x14)) -10780 # if v is an addr, abort -10781 (lookup *esi *(esi+4)) # => eax -10782 (lookup *(eax+8) *(eax+0xc)) # Var-type Var-type => eax -10783 (is-mu-addr-type? %eax) # => eax -10784 3d/compare-eax-and 0/imm32/false -10785 0f 85/jump-if-!= $populate-mu-type:error2/disp32 -10786 # if v is an array, abort (we could support it, but initialization gets complex) -10787 (lookup *esi *(esi+4)) # => eax -10788 (lookup *(eax+8) *(eax+0xc)) # Var-type Var-type => eax -10789 (is-mu-array-type? %eax) # => eax -10790 3d/compare-eax-and 0/imm32/false -10791 0f 85/jump-if-!= $populate-mu-type:error3/disp32 -10792 # var tmp/ecx -10793 51/push-ecx -10794 $populate-mu-type:create-typeinfo-fields: -10795 # var r/ebx: (handle typeinfo-entry) -10796 (find-or-create-typeinfo-fields %edi %edx %ebx) -10797 # r->index = curr-index -10798 (lookup *ebx *(ebx+4)) # => eax -10799 8b/-> *(ebp-4) 1/r32/ecx -10800 #? (write-buffered Stderr "saving index ") -10801 #? (write-int32-hex-buffered Stderr %ecx) -10802 #? (write-buffered Stderr " at ") -10803 #? (write-int32-hex-buffered Stderr %edi) -10804 #? (write-buffered Stderr Newline) -10805 #? (flush Stderr) -10806 89/<- *(eax+8) 1/r32/ecx # Typeinfo-entry-index -10807 # ++curr-index -10808 ff 0/subop/increment *(ebp-4) -10809 $populate-mu-type:set-input-type: -10810 # r->input-var = v -10811 8b/-> *esi 1/r32/ecx -10812 89/<- *eax 1/r32/ecx # Typeinfo-entry-input-var -10813 8b/-> *(esi+4) 1/r32/ecx -10814 89/<- *(eax+4) 1/r32/ecx # Typeinfo-entry-input-var -10815 # restore line -10816 59/pop-to-ecx -10817 { -10818 $populate-mu-type:create-output-type: -10819 # if (r->output-var == 0) create a new var with some placeholder data -10820 81 7/subop/compare *(eax+0xc) 0/imm32 # Typeinfo-entry-output-var -10821 75/jump-if-!= break/disp8 -10822 8d/copy-address *(eax+0xc) 0/r32/eax # Typeinfo-entry-output-var -10823 (new-literal Heap %edx %eax) -10824 } -10825 e9/jump loop/disp32 -10826 } -10827 $populate-mu-type:invalidate-total-size-in-bytes: -10828 # Offsets and total size may not be accurate here since we may not yet -10829 # have encountered the element types. -10830 # We'll recompute them separately after parsing the entire program. -10831 c7 0/subop/copy *(edi+0xc) -2/imm32/uninitialized # Typeinfo-total-size-in-bytes -10832 $populate-mu-type:end: -10833 # . reclaim locals -10834 81 0/subop/add %esp 0x224/imm32 -10835 # . restore registers -10836 5f/pop-to-edi -10837 5e/pop-to-esi -10838 5b/pop-to-ebx -10839 5a/pop-to-edx -10840 59/pop-to-ecx -10841 58/pop-to-eax -10842 # reclaim curr-index -10843 81 0/subop/add %esp 4/imm32 -10844 # . epilogue -10845 89/<- %esp 5/r32/ebp -10846 5d/pop-to-ebp -10847 c3/return -10848 -10849 $populate-mu-type:error1: -10850 # error("incomplete type definition '" t->name "'\n") -10851 (write-buffered *(ebp+0x10) "incomplete type definition '") -10852 (type-name *edi) # Typeinfo-id => eax -10853 (write-buffered *(ebp+0x10) %eax) -10854 (write-buffered *(ebp+0x10) "\n") -10855 (flush *(ebp+0x10)) -10856 (stop *(ebp+0x14) 1) -10857 # never gets here -10858 -10859 $populate-mu-type:error2: -10860 # error("type " t->name ": invalid type 'addr'\n") -10861 (write-buffered *(ebp+0x10) "type ") -10862 (type-name *edi) # Typeinfo-id => eax -10863 (write-buffered *(ebp+0x10) %eax) -10864 (write-buffered *(ebp+0x10) ": invalid type 'addr'\n") -10865 (flush *(ebp+0x10)) -10866 (stop *(ebp+0x14) 1) -10867 # never gets here -10868 -10869 $populate-mu-type:error3: -10870 # error("type " t->name ": invalid type 'array'\n") -10871 (write-buffered *(ebp+0x10) "type ") -10872 (type-name *edi) # Typeinfo-id => eax -10873 (write-buffered *(ebp+0x10) %eax) -10874 (write-buffered *(ebp+0x10) ": invalid type 'array'\n") -10875 (flush *(ebp+0x10)) -10876 (stop *(ebp+0x14) 1) -10877 # never gets here -10878 -10879 type-name: # index: int -> result/eax: (addr array byte) -10880 # . prologue -10881 55/push-ebp -10882 89/<- %ebp 4/r32/esp -10883 # -10884 (index Type-id *(ebp+8)) -10885 $type-name:end: -10886 # . epilogue -10887 89/<- %esp 5/r32/ebp -10888 5d/pop-to-ebp -10889 c3/return -10890 -10891 index: # arr: (addr stream (handle array byte)), index: int -> result/eax: (addr array byte) -10892 # . prologue -10893 55/push-ebp -10894 89/<- %ebp 4/r32/esp -10895 # . save registers -10896 56/push-esi -10897 # TODO: bounds-check index -10898 # esi = arr -10899 8b/-> *(ebp+8) 6/r32/esi -10900 # eax = index -10901 8b/-> *(ebp+0xc) 0/r32/eax -10902 # eax = *(arr + 12 + index) -10903 8b/-> *(esi+eax<<2+0xc) 0/r32/eax -10904 $index:end: -10905 # . restore registers -10906 5e/pop-to-esi -10907 # . epilogue -10908 89/<- %esp 5/r32/ebp -10909 5d/pop-to-ebp -10910 c3/return -10911 -10912 ####################################################### -10913 # Compute type sizes -10914 ####################################################### -10915 -10916 # Compute the sizes of all user-defined types. -10917 # We'll need the sizes of their elements, which may be other user-defined -10918 # types, which we will compute as needed. -10919 -10920 # Initially, all user-defined types have their sizes set to -2 (invalid) -10921 populate-mu-type-sizes: # err: (addr buffered-file), ed: (addr exit-descriptor) -10922 # . prologue -10923 55/push-ebp -10924 89/<- %ebp 4/r32/esp -10925 $populate-mu-type-sizes:total-sizes: -10926 # var curr/eax: (addr typeinfo) = lookup(Program->types) -10927 (lookup *_Program-types *_Program-types->payload) # => eax -10928 { -10929 # if (curr == null) break -10930 3d/compare-eax-and 0/imm32/null -10931 74/jump-if-= break/disp8 -10932 (populate-mu-type-sizes-in-type %eax *(ebp+8) *(ebp+0xc)) -10933 # curr = lookup(curr->next) -10934 (lookup *(eax+0x10) *(eax+0x14)) # Typeinfo-next Typeinfo-next => eax -10935 eb/jump loop/disp8 -10936 } -10937 $populate-mu-type-sizes:offsets: -10938 # curr = *Program->types -10939 (lookup *_Program-types *_Program-types->payload) # => eax -10940 { -10941 # if (curr == null) break -10942 3d/compare-eax-and 0/imm32/null -10943 74/jump-if-= break/disp8 -10944 (populate-mu-type-offsets %eax *(ebp+8) *(ebp+0xc)) -10945 # curr = curr->next -10946 (lookup *(eax+0x10) *(eax+0x14)) # Typeinfo-next Typeinfo-next => eax -10947 eb/jump loop/disp8 -10948 } -10949 $populate-mu-type-sizes:end: -10950 # . epilogue -10951 89/<- %esp 5/r32/ebp -10952 5d/pop-to-ebp -10953 c3/return -10954 -10955 # compute sizes of all fields, recursing as necessary -10956 # sum up all their sizes to arrive at total size -10957 # fields may be out of order, but that doesn't affect the answer -10958 populate-mu-type-sizes-in-type: # T: (addr typeinfo), err: (addr buffered-file), ed: (addr exit-descriptor) -10959 # . prologue -10960 55/push-ebp -10961 89/<- %ebp 4/r32/esp -10962 # . save registers -10963 50/push-eax -10964 51/push-ecx -10965 52/push-edx -10966 56/push-esi -10967 57/push-edi -10968 # esi = T -10969 8b/-> *(ebp+8) 6/r32/esi -10970 # if T is already computed, return -10971 81 7/subop/compare *(esi+0xc) 0/imm32 # Typeinfo-total-size-in-bytes -10972 0f 8d/jump-if->= $populate-mu-type-sizes-in-type:end/disp32 -10973 # if T is being computed, abort -10974 81 7/subop/compare *(esi+0xc) -1/imm32/being-computed # Typeinfo-total-size-in-bytes -10975 0f 84/jump-if-= $populate-mu-type-sizes-in-type:abort/disp32 -10976 # tag T (-2 to -1) to avoid infinite recursion -10977 c7 0/subop/copy *(esi+0xc) -1/imm32/being-computed # Typeinfo-total-size-in-bytes -10978 # var total-size/edi: int = 0 -10979 bf/copy-to-edi 0/imm32 -10980 # - for every field, if it's a user-defined type, compute its size -10981 # var table/ecx: (addr table (handle array byte) (handle typeinfo-entry)) = lookup(T->fields) -10982 (lookup *(esi+4) *(esi+8)) # Typeinfo-fields Typeinfo-fields => eax -10983 89/<- %ecx 0/r32/eax -10984 # var table-size/edx: int = table->write -10985 8b/-> *ecx 2/r32/edx # stream-write -10986 # var curr/ecx: (addr table_row) = table->data -10987 8d/copy-address *(ecx+0xc) 1/r32/ecx -10988 # var max/edx: (addr table_row) = table->data + table->write -10989 8d/copy-address *(ecx+edx) 2/r32/edx -10990 { -10991 $populate-mu-type-sizes-in-type:loop: -10992 # if (curr >= max) break -10993 39/compare %ecx 2/r32/edx -10994 73/jump-if-addr>= break/disp8 -10995 # var t/eax: (addr typeinfo-entry) = lookup(curr->value) -10996 (lookup *(ecx+8) *(ecx+0xc)) # => eax -10997 # if (t->input-var == 0) silently ignore it; we'll emit a nice error message while type-checking -10998 81 7/subop/compare *eax 0/imm32 # Typeinfo-entry-input-var -10999 74/jump-if-= $populate-mu-type-sizes-in-type:end/disp8 -11000 # compute size of t->input-var -11001 (lookup *eax *(eax+4)) # Typeinfo-entry-input-var Typeinfo-entry-input-var => eax -11002 (compute-size-of-var %eax) # => eax -11003 # result += eax -11004 01/add-to %edi 0/r32/eax -11005 # curr += row-size -11006 81 0/subop/add %ecx 0x10/imm32 # Typeinfo-fields-row-size -11007 # -11008 eb/jump loop/disp8 -11009 } -11010 # - save result -11011 89/<- *(esi+0xc) 7/r32/edi # Typeinfo-total-size-in-bytes -11012 $populate-mu-type-sizes-in-type:end: -11013 # . restore registers -11014 5f/pop-to-edi -11015 5e/pop-to-esi -11016 5a/pop-to-edx -11017 59/pop-to-ecx -11018 58/pop-to-eax -11019 # . epilogue -11020 89/<- %esp 5/r32/ebp -11021 5d/pop-to-ebp -11022 c3/return -11023 -11024 $populate-mu-type-sizes-in-type:abort: -11025 (write-buffered *(ebp+0xc) "cycle in type definitions\n") -11026 (flush *(ebp+0xc)) -11027 (stop *(ebp+0x10) 1) -11028 # never gets here -11029 -11030 # Analogous to size-of, except we need to compute what size-of can just read -11031 # off the right data structures. -11032 compute-size-of-var: # in: (addr var) -> result/eax: int -11033 # . prologue -11034 55/push-ebp -11035 89/<- %ebp 4/r32/esp -11036 # . push registers -11037 51/push-ecx -11038 # var t/ecx: (addr type-tree) = lookup(v->type) -11039 8b/-> *(ebp+8) 1/r32/ecx -11040 (lookup *(ecx+8) *(ecx+0xc)) # Var-type Var-type => eax -11041 89/<- %ecx 0/r32/eax -11042 # if (t->is-atom == false) t = lookup(t->left) -11043 { -11044 81 7/subop/compare *ecx 0/imm32/false # Type-tree-is-atom -11045 75/jump-if-!= break/disp8 -11046 (lookup *(ecx+4) *(ecx+8)) # Type-tree-left Type-tree-left => eax -11047 89/<- %ecx 0/r32/eax -11048 } -11049 # TODO: ensure t is an atom -11050 (compute-size-of-type-id *(ecx+4)) # Type-tree-value => eax -11051 $compute-size-of-var:end: -11052 # . restore registers -11053 59/pop-to-ecx -11054 # . epilogue -11055 89/<- %esp 5/r32/ebp -11056 5d/pop-to-ebp -11057 c3/return -11058 -11059 compute-size-of-type-id: # t: type-id -> result/eax: int -11060 # . prologue -11061 55/push-ebp -11062 89/<- %ebp 4/r32/esp -11063 # . save registers -11064 51/push-ecx -11065 # var out/ecx: (handle typeinfo) -11066 68/push 0/imm32 -11067 68/push 0/imm32 -11068 89/<- %ecx 4/r32/esp -11069 # eax = t -11070 8b/-> *(ebp+8) 0/r32/eax -11071 # if t is a literal, return 0 -11072 3d/compare-eax-and 0/imm32/literal -11073 0f 84/jump-if-= $compute-size-of-type-id:end/disp32 # eax changes type from type-id to int -11074 # if t is a byte, return 4 (because we don't really support non-multiples of 4) -11075 3d/compare-eax-and 8/imm32/byte -11076 { -11077 75/jump-if-!= break/disp8 -11078 b8/copy-to-eax 4/imm32 -11079 eb/jump $compute-size-of-type-id:end/disp8 -11080 } -11081 # if t is a handle, return 8 -11082 3d/compare-eax-and 4/imm32/handle -11083 { -11084 75/jump-if-!= break/disp8 -11085 b8/copy-to-eax 8/imm32 -11086 eb/jump $compute-size-of-type-id:end/disp8 # eax changes type from type-id to int -11087 } -11088 # if t is a user-defined type, compute its size -11089 # TODO: support non-atom type -11090 (find-typeinfo %eax %ecx) -11091 { -11092 81 7/subop/compare *ecx 0/imm32 -11093 74/jump-if-= break/disp8 -11094 $compute-size-of-type-id:user-defined: -11095 (populate-mu-type-sizes %eax) -11096 8b/-> *(eax+0xc) 0/r32/eax # Typeinfo-total-size-in-bytes -11097 eb/jump $compute-size-of-type-id:end/disp8 -11098 } -11099 # otherwise return the word size -11100 b8/copy-to-eax 4/imm32 -11101 $compute-size-of-type-id:end: -11102 # . reclaim locals -11103 81 0/subop/add %esp 8/imm32 -11104 # . restore registers -11105 59/pop-to-ecx -11106 # . epilogue -11107 89/<- %esp 5/r32/ebp -11108 5d/pop-to-ebp -11109 c3/return -11110 -11111 # at this point we have total sizes for all user-defined types -11112 # compute offsets for each element -11113 # complication: fields may be out of order -11114 populate-mu-type-offsets: # in: (addr typeinfo), err: (addr buffered-file), ed: (addr exit-descriptor) -11115 # . prologue -11116 55/push-ebp -11117 89/<- %ebp 4/r32/esp -11118 # . save registers -11119 50/push-eax -11120 51/push-ecx -11121 52/push-edx -11122 53/push-ebx -11123 56/push-esi -11124 57/push-edi -11125 #? (dump-typeinfos "aaa\n") -11126 # var curr-offset/edi: int = 0 -11127 bf/copy-to-edi 0/imm32 -11128 # var table/ecx: (addr table string_key (handle typeinfo-entry)) = lookup(in->fields) -11129 8b/-> *(ebp+8) 1/r32/ecx -11130 (lookup *(ecx+4) *(ecx+8)) # Typeinfo-fields Typeinfo-fields => eax -11131 89/<- %ecx 0/r32/eax -11132 # var num-elems/edx: int = table->write / Typeinfo-fields-row-size -11133 8b/-> *ecx 2/r32/edx # stream-write -11134 c1 5/subop/shift-right-logical %edx 4/imm8 -11135 # var i/ebx: int = 0 -11136 bb/copy-to-ebx 0/imm32 -11137 { -11138 $populate-mu-type-offsets:loop: -11139 39/compare %ebx 2/r32/edx -11140 0f 8d/jump-if->= break/disp32 -11141 #? (write-buffered Stderr "looking up index ") -11142 #? (write-int32-hex-buffered Stderr %ebx) -11143 #? (write-buffered Stderr " in ") -11144 #? (write-int32-hex-buffered Stderr *(ebp+8)) -11145 #? (write-buffered Stderr Newline) -11146 #? (flush Stderr) -11147 # var v/esi: (addr typeinfo-entry) -11148 (locate-typeinfo-entry-with-index %ecx %ebx *(ebp+0xc) *(ebp+0x10)) # => eax -11149 89/<- %esi 0/r32/eax -11150 # if v is null, silently move on; we'll emit a nice error message while type-checking -11151 81 7/subop/compare %esi 0/imm32 # Typeinfo-entry-input-var -11152 74/jump-if-= $populate-mu-type-offsets:end/disp8 -11153 # if (v->input-var == 0) silently ignore v; we'll emit a nice error message while type-checking -11154 81 7/subop/compare *esi 0/imm32 # Typeinfo-entry-input-var -11155 74/jump-if-= $populate-mu-type-offsets:end/disp8 -11156 # v->output-var->offset = curr-offset -11157 # . eax: (addr var) -11158 (lookup *(esi+0xc) *(esi+0x10)) # Typeinfo-entry-output-var Typeinfo-entry-output-var => eax -11159 89/<- *(eax+0x14) 7/r32/edi # Var-offset -11160 # curr-offset += size-of(v->input-var) -11161 (lookup *esi *(esi+4)) # Typeinfo-entry-input-var Typeinfo-entry-input-var => eax -11162 (size-of %eax) # => eax -11163 01/add-to %edi 0/r32/eax -11164 # ++i -11165 43/increment-ebx -11166 e9/jump loop/disp32 -11167 } -11168 $populate-mu-type-offsets:end: -11169 # . restore registers -11170 5f/pop-to-edi -11171 5e/pop-to-esi -11172 5b/pop-to-ebx -11173 5a/pop-to-edx -11174 59/pop-to-ecx -11175 58/pop-to-eax -11176 # . epilogue -11177 89/<- %esp 5/r32/ebp -11178 5d/pop-to-ebp -11179 c3/return -11180 -11181 locate-typeinfo-entry-with-index: # table: (addr table (handle array byte) (handle typeinfo-entry)), idx: int, err: (addr buffered-file), ed: (addr exit-descriptor) -> result/eax: (addr typeinfo-entry) -11182 # . prologue -11183 55/push-ebp -11184 89/<- %ebp 4/r32/esp -11185 # . save registers -11186 51/push-ecx -11187 52/push-edx -11188 53/push-ebx -11189 56/push-esi -11190 57/push-edi -11191 # esi = table -11192 8b/-> *(ebp+8) 6/r32/esi -11193 # var curr/ecx: (addr row (handle array byte) (handle typeinfo-entry)) = table->data -11194 8d/copy-address *(esi+0xc) 1/r32/ecx -11195 # var max/edx: (addr byte) = &table->data[table->write] -11196 8b/-> *esi 2/r32/edx -11197 8d/copy-address *(ecx+edx) 2/r32/edx -11198 { -11199 $locate-typeinfo-entry-with-index:loop: -11200 39/compare %ecx 2/r32/edx -11201 73/jump-if-addr>= break/disp8 -11202 # var v/eax: (addr typeinfo-entry) -11203 (lookup *(ecx+8) *(ecx+0xc)) # => eax -11204 # if (v->index == idx) return v -11205 8b/-> *(eax+8) 3/r32/ebx # Typeinfo-entry-index -11206 #? (write-buffered Stderr "comparing ") -11207 #? (write-int32-hex-buffered Stderr %ebx) -11208 #? (write-buffered Stderr " and ") -11209 #? (write-int32-hex-buffered Stderr *(ebp+0xc)) -11210 #? (write-buffered Stderr Newline) -11211 #? (flush Stderr) -11212 39/compare *(ebp+0xc) 3/r32/ebx -11213 74/jump-if-= $locate-typeinfo-entry-with-index:end/disp8 -11214 # curr += Typeinfo-entry-size -11215 81 0/subop/add %ecx 0x10/imm32 # Typeinfo-entry-size -11216 # -11217 eb/jump loop/disp8 -11218 } -11219 # return 0 -11220 b8/copy-to-eax 0/imm32 -11221 $locate-typeinfo-entry-with-index:end: -11222 #? (write-buffered Stderr "returning ") -11223 #? (write-int32-hex-buffered Stderr %eax) -11224 #? (write-buffered Stderr Newline) -11225 #? (flush Stderr) -11226 # . restore registers -11227 5f/pop-to-edi -11228 5e/pop-to-esi -11229 5b/pop-to-ebx -11230 5a/pop-to-edx -11231 59/pop-to-ecx -11232 # . epilogue -11233 89/<- %esp 5/r32/ebp -11234 5d/pop-to-ebp -11235 c3/return -11236 -11237 dump-typeinfos: # hdr: (addr array byte) -11238 # . prologue -11239 55/push-ebp -11240 89/<- %ebp 4/r32/esp -11241 # . save registers -11242 50/push-eax -11243 # -11244 (write-buffered Stderr *(ebp+8)) -11245 (flush Stderr) -11246 # var curr/eax: (addr typeinfo) = lookup(Program->types) -11247 (lookup *_Program-types *_Program-types->payload) # => eax -11248 { -11249 # if (curr == null) break -11250 3d/compare-eax-and 0/imm32 -11251 74/jump-if-= break/disp8 -11252 (write-buffered Stderr "---\n") -11253 (flush Stderr) -11254 (dump-typeinfo %eax) -11255 # curr = lookup(curr->next) -11256 (lookup *(eax+0x10) *(eax+0x14)) # Typeinfo-next Typeinfo-next => eax -11257 eb/jump loop/disp8 -11258 } -11259 $dump-typeinfos:end: -11260 # . restore registers -11261 58/pop-to-eax -11262 # . epilogue -11263 89/<- %esp 5/r32/ebp -11264 5d/pop-to-ebp -11265 c3/return -11266 -11267 dump-typeinfo: # in: (addr typeinfo) -11268 # . prologue -11269 55/push-ebp -11270 89/<- %ebp 4/r32/esp -11271 # . save registers -11272 50/push-eax -11273 51/push-ecx -11274 52/push-edx -11275 53/push-ebx -11276 56/push-esi -11277 57/push-edi -11278 # esi = in -11279 8b/-> *(ebp+8) 6/r32/esi -11280 # var table/ecx: (addr table (handle array byte) (handle typeinfo-entry)) = lookup(T->fields) -11281 (lookup *(esi+4) *(esi+8)) # Typeinfo-fields Typeinfo-fields => eax -11282 89/<- %ecx 0/r32/eax -11283 (write-buffered Stderr "id:") -11284 (write-int32-hex-buffered Stderr *esi) -11285 (write-buffered Stderr "\n") -11286 (write-buffered Stderr "fields @ ") -11287 (write-int32-hex-buffered Stderr %ecx) -11288 (write-buffered Stderr Newline) -11289 (flush Stderr) -11290 (write-buffered Stderr " write: ") -11291 (write-int32-hex-buffered Stderr *ecx) -11292 (write-buffered Stderr Newline) -11293 (flush Stderr) -11294 (write-buffered Stderr " read: ") -11295 (write-int32-hex-buffered Stderr *(ecx+4)) -11296 (write-buffered Stderr Newline) -11297 (flush Stderr) -11298 (write-buffered Stderr " size: ") -11299 (write-int32-hex-buffered Stderr *(ecx+8)) -11300 (write-buffered Stderr Newline) -11301 (flush Stderr) -11302 # var table-size/edx: int = table->write -11303 8b/-> *ecx 2/r32/edx # stream-write -11304 # var curr/ecx: (addr table_row) = table->data -11305 8d/copy-address *(ecx+0xc) 1/r32/ecx -11306 # var max/edx: (addr table_row) = table->data + table->write -11307 8d/copy-address *(ecx+edx) 2/r32/edx -11308 { -11309 $dump-typeinfo:loop: -11310 # if (curr >= max) break -11311 39/compare %ecx 2/r32/edx -11312 0f 83/jump-if-addr>= break/disp32 -11313 (write-buffered Stderr " row:\n") -11314 (write-buffered Stderr " key: ") -11315 (write-int32-hex-buffered Stderr *ecx) -11316 (write-buffered Stderr ",") -11317 (write-int32-hex-buffered Stderr *(ecx+4)) -11318 (write-buffered Stderr " = '") -11319 (lookup *ecx *(ecx+4)) -11320 (write-buffered Stderr %eax) -11321 (write-buffered Stderr "' @ ") -11322 (write-int32-hex-buffered Stderr %eax) -11323 (write-buffered Stderr Newline) -11324 (flush Stderr) -11325 (write-buffered Stderr " value: ") -11326 (write-int32-hex-buffered Stderr *(ecx+8)) -11327 (write-buffered Stderr ",") -11328 (write-int32-hex-buffered Stderr *(ecx+0xc)) -11329 (write-buffered Stderr " = typeinfo-entry@") -11330 (lookup *(ecx+8) *(ecx+0xc)) -11331 (write-int32-hex-buffered Stderr %eax) -11332 (write-buffered Stderr Newline) -11333 (flush Stderr) -11334 (write-buffered Stderr " input var@") -11335 (dump-var 5 %eax) -11336 (lookup *(ecx+8) *(ecx+0xc)) -11337 (write-buffered Stderr " index: ") -11338 (write-int32-hex-buffered Stderr *(eax+8)) -11339 (write-buffered Stderr Newline) -11340 (flush Stderr) -11341 (write-buffered Stderr " output var@") -11342 8d/copy-address *(eax+0xc) 0/r32/eax # Typeinfo-entry-output-var -11343 (dump-var 5 %eax) -11344 (flush Stderr) -11345 # curr += row-size -11346 81 0/subop/add %ecx 0x10/imm32 # Typeinfo-fields-row-size -11347 # -11348 e9/jump loop/disp32 -11349 } -11350 $dump-typeinfo:end: -11351 # . restore registers -11352 5f/pop-to-edi -11353 5e/pop-to-esi -11354 5b/pop-to-ebx -11355 5a/pop-to-edx -11356 59/pop-to-ecx -11357 58/pop-to-eax -11358 # . epilogue -11359 89/<- %esp 5/r32/ebp -11360 5d/pop-to-ebp -11361 c3/return -11362 -11363 dump-var: # indent: int, v: (addr handle var) -11364 # . prologue -11365 55/push-ebp -11366 89/<- %ebp 4/r32/esp -11367 # . save registers -11368 50/push-eax -11369 53/push-ebx -11370 # eax = v -11371 8b/-> *(ebp+0xc) 0/r32/eax -11372 # -11373 (write-int32-hex-buffered Stderr *eax) -11374 (write-buffered Stderr ",") -11375 (write-int32-hex-buffered Stderr *(eax+4)) -11376 (write-buffered Stderr "->") -11377 (lookup *eax *(eax+4)) -11378 (write-int32-hex-buffered Stderr %eax) -11379 (write-buffered Stderr Newline) -11380 (flush Stderr) -11381 { -11382 3d/compare-eax-and 0/imm32 -11383 0f 84/jump-if-= break/disp32 -11384 (emit-indent Stderr *(ebp+8)) -11385 (write-buffered Stderr "name: ") -11386 89/<- %ebx 0/r32/eax -11387 (write-int32-hex-buffered Stderr *ebx) # Var-name -11388 (write-buffered Stderr ",") -11389 (write-int32-hex-buffered Stderr *(ebx+4)) # Var-name -11390 (write-buffered Stderr "->") -11391 (lookup *ebx *(ebx+4)) # Var-name -11392 (write-int32-hex-buffered Stderr %eax) -11393 { -11394 3d/compare-eax-and 0/imm32 -11395 74/jump-if-= break/disp8 -11396 (write-buffered Stderr Space) -11397 (write-buffered Stderr %eax) -11398 } -11399 (write-buffered Stderr Newline) -11400 (flush Stderr) -11401 (emit-indent Stderr *(ebp+8)) -11402 (write-buffered Stderr "block depth: ") -11403 (write-int32-hex-buffered Stderr *(ebx+0x10)) # Var-block-depth -11404 (write-buffered Stderr Newline) -11405 (flush Stderr) -11406 (emit-indent Stderr *(ebp+8)) -11407 (write-buffered Stderr "stack offset: ") -11408 (write-int32-hex-buffered Stderr *(ebx+0x14)) # Var-offset -11409 (write-buffered Stderr Newline) -11410 (flush Stderr) -11411 (emit-indent Stderr *(ebp+8)) -11412 (write-buffered Stderr "reg: ") -11413 (write-int32-hex-buffered Stderr *(ebx+0x18)) # Var-register -11414 (write-buffered Stderr ",") -11415 (write-int32-hex-buffered Stderr *(ebx+0x1c)) # Var-register -11416 (write-buffered Stderr "->") -11417 (flush Stderr) -11418 (lookup *(ebx+0x18) *(ebx+0x1c)) # Var-register -11419 (write-int32-hex-buffered Stderr %eax) -11420 { -11421 3d/compare-eax-and 0/imm32 -11422 74/jump-if-= break/disp8 -11423 (write-buffered Stderr Space) -11424 (write-buffered Stderr %eax) -11425 } -11426 (write-buffered Stderr Newline) -11427 (flush Stderr) -11428 } -11429 $dump-var:end: -11430 # . restore registers -11431 5b/pop-to-ebx -11432 58/pop-to-eax -11433 # . epilogue -11434 89/<- %esp 5/r32/ebp -11435 5d/pop-to-ebp -11436 c3/return -11437 -11438 ####################################################### -11439 # Type-checking -11440 ####################################################### -11441 -11442 check-mu-types: # err: (addr buffered-file), ed: (addr exit-descriptor) -11443 # . prologue -11444 55/push-ebp -11445 89/<- %ebp 4/r32/esp -11446 # . save registers -11447 50/push-eax -11448 # var curr/eax: (addr function) = lookup(Program->functions) -11449 (lookup *_Program-functions *_Program-functions->payload) # => eax -11450 { -11451 $check-mu-types:loop: -11452 # if (curr == null) break -11453 3d/compare-eax-and 0/imm32 -11454 0f 84/jump-if-= break/disp32 -11455 +-- 8 lines: #? # dump curr->name --------------------------------------------------------------------------------------------------------------------------------------------------------------------------- -11463 (check-mu-function %eax *(ebp+8) *(ebp+0xc)) -11464 # curr = lookup(curr->next) -11465 (lookup *(eax+0x20) *(eax+0x24)) # Function-next Function-next => eax -11466 e9/jump loop/disp32 -11467 } -11468 $check-mu-types:end: -11469 # . restore registers +10750 89/<- %esi 4/r32/esp +10751 # var r/ebx: (handle typeinfo-entry) +10752 68/push 0/imm32 +10753 68/push 0/imm32 +10754 89/<- %ebx 4/r32/esp +10755 { +10756 $populate-mu-type:line-loop: +10757 (clear-stream %ecx) +10758 (read-line-buffered *(ebp+8) %ecx) +10759 # if (line->write == 0) abort +10760 81 7/subop/compare *ecx 0/imm32 +10761 0f 84/jump-if-= $populate-mu-type:error1/disp32 +10762 +-- 6 lines: #? # dump line ------------------------------------------------------------------------------------------------------------------------------------------------------ +10768 (next-mu-token %ecx %edx) +10769 # if slice-empty?(word-slice) continue +10770 (slice-empty? %edx) # => eax +10771 3d/compare-eax-and 0/imm32 +10772 0f 85/jump-if-!= loop/disp32 +10773 # if slice-equal?(word-slice, "}") break +10774 (slice-equal? %edx "}") +10775 3d/compare-eax-and 0/imm32 +10776 0f 85/jump-if-!= break/disp32 +10777 $populate-mu-type:parse-element: +10778 # v = parse-var-with-type(word-slice, first-line) +10779 # must do this first to strip the trailing ':' from word-slice before +10780 # using it in find-or-create-typeinfo-fields below +10781 # TODO: clean up that mutation in parse-var-with-type +10782 (parse-var-with-type %edx %ecx %esi *(ebp+0x10) *(ebp+0x14)) +10783 # if v is an addr, abort +10784 (lookup *esi *(esi+4)) # => eax +10785 (lookup *(eax+8) *(eax+0xc)) # Var-type Var-type => eax +10786 (is-mu-addr-type? %eax) # => eax +10787 3d/compare-eax-and 0/imm32/false +10788 0f 85/jump-if-!= $populate-mu-type:error2/disp32 +10789 # if v is an array, abort (we could support it, but initialization gets complex) +10790 (lookup *esi *(esi+4)) # => eax +10791 (lookup *(eax+8) *(eax+0xc)) # Var-type Var-type => eax +10792 (is-mu-array-type? %eax) # => eax +10793 3d/compare-eax-and 0/imm32/false +10794 0f 85/jump-if-!= $populate-mu-type:error3/disp32 +10795 # if v is a slice, abort +10796 (lookup *esi *(esi+4)) # => eax +10797 (lookup *(eax+8) *(eax+0xc)) # Var-type Var-type => eax +10798 (is-simple-mu-type? %eax 0xc) # slice => eax +10799 3d/compare-eax-and 0/imm32/false +10800 0f 85/jump-if-!= $populate-mu-type:error4/disp32 +10801 # if v is a stream, abort (we could support it, but initialization gets even more complex) +10802 (lookup *esi *(esi+4)) # => eax +10803 (lookup *(eax+8) *(eax+0xc)) # Var-type Var-type => eax +10804 (is-mu-stream-type? %eax) # => eax +10805 3d/compare-eax-and 0/imm32/false +10806 0f 85/jump-if-!= $populate-mu-type:error5/disp32 +10807 # var tmp/ecx +10808 51/push-ecx +10809 $populate-mu-type:create-typeinfo-fields: +10810 # var r/ebx: (handle typeinfo-entry) +10811 (find-or-create-typeinfo-fields %edi %edx %ebx) +10812 # r->index = curr-index +10813 (lookup *ebx *(ebx+4)) # => eax +10814 8b/-> *(ebp-4) 1/r32/ecx +10815 #? (write-buffered Stderr "saving index ") +10816 #? (write-int32-hex-buffered Stderr %ecx) +10817 #? (write-buffered Stderr " at ") +10818 #? (write-int32-hex-buffered Stderr %edi) +10819 #? (write-buffered Stderr Newline) +10820 #? (flush Stderr) +10821 89/<- *(eax+8) 1/r32/ecx # Typeinfo-entry-index +10822 # ++curr-index +10823 ff 0/subop/increment *(ebp-4) +10824 $populate-mu-type:set-input-type: +10825 # r->input-var = v +10826 8b/-> *esi 1/r32/ecx +10827 89/<- *eax 1/r32/ecx # Typeinfo-entry-input-var +10828 8b/-> *(esi+4) 1/r32/ecx +10829 89/<- *(eax+4) 1/r32/ecx # Typeinfo-entry-input-var +10830 # restore line +10831 59/pop-to-ecx +10832 { +10833 $populate-mu-type:create-output-type: +10834 # if (r->output-var == 0) create a new var with some placeholder data +10835 81 7/subop/compare *(eax+0xc) 0/imm32 # Typeinfo-entry-output-var +10836 75/jump-if-!= break/disp8 +10837 8d/copy-address *(eax+0xc) 0/r32/eax # Typeinfo-entry-output-var +10838 (new-literal Heap %edx %eax) +10839 } +10840 e9/jump loop/disp32 +10841 } +10842 $populate-mu-type:invalidate-total-size-in-bytes: +10843 # Offsets and total size may not be accurate here since we may not yet +10844 # have encountered the element types. +10845 # We'll recompute them separately after parsing the entire program. +10846 c7 0/subop/copy *(edi+0xc) -2/imm32/uninitialized # Typeinfo-total-size-in-bytes +10847 $populate-mu-type:end: +10848 # . reclaim locals +10849 81 0/subop/add %esp 0x224/imm32 +10850 # . restore registers +10851 5f/pop-to-edi +10852 5e/pop-to-esi +10853 5b/pop-to-ebx +10854 5a/pop-to-edx +10855 59/pop-to-ecx +10856 58/pop-to-eax +10857 # reclaim curr-index +10858 81 0/subop/add %esp 4/imm32 +10859 # . epilogue +10860 89/<- %esp 5/r32/ebp +10861 5d/pop-to-ebp +10862 c3/return +10863 +10864 $populate-mu-type:error1: +10865 # error("incomplete type definition '" t->name "'\n") +10866 (write-buffered *(ebp+0x10) "incomplete type definition '") +10867 (type-name *edi) # Typeinfo-id => eax +10868 (write-buffered *(ebp+0x10) %eax) +10869 (write-buffered *(ebp+0x10) "\n") +10870 (flush *(ebp+0x10)) +10871 (stop *(ebp+0x14) 1) +10872 # never gets here +10873 +10874 $populate-mu-type:error2: +10875 (write-buffered *(ebp+0x10) "type ") +10876 (type-name *edi) # Typeinfo-id => eax +10877 (write-buffered *(ebp+0x10) %eax) +10878 (write-buffered *(ebp+0x10) ": 'addr' elements not allowed\n") +10879 (flush *(ebp+0x10)) +10880 (stop *(ebp+0x14) 1) +10881 # never gets here +10882 +10883 $populate-mu-type:error3: +10884 (write-buffered *(ebp+0x10) "type ") +10885 (type-name *edi) # Typeinfo-id => eax +10886 (write-buffered *(ebp+0x10) %eax) +10887 (write-buffered *(ebp+0x10) ": 'array' elements not allowed for now\n") +10888 (flush *(ebp+0x10)) +10889 (stop *(ebp+0x14) 1) +10890 # never gets here +10891 +10892 $populate-mu-type:error4: +10893 (write-buffered *(ebp+0x10) "type ") +10894 (type-name *edi) # Typeinfo-id => eax +10895 (write-buffered *(ebp+0x10) %eax) +10896 (write-buffered *(ebp+0x10) ": 'slice' elements not allowed\n") +10897 (flush *(ebp+0x10)) +10898 (stop *(ebp+0x14) 1) +10899 # never gets here +10900 +10901 $populate-mu-type:error5: +10902 (write-buffered *(ebp+0x10) "type ") +10903 (type-name *edi) # Typeinfo-id => eax +10904 (write-buffered *(ebp+0x10) %eax) +10905 (write-buffered *(ebp+0x10) ": 'stream' elements not allowed for now\n") +10906 (flush *(ebp+0x10)) +10907 (stop *(ebp+0x14) 1) +10908 # never gets here +10909 +10910 type-name: # index: int -> result/eax: (addr array byte) +10911 # . prologue +10912 55/push-ebp +10913 89/<- %ebp 4/r32/esp +10914 # +10915 (index Type-id *(ebp+8)) +10916 $type-name:end: +10917 # . epilogue +10918 89/<- %esp 5/r32/ebp +10919 5d/pop-to-ebp +10920 c3/return +10921 +10922 index: # arr: (addr stream (handle array byte)), index: int -> result/eax: (addr array byte) +10923 # . prologue +10924 55/push-ebp +10925 89/<- %ebp 4/r32/esp +10926 # . save registers +10927 56/push-esi +10928 # TODO: bounds-check index +10929 # esi = arr +10930 8b/-> *(ebp+8) 6/r32/esi +10931 # eax = index +10932 8b/-> *(ebp+0xc) 0/r32/eax +10933 # eax = *(arr + 12 + index) +10934 8b/-> *(esi+eax<<2+0xc) 0/r32/eax +10935 $index:end: +10936 # . restore registers +10937 5e/pop-to-esi +10938 # . epilogue +10939 89/<- %esp 5/r32/ebp +10940 5d/pop-to-ebp +10941 c3/return +10942 +10943 ####################################################### +10944 # Compute type sizes +10945 ####################################################### +10946 +10947 # Compute the sizes of all user-defined types. +10948 # We'll need the sizes of their elements, which may be other user-defined +10949 # types, which we will compute as needed. +10950 +10951 # Initially, all user-defined types have their sizes set to -2 (invalid) +10952 populate-mu-type-sizes: # err: (addr buffered-file), ed: (addr exit-descriptor) +10953 # . prologue +10954 55/push-ebp +10955 89/<- %ebp 4/r32/esp +10956 $populate-mu-type-sizes:total-sizes: +10957 # var curr/eax: (addr typeinfo) = lookup(Program->types) +10958 (lookup *_Program-types *_Program-types->payload) # => eax +10959 { +10960 # if (curr == null) break +10961 3d/compare-eax-and 0/imm32/null +10962 74/jump-if-= break/disp8 +10963 (populate-mu-type-sizes-in-type %eax *(ebp+8) *(ebp+0xc)) +10964 # curr = lookup(curr->next) +10965 (lookup *(eax+0x10) *(eax+0x14)) # Typeinfo-next Typeinfo-next => eax +10966 eb/jump loop/disp8 +10967 } +10968 $populate-mu-type-sizes:offsets: +10969 # curr = *Program->types +10970 (lookup *_Program-types *_Program-types->payload) # => eax +10971 { +10972 # if (curr == null) break +10973 3d/compare-eax-and 0/imm32/null +10974 74/jump-if-= break/disp8 +10975 (populate-mu-type-offsets %eax *(ebp+8) *(ebp+0xc)) +10976 # curr = curr->next +10977 (lookup *(eax+0x10) *(eax+0x14)) # Typeinfo-next Typeinfo-next => eax +10978 eb/jump loop/disp8 +10979 } +10980 $populate-mu-type-sizes:end: +10981 # . epilogue +10982 89/<- %esp 5/r32/ebp +10983 5d/pop-to-ebp +10984 c3/return +10985 +10986 # compute sizes of all fields, recursing as necessary +10987 # sum up all their sizes to arrive at total size +10988 # fields may be out of order, but that doesn't affect the answer +10989 populate-mu-type-sizes-in-type: # T: (addr typeinfo), err: (addr buffered-file), ed: (addr exit-descriptor) +10990 # . prologue +10991 55/push-ebp +10992 89/<- %ebp 4/r32/esp +10993 # . save registers +10994 50/push-eax +10995 51/push-ecx +10996 52/push-edx +10997 56/push-esi +10998 57/push-edi +10999 # esi = T +11000 8b/-> *(ebp+8) 6/r32/esi +11001 # if T is already computed, return +11002 81 7/subop/compare *(esi+0xc) 0/imm32 # Typeinfo-total-size-in-bytes +11003 0f 8d/jump-if->= $populate-mu-type-sizes-in-type:end/disp32 +11004 # if T is being computed, abort +11005 81 7/subop/compare *(esi+0xc) -1/imm32/being-computed # Typeinfo-total-size-in-bytes +11006 0f 84/jump-if-= $populate-mu-type-sizes-in-type:abort/disp32 +11007 # tag T (-2 to -1) to avoid infinite recursion +11008 c7 0/subop/copy *(esi+0xc) -1/imm32/being-computed # Typeinfo-total-size-in-bytes +11009 # var total-size/edi: int = 0 +11010 bf/copy-to-edi 0/imm32 +11011 # - for every field, if it's a user-defined type, compute its size +11012 # var table/ecx: (addr table (handle array byte) (handle typeinfo-entry)) = lookup(T->fields) +11013 (lookup *(esi+4) *(esi+8)) # Typeinfo-fields Typeinfo-fields => eax +11014 89/<- %ecx 0/r32/eax +11015 # var table-size/edx: int = table->write +11016 8b/-> *ecx 2/r32/edx # stream-write +11017 # var curr/ecx: (addr table_row) = table->data +11018 8d/copy-address *(ecx+0xc) 1/r32/ecx +11019 # var max/edx: (addr table_row) = table->data + table->write +11020 8d/copy-address *(ecx+edx) 2/r32/edx +11021 { +11022 $populate-mu-type-sizes-in-type:loop: +11023 # if (curr >= max) break +11024 39/compare %ecx 2/r32/edx +11025 73/jump-if-addr>= break/disp8 +11026 # var t/eax: (addr typeinfo-entry) = lookup(curr->value) +11027 (lookup *(ecx+8) *(ecx+0xc)) # => eax +11028 # if (t->input-var == 0) silently ignore it; we'll emit a nice error message while type-checking +11029 81 7/subop/compare *eax 0/imm32 # Typeinfo-entry-input-var +11030 74/jump-if-= $populate-mu-type-sizes-in-type:end/disp8 +11031 # compute size of t->input-var +11032 (lookup *eax *(eax+4)) # Typeinfo-entry-input-var Typeinfo-entry-input-var => eax +11033 (compute-size-of-var %eax) # => eax +11034 # result += eax +11035 01/add-to %edi 0/r32/eax +11036 # curr += row-size +11037 81 0/subop/add %ecx 0x10/imm32 # Typeinfo-fields-row-size +11038 # +11039 eb/jump loop/disp8 +11040 } +11041 # - save result +11042 89/<- *(esi+0xc) 7/r32/edi # Typeinfo-total-size-in-bytes +11043 $populate-mu-type-sizes-in-type:end: +11044 # . restore registers +11045 5f/pop-to-edi +11046 5e/pop-to-esi +11047 5a/pop-to-edx +11048 59/pop-to-ecx +11049 58/pop-to-eax +11050 # . epilogue +11051 89/<- %esp 5/r32/ebp +11052 5d/pop-to-ebp +11053 c3/return +11054 +11055 $populate-mu-type-sizes-in-type:abort: +11056 (write-buffered *(ebp+0xc) "cycle in type definitions\n") +11057 (flush *(ebp+0xc)) +11058 (stop *(ebp+0x10) 1) +11059 # never gets here +11060 +11061 # Analogous to size-of, except we need to compute what size-of can just read +11062 # off the right data structures. +11063 compute-size-of-var: # in: (addr var) -> result/eax: int +11064 # . prologue +11065 55/push-ebp +11066 89/<- %ebp 4/r32/esp +11067 # . push registers +11068 51/push-ecx +11069 # var t/ecx: (addr type-tree) = lookup(v->type) +11070 8b/-> *(ebp+8) 1/r32/ecx +11071 (lookup *(ecx+8) *(ecx+0xc)) # Var-type Var-type => eax +11072 89/<- %ecx 0/r32/eax +11073 # if (t->is-atom == false) t = lookup(t->left) +11074 { +11075 81 7/subop/compare *ecx 0/imm32/false # Type-tree-is-atom +11076 75/jump-if-!= break/disp8 +11077 (lookup *(ecx+4) *(ecx+8)) # Type-tree-left Type-tree-left => eax +11078 89/<- %ecx 0/r32/eax +11079 } +11080 # TODO: ensure t is an atom +11081 (compute-size-of-type-id *(ecx+4)) # Type-tree-value => eax +11082 $compute-size-of-var:end: +11083 # . restore registers +11084 59/pop-to-ecx +11085 # . epilogue +11086 89/<- %esp 5/r32/ebp +11087 5d/pop-to-ebp +11088 c3/return +11089 +11090 compute-size-of-type-id: # t: type-id -> result/eax: int +11091 # . prologue +11092 55/push-ebp +11093 89/<- %ebp 4/r32/esp +11094 # . save registers +11095 51/push-ecx +11096 # var out/ecx: (handle typeinfo) +11097 68/push 0/imm32 +11098 68/push 0/imm32 +11099 89/<- %ecx 4/r32/esp +11100 # eax = t +11101 8b/-> *(ebp+8) 0/r32/eax +11102 # if t is a literal, return 0 +11103 3d/compare-eax-and 0/imm32/literal +11104 0f 84/jump-if-= $compute-size-of-type-id:end/disp32 # eax changes type from type-id to int +11105 # if t is a byte, return 4 (because we don't really support non-multiples of 4) +11106 3d/compare-eax-and 8/imm32/byte +11107 { +11108 75/jump-if-!= break/disp8 +11109 b8/copy-to-eax 4/imm32 +11110 eb/jump $compute-size-of-type-id:end/disp8 +11111 } +11112 # if t is a handle, return 8 +11113 3d/compare-eax-and 4/imm32/handle +11114 { +11115 75/jump-if-!= break/disp8 +11116 b8/copy-to-eax 8/imm32 +11117 eb/jump $compute-size-of-type-id:end/disp8 # eax changes type from type-id to int +11118 } +11119 # if t is a slice, return 8 +11120 3d/compare-eax-and 0xc/imm32/slice +11121 { +11122 75/jump-if-!= break/disp8 +11123 b8/copy-to-eax 8/imm32 +11124 eb/jump $compute-size-of-type-id:end/disp8 # eax changes type from type-id to int +11125 } +11126 # if t is a user-defined type, compute its size +11127 # TODO: support non-atom type +11128 (find-typeinfo %eax %ecx) +11129 { +11130 81 7/subop/compare *ecx 0/imm32 +11131 74/jump-if-= break/disp8 +11132 $compute-size-of-type-id:user-defined: +11133 (populate-mu-type-sizes %eax) +11134 8b/-> *(eax+0xc) 0/r32/eax # Typeinfo-total-size-in-bytes +11135 eb/jump $compute-size-of-type-id:end/disp8 +11136 } +11137 # otherwise return the word size +11138 b8/copy-to-eax 4/imm32 +11139 $compute-size-of-type-id:end: +11140 # . reclaim locals +11141 81 0/subop/add %esp 8/imm32 +11142 # . restore registers +11143 59/pop-to-ecx +11144 # . epilogue +11145 89/<- %esp 5/r32/ebp +11146 5d/pop-to-ebp +11147 c3/return +11148 +11149 # at this point we have total sizes for all user-defined types +11150 # compute offsets for each element +11151 # complication: fields may be out of order +11152 populate-mu-type-offsets: # in: (addr typeinfo), err: (addr buffered-file), ed: (addr exit-descriptor) +11153 # . prologue +11154 55/push-ebp +11155 89/<- %ebp 4/r32/esp +11156 # . save registers +11157 50/push-eax +11158 51/push-ecx +11159 52/push-edx +11160 53/push-ebx +11161 56/push-esi +11162 57/push-edi +11163 #? (dump-typeinfos "aaa\n") +11164 # var curr-offset/edi: int = 0 +11165 bf/copy-to-edi 0/imm32 +11166 # var table/ecx: (addr table string_key (handle typeinfo-entry)) = lookup(in->fields) +11167 8b/-> *(ebp+8) 1/r32/ecx +11168 (lookup *(ecx+4) *(ecx+8)) # Typeinfo-fields Typeinfo-fields => eax +11169 89/<- %ecx 0/r32/eax +11170 # var num-elems/edx: int = table->write / Typeinfo-fields-row-size +11171 8b/-> *ecx 2/r32/edx # stream-write +11172 c1 5/subop/shift-right-logical %edx 4/imm8 +11173 # var i/ebx: int = 0 +11174 bb/copy-to-ebx 0/imm32 +11175 { +11176 $populate-mu-type-offsets:loop: +11177 39/compare %ebx 2/r32/edx +11178 0f 8d/jump-if->= break/disp32 +11179 #? (write-buffered Stderr "looking up index ") +11180 #? (write-int32-hex-buffered Stderr %ebx) +11181 #? (write-buffered Stderr " in ") +11182 #? (write-int32-hex-buffered Stderr *(ebp+8)) +11183 #? (write-buffered Stderr Newline) +11184 #? (flush Stderr) +11185 # var v/esi: (addr typeinfo-entry) +11186 (locate-typeinfo-entry-with-index %ecx %ebx *(ebp+0xc) *(ebp+0x10)) # => eax +11187 89/<- %esi 0/r32/eax +11188 # if v is null, silently move on; we'll emit a nice error message while type-checking +11189 81 7/subop/compare %esi 0/imm32 # Typeinfo-entry-input-var +11190 74/jump-if-= $populate-mu-type-offsets:end/disp8 +11191 # if (v->input-var == 0) silently ignore v; we'll emit a nice error message while type-checking +11192 81 7/subop/compare *esi 0/imm32 # Typeinfo-entry-input-var +11193 74/jump-if-= $populate-mu-type-offsets:end/disp8 +11194 # v->output-var->offset = curr-offset +11195 # . eax: (addr var) +11196 (lookup *(esi+0xc) *(esi+0x10)) # Typeinfo-entry-output-var Typeinfo-entry-output-var => eax +11197 89/<- *(eax+0x14) 7/r32/edi # Var-offset +11198 # curr-offset += size-of(v->input-var) +11199 (lookup *esi *(esi+4)) # Typeinfo-entry-input-var Typeinfo-entry-input-var => eax +11200 (size-of %eax) # => eax +11201 01/add-to %edi 0/r32/eax +11202 # ++i +11203 43/increment-ebx +11204 e9/jump loop/disp32 +11205 } +11206 $populate-mu-type-offsets:end: +11207 # . restore registers +11208 5f/pop-to-edi +11209 5e/pop-to-esi +11210 5b/pop-to-ebx +11211 5a/pop-to-edx +11212 59/pop-to-ecx +11213 58/pop-to-eax +11214 # . epilogue +11215 89/<- %esp 5/r32/ebp +11216 5d/pop-to-ebp +11217 c3/return +11218 +11219 locate-typeinfo-entry-with-index: # table: (addr table (handle array byte) (handle typeinfo-entry)), idx: int, err: (addr buffered-file), ed: (addr exit-descriptor) -> result/eax: (addr typeinfo-entry) +11220 # . prologue +11221 55/push-ebp +11222 89/<- %ebp 4/r32/esp +11223 # . save registers +11224 51/push-ecx +11225 52/push-edx +11226 53/push-ebx +11227 56/push-esi +11228 57/push-edi +11229 # esi = table +11230 8b/-> *(ebp+8) 6/r32/esi +11231 # var curr/ecx: (addr row (handle array byte) (handle typeinfo-entry)) = table->data +11232 8d/copy-address *(esi+0xc) 1/r32/ecx +11233 # var max/edx: (addr byte) = &table->data[table->write] +11234 8b/-> *esi 2/r32/edx +11235 8d/copy-address *(ecx+edx) 2/r32/edx +11236 { +11237 $locate-typeinfo-entry-with-index:loop: +11238 39/compare %ecx 2/r32/edx +11239 73/jump-if-addr>= break/disp8 +11240 # var v/eax: (addr typeinfo-entry) +11241 (lookup *(ecx+8) *(ecx+0xc)) # => eax +11242 # if (v->index == idx) return v +11243 8b/-> *(eax+8) 3/r32/ebx # Typeinfo-entry-index +11244 #? (write-buffered Stderr "comparing ") +11245 #? (write-int32-hex-buffered Stderr %ebx) +11246 #? (write-buffered Stderr " and ") +11247 #? (write-int32-hex-buffered Stderr *(ebp+0xc)) +11248 #? (write-buffered Stderr Newline) +11249 #? (flush Stderr) +11250 39/compare *(ebp+0xc) 3/r32/ebx +11251 74/jump-if-= $locate-typeinfo-entry-with-index:end/disp8 +11252 # curr += Typeinfo-entry-size +11253 81 0/subop/add %ecx 0x10/imm32 # Typeinfo-entry-size +11254 # +11255 eb/jump loop/disp8 +11256 } +11257 # return 0 +11258 b8/copy-to-eax 0/imm32 +11259 $locate-typeinfo-entry-with-index:end: +11260 #? (write-buffered Stderr "returning ") +11261 #? (write-int32-hex-buffered Stderr %eax) +11262 #? (write-buffered Stderr Newline) +11263 #? (flush Stderr) +11264 # . restore registers +11265 5f/pop-to-edi +11266 5e/pop-to-esi +11267 5b/pop-to-ebx +11268 5a/pop-to-edx +11269 59/pop-to-ecx +11270 # . epilogue +11271 89/<- %esp 5/r32/ebp +11272 5d/pop-to-ebp +11273 c3/return +11274 +11275 dump-typeinfos: # hdr: (addr array byte) +11276 # . prologue +11277 55/push-ebp +11278 89/<- %ebp 4/r32/esp +11279 # . save registers +11280 50/push-eax +11281 # +11282 (write-buffered Stderr *(ebp+8)) +11283 (flush Stderr) +11284 # var curr/eax: (addr typeinfo) = lookup(Program->types) +11285 (lookup *_Program-types *_Program-types->payload) # => eax +11286 { +11287 # if (curr == null) break +11288 3d/compare-eax-and 0/imm32 +11289 74/jump-if-= break/disp8 +11290 (write-buffered Stderr "---\n") +11291 (flush Stderr) +11292 (dump-typeinfo %eax) +11293 # curr = lookup(curr->next) +11294 (lookup *(eax+0x10) *(eax+0x14)) # Typeinfo-next Typeinfo-next => eax +11295 eb/jump loop/disp8 +11296 } +11297 $dump-typeinfos:end: +11298 # . restore registers +11299 58/pop-to-eax +11300 # . epilogue +11301 89/<- %esp 5/r32/ebp +11302 5d/pop-to-ebp +11303 c3/return +11304 +11305 dump-typeinfo: # in: (addr typeinfo) +11306 # . prologue +11307 55/push-ebp +11308 89/<- %ebp 4/r32/esp +11309 # . save registers +11310 50/push-eax +11311 51/push-ecx +11312 52/push-edx +11313 53/push-ebx +11314 56/push-esi +11315 57/push-edi +11316 # esi = in +11317 8b/-> *(ebp+8) 6/r32/esi +11318 # var table/ecx: (addr table (handle array byte) (handle typeinfo-entry)) = lookup(T->fields) +11319 (lookup *(esi+4) *(esi+8)) # Typeinfo-fields Typeinfo-fields => eax +11320 89/<- %ecx 0/r32/eax +11321 (write-buffered Stderr "id:") +11322 (write-int32-hex-buffered Stderr *esi) +11323 (write-buffered Stderr "\n") +11324 (write-buffered Stderr "fields @ ") +11325 (write-int32-hex-buffered Stderr %ecx) +11326 (write-buffered Stderr Newline) +11327 (flush Stderr) +11328 (write-buffered Stderr " write: ") +11329 (write-int32-hex-buffered Stderr *ecx) +11330 (write-buffered Stderr Newline) +11331 (flush Stderr) +11332 (write-buffered Stderr " read: ") +11333 (write-int32-hex-buffered Stderr *(ecx+4)) +11334 (write-buffered Stderr Newline) +11335 (flush Stderr) +11336 (write-buffered Stderr " size: ") +11337 (write-int32-hex-buffered Stderr *(ecx+8)) +11338 (write-buffered Stderr Newline) +11339 (flush Stderr) +11340 # var table-size/edx: int = table->write +11341 8b/-> *ecx 2/r32/edx # stream-write +11342 # var curr/ecx: (addr table_row) = table->data +11343 8d/copy-address *(ecx+0xc) 1/r32/ecx +11344 # var max/edx: (addr table_row) = table->data + table->write +11345 8d/copy-address *(ecx+edx) 2/r32/edx +11346 { +11347 $dump-typeinfo:loop: +11348 # if (curr >= max) break +11349 39/compare %ecx 2/r32/edx +11350 0f 83/jump-if-addr>= break/disp32 +11351 (write-buffered Stderr " row:\n") +11352 (write-buffered Stderr " key: ") +11353 (write-int32-hex-buffered Stderr *ecx) +11354 (write-buffered Stderr ",") +11355 (write-int32-hex-buffered Stderr *(ecx+4)) +11356 (write-buffered Stderr " = '") +11357 (lookup *ecx *(ecx+4)) +11358 (write-buffered Stderr %eax) +11359 (write-buffered Stderr "' @ ") +11360 (write-int32-hex-buffered Stderr %eax) +11361 (write-buffered Stderr Newline) +11362 (flush Stderr) +11363 (write-buffered Stderr " value: ") +11364 (write-int32-hex-buffered Stderr *(ecx+8)) +11365 (write-buffered Stderr ",") +11366 (write-int32-hex-buffered Stderr *(ecx+0xc)) +11367 (write-buffered Stderr " = typeinfo-entry@") +11368 (lookup *(ecx+8) *(ecx+0xc)) +11369 (write-int32-hex-buffered Stderr %eax) +11370 (write-buffered Stderr Newline) +11371 (flush Stderr) +11372 (write-buffered Stderr " input var@") +11373 (dump-var 5 %eax) +11374 (lookup *(ecx+8) *(ecx+0xc)) +11375 (write-buffered Stderr " index: ") +11376 (write-int32-hex-buffered Stderr *(eax+8)) +11377 (write-buffered Stderr Newline) +11378 (flush Stderr) +11379 (write-buffered Stderr " output var@") +11380 8d/copy-address *(eax+0xc) 0/r32/eax # Typeinfo-entry-output-var +11381 (dump-var 5 %eax) +11382 (flush Stderr) +11383 # curr += row-size +11384 81 0/subop/add %ecx 0x10/imm32 # Typeinfo-fields-row-size +11385 # +11386 e9/jump loop/disp32 +11387 } +11388 $dump-typeinfo:end: +11389 # . restore registers +11390 5f/pop-to-edi +11391 5e/pop-to-esi +11392 5b/pop-to-ebx +11393 5a/pop-to-edx +11394 59/pop-to-ecx +11395 58/pop-to-eax +11396 # . epilogue +11397 89/<- %esp 5/r32/ebp +11398 5d/pop-to-ebp +11399 c3/return +11400 +11401 dump-var: # indent: int, v: (addr handle var) +11402 # . prologue +11403 55/push-ebp +11404 89/<- %ebp 4/r32/esp +11405 # . save registers +11406 50/push-eax +11407 53/push-ebx +11408 # eax = v +11409 8b/-> *(ebp+0xc) 0/r32/eax +11410 # +11411 (write-int32-hex-buffered Stderr *eax) +11412 (write-buffered Stderr ",") +11413 (write-int32-hex-buffered Stderr *(eax+4)) +11414 (write-buffered Stderr "->") +11415 (lookup *eax *(eax+4)) +11416 (write-int32-hex-buffered Stderr %eax) +11417 (write-buffered Stderr Newline) +11418 (flush Stderr) +11419 { +11420 3d/compare-eax-and 0/imm32 +11421 0f 84/jump-if-= break/disp32 +11422 (emit-indent Stderr *(ebp+8)) +11423 (write-buffered Stderr "name: ") +11424 89/<- %ebx 0/r32/eax +11425 (write-int32-hex-buffered Stderr *ebx) # Var-name +11426 (write-buffered Stderr ",") +11427 (write-int32-hex-buffered Stderr *(ebx+4)) # Var-name +11428 (write-buffered Stderr "->") +11429 (lookup *ebx *(ebx+4)) # Var-name +11430 (write-int32-hex-buffered Stderr %eax) +11431 { +11432 3d/compare-eax-and 0/imm32 +11433 74/jump-if-= break/disp8 +11434 (write-buffered Stderr Space) +11435 (write-buffered Stderr %eax) +11436 } +11437 (write-buffered Stderr Newline) +11438 (flush Stderr) +11439 (emit-indent Stderr *(ebp+8)) +11440 (write-buffered Stderr "block depth: ") +11441 (write-int32-hex-buffered Stderr *(ebx+0x10)) # Var-block-depth +11442 (write-buffered Stderr Newline) +11443 (flush Stderr) +11444 (emit-indent Stderr *(ebp+8)) +11445 (write-buffered Stderr "stack offset: ") +11446 (write-int32-hex-buffered Stderr *(ebx+0x14)) # Var-offset +11447 (write-buffered Stderr Newline) +11448 (flush Stderr) +11449 (emit-indent Stderr *(ebp+8)) +11450 (write-buffered Stderr "reg: ") +11451 (write-int32-hex-buffered Stderr *(ebx+0x18)) # Var-register +11452 (write-buffered Stderr ",") +11453 (write-int32-hex-buffered Stderr *(ebx+0x1c)) # Var-register +11454 (write-buffered Stderr "->") +11455 (flush Stderr) +11456 (lookup *(ebx+0x18) *(ebx+0x1c)) # Var-register +11457 (write-int32-hex-buffered Stderr %eax) +11458 { +11459 3d/compare-eax-and 0/imm32 +11460 74/jump-if-= break/disp8 +11461 (write-buffered Stderr Space) +11462 (write-buffered Stderr %eax) +11463 } +11464 (write-buffered Stderr Newline) +11465 (flush Stderr) +11466 } +11467 $dump-var:end: +11468 # . restore registers +11469 5b/pop-to-ebx 11470 58/pop-to-eax 11471 # . epilogue 11472 89/<- %esp 5/r32/ebp 11473 5d/pop-to-ebp 11474 c3/return 11475 -11476 check-mu-function: # fn: (addr function), err: (addr buffered-file), ed: (addr exit-descriptor) -11477 # . prologue -11478 55/push-ebp -11479 89/<- %ebp 4/r32/esp -11480 # . save registers -11481 50/push-eax -11482 # eax = f -11483 8b/-> *(ebp+8) 0/r32/eax -11484 # TODO: anything to check in header? -11485 # var body/eax: (addr block) = lookup(f->body) -11486 (lookup *(eax+0x18) *(eax+0x1c)) # Function-body Function-body => eax -11487 (check-mu-block %eax *(ebp+8) *(ebp+0xc) *(ebp+0x10)) -11488 $check-mu-function:end: -11489 # . restore registers -11490 58/pop-to-eax -11491 # . epilogue -11492 89/<- %esp 5/r32/ebp -11493 5d/pop-to-ebp -11494 c3/return -11495 -11496 check-mu-block: # block: (addr block), fn: (addr function), err: (addr buffered-file), ed: (addr exit-descriptor) -11497 # . prologue -11498 55/push-ebp -11499 89/<- %ebp 4/r32/esp -11500 # . save registers -11501 50/push-eax -11502 # eax = block -11503 8b/-> *(ebp+8) 0/r32/eax -11504 # var stmts/eax: (addr list stmt) = lookup(block->statements) -11505 (lookup *(eax+4) *(eax+8)) # Block-stmts Block-stmts => eax -11506 # -11507 { -11508 $check-mu-block:check-empty: -11509 3d/compare-eax-and 0/imm32 -11510 0f 84/jump-if-= break/disp32 -11511 # emit block->statements -11512 (check-mu-stmt-list %eax *(ebp+0xc) *(ebp+0x10) *(ebp+0x14)) -11513 } -11514 $check-mu-block:end: -11515 # . restore registers -11516 58/pop-to-eax -11517 # . epilogue -11518 89/<- %esp 5/r32/ebp -11519 5d/pop-to-ebp -11520 c3/return -11521 -11522 check-mu-stmt-list: # stmts: (addr list stmt), fn: (addr function), err: (addr buffered-file), ed: (addr exit-descriptor) -11523 # . prologue -11524 55/push-ebp -11525 89/<- %ebp 4/r32/esp -11526 # . save registers -11527 50/push-eax -11528 56/push-esi -11529 # esi = stmts -11530 8b/-> *(ebp+8) 6/r32/esi -11531 { -11532 $check-mu-stmt-list:loop: -11533 81 7/subop/compare %esi 0/imm32 -11534 0f 84/jump-if-= break/disp32 -11535 # var curr-stmt/eax: (addr stmt) = lookup(stmts->value) -11536 (lookup *esi *(esi+4)) # List-value List-value => eax -11537 { -11538 $check-mu-stmt-list:check-for-block: -11539 81 7/subop/compare *eax 0/imm32/block # Stmt-tag -11540 75/jump-if-!= break/disp8 -11541 $check-mu-stmt-list:block: -11542 (check-mu-block %eax *(ebp+0xc) *(ebp+0x10) *(ebp+0x14)) -11543 eb/jump $check-mu-stmt-list:continue/disp8 -11544 } -11545 { -11546 $check-mu-stmt-list:check-for-stmt1: -11547 81 7/subop/compare *eax 1/imm32/stmt1 # Stmt-tag -11548 0f 85/jump-if-!= break/disp32 -11549 $check-mu-stmt-list:stmt1: -11550 (check-mu-stmt %eax *(ebp+0xc) *(ebp+0x10) *(ebp+0x14)) -11551 eb/jump $check-mu-stmt-list:continue/disp8 -11552 } -11553 { -11554 $check-mu-stmt-list:check-for-reg-var-def: -11555 81 7/subop/compare *eax 3/imm32/reg-var-def # Stmt-tag -11556 0f 85/jump-if-!= break/disp32 -11557 $check-mu-stmt-list:reg-var-def: -11558 (check-mu-stmt %eax *(ebp+0xc) *(ebp+0x10) *(ebp+0x14)) -11559 eb/jump $check-mu-stmt-list:continue/disp8 -11560 } -11561 $check-mu-stmt-list:continue: -11562 # TODO: raise an error on unrecognized Stmt-tag -11563 (lookup *(esi+8) *(esi+0xc)) # List-next List-next => eax -11564 89/<- %esi 0/r32/eax -11565 e9/jump loop/disp32 -11566 } -11567 $check-mu-stmt-list:end: -11568 # . restore registers -11569 5e/pop-to-esi -11570 58/pop-to-eax -11571 # . epilogue -11572 89/<- %esp 5/r32/ebp -11573 5d/pop-to-ebp -11574 c3/return -11575 -11576 check-mu-stmt: # stmt: (addr stmt), fn: (addr function), err: (addr buffered-file), ed: (addr exit-descriptor) -11577 # . prologue -11578 55/push-ebp -11579 89/<- %ebp 4/r32/esp -11580 # . save registers -11581 50/push-eax -11582 # - if stmt's operation matches a primitive, check against it -11583 (has-primitive-name? *(ebp+8)) # => eax -11584 3d/compare-eax-and 0/imm32/false -11585 { -11586 74/jump-if-= break/disp8 -11587 (check-mu-primitive *(ebp+8) *(ebp+0xc) *(ebp+0x10) *(ebp+0x14)) -11588 e9/jump $check-mu-stmt:end/disp32 -11589 } -11590 # - otherwise find a function to check against -11591 # var f/eax: (addr function) = lookup(*Program->functions) -11592 (lookup *_Program-functions *_Program-functions->payload) # => eax -11593 (find-matching-function %eax *(ebp+8)) # => eax -11594 3d/compare-eax-and 0/imm32 -11595 { -11596 74/jump-if-= break/disp8 -11597 (check-mu-call *(ebp+8) %eax *(ebp+0xc) *(ebp+0x10) *(ebp+0x14)) -11598 eb/jump $check-mu-stmt:end/disp8 -11599 } -11600 # var f/eax: (addr function) = lookup(*Program->signatures) -11601 (lookup *_Program-signatures *_Program-signatures->payload) # => eax -11602 (find-matching-function %eax *(ebp+8)) # => eax -11603 3d/compare-eax-and 0/imm32 -11604 { -11605 74/jump-if-= break/disp8 -11606 (check-mu-call *(ebp+8) %eax *(ebp+0xc) *(ebp+0x10) *(ebp+0x14)) -11607 eb/jump $check-mu-stmt:end/disp8 -11608 } -11609 # - otherwise abort -11610 e9/jump $check-mu-stmt:unknown-call/disp32 -11611 $check-mu-stmt:end: -11612 # . restore registers -11613 58/pop-to-eax -11614 # . epilogue -11615 89/<- %esp 5/r32/ebp -11616 5d/pop-to-ebp -11617 c3/return -11618 -11619 $check-mu-stmt:unknown-call: -11620 (write-buffered *(ebp+0x10) "unknown function '") -11621 8b/-> *(ebp+8) 0/r32/eax -11622 (lookup *(eax+4) *(eax+8)) # Stmt1-operation Stmt1-operation => eax -11623 (write-buffered *(ebp+0x10) %eax) -11624 (write-buffered *(ebp+0x10) "'\n") -11625 (flush *(ebp+0x10)) -11626 (stop *(ebp+0x14) 1) -11627 # never gets here -11628 -11629 has-primitive-name?: # stmt: (addr stmt) -> result/eax: boolean -11630 # . prologue -11631 55/push-ebp -11632 89/<- %ebp 4/r32/esp -11633 # . save registers -11634 51/push-ecx -11635 56/push-esi -11636 # var name/esi: (addr array byte) = lookup(stmt->operation) -11637 8b/-> *(ebp+8) 6/r32/esi -11638 (lookup *(esi+4) *(esi+8)) # Stmt1-operation Stmt1-operation => eax -11639 89/<- %esi 0/r32/eax -11640 # if (name == "get") return true -11641 (string-equal? %esi "get") # => eax -11642 3d/compare-eax-and 0/imm32/false -11643 0f 85/jump-if-!= $has-primitive-name?:end/disp32 -11644 # if (name == "index") return true -11645 (string-equal? %esi "index") # => eax -11646 3d/compare-eax-and 0/imm32/false -11647 0f 85/jump-if-!= $has-primitive-name?:end/disp32 -11648 # if (name == "length") return true -11649 (string-equal? %esi "length") # => eax -11650 3d/compare-eax-and 0/imm32/false -11651 0f 85/jump-if-!= $has-primitive-name?:end/disp32 -11652 # if (name == "compute-offset") return true -11653 (string-equal? %esi "compute-offset") # => eax -11654 3d/compare-eax-and 0/imm32/false -11655 0f 85/jump-if-!= $has-primitive-name?:end/disp32 -11656 # if (name == "allocate") return true -11657 (string-equal? %esi "allocate") # => eax -11658 3d/compare-eax-and 0/imm32/false -11659 0f 85/jump-if-!= $has-primitive-name?:end/disp32 -11660 # if (name == "populate") return true -11661 (string-equal? %esi "populate") # => eax -11662 3d/compare-eax-and 0/imm32/false -11663 0f 85/jump-if-!= $has-primitive-name?:end/disp32 -11664 # var curr/ecx: (addr primitive) = Primitives -11665 b9/copy-to-ecx Primitives/imm32 -11666 { -11667 $has-primitive-name?:loop: -11668 # if (curr == null) break -11669 81 7/subop/compare %ecx 0/imm32 -11670 74/jump-if-= break/disp8 -11671 # if (primitive->name == name) return true -11672 (lookup *ecx *(ecx+4)) # Primitive-name Primitive-name => eax -11673 (string-equal? %esi %eax) # => eax -11674 3d/compare-eax-and 0/imm32/false -11675 75/jump-if-!= $has-primitive-name?:end/disp8 -11676 $has-primitive-name?:next-primitive: -11677 # curr = curr->next -11678 (lookup *(ecx+0x38) *(ecx+0x3c)) # Primitive-next Primitive-next => eax -11679 89/<- %ecx 0/r32/eax -11680 # -11681 e9/jump loop/disp32 -11682 } -11683 # return null -11684 b8/copy-to-eax 0/imm32 -11685 $has-primitive-name?:end: -11686 # . restore registers -11687 5e/pop-to-esi -11688 59/pop-to-ecx -11689 # . epilogue -11690 89/<- %esp 5/r32/ebp -11691 5d/pop-to-ebp -11692 c3/return -11693 -11694 check-mu-primitive: # stmt: (addr stmt), fn: (addr function), err: (addr buffered-file), ed: (addr exit-descriptor) -11695 # . prologue -11696 55/push-ebp -11697 89/<- %ebp 4/r32/esp -11698 # . save registers -11699 50/push-eax -11700 51/push-ecx -11701 # var op/ecx: (addr array byte) = lookup(stmt->operation) -11702 8b/-> *(ebp+8) 0/r32/eax -11703 (lookup *(eax+4) *(eax+8)) # Stmt1-operation Stmt1-operation => eax -11704 89/<- %ecx 0/r32/eax -11705 # if (op == "copy") check-mu-copy-stmt -11706 { -11707 (string-equal? %ecx "copy") # => eax -11708 3d/compare-eax-and 0/imm32/false -11709 74/jump-if-= break/disp8 -11710 (check-mu-copy-stmt *(ebp+8) *(ebp+0xc) *(ebp+0x10) *(ebp+0x14)) -11711 e9/jump $check-mu-primitive:end/disp32 -11712 } -11713 # if (op == "copy-to") check-mu-copy-to-stmt -11714 { -11715 (string-equal? %ecx "copy-to") # => eax -11716 3d/compare-eax-and 0/imm32/false -11717 74/jump-if-= break/disp8 -11718 (check-mu-copy-to-stmt *(ebp+8) *(ebp+0xc) *(ebp+0x10) *(ebp+0x14)) -11719 e9/jump $check-mu-primitive:end/disp32 -11720 } -11721 # if (op == "compare") check-mu-compare-stmt -11722 { -11723 (string-equal? %ecx "compare") # => eax +11476 ####################################################### +11477 # Type-checking +11478 ####################################################### +11479 +11480 check-mu-types: # err: (addr buffered-file), ed: (addr exit-descriptor) +11481 # . prologue +11482 55/push-ebp +11483 89/<- %ebp 4/r32/esp +11484 # . save registers +11485 50/push-eax +11486 # var curr/eax: (addr function) = lookup(Program->functions) +11487 (lookup *_Program-functions *_Program-functions->payload) # => eax +11488 { +11489 $check-mu-types:loop: +11490 # if (curr == null) break +11491 3d/compare-eax-and 0/imm32 +11492 0f 84/jump-if-= break/disp32 +11493 +-- 8 lines: #? # dump curr->name ------------------------------------------------------------------------------------------------------------------------------------------------ +11501 (check-mu-function %eax *(ebp+8) *(ebp+0xc)) +11502 # curr = lookup(curr->next) +11503 (lookup *(eax+0x20) *(eax+0x24)) # Function-next Function-next => eax +11504 e9/jump loop/disp32 +11505 } +11506 $check-mu-types:end: +11507 # . restore registers +11508 58/pop-to-eax +11509 # . epilogue +11510 89/<- %esp 5/r32/ebp +11511 5d/pop-to-ebp +11512 c3/return +11513 +11514 check-mu-function: # fn: (addr function), err: (addr buffered-file), ed: (addr exit-descriptor) +11515 # . prologue +11516 55/push-ebp +11517 89/<- %ebp 4/r32/esp +11518 # . save registers +11519 50/push-eax +11520 # eax = f +11521 8b/-> *(ebp+8) 0/r32/eax +11522 # TODO: anything to check in header? +11523 # var body/eax: (addr block) = lookup(f->body) +11524 (lookup *(eax+0x18) *(eax+0x1c)) # Function-body Function-body => eax +11525 (check-mu-block %eax *(ebp+8) *(ebp+0xc) *(ebp+0x10)) +11526 $check-mu-function:end: +11527 # . restore registers +11528 58/pop-to-eax +11529 # . epilogue +11530 89/<- %esp 5/r32/ebp +11531 5d/pop-to-ebp +11532 c3/return +11533 +11534 check-mu-block: # block: (addr block), fn: (addr function), err: (addr buffered-file), ed: (addr exit-descriptor) +11535 # . prologue +11536 55/push-ebp +11537 89/<- %ebp 4/r32/esp +11538 # . save registers +11539 50/push-eax +11540 # eax = block +11541 8b/-> *(ebp+8) 0/r32/eax +11542 # var stmts/eax: (addr list stmt) = lookup(block->statements) +11543 (lookup *(eax+4) *(eax+8)) # Block-stmts Block-stmts => eax +11544 # +11545 { +11546 $check-mu-block:check-empty: +11547 3d/compare-eax-and 0/imm32 +11548 0f 84/jump-if-= break/disp32 +11549 # emit block->statements +11550 (check-mu-stmt-list %eax *(ebp+0xc) *(ebp+0x10) *(ebp+0x14)) +11551 } +11552 $check-mu-block:end: +11553 # . restore registers +11554 58/pop-to-eax +11555 # . epilogue +11556 89/<- %esp 5/r32/ebp +11557 5d/pop-to-ebp +11558 c3/return +11559 +11560 check-mu-stmt-list: # stmts: (addr list stmt), fn: (addr function), err: (addr buffered-file), ed: (addr exit-descriptor) +11561 # . prologue +11562 55/push-ebp +11563 89/<- %ebp 4/r32/esp +11564 # . save registers +11565 50/push-eax +11566 56/push-esi +11567 # esi = stmts +11568 8b/-> *(ebp+8) 6/r32/esi +11569 { +11570 $check-mu-stmt-list:loop: +11571 81 7/subop/compare %esi 0/imm32 +11572 0f 84/jump-if-= break/disp32 +11573 # var curr-stmt/eax: (addr stmt) = lookup(stmts->value) +11574 (lookup *esi *(esi+4)) # List-value List-value => eax +11575 { +11576 $check-mu-stmt-list:check-for-block: +11577 81 7/subop/compare *eax 0/imm32/block # Stmt-tag +11578 75/jump-if-!= break/disp8 +11579 $check-mu-stmt-list:block: +11580 (check-mu-block %eax *(ebp+0xc) *(ebp+0x10) *(ebp+0x14)) +11581 eb/jump $check-mu-stmt-list:continue/disp8 +11582 } +11583 { +11584 $check-mu-stmt-list:check-for-stmt1: +11585 81 7/subop/compare *eax 1/imm32/stmt1 # Stmt-tag +11586 0f 85/jump-if-!= break/disp32 +11587 $check-mu-stmt-list:stmt1: +11588 (check-mu-stmt %eax *(ebp+0xc) *(ebp+0x10) *(ebp+0x14)) +11589 eb/jump $check-mu-stmt-list:continue/disp8 +11590 } +11591 { +11592 $check-mu-stmt-list:check-for-reg-var-def: +11593 81 7/subop/compare *eax 3/imm32/reg-var-def # Stmt-tag +11594 0f 85/jump-if-!= break/disp32 +11595 $check-mu-stmt-list:reg-var-def: +11596 (check-mu-stmt %eax *(ebp+0xc) *(ebp+0x10) *(ebp+0x14)) +11597 eb/jump $check-mu-stmt-list:continue/disp8 +11598 } +11599 $check-mu-stmt-list:continue: +11600 # TODO: raise an error on unrecognized Stmt-tag +11601 (lookup *(esi+8) *(esi+0xc)) # List-next List-next => eax +11602 89/<- %esi 0/r32/eax +11603 e9/jump loop/disp32 +11604 } +11605 $check-mu-stmt-list:end: +11606 # . restore registers +11607 5e/pop-to-esi +11608 58/pop-to-eax +11609 # . epilogue +11610 89/<- %esp 5/r32/ebp +11611 5d/pop-to-ebp +11612 c3/return +11613 +11614 check-mu-stmt: # stmt: (addr stmt), fn: (addr function), err: (addr buffered-file), ed: (addr exit-descriptor) +11615 # . prologue +11616 55/push-ebp +11617 89/<- %ebp 4/r32/esp +11618 # . save registers +11619 50/push-eax +11620 # - if stmt's operation matches a primitive, check against it +11621 (has-primitive-name? *(ebp+8)) # => eax +11622 3d/compare-eax-and 0/imm32/false +11623 { +11624 74/jump-if-= break/disp8 +11625 (check-mu-primitive *(ebp+8) *(ebp+0xc) *(ebp+0x10) *(ebp+0x14)) +11626 e9/jump $check-mu-stmt:end/disp32 +11627 } +11628 # - otherwise find a function to check against +11629 # var f/eax: (addr function) = lookup(*Program->functions) +11630 (lookup *_Program-functions *_Program-functions->payload) # => eax +11631 (find-matching-function %eax *(ebp+8)) # => eax +11632 3d/compare-eax-and 0/imm32 +11633 { +11634 74/jump-if-= break/disp8 +11635 (check-mu-call *(ebp+8) %eax *(ebp+0xc) *(ebp+0x10) *(ebp+0x14)) +11636 eb/jump $check-mu-stmt:end/disp8 +11637 } +11638 # var f/eax: (addr function) = lookup(*Program->signatures) +11639 (lookup *_Program-signatures *_Program-signatures->payload) # => eax +11640 (find-matching-function %eax *(ebp+8)) # => eax +11641 3d/compare-eax-and 0/imm32 +11642 { +11643 74/jump-if-= break/disp8 +11644 (check-mu-call *(ebp+8) %eax *(ebp+0xc) *(ebp+0x10) *(ebp+0x14)) +11645 eb/jump $check-mu-stmt:end/disp8 +11646 } +11647 # - otherwise abort +11648 e9/jump $check-mu-stmt:unknown-call/disp32 +11649 $check-mu-stmt:end: +11650 # . restore registers +11651 58/pop-to-eax +11652 # . epilogue +11653 89/<- %esp 5/r32/ebp +11654 5d/pop-to-ebp +11655 c3/return +11656 +11657 $check-mu-stmt:unknown-call: +11658 (write-buffered *(ebp+0x10) "unknown function '") +11659 8b/-> *(ebp+8) 0/r32/eax +11660 (lookup *(eax+4) *(eax+8)) # Stmt1-operation Stmt1-operation => eax +11661 (write-buffered *(ebp+0x10) %eax) +11662 (write-buffered *(ebp+0x10) "'\n") +11663 (flush *(ebp+0x10)) +11664 (stop *(ebp+0x14) 1) +11665 # never gets here +11666 +11667 has-primitive-name?: # stmt: (addr stmt) -> result/eax: boolean +11668 # . prologue +11669 55/push-ebp +11670 89/<- %ebp 4/r32/esp +11671 # . save registers +11672 51/push-ecx +11673 56/push-esi +11674 # var name/esi: (addr array byte) = lookup(stmt->operation) +11675 8b/-> *(ebp+8) 6/r32/esi +11676 (lookup *(esi+4) *(esi+8)) # Stmt1-operation Stmt1-operation => eax +11677 89/<- %esi 0/r32/eax +11678 # if (name == "get") return true +11679 (string-equal? %esi "get") # => eax +11680 3d/compare-eax-and 0/imm32/false +11681 0f 85/jump-if-!= $has-primitive-name?:end/disp32 +11682 # if (name == "index") return true +11683 (string-equal? %esi "index") # => eax +11684 3d/compare-eax-and 0/imm32/false +11685 0f 85/jump-if-!= $has-primitive-name?:end/disp32 +11686 # if (name == "length") return true +11687 (string-equal? %esi "length") # => eax +11688 3d/compare-eax-and 0/imm32/false +11689 0f 85/jump-if-!= $has-primitive-name?:end/disp32 +11690 # if (name == "compute-offset") return true +11691 (string-equal? %esi "compute-offset") # => eax +11692 3d/compare-eax-and 0/imm32/false +11693 0f 85/jump-if-!= $has-primitive-name?:end/disp32 +11694 # if (name == "allocate") return true +11695 (string-equal? %esi "allocate") # => eax +11696 3d/compare-eax-and 0/imm32/false +11697 0f 85/jump-if-!= $has-primitive-name?:end/disp32 +11698 # if (name == "populate") return true +11699 (string-equal? %esi "populate") # => eax +11700 3d/compare-eax-and 0/imm32/false +11701 0f 85/jump-if-!= $has-primitive-name?:end/disp32 +11702 # if (name == "populate-stream") return true +11703 (string-equal? %esi "populate-stream") # => eax +11704 3d/compare-eax-and 0/imm32/false +11705 0f 85/jump-if-!= $has-primitive-name?:end/disp32 +11706 # if (name == "read-from-stream") return true +11707 (string-equal? %esi "read-from-stream") # => eax +11708 3d/compare-eax-and 0/imm32/false +11709 0f 85/jump-if-!= $has-primitive-name?:end/disp32 +11710 # if (name == "write-to-stream") return true +11711 (string-equal? %esi "write-to-stream") # => eax +11712 3d/compare-eax-and 0/imm32/false +11713 0f 85/jump-if-!= $has-primitive-name?:end/disp32 +11714 # var curr/ecx: (addr primitive) = Primitives +11715 b9/copy-to-ecx Primitives/imm32 +11716 { +11717 $has-primitive-name?:loop: +11718 # if (curr == null) break +11719 81 7/subop/compare %ecx 0/imm32 +11720 74/jump-if-= break/disp8 +11721 # if (primitive->name == name) return true +11722 (lookup *ecx *(ecx+4)) # Primitive-name Primitive-name => eax +11723 (string-equal? %esi %eax) # => eax 11724 3d/compare-eax-and 0/imm32/false -11725 74/jump-if-= break/disp8 -11726 (check-mu-compare-stmt *(ebp+8) *(ebp+0xc) *(ebp+0x10) *(ebp+0x14)) -11727 e9/jump $check-mu-primitive:end/disp32 -11728 } -11729 # if (op == "address") check-mu-address-stmt -11730 { -11731 (string-equal? %ecx "address") # => eax -11732 3d/compare-eax-and 0/imm32/false -11733 74/jump-if-= break/disp8 -11734 (check-mu-address-stmt *(ebp+8) *(ebp+0xc) *(ebp+0x10) *(ebp+0x14)) -11735 e9/jump $check-mu-primitive:end/disp32 -11736 } -11737 # if (op == "get") check-mu-get-stmt -11738 { -11739 (string-equal? %ecx "get") # => eax -11740 3d/compare-eax-and 0/imm32/false -11741 74/jump-if-= break/disp8 -11742 (check-mu-get-stmt *(ebp+8) *(ebp+0xc) *(ebp+0x10) *(ebp+0x14)) -11743 e9/jump $check-mu-primitive:end/disp32 -11744 } -11745 # if (op == "index") check-mu-index-stmt -11746 { -11747 (string-equal? %ecx "index") # => eax -11748 3d/compare-eax-and 0/imm32/false -11749 74/jump-if-= break/disp8 -11750 (check-mu-index-stmt *(ebp+8) *(ebp+0xc) *(ebp+0x10) *(ebp+0x14)) -11751 e9/jump $check-mu-primitive:end/disp32 -11752 } -11753 # if (op == "length") check-mu-length-stmt -11754 { -11755 (string-equal? %ecx "length") # => eax -11756 3d/compare-eax-and 0/imm32/false -11757 74/jump-if-= break/disp8 -11758 (check-mu-length-stmt *(ebp+8) *(ebp+0xc) *(ebp+0x10) *(ebp+0x14)) -11759 e9/jump $check-mu-primitive:end/disp32 -11760 } -11761 # if (op == "compute-offset") check-mu-compute-offset-stmt -11762 { -11763 (string-equal? %ecx "compute-offset") # => eax -11764 3d/compare-eax-and 0/imm32/false -11765 74/jump-if-= break/disp8 -11766 (check-mu-compute-offset-stmt *(ebp+8) *(ebp+0xc) *(ebp+0x10) *(ebp+0x14)) -11767 e9/jump $check-mu-primitive:end/disp32 -11768 } -11769 # if (op == "allocate") check-mu-allocate-stmt -11770 { -11771 (string-equal? %ecx "allocate") # => eax -11772 3d/compare-eax-and 0/imm32/false -11773 74/jump-if-= break/disp8 -11774 (check-mu-allocate-stmt *(ebp+8) *(ebp+0xc) *(ebp+0x10) *(ebp+0x14)) -11775 e9/jump $check-mu-primitive:end/disp32 -11776 } -11777 # if (op == "populate") check-mu-populate-stmt -11778 { -11779 (string-equal? %ecx "populate") # => eax -11780 3d/compare-eax-and 0/imm32/false -11781 74/jump-if-= break/disp8 -11782 (check-mu-populate-stmt *(ebp+8) *(ebp+0xc) *(ebp+0x10) *(ebp+0x14)) -11783 e9/jump $check-mu-primitive:end/disp32 -11784 } -11785 # otherwise check-numberlike-stmt -11786 (check-mu-numberlike-primitive *(ebp+8) *(ebp+0xc) *(ebp+0x10) *(ebp+0x14)) -11787 $check-mu-primitive:end: -11788 # . restore registers -11789 59/pop-to-ecx -11790 58/pop-to-eax -11791 # . epilogue -11792 89/<- %esp 5/r32/ebp -11793 5d/pop-to-ebp -11794 c3/return -11795 -11796 # by default, Mu primitives should only operate on 'number-like' types -11797 check-mu-numberlike-primitive: # stmt: (addr stmt), fn: (addr function), err: (addr buffered-file), ed: (addr exit-descriptor) -11798 # . prologue -11799 55/push-ebp -11800 89/<- %ebp 4/r32/esp -11801 # . save registers -11802 50/push-eax -11803 51/push-ecx -11804 56/push-esi -11805 # esi = stmt -11806 8b/-> *(ebp+8) 6/r32/esi -11807 # var gas/ecx: int = 2 -11808 b9/copy-to-ecx 2/imm32 -11809 # - check at most 1 output -11810 # var output/eax: (addr stmt-var) = stmt->outputs -11811 (lookup *(esi+0x14) *(esi+0x18)) # Stmt1-outputs Stmt1-outputs => eax +11725 75/jump-if-!= $has-primitive-name?:end/disp8 +11726 $has-primitive-name?:next-primitive: +11727 # curr = curr->next +11728 (lookup *(ecx+0x38) *(ecx+0x3c)) # Primitive-next Primitive-next => eax +11729 89/<- %ecx 0/r32/eax +11730 # +11731 e9/jump loop/disp32 +11732 } +11733 # return null +11734 b8/copy-to-eax 0/imm32 +11735 $has-primitive-name?:end: +11736 # . restore registers +11737 5e/pop-to-esi +11738 59/pop-to-ecx +11739 # . epilogue +11740 89/<- %esp 5/r32/ebp +11741 5d/pop-to-ebp +11742 c3/return +11743 +11744 check-mu-primitive: # stmt: (addr stmt), fn: (addr function), err: (addr buffered-file), ed: (addr exit-descriptor) +11745 # . prologue +11746 55/push-ebp +11747 89/<- %ebp 4/r32/esp +11748 # . save registers +11749 50/push-eax +11750 51/push-ecx +11751 # var op/ecx: (addr array byte) = lookup(stmt->operation) +11752 8b/-> *(ebp+8) 0/r32/eax +11753 (lookup *(eax+4) *(eax+8)) # Stmt1-operation Stmt1-operation => eax +11754 89/<- %ecx 0/r32/eax +11755 # if (op == "copy") check-mu-copy-stmt +11756 { +11757 (string-equal? %ecx "copy") # => eax +11758 3d/compare-eax-and 0/imm32/false +11759 74/jump-if-= break/disp8 +11760 (check-mu-copy-stmt *(ebp+8) *(ebp+0xc) *(ebp+0x10) *(ebp+0x14)) +11761 e9/jump $check-mu-primitive:end/disp32 +11762 } +11763 # if (op == "copy-to") check-mu-copy-to-stmt +11764 { +11765 (string-equal? %ecx "copy-to") # => eax +11766 3d/compare-eax-and 0/imm32/false +11767 74/jump-if-= break/disp8 +11768 (check-mu-copy-to-stmt *(ebp+8) *(ebp+0xc) *(ebp+0x10) *(ebp+0x14)) +11769 e9/jump $check-mu-primitive:end/disp32 +11770 } +11771 # if (op == "compare") check-mu-compare-stmt +11772 { +11773 (string-equal? %ecx "compare") # => eax +11774 3d/compare-eax-and 0/imm32/false +11775 74/jump-if-= break/disp8 +11776 (check-mu-compare-stmt *(ebp+8) *(ebp+0xc) *(ebp+0x10) *(ebp+0x14)) +11777 e9/jump $check-mu-primitive:end/disp32 +11778 } +11779 # if (op == "address") check-mu-address-stmt +11780 { +11781 (string-equal? %ecx "address") # => eax +11782 3d/compare-eax-and 0/imm32/false +11783 74/jump-if-= break/disp8 +11784 (check-mu-address-stmt *(ebp+8) *(ebp+0xc) *(ebp+0x10) *(ebp+0x14)) +11785 e9/jump $check-mu-primitive:end/disp32 +11786 } +11787 # if (op == "get") check-mu-get-stmt +11788 { +11789 (string-equal? %ecx "get") # => eax +11790 3d/compare-eax-and 0/imm32/false +11791 74/jump-if-= break/disp8 +11792 (check-mu-get-stmt *(ebp+8) *(ebp+0xc) *(ebp+0x10) *(ebp+0x14)) +11793 e9/jump $check-mu-primitive:end/disp32 +11794 } +11795 # if (op == "index") check-mu-index-stmt +11796 { +11797 (string-equal? %ecx "index") # => eax +11798 3d/compare-eax-and 0/imm32/false +11799 74/jump-if-= break/disp8 +11800 (check-mu-index-stmt *(ebp+8) *(ebp+0xc) *(ebp+0x10) *(ebp+0x14)) +11801 e9/jump $check-mu-primitive:end/disp32 +11802 } +11803 # if (op == "length") check-mu-length-stmt +11804 { +11805 (string-equal? %ecx "length") # => eax +11806 3d/compare-eax-and 0/imm32/false +11807 74/jump-if-= break/disp8 +11808 (check-mu-length-stmt *(ebp+8) *(ebp+0xc) *(ebp+0x10) *(ebp+0x14)) +11809 e9/jump $check-mu-primitive:end/disp32 +11810 } +11811 # if (op == "compute-offset") check-mu-compute-offset-stmt 11812 { -11813 3d/compare-eax-and 0/imm32 -11814 74/jump-if-= break/disp8 -11815 $check-mu-numberlike-primitive:output: -11816 (check-mu-numberlike-output %eax *(ebp+8) *(ebp+0xc) *(ebp+0x10) *(ebp+0x14)) -11817 (lookup *(eax+8) *(eax+0xc)) # Stmt-var-next Stmt-var-next => eax -11818 3d/compare-eax-and 0/imm32 -11819 0f 85/jump-if-!= $check-mu-numberlike-primitive:error-too-many-outputs/disp32 -11820 # check output is in a register -11821 # --gas -11822 49/decrement-ecx -11823 } -11824 # - check first inout -11825 (lookup *(esi+0xc) *(esi+0x10)) # Stmt1-inouts Stmt1-inouts => eax -11826 { -11827 3d/compare-eax-and 0/imm32 -11828 0f 84/jump-if-= $check-mu-numberlike-primitive:end/disp32 -11829 $check-mu-numberlike-primitive:first-inout: -11830 (check-mu-numberlike-arg %eax *(ebp+8) *(ebp+0xc) *(ebp+0x10) *(ebp+0x14)) -11831 # --gas -11832 49/decrement-ecx -11833 } -11834 # - check second inout -11835 (lookup *(eax+8) *(eax+0xc)) # Stmt-var-next Stmt-var-next => eax +11813 (string-equal? %ecx "compute-offset") # => eax +11814 3d/compare-eax-and 0/imm32/false +11815 74/jump-if-= break/disp8 +11816 (check-mu-compute-offset-stmt *(ebp+8) *(ebp+0xc) *(ebp+0x10) *(ebp+0x14)) +11817 e9/jump $check-mu-primitive:end/disp32 +11818 } +11819 # if (op == "allocate") check-mu-allocate-stmt +11820 { +11821 (string-equal? %ecx "allocate") # => eax +11822 3d/compare-eax-and 0/imm32/false +11823 74/jump-if-= break/disp8 +11824 (check-mu-allocate-stmt *(ebp+8) *(ebp+0xc) *(ebp+0x10) *(ebp+0x14)) +11825 e9/jump $check-mu-primitive:end/disp32 +11826 } +11827 # if (op == "populate") check-mu-populate-stmt +11828 { +11829 (string-equal? %ecx "populate") # => eax +11830 3d/compare-eax-and 0/imm32/false +11831 74/jump-if-= break/disp8 +11832 (check-mu-populate-stmt *(ebp+8) *(ebp+0xc) *(ebp+0x10) *(ebp+0x14)) +11833 e9/jump $check-mu-primitive:end/disp32 +11834 } +11835 # if (op == "populate-stream") check-mu-populate-stream-stmt 11836 { -11837 3d/compare-eax-and 0/imm32 -11838 74/jump-if-= $check-mu-numberlike-primitive:end/disp8 -11839 $check-mu-numberlike-primitive:second-inout: -11840 # is a second inout allowed? -11841 81 7/subop/compare %ecx 0/imm32 -11842 0f 84/jump-if-= $check-mu-numberlike-primitive:error-too-many-inouts/disp32 -11843 $check-mu-numberlike-primitive:second-inout-permitted: -11844 (check-mu-numberlike-arg %eax *(ebp+8) *(ebp+0xc) *(ebp+0x10) *(ebp+0x14)) -11845 } -11846 $check-mu-numberlike-primitive:third-inout: -11847 # if there's a third arg, raise an error -11848 81 7/subop/compare *(eax+8) 0/imm32 # Stmt-var-next -11849 0f 85/jump-if-!= $check-mu-numberlike-primitive:error-too-many-inouts/disp32 -11850 $check-mu-numberlike-primitive:end: -11851 # . restore registers -11852 5e/pop-to-esi -11853 59/pop-to-ecx -11854 58/pop-to-eax -11855 # . epilogue -11856 89/<- %esp 5/r32/ebp -11857 5d/pop-to-ebp -11858 c3/return -11859 -11860 $check-mu-numberlike-primitive:error-too-many-inouts: -11861 (write-buffered *(ebp+0x10) "fn ") -11862 8b/-> *(ebp+0xc) 0/r32/eax -11863 (lookup *eax *(eax+4)) # Function-name Function-name => eax -11864 (write-buffered *(ebp+0x10) %eax) -11865 (write-buffered *(ebp+0x10) ": stmt ") -11866 (lookup *(esi+4) *(esi+8)) # Stmt1-operation Stmt1-operation => eax -11867 (write-buffered *(ebp+0x10) %eax) -11868 (write-buffered *(ebp+0x10) ": too many inouts; most primitives support at most two arguments, across inouts and outputs\n") -11869 (flush *(ebp+0x10)) -11870 (stop *(ebp+0x14) 1) -11871 # never gets here -11872 -11873 $check-mu-numberlike-primitive:error-too-many-outputs: -11874 (write-buffered *(ebp+0x10) "fn ") -11875 8b/-> *(ebp+0xc) 0/r32/eax -11876 (lookup *eax *(eax+4)) # Function-name Function-name => eax -11877 (write-buffered *(ebp+0x10) %eax) -11878 (write-buffered *(ebp+0x10) ": stmt ") -11879 (lookup *(esi+4) *(esi+8)) # Stmt1-operation Stmt1-operation => eax -11880 (write-buffered *(ebp+0x10) %eax) -11881 (write-buffered *(ebp+0x10) ": too many outputs; most primitives support at most one output\n") -11882 (flush *(ebp+0x10)) -11883 (stop *(ebp+0x14) 1) -11884 # never gets here -11885 -11886 check-mu-numberlike-arg: # v: (addr stmt-var), stmt: (addr stmt), fn: (addr function), err: (addr buffered-file), ed: (addr exit-descriptor) -11887 # . prologue -11888 55/push-ebp -11889 89/<- %ebp 4/r32/esp -11890 # . save registers -11891 50/push-eax -11892 56/push-esi -11893 # var t/esi: (addr type-tree) = lookup(v->value->type) -11894 8b/-> *(ebp+8) 0/r32/eax -11895 (lookup *eax *(eax+4)) # Stmt-var-value Stmt-var-value => eax -11896 (lookup *(eax+8) *(eax+0xc)) # Var-type Var-type => eax -11897 89/<- %esi 0/r32/eax -11898 $check-mu-numberlike-arg:check-literal: -11899 # if t is an int, return -11900 (is-simple-mu-type? %esi 0) # literal => eax -11901 3d/compare-eax-and 0/imm32/false -11902 75/jump-if-!= $check-mu-numberlike-arg:end/disp8 -11903 $check-mu-numberlike-arg:check-addr: -11904 # if t is an addr and v is dereferenced, return -11905 { -11906 (is-mu-addr-type? %esi) # => eax -11907 3d/compare-eax-and 0/imm32/false -11908 74/jump-if-= break/disp8 -11909 8b/-> *(ebp+8) 0/r32/eax -11910 8b/-> *(eax+0x10) 0/r32/eax -11911 3d/compare-eax-and 0/imm32/false -11912 75/jump-if-!= $check-mu-numberlike-arg:end/disp8 -11913 } -11914 $check-mu-numberlike-arg:output-checks: -11915 (check-mu-numberlike-output *(ebp+8) *(ebp+0xc) *(ebp+0x10) *(ebp+0x14) *(ebp+0x18)) -11916 $check-mu-numberlike-arg:end: -11917 # . restore registers -11918 5e/pop-to-esi -11919 58/pop-to-eax -11920 # . epilogue -11921 89/<- %esp 5/r32/ebp -11922 5d/pop-to-ebp -11923 c3/return -11924 -11925 check-mu-numberlike-output: # v: (addr stmt-var), stmt: (addr stmt), fn: (addr function), err: (addr buffered-file), ed: (addr exit-descriptor) -11926 # . prologue -11927 55/push-ebp -11928 89/<- %ebp 4/r32/esp -11929 # . save registers -11930 50/push-eax -11931 56/push-esi -11932 # var t/esi: (addr type-tree) = lookup(v->value->type) -11933 8b/-> *(ebp+8) 0/r32/eax -11934 (lookup *eax *(eax+4)) # Stmt-var-value Stmt-var-value => eax -11935 (lookup *(eax+8) *(eax+0xc)) # Var-type Var-type => eax -11936 89/<- %esi 0/r32/eax -11937 $check-mu-numberlike-output:check-int: -11938 # if t is an int, return -11939 (is-simple-mu-type? %esi 1) # int => eax -11940 3d/compare-eax-and 0/imm32/false -11941 75/jump-if-!= $check-mu-numberlike-output:end/disp8 -11942 $check-mu-numberlike-output:check-boolean: -11943 # if t is a boolean, return -11944 (is-simple-mu-type? %esi 5) # boolean => eax -11945 3d/compare-eax-and 0/imm32/false -11946 75/jump-if-!= $check-mu-numberlike-output:end/disp8 -11947 $check-mu-numberlike-output:check-byte: -11948 # if t is a byte, return -11949 (is-simple-mu-type? %esi 8) # byte => eax -11950 3d/compare-eax-and 0/imm32/false -11951 75/jump-if-!= $check-mu-numberlike-output:end/disp8 -11952 e9/jump $check-mu-numberlike-output:fail/disp32 -11953 $check-mu-numberlike-output:end: -11954 # . restore registers -11955 5e/pop-to-esi -11956 58/pop-to-eax -11957 # . epilogue -11958 89/<- %esp 5/r32/ebp -11959 5d/pop-to-ebp -11960 c3/return -11961 -11962 $check-mu-numberlike-output:fail: -11963 # otherwise raise an error -11964 (write-buffered *(ebp+0x14) "fn ") -11965 8b/-> *(ebp+0x10) 0/r32/eax -11966 (lookup *eax *(eax+4)) # Function-name Function-name => eax -11967 (write-buffered *(ebp+0x14) %eax) -11968 (write-buffered *(ebp+0x14) ": stmt ") -11969 8b/-> *(ebp+0xc) 0/r32/eax -11970 (lookup *(eax+4) *(eax+8)) # Stmt1-operation Stmt1-operation => eax -11971 (write-buffered *(ebp+0x14) %eax) -11972 (write-buffered *(ebp+0x14) ": only non-addr scalar args permitted\n") -11973 (flush *(ebp+0x14)) -11974 (stop *(ebp+0x18) 1) -11975 # never gets here -11976 -11977 check-mu-copy-stmt: # stmt: (addr stmt), fn: (addr function), err: (addr buffered-file), ed: (addr exit-descriptor) -11978 # . prologue -11979 55/push-ebp -11980 89/<- %ebp 4/r32/esp -11981 # . save registers -11982 $check-mu-copy-stmt:end: -11983 # . restore registers -11984 # . epilogue -11985 89/<- %esp 5/r32/ebp -11986 5d/pop-to-ebp -11987 c3/return -11988 -11989 check-mu-copy-to-stmt: # stmt: (addr stmt), fn: (addr function), err: (addr buffered-file), ed: (addr exit-descriptor) -11990 # . prologue -11991 55/push-ebp -11992 89/<- %ebp 4/r32/esp -11993 # . save registers -11994 $check-mu-copy-to-stmt:end: -11995 # . restore registers -11996 # . epilogue -11997 89/<- %esp 5/r32/ebp -11998 5d/pop-to-ebp -11999 c3/return -12000 -12001 check-mu-compare-stmt: # stmt: (addr stmt), fn: (addr function), err: (addr buffered-file), ed: (addr exit-descriptor) -12002 # . prologue -12003 55/push-ebp -12004 89/<- %ebp 4/r32/esp -12005 # . save registers -12006 $check-mu-compare-stmt:end: -12007 # . restore registers -12008 # . epilogue -12009 89/<- %esp 5/r32/ebp -12010 5d/pop-to-ebp -12011 c3/return -12012 -12013 check-mu-address-stmt: # stmt: (addr stmt), fn: (addr function), err: (addr buffered-file), ed: (addr exit-descriptor) -12014 # . prologue -12015 55/push-ebp -12016 89/<- %ebp 4/r32/esp -12017 # . save registers -12018 $check-mu-address-stmt:end: -12019 # . restore registers -12020 # . epilogue -12021 89/<- %esp 5/r32/ebp -12022 5d/pop-to-ebp -12023 c3/return -12024 -12025 check-mu-get-stmt: # stmt: (addr stmt), fn: (addr function), err: (addr buffered-file), ed: (addr exit-descriptor) -12026 # . prologue -12027 55/push-ebp -12028 89/<- %ebp 4/r32/esp -12029 # . save registers -12030 50/push-eax -12031 51/push-ecx -12032 52/push-edx -12033 53/push-ebx -12034 56/push-esi -12035 57/push-edi -12036 # esi = stmt -12037 8b/-> *(ebp+8) 6/r32/esi -12038 # - check for 0 inouts -12039 # var base/ecx: (addr var) = stmt->inouts->value -12040 (lookup *(esi+0xc) *(esi+0x10)) # Stmt1-inouts Stmt1-inouts => eax -12041 3d/compare-eax-and 0/imm32/false -12042 0f 84/jump-if-= $check-mu-get-stmt:error-too-few-inouts/disp32 -12043 (lookup *eax *(eax+4)) # Stmt-var-value Stmt-var-value => eax -12044 89/<- %ecx 0/r32/eax -12045 $check-mu-get-stmt:check-base: -12046 # - check base type -12047 # if it's an 'addr', check that it's in a register -12048 # var base-type/ebx: (addr type-tree) = lookup(base->type) -12049 (lookup *(ecx+8) *(ecx+0xc)) # Var-type Var-type => eax -12050 89/<- %ebx 0/r32/eax -12051 { -12052 81 7/subop/compare *ebx 0/imm32/false # Type-tree-is-atom -12053 0f 85/jump-if-!= break/disp32 -12054 $check-mu-get-stmt:base-is-compound: -12055 # if (type->left != addr) break -12056 (lookup *(ebx+4) *(ebx+8)) # Type-tree-left Type-tree-left => eax -12057 (is-simple-mu-type? %eax 2) # => eax -12058 3d/compare-eax-and 0/imm32/false -12059 74/jump-if-= break/disp8 -12060 $check-mu-get-stmt:base-is-addr: -12061 # now check for register -12062 81 7/subop/compare *(ecx+0x18) 0/imm32 # Var-register -12063 0f 84/jump-if-= $check-mu-get-stmt:error-base-type-addr-but-not-register/disp32 -12064 $check-mu-get-stmt:base-is-addr-in-register: -12065 # type->left is now an addr; skip it -12066 (lookup *(ebx+0xc) *(ebx+0x10)) # Type-tree-right Type-tree-right => eax -12067 81 7/subop/compare *(eax+0xc) 0/imm32 # Type-tree-right -12068 0f 85/jump-if-!= $check-mu-get-stmt:error-bad-base/disp32 -12069 $check-mu-get-stmt:base-is-addr-to-atom-in-register: -12070 (lookup *(eax+4) *(eax+8)) # Type-tree-left Type-tree-left => eax -12071 89/<- %ebx 0/r32/eax -12072 } -12073 $check-mu-get-stmt:check-base-typeinfo: -12074 # ensure type is a container -12075 # var base-type-id/ebx: type-id = base-type->value -12076 8b/-> *(ebx+4) 3/r32/ebx # Type-tree-value -12077 (is-container? %ebx) # => eax -12078 3d/compare-eax-and 0/imm32/false -12079 0f 84/jump-if-= $check-mu-get-stmt:error-bad-base/disp32 -12080 # var base-typeinfo/edx: (addr typeinfo) = find-typeinfo(base-type-id) -12081 # . var container/ecx: (handle typeinfo) -12082 68/push 0/imm32 -12083 68/push 0/imm32 -12084 89/<- %ecx 4/r32/esp -12085 # . -12086 (find-typeinfo %ebx %ecx) -12087 (lookup *ecx *(ecx+4)) # => eax -12088 # . reclaim container -12089 81 0/subop/add %esp 8/imm32 -12090 # . -12091 89/<- %edx 0/r32/eax -12092 # var offset/ecx: (addr stmt-var) = stmt->inouts->next -12093 (lookup *(esi+0xc) *(esi+0x10)) # Stmt1-inouts Stmt1-inouts => eax -12094 (lookup *(eax+8) *(eax+0xc)) # Stmt-var-next Stmt-var-next => eax -12095 89/<- %ecx 0/r32/eax -12096 # - check for 1 inout -12097 3d/compare-eax-and 0/imm32/false -12098 0f 84/jump-if-= $check-mu-get-stmt:error-too-few-inouts/disp32 -12099 # var offset/ecx: (addr var) = lookup(offset->value) -12100 (lookup *ecx *(ecx+4)) # Stmt-var-value Stmt-var-value => eax -12101 89/<- %ecx 0/r32/eax -12102 # - check for valid field -12103 81 7/subop/compare *(ecx+0x14) -1/imm32/uninitialized # Var-offset -12104 0f 84/jump-if-= $check-mu-get-stmt:error-bad-field/disp32 -12105 # - check for too many inouts -12106 (lookup *(esi+0xc) *(esi+0x10)) # Stmt1-inouts Stmt1-inouts => eax -12107 (lookup *(eax+8) *(eax+0xc)) # Stmt-var-next Stmt-var-next => eax -12108 (lookup *(eax+8) *(eax+0xc)) # Stmt-var-next Stmt-var-next => eax -12109 3d/compare-eax-and 0/imm32/false -12110 0f 85/jump-if-!= $check-mu-get-stmt:error-too-many-inouts/disp32 -12111 # var output/edi: (addr var) = stmt->outputs->value -12112 (lookup *(esi+0x14) *(esi+0x18)) # Stmt1-outputs Stmt1-outputs => eax -12113 # - check for 0 outputs -12114 3d/compare-eax-and 0/imm32/false -12115 0f 84/jump-if-= $check-mu-get-stmt:error-too-few-outputs/disp32 -12116 (lookup *eax *(eax+4)) # Stmt-var-value Stmt-var-value => eax -12117 89/<- %edi 0/r32/eax -12118 $check-mu-get-stmt:check-output-type: -12119 # - check output type -12120 # must be in register -12121 (lookup *(edi+0x18) *(edi+0x1c)) # Var-register Var-register => eax -12122 3d/compare-eax-and 0/imm32 -12123 0f 84/jump-if-= $check-mu-get-stmt:error-output-not-in-register/disp32 -12124 # must have a non-atomic type -12125 (lookup *(edi+8) *(edi+0xc)) # Var-type Var-type => eax -12126 81 7/subop/compare *eax 0/imm32/false # Type-tree-is-atom -12127 0f 85/jump-if-!= $check-mu-get-stmt:error-output-type-not-address/disp32 -12128 # type must start with (addr ...) -12129 (lookup *(eax+4) *(eax+8)) # Type-tree-left Type-tree-left => eax -12130 (is-simple-mu-type? %eax 2) # => eax -12131 3d/compare-eax-and 0/imm32/false -12132 0f 84/jump-if-= $check-mu-get-stmt:error-output-type-not-address/disp32 -12133 $check-mu-get-stmt:check-output-type-match: -12134 # payload of addr type must match 'type' definition -12135 (lookup *(edi+8) *(edi+0xc)) # Var-type Var-type => eax -12136 (lookup *(eax+0xc) *(eax+0x10)) # Type-tree-right Type-tree-right => eax -12137 # if (payload->right == null) payload = payload->left -12138 81 7/subop/compare *(eax+0xc) 0/imm32/null # Type-tree-right -12139 { -12140 75/jump-if-!= break/disp8 -12141 (lookup *(eax+4) *(eax+8)) # Type-tree-left Type-tree-left => eax -12142 } -12143 89/<- %edi 0/r32/eax -12144 # . var output-name/ecx: (addr array byte) -12145 (lookup *ecx *(ecx+4)) # Var-name Var-name => eax -12146 89/<- %ecx 0/r32/eax -12147 # . var base-typeinfo-entry/eax: (addr handle typeinfo-entry) -12148 (lookup *(edx+4) *(edx+8)) # Typeinfo-fields Typeinfo-fields => eax -12149 (get %eax %ecx 0x10) # => eax -12150 # . -12151 (lookup *eax *(eax+4)) # => eax -12152 (lookup *eax *(eax+4)) # Typeinfo-entry-input-var Typeinfo-entry-input-var => eax -12153 (lookup *(eax+8) *(eax+0xc)) # Var-type Var-type => eax -12154 # . -12155 (type-equal? %edi %eax) # => eax -12156 3d/compare-eax-and 0/imm32/false -12157 0f 84/jump-if-= $check-mu-get-stmt:error-bad-output-type/disp32 -12158 # - check for too many outputs -12159 (lookup *(esi+0x14) *(esi+0x18)) # Stmt1-outputs Stmt1-outputs => eax -12160 (lookup *(eax+8) *(eax+0xc)) # Stmt-var-next Stmt-var-next => eax -12161 3d/compare-eax-and 0/imm32/false -12162 0f 85/jump-if-!= $check-mu-get-stmt:error-too-many-outputs/disp32 -12163 $check-mu-get-stmt:end: -12164 # . restore registers -12165 5f/pop-to-edi -12166 5e/pop-to-esi -12167 5b/pop-to-ebx -12168 5a/pop-to-edx -12169 59/pop-to-ecx -12170 58/pop-to-eax -12171 # . epilogue -12172 89/<- %esp 5/r32/ebp -12173 5d/pop-to-ebp -12174 c3/return -12175 -12176 $check-mu-get-stmt:error-too-few-inouts: -12177 (write-buffered *(ebp+0x10) "fn ") -12178 8b/-> *(ebp+0xc) 0/r32/eax -12179 (lookup *eax *(eax+4)) # Function-name Function-name => eax -12180 (write-buffered *(ebp+0x10) %eax) -12181 (write-buffered *(ebp+0x10) ": stmt get: too few inouts (2 required)\n") -12182 (flush *(ebp+0x10)) -12183 (stop *(ebp+0x14) 1) -12184 # never gets here -12185 -12186 $check-mu-get-stmt:error-too-many-inouts: -12187 (write-buffered *(ebp+0x10) "fn ") -12188 8b/-> *(ebp+0xc) 0/r32/eax -12189 (lookup *eax *(eax+4)) # Function-name Function-name => eax -12190 (write-buffered *(ebp+0x10) %eax) -12191 (write-buffered *(ebp+0x10) ": stmt get: too many inouts (2 required)\n") -12192 (flush *(ebp+0x10)) -12193 (stop *(ebp+0x14) 1) -12194 # never gets here -12195 -12196 $check-mu-get-stmt:error-too-few-outputs: -12197 (write-buffered *(ebp+0x10) "fn ") -12198 8b/-> *(ebp+0xc) 0/r32/eax -12199 (lookup *eax *(eax+4)) # Function-name Function-name => eax -12200 (write-buffered *(ebp+0x10) %eax) -12201 (write-buffered *(ebp+0x10) ": stmt get: must have an output\n") -12202 (flush *(ebp+0x10)) -12203 (stop *(ebp+0x14) 1) -12204 # never gets here -12205 -12206 $check-mu-get-stmt:error-too-many-outputs: -12207 (write-buffered *(ebp+0x10) "fn ") -12208 8b/-> *(ebp+0xc) 0/r32/eax -12209 (lookup *eax *(eax+4)) # Function-name Function-name => eax -12210 (write-buffered *(ebp+0x10) %eax) -12211 (write-buffered *(ebp+0x10) ": stmt get: too many outputs (1 required)\n") -12212 (flush *(ebp+0x10)) -12213 (stop *(ebp+0x14) 1) -12214 # never gets here -12215 -12216 $check-mu-get-stmt:error-bad-base: -12217 # error("fn " fn ": stmt get: var '" base->name "' must have a 'type' definition\n") -12218 (write-buffered *(ebp+0x10) "fn ") -12219 8b/-> *(ebp+0xc) 0/r32/eax -12220 (lookup *eax *(eax+4)) # Function-name Function-name => eax -12221 (write-buffered *(ebp+0x10) %eax) -12222 (write-buffered *(ebp+0x10) ": stmt get: var '") -12223 (lookup *(esi+0xc) *(esi+0x10)) # Stmt1-inouts Stmt1-inouts => eax -12224 (lookup *eax *(eax+4)) # Stmt-var-value Stmt-var-value => eax -12225 (lookup *eax *(eax+4)) # Var-name Var-name => eax -12226 (write-buffered *(ebp+0x10) %eax) -12227 (write-buffered *(ebp+0x10) "' must have a 'type' definition\n") -12228 (flush *(ebp+0x10)) -12229 (stop *(ebp+0x14) 1) -12230 # never gets here -12231 -12232 $check-mu-get-stmt:error-base-type-addr-but-not-register: -12233 (write-buffered *(ebp+0x10) "fn ") -12234 8b/-> *(ebp+0xc) 0/r32/eax -12235 (lookup *eax *(eax+4)) # Function-name Function-name => eax -12236 (write-buffered *(ebp+0x10) %eax) -12237 (write-buffered *(ebp+0x10) ": stmt get: var '") -12238 (lookup *(esi+0xc) *(esi+0x10)) # Stmt1-inouts Stmt1-inouts => eax -12239 (lookup *eax *(eax+4)) # Stmt-var-value Stmt-var-value => eax -12240 (lookup *eax *(eax+4)) # Var-name Var-name => eax -12241 (write-buffered *(ebp+0x10) %eax) -12242 (write-buffered *(ebp+0x10) "' is an 'addr' type, and so must live in a register\n") -12243 (flush *(ebp+0x10)) -12244 (stop *(ebp+0x14) 1) -12245 # never gets here -12246 -12247 $check-mu-get-stmt:error-bad-field: -12248 # error("fn " fn ": stmt get: type " type " has no member called '" curr->name "'\n") -12249 (write-buffered *(ebp+0x10) "fn ") -12250 8b/-> *(ebp+0xc) 0/r32/eax -12251 (lookup *eax *(eax+4)) # Function-name Function-name => eax -12252 (write-buffered *(ebp+0x10) %eax) -12253 (write-buffered *(ebp+0x10) ": stmt get: type '") -12254 # . write(Type-id->data[tmp]) -12255 bf/copy-to-edi Type-id/imm32 -12256 (write-buffered *(ebp+0x10) *(edi+ebx<<2+0xc)) -12257 # . -12258 (write-buffered *(ebp+0x10) "' has no member called '") -12259 (lookup *ecx *(ecx+4)) # Var-name Var-name => eax -12260 (write-buffered *(ebp+0x10) %eax) -12261 (write-buffered *(ebp+0x10) "'\n") -12262 (flush *(ebp+0x10)) -12263 (stop *(ebp+0x14) 1) -12264 # never gets here -12265 -12266 $check-mu-get-stmt:error-output-not-in-register: -12267 (write-buffered *(ebp+0x10) "fn ") -12268 8b/-> *(ebp+0xc) 0/r32/eax -12269 (lookup *eax *(eax+4)) # Function-name Function-name => eax -12270 (write-buffered *(ebp+0x10) %eax) -12271 (write-buffered *(ebp+0x10) ": stmt get: output '") -12272 (lookup *edi *(edi+4)) # Var-name Var-name => eax -12273 (write-buffered *(ebp+0x10) %eax) -12274 (write-buffered *(ebp+0x10) "' is not in a register\n") -12275 (flush *(ebp+0x10)) -12276 (stop *(ebp+0x14) 1) -12277 # never gets here -12278 -12279 $check-mu-get-stmt:error-output-type-not-address: -12280 (write-buffered *(ebp+0x10) "fn ") -12281 8b/-> *(ebp+0xc) 0/r32/eax -12282 (lookup *eax *(eax+4)) # Function-name Function-name => eax -12283 (write-buffered *(ebp+0x10) %eax) -12284 (write-buffered *(ebp+0x10) ": stmt get: output must be an address\n") -12285 (flush *(ebp+0x10)) -12286 (stop *(ebp+0x14) 1) -12287 # never gets here -12288 -12289 $check-mu-get-stmt:error-bad-output-type: -12290 (write-buffered *(ebp+0x10) "fn ") -12291 8b/-> *(ebp+0xc) 0/r32/eax -12292 (lookup *eax *(eax+4)) # Function-name Function-name => eax -12293 (write-buffered *(ebp+0x10) %eax) -12294 (write-buffered *(ebp+0x10) ": stmt get: wrong output type for member '") -12295 (write-buffered *(ebp+0x10) %ecx) -12296 (write-buffered *(ebp+0x10) "' of type '") -12297 bf/copy-to-edi Type-id/imm32 -12298 (write-buffered *(ebp+0x10) *(edi+ebx<<2+0xc)) -12299 (write-buffered *(ebp+0x10) "'\n") -12300 (flush *(ebp+0x10)) -12301 (stop *(ebp+0x14) 1) -12302 # never gets here -12303 -12304 check-mu-index-stmt: # stmt: (addr stmt), fn: (addr function), err: (addr buffered-file), ed: (addr exit-descriptor) -12305 # . prologue -12306 55/push-ebp -12307 89/<- %ebp 4/r32/esp -12308 # . save registers -12309 $check-mu-index-stmt:end: -12310 # . restore registers -12311 # . epilogue -12312 89/<- %esp 5/r32/ebp -12313 5d/pop-to-ebp -12314 c3/return -12315 -12316 check-mu-length-stmt: # stmt: (addr stmt), fn: (addr function), err: (addr buffered-file), ed: (addr exit-descriptor) -12317 # . prologue -12318 55/push-ebp -12319 89/<- %ebp 4/r32/esp -12320 # . save registers -12321 $check-mu-length-stmt:end: -12322 # . restore registers -12323 # . epilogue -12324 89/<- %esp 5/r32/ebp -12325 5d/pop-to-ebp -12326 c3/return -12327 -12328 check-mu-compute-offset-stmt: # stmt: (addr stmt), fn: (addr function), err: (addr buffered-file), ed: (addr exit-descriptor) -12329 # . prologue -12330 55/push-ebp -12331 89/<- %ebp 4/r32/esp -12332 # . save registers -12333 $check-mu-compute-offset-stmt:end: -12334 # . restore registers -12335 # . epilogue -12336 89/<- %esp 5/r32/ebp -12337 5d/pop-to-ebp -12338 c3/return +11837 (string-equal? %ecx "populate-stream") # => eax +11838 3d/compare-eax-and 0/imm32/false +11839 74/jump-if-= break/disp8 +11840 (check-mu-populate-stream-stmt *(ebp+8) *(ebp+0xc) *(ebp+0x10) *(ebp+0x14)) +11841 e9/jump $check-mu-primitive:end/disp32 +11842 } +11843 # if (op == "read-from-stream") check-mu-read-from-stream-stmt +11844 { +11845 (string-equal? %ecx "read-from-stream") # => eax +11846 3d/compare-eax-and 0/imm32/false +11847 74/jump-if-= break/disp8 +11848 (check-mu-read-from-stream-stmt *(ebp+8) *(ebp+0xc) *(ebp+0x10) *(ebp+0x14)) +11849 e9/jump $check-mu-primitive:end/disp32 +11850 } +11851 # if (op == "write-to-stream") check-mu-write-to-stream-stmt +11852 { +11853 (string-equal? %ecx "write-to-stream") # => eax +11854 3d/compare-eax-and 0/imm32/false +11855 74/jump-if-= break/disp8 +11856 (check-mu-write-to-stream-stmt *(ebp+8) *(ebp+0xc) *(ebp+0x10) *(ebp+0x14)) +11857 e9/jump $check-mu-primitive:end/disp32 +11858 } +11859 # otherwise check-numberlike-stmt +11860 (check-mu-numberlike-primitive *(ebp+8) *(ebp+0xc) *(ebp+0x10) *(ebp+0x14)) +11861 $check-mu-primitive:end: +11862 # . restore registers +11863 59/pop-to-ecx +11864 58/pop-to-eax +11865 # . epilogue +11866 89/<- %esp 5/r32/ebp +11867 5d/pop-to-ebp +11868 c3/return +11869 +11870 # by default, Mu primitives should only operate on 'number-like' types +11871 check-mu-numberlike-primitive: # stmt: (addr stmt), fn: (addr function), err: (addr buffered-file), ed: (addr exit-descriptor) +11872 # . prologue +11873 55/push-ebp +11874 89/<- %ebp 4/r32/esp +11875 # . save registers +11876 50/push-eax +11877 51/push-ecx +11878 56/push-esi +11879 # esi = stmt +11880 8b/-> *(ebp+8) 6/r32/esi +11881 # var gas/ecx: int = 2 +11882 b9/copy-to-ecx 2/imm32 +11883 # - check at most 1 output +11884 # var output/eax: (addr stmt-var) = stmt->outputs +11885 (lookup *(esi+0x14) *(esi+0x18)) # Stmt1-outputs Stmt1-outputs => eax +11886 { +11887 3d/compare-eax-and 0/imm32 +11888 74/jump-if-= break/disp8 +11889 $check-mu-numberlike-primitive:output: +11890 (check-mu-numberlike-output %eax *(ebp+8) *(ebp+0xc) *(ebp+0x10) *(ebp+0x14)) +11891 (lookup *(eax+8) *(eax+0xc)) # Stmt-var-next Stmt-var-next => eax +11892 3d/compare-eax-and 0/imm32 +11893 0f 85/jump-if-!= $check-mu-numberlike-primitive:error-too-many-outputs/disp32 +11894 # check output is in a register +11895 # --gas +11896 49/decrement-ecx +11897 } +11898 # - check first inout +11899 (lookup *(esi+0xc) *(esi+0x10)) # Stmt1-inouts Stmt1-inouts => eax +11900 { +11901 3d/compare-eax-and 0/imm32 +11902 0f 84/jump-if-= $check-mu-numberlike-primitive:end/disp32 +11903 $check-mu-numberlike-primitive:first-inout: +11904 (check-mu-numberlike-arg %eax *(ebp+8) *(ebp+0xc) *(ebp+0x10) *(ebp+0x14)) +11905 # --gas +11906 49/decrement-ecx +11907 } +11908 # - check second inout +11909 (lookup *(eax+8) *(eax+0xc)) # Stmt-var-next Stmt-var-next => eax +11910 { +11911 3d/compare-eax-and 0/imm32 +11912 74/jump-if-= $check-mu-numberlike-primitive:end/disp8 +11913 $check-mu-numberlike-primitive:second-inout: +11914 # is a second inout allowed? +11915 81 7/subop/compare %ecx 0/imm32 +11916 0f 84/jump-if-= $check-mu-numberlike-primitive:error-too-many-inouts/disp32 +11917 $check-mu-numberlike-primitive:second-inout-permitted: +11918 (check-mu-numberlike-arg %eax *(ebp+8) *(ebp+0xc) *(ebp+0x10) *(ebp+0x14)) +11919 } +11920 $check-mu-numberlike-primitive:third-inout: +11921 # if there's a third arg, raise an error +11922 81 7/subop/compare *(eax+8) 0/imm32 # Stmt-var-next +11923 0f 85/jump-if-!= $check-mu-numberlike-primitive:error-too-many-inouts/disp32 +11924 $check-mu-numberlike-primitive:end: +11925 # . restore registers +11926 5e/pop-to-esi +11927 59/pop-to-ecx +11928 58/pop-to-eax +11929 # . epilogue +11930 89/<- %esp 5/r32/ebp +11931 5d/pop-to-ebp +11932 c3/return +11933 +11934 $check-mu-numberlike-primitive:error-too-many-inouts: +11935 (write-buffered *(ebp+0x10) "fn ") +11936 8b/-> *(ebp+0xc) 0/r32/eax +11937 (lookup *eax *(eax+4)) # Function-name Function-name => eax +11938 (write-buffered *(ebp+0x10) %eax) +11939 (write-buffered *(ebp+0x10) ": stmt ") +11940 (lookup *(esi+4) *(esi+8)) # Stmt1-operation Stmt1-operation => eax +11941 (write-buffered *(ebp+0x10) %eax) +11942 (write-buffered *(ebp+0x10) ": too many inouts; most primitives support at most two arguments, across inouts and outputs\n") +11943 (flush *(ebp+0x10)) +11944 (stop *(ebp+0x14) 1) +11945 # never gets here +11946 +11947 $check-mu-numberlike-primitive:error-too-many-outputs: +11948 (write-buffered *(ebp+0x10) "fn ") +11949 8b/-> *(ebp+0xc) 0/r32/eax +11950 (lookup *eax *(eax+4)) # Function-name Function-name => eax +11951 (write-buffered *(ebp+0x10) %eax) +11952 (write-buffered *(ebp+0x10) ": stmt ") +11953 (lookup *(esi+4) *(esi+8)) # Stmt1-operation Stmt1-operation => eax +11954 (write-buffered *(ebp+0x10) %eax) +11955 (write-buffered *(ebp+0x10) ": too many outputs; most primitives support at most one output\n") +11956 (flush *(ebp+0x10)) +11957 (stop *(ebp+0x14) 1) +11958 # never gets here +11959 +11960 check-mu-numberlike-arg: # v: (addr stmt-var), stmt: (addr stmt), fn: (addr function), err: (addr buffered-file), ed: (addr exit-descriptor) +11961 # . prologue +11962 55/push-ebp +11963 89/<- %ebp 4/r32/esp +11964 # . save registers +11965 50/push-eax +11966 56/push-esi +11967 # var t/esi: (addr type-tree) = lookup(v->value->type) +11968 8b/-> *(ebp+8) 0/r32/eax +11969 (lookup *eax *(eax+4)) # Stmt-var-value Stmt-var-value => eax +11970 (lookup *(eax+8) *(eax+0xc)) # Var-type Var-type => eax +11971 89/<- %esi 0/r32/eax +11972 $check-mu-numberlike-arg:check-literal: +11973 # if t is an int, return +11974 (is-simple-mu-type? %esi 0) # literal => eax +11975 3d/compare-eax-and 0/imm32/false +11976 75/jump-if-!= $check-mu-numberlike-arg:end/disp8 +11977 $check-mu-numberlike-arg:check-addr: +11978 # if t is an addr and v is dereferenced, return +11979 { +11980 (is-mu-addr-type? %esi) # => eax +11981 3d/compare-eax-and 0/imm32/false +11982 74/jump-if-= break/disp8 +11983 8b/-> *(ebp+8) 0/r32/eax +11984 8b/-> *(eax+0x10) 0/r32/eax +11985 3d/compare-eax-and 0/imm32/false +11986 75/jump-if-!= $check-mu-numberlike-arg:end/disp8 +11987 } +11988 $check-mu-numberlike-arg:output-checks: +11989 (check-mu-numberlike-output *(ebp+8) *(ebp+0xc) *(ebp+0x10) *(ebp+0x14) *(ebp+0x18)) +11990 $check-mu-numberlike-arg:end: +11991 # . restore registers +11992 5e/pop-to-esi +11993 58/pop-to-eax +11994 # . epilogue +11995 89/<- %esp 5/r32/ebp +11996 5d/pop-to-ebp +11997 c3/return +11998 +11999 check-mu-numberlike-output: # v: (addr stmt-var), stmt: (addr stmt), fn: (addr function), err: (addr buffered-file), ed: (addr exit-descriptor) +12000 # . prologue +12001 55/push-ebp +12002 89/<- %ebp 4/r32/esp +12003 # . save registers +12004 50/push-eax +12005 56/push-esi +12006 # var t/esi: (addr type-tree) = lookup(v->value->type) +12007 8b/-> *(ebp+8) 0/r32/eax +12008 (lookup *eax *(eax+4)) # Stmt-var-value Stmt-var-value => eax +12009 (lookup *(eax+8) *(eax+0xc)) # Var-type Var-type => eax +12010 89/<- %esi 0/r32/eax +12011 $check-mu-numberlike-output:check-int: +12012 # if t is an int, return +12013 (is-simple-mu-type? %esi 1) # int => eax +12014 3d/compare-eax-and 0/imm32/false +12015 75/jump-if-!= $check-mu-numberlike-output:end/disp8 +12016 $check-mu-numberlike-output:check-boolean: +12017 # if t is a boolean, return +12018 (is-simple-mu-type? %esi 5) # boolean => eax +12019 3d/compare-eax-and 0/imm32/false +12020 75/jump-if-!= $check-mu-numberlike-output:end/disp8 +12021 $check-mu-numberlike-output:check-byte: +12022 # if t is a byte, return +12023 (is-simple-mu-type? %esi 8) # byte => eax +12024 3d/compare-eax-and 0/imm32/false +12025 75/jump-if-!= $check-mu-numberlike-output:end/disp8 +12026 e9/jump $check-mu-numberlike-output:fail/disp32 +12027 $check-mu-numberlike-output:end: +12028 # . restore registers +12029 5e/pop-to-esi +12030 58/pop-to-eax +12031 # . epilogue +12032 89/<- %esp 5/r32/ebp +12033 5d/pop-to-ebp +12034 c3/return +12035 +12036 $check-mu-numberlike-output:fail: +12037 # otherwise raise an error +12038 (write-buffered *(ebp+0x14) "fn ") +12039 8b/-> *(ebp+0x10) 0/r32/eax +12040 (lookup *eax *(eax+4)) # Function-name Function-name => eax +12041 (write-buffered *(ebp+0x14) %eax) +12042 (write-buffered *(ebp+0x14) ": stmt ") +12043 8b/-> *(ebp+0xc) 0/r32/eax +12044 (lookup *(eax+4) *(eax+8)) # Stmt1-operation Stmt1-operation => eax +12045 (write-buffered *(ebp+0x14) %eax) +12046 (write-buffered *(ebp+0x14) ": only non-addr scalar args permitted\n") +12047 (flush *(ebp+0x14)) +12048 (stop *(ebp+0x18) 1) +12049 # never gets here +12050 +12051 check-mu-copy-stmt: # stmt: (addr stmt), fn: (addr function), err: (addr buffered-file), ed: (addr exit-descriptor) +12052 # . prologue +12053 55/push-ebp +12054 89/<- %ebp 4/r32/esp +12055 # . save registers +12056 $check-mu-copy-stmt:end: +12057 # . restore registers +12058 # . epilogue +12059 89/<- %esp 5/r32/ebp +12060 5d/pop-to-ebp +12061 c3/return +12062 +12063 check-mu-copy-to-stmt: # stmt: (addr stmt), fn: (addr function), err: (addr buffered-file), ed: (addr exit-descriptor) +12064 # . prologue +12065 55/push-ebp +12066 89/<- %ebp 4/r32/esp +12067 # . save registers +12068 $check-mu-copy-to-stmt:end: +12069 # . restore registers +12070 # . epilogue +12071 89/<- %esp 5/r32/ebp +12072 5d/pop-to-ebp +12073 c3/return +12074 +12075 check-mu-compare-stmt: # stmt: (addr stmt), fn: (addr function), err: (addr buffered-file), ed: (addr exit-descriptor) +12076 # . prologue +12077 55/push-ebp +12078 89/<- %ebp 4/r32/esp +12079 # . save registers +12080 $check-mu-compare-stmt:end: +12081 # . restore registers +12082 # . epilogue +12083 89/<- %esp 5/r32/ebp +12084 5d/pop-to-ebp +12085 c3/return +12086 +12087 check-mu-address-stmt: # stmt: (addr stmt), fn: (addr function), err: (addr buffered-file), ed: (addr exit-descriptor) +12088 # . prologue +12089 55/push-ebp +12090 89/<- %ebp 4/r32/esp +12091 # . save registers +12092 $check-mu-address-stmt:end: +12093 # . restore registers +12094 # . epilogue +12095 89/<- %esp 5/r32/ebp +12096 5d/pop-to-ebp +12097 c3/return +12098 +12099 check-mu-get-stmt: # stmt: (addr stmt), fn: (addr function), err: (addr buffered-file), ed: (addr exit-descriptor) +12100 # . prologue +12101 55/push-ebp +12102 89/<- %ebp 4/r32/esp +12103 # . save registers +12104 50/push-eax +12105 51/push-ecx +12106 52/push-edx +12107 53/push-ebx +12108 56/push-esi +12109 57/push-edi +12110 # esi = stmt +12111 8b/-> *(ebp+8) 6/r32/esi +12112 # - check for 0 inouts +12113 # var base/ecx: (addr var) = stmt->inouts->value +12114 (lookup *(esi+0xc) *(esi+0x10)) # Stmt1-inouts Stmt1-inouts => eax +12115 3d/compare-eax-and 0/imm32/false +12116 0f 84/jump-if-= $check-mu-get-stmt:error-too-few-inouts/disp32 +12117 (lookup *eax *(eax+4)) # Stmt-var-value Stmt-var-value => eax +12118 89/<- %ecx 0/r32/eax +12119 $check-mu-get-stmt:check-base: +12120 # - check base type +12121 # if it's an 'addr', check that it's in a register +12122 # var base-type/ebx: (addr type-tree) = lookup(base->type) +12123 (lookup *(ecx+8) *(ecx+0xc)) # Var-type Var-type => eax +12124 89/<- %ebx 0/r32/eax +12125 { +12126 81 7/subop/compare *ebx 0/imm32/false # Type-tree-is-atom +12127 0f 85/jump-if-!= break/disp32 +12128 $check-mu-get-stmt:base-is-compound: +12129 # if (type->left != addr) break +12130 (lookup *(ebx+4) *(ebx+8)) # Type-tree-left Type-tree-left => eax +12131 (is-simple-mu-type? %eax 2) # => eax +12132 3d/compare-eax-and 0/imm32/false +12133 74/jump-if-= break/disp8 +12134 $check-mu-get-stmt:base-is-addr: +12135 # now check for register +12136 81 7/subop/compare *(ecx+0x18) 0/imm32 # Var-register +12137 0f 84/jump-if-= $check-mu-get-stmt:error-base-type-addr-but-not-register/disp32 +12138 $check-mu-get-stmt:base-is-addr-in-register: +12139 # type->left is now an addr; skip it +12140 (lookup *(ebx+0xc) *(ebx+0x10)) # Type-tree-right Type-tree-right => eax +12141 81 7/subop/compare *(eax+0xc) 0/imm32 # Type-tree-right +12142 0f 85/jump-if-!= $check-mu-get-stmt:error-bad-base/disp32 +12143 $check-mu-get-stmt:base-is-addr-to-atom-in-register: +12144 (lookup *(eax+4) *(eax+8)) # Type-tree-left Type-tree-left => eax +12145 89/<- %ebx 0/r32/eax +12146 } +12147 $check-mu-get-stmt:check-base-typeinfo: +12148 # ensure type is a container +12149 # var base-type-id/ebx: type-id = base-type->value +12150 8b/-> *(ebx+4) 3/r32/ebx # Type-tree-value +12151 (is-container? %ebx) # => eax +12152 3d/compare-eax-and 0/imm32/false +12153 0f 84/jump-if-= $check-mu-get-stmt:error-bad-base/disp32 +12154 # var base-typeinfo/edx: (addr typeinfo) = find-typeinfo(base-type-id) +12155 # . var container/ecx: (handle typeinfo) +12156 68/push 0/imm32 +12157 68/push 0/imm32 +12158 89/<- %ecx 4/r32/esp +12159 # . +12160 (find-typeinfo %ebx %ecx) +12161 (lookup *ecx *(ecx+4)) # => eax +12162 # . reclaim container +12163 81 0/subop/add %esp 8/imm32 +12164 # . +12165 89/<- %edx 0/r32/eax +12166 # var offset/ecx: (addr stmt-var) = stmt->inouts->next +12167 (lookup *(esi+0xc) *(esi+0x10)) # Stmt1-inouts Stmt1-inouts => eax +12168 (lookup *(eax+8) *(eax+0xc)) # Stmt-var-next Stmt-var-next => eax +12169 89/<- %ecx 0/r32/eax +12170 # - check for 1 inout +12171 3d/compare-eax-and 0/imm32/false +12172 0f 84/jump-if-= $check-mu-get-stmt:error-too-few-inouts/disp32 +12173 # var offset/ecx: (addr var) = lookup(offset->value) +12174 (lookup *ecx *(ecx+4)) # Stmt-var-value Stmt-var-value => eax +12175 89/<- %ecx 0/r32/eax +12176 # - check for valid field +12177 81 7/subop/compare *(ecx+0x14) -1/imm32/uninitialized # Var-offset +12178 0f 84/jump-if-= $check-mu-get-stmt:error-bad-field/disp32 +12179 # - check for too many inouts +12180 (lookup *(esi+0xc) *(esi+0x10)) # Stmt1-inouts Stmt1-inouts => eax +12181 (lookup *(eax+8) *(eax+0xc)) # Stmt-var-next Stmt-var-next => eax +12182 (lookup *(eax+8) *(eax+0xc)) # Stmt-var-next Stmt-var-next => eax +12183 3d/compare-eax-and 0/imm32/false +12184 0f 85/jump-if-!= $check-mu-get-stmt:error-too-many-inouts/disp32 +12185 # var output/edi: (addr var) = stmt->outputs->value +12186 (lookup *(esi+0x14) *(esi+0x18)) # Stmt1-outputs Stmt1-outputs => eax +12187 # - check for 0 outputs +12188 3d/compare-eax-and 0/imm32/false +12189 0f 84/jump-if-= $check-mu-get-stmt:error-too-few-outputs/disp32 +12190 (lookup *eax *(eax+4)) # Stmt-var-value Stmt-var-value => eax +12191 89/<- %edi 0/r32/eax +12192 $check-mu-get-stmt:check-output-type: +12193 # - check output type +12194 # must be in register +12195 (lookup *(edi+0x18) *(edi+0x1c)) # Var-register Var-register => eax +12196 3d/compare-eax-and 0/imm32 +12197 0f 84/jump-if-= $check-mu-get-stmt:error-output-not-in-register/disp32 +12198 # must have a non-atomic type +12199 (lookup *(edi+8) *(edi+0xc)) # Var-type Var-type => eax +12200 81 7/subop/compare *eax 0/imm32/false # Type-tree-is-atom +12201 0f 85/jump-if-!= $check-mu-get-stmt:error-output-type-not-address/disp32 +12202 # type must start with (addr ...) +12203 (lookup *(eax+4) *(eax+8)) # Type-tree-left Type-tree-left => eax +12204 (is-simple-mu-type? %eax 2) # => eax +12205 3d/compare-eax-and 0/imm32/false +12206 0f 84/jump-if-= $check-mu-get-stmt:error-output-type-not-address/disp32 +12207 $check-mu-get-stmt:check-output-type-match: +12208 # payload of addr type must match 'type' definition +12209 (lookup *(edi+8) *(edi+0xc)) # Var-type Var-type => eax +12210 (lookup *(eax+0xc) *(eax+0x10)) # Type-tree-right Type-tree-right => eax +12211 # if (payload->right == null) payload = payload->left +12212 81 7/subop/compare *(eax+0xc) 0/imm32/null # Type-tree-right +12213 { +12214 75/jump-if-!= break/disp8 +12215 (lookup *(eax+4) *(eax+8)) # Type-tree-left Type-tree-left => eax +12216 } +12217 89/<- %edi 0/r32/eax +12218 # . var output-name/ecx: (addr array byte) +12219 (lookup *ecx *(ecx+4)) # Var-name Var-name => eax +12220 89/<- %ecx 0/r32/eax +12221 # . var base-typeinfo-entry/eax: (addr handle typeinfo-entry) +12222 (lookup *(edx+4) *(edx+8)) # Typeinfo-fields Typeinfo-fields => eax +12223 (get %eax %ecx 0x10) # => eax +12224 # . +12225 (lookup *eax *(eax+4)) # => eax +12226 (lookup *eax *(eax+4)) # Typeinfo-entry-input-var Typeinfo-entry-input-var => eax +12227 (lookup *(eax+8) *(eax+0xc)) # Var-type Var-type => eax +12228 # . +12229 (type-equal? %edi %eax) # => eax +12230 3d/compare-eax-and 0/imm32/false +12231 0f 84/jump-if-= $check-mu-get-stmt:error-bad-output-type/disp32 +12232 # - check for too many outputs +12233 (lookup *(esi+0x14) *(esi+0x18)) # Stmt1-outputs Stmt1-outputs => eax +12234 (lookup *(eax+8) *(eax+0xc)) # Stmt-var-next Stmt-var-next => eax +12235 3d/compare-eax-and 0/imm32/false +12236 0f 85/jump-if-!= $check-mu-get-stmt:error-too-many-outputs/disp32 +12237 $check-mu-get-stmt:end: +12238 # . restore registers +12239 5f/pop-to-edi +12240 5e/pop-to-esi +12241 5b/pop-to-ebx +12242 5a/pop-to-edx +12243 59/pop-to-ecx +12244 58/pop-to-eax +12245 # . epilogue +12246 89/<- %esp 5/r32/ebp +12247 5d/pop-to-ebp +12248 c3/return +12249 +12250 $check-mu-get-stmt:error-too-few-inouts: +12251 (write-buffered *(ebp+0x10) "fn ") +12252 8b/-> *(ebp+0xc) 0/r32/eax +12253 (lookup *eax *(eax+4)) # Function-name Function-name => eax +12254 (write-buffered *(ebp+0x10) %eax) +12255 (write-buffered *(ebp+0x10) ": stmt get: too few inouts (2 required)\n") +12256 (flush *(ebp+0x10)) +12257 (stop *(ebp+0x14) 1) +12258 # never gets here +12259 +12260 $check-mu-get-stmt:error-too-many-inouts: +12261 (write-buffered *(ebp+0x10) "fn ") +12262 8b/-> *(ebp+0xc) 0/r32/eax +12263 (lookup *eax *(eax+4)) # Function-name Function-name => eax +12264 (write-buffered *(ebp+0x10) %eax) +12265 (write-buffered *(ebp+0x10) ": stmt get: too many inouts (2 required)\n") +12266 (flush *(ebp+0x10)) +12267 (stop *(ebp+0x14) 1) +12268 # never gets here +12269 +12270 $check-mu-get-stmt:error-too-few-outputs: +12271 (write-buffered *(ebp+0x10) "fn ") +12272 8b/-> *(ebp+0xc) 0/r32/eax +12273 (lookup *eax *(eax+4)) # Function-name Function-name => eax +12274 (write-buffered *(ebp+0x10) %eax) +12275 (write-buffered *(ebp+0x10) ": stmt get: must have an output\n") +12276 (flush *(ebp+0x10)) +12277 (stop *(ebp+0x14) 1) +12278 # never gets here +12279 +12280 $check-mu-get-stmt:error-too-many-outputs: +12281 (write-buffered *(ebp+0x10) "fn ") +12282 8b/-> *(ebp+0xc) 0/r32/eax +12283 (lookup *eax *(eax+4)) # Function-name Function-name => eax +12284 (write-buffered *(ebp+0x10) %eax) +12285 (write-buffered *(ebp+0x10) ": stmt get: too many outputs (1 required)\n") +12286 (flush *(ebp+0x10)) +12287 (stop *(ebp+0x14) 1) +12288 # never gets here +12289 +12290 $check-mu-get-stmt:error-bad-base: +12291 # error("fn " fn ": stmt get: var '" base->name "' must have a 'type' definition\n") +12292 (write-buffered *(ebp+0x10) "fn ") +12293 8b/-> *(ebp+0xc) 0/r32/eax +12294 (lookup *eax *(eax+4)) # Function-name Function-name => eax +12295 (write-buffered *(ebp+0x10) %eax) +12296 (write-buffered *(ebp+0x10) ": stmt get: var '") +12297 (lookup *(esi+0xc) *(esi+0x10)) # Stmt1-inouts Stmt1-inouts => eax +12298 (lookup *eax *(eax+4)) # Stmt-var-value Stmt-var-value => eax +12299 (lookup *eax *(eax+4)) # Var-name Var-name => eax +12300 (write-buffered *(ebp+0x10) %eax) +12301 (write-buffered *(ebp+0x10) "' must have a 'type' definition\n") +12302 (flush *(ebp+0x10)) +12303 (stop *(ebp+0x14) 1) +12304 # never gets here +12305 +12306 $check-mu-get-stmt:error-base-type-addr-but-not-register: +12307 (write-buffered *(ebp+0x10) "fn ") +12308 8b/-> *(ebp+0xc) 0/r32/eax +12309 (lookup *eax *(eax+4)) # Function-name Function-name => eax +12310 (write-buffered *(ebp+0x10) %eax) +12311 (write-buffered *(ebp+0x10) ": stmt get: var '") +12312 (lookup *(esi+0xc) *(esi+0x10)) # Stmt1-inouts Stmt1-inouts => eax +12313 (lookup *eax *(eax+4)) # Stmt-var-value Stmt-var-value => eax +12314 (lookup *eax *(eax+4)) # Var-name Var-name => eax +12315 (write-buffered *(ebp+0x10) %eax) +12316 (write-buffered *(ebp+0x10) "' is an 'addr' type, and so must live in a register\n") +12317 (flush *(ebp+0x10)) +12318 (stop *(ebp+0x14) 1) +12319 # never gets here +12320 +12321 $check-mu-get-stmt:error-bad-field: +12322 # error("fn " fn ": stmt get: type " type " has no member called '" curr->name "'\n") +12323 (write-buffered *(ebp+0x10) "fn ") +12324 8b/-> *(ebp+0xc) 0/r32/eax +12325 (lookup *eax *(eax+4)) # Function-name Function-name => eax +12326 (write-buffered *(ebp+0x10) %eax) +12327 (write-buffered *(ebp+0x10) ": stmt get: type '") +12328 # . write(Type-id->data[tmp]) +12329 bf/copy-to-edi Type-id/imm32 +12330 (write-buffered *(ebp+0x10) *(edi+ebx<<2+0xc)) +12331 # . +12332 (write-buffered *(ebp+0x10) "' has no member called '") +12333 (lookup *ecx *(ecx+4)) # Var-name Var-name => eax +12334 (write-buffered *(ebp+0x10) %eax) +12335 (write-buffered *(ebp+0x10) "'\n") +12336 (flush *(ebp+0x10)) +12337 (stop *(ebp+0x14) 1) +12338 # never gets here 12339 -12340 check-mu-allocate-stmt: # stmt: (addr stmt), fn: (addr function), err: (addr buffered-file), ed: (addr exit-descriptor) -12341 # . prologue -12342 55/push-ebp -12343 89/<- %ebp 4/r32/esp -12344 # . save registers -12345 $check-mu-allocate-stmt:end: -12346 # . restore registers -12347 # . epilogue -12348 89/<- %esp 5/r32/ebp -12349 5d/pop-to-ebp -12350 c3/return -12351 -12352 check-mu-populate-stmt: # stmt: (addr stmt), fn: (addr function), err: (addr buffered-file), ed: (addr exit-descriptor) -12353 # . prologue -12354 55/push-ebp -12355 89/<- %ebp 4/r32/esp -12356 # . save registers -12357 $check-mu-populate-stmt:end: -12358 # . restore registers -12359 # . epilogue -12360 89/<- %esp 5/r32/ebp -12361 5d/pop-to-ebp -12362 c3/return -12363 -12364 check-mu-call: # stmt: (addr stmt), callee: (addr function), fn: (addr function), err: (addr buffered-file), ed: (addr exit-descriptor) -12365 # . prologue -12366 55/push-ebp -12367 89/<- %ebp 4/r32/esp -12368 # var type-parameters: (addr table (handle array byte) (addr type-tree) 8) -12369 68/push 0/imm32 -12370 # var type-parameters-storage: (table (handle array byte) (addr type-tree) 8) -12371 81 5/subop/subtract %esp 0x60/imm32 -12372 68/push 0x60/imm32/size -12373 68/push 0/imm32/read -12374 68/push 0/imm32/write -12375 # save a pointer to type-parameters-storage at type-parameters -12376 89/<- *(ebp-4) 4/r32/esp -12377 (clear-stream *(ebp-4)) -12378 # . save registers -12379 50/push-eax -12380 51/push-ecx -12381 52/push-edx -12382 53/push-ebx -12383 56/push-esi -12384 57/push-edi -12385 # esi = stmt -12386 8b/-> *(ebp+8) 6/r32/esi -12387 # edi = callee -12388 8b/-> *(ebp+0xc) 7/r32/edi -12389 # var inouts/ecx: (addr stmt-var) = lookup(stmt->inouts) -12390 (lookup *(esi+0xc) *(esi+0x10)) # Stmt1-inouts Stmt1-inouts => eax -12391 89/<- %ecx 0/r32/eax -12392 # var expected/edx: (addr list var) = lookup(f->inouts) -12393 (lookup *(edi+8) *(edi+0xc)) # Function-inouts Function-inouts => eax -12394 89/<- %edx 0/r32/eax -12395 { -12396 $check-mu-call:check-for-inouts: -12397 # if (inouts == 0) break -12398 81 7/subop/compare %ecx 0/imm32 -12399 0f 84/jump-if-= break/disp32 -12400 # if (expected == 0) error -12401 81 7/subop/compare %edx 0/imm32 -12402 0f 84/jump-if-= break/disp32 -12403 $check-mu-call:check-inout-type: -12404 # var v/eax: (addr v) = lookup(inouts->value) -12405 (lookup *ecx *(ecx+4)) # Stmt-var-value Stmt-var-value => eax -12406 # var t/ebx: (addr type-tree) = lookup(v->type) -12407 (lookup *(eax+8) *(eax+0xc)) # Var-type Var-type => eax -12408 89/<- %ebx 0/r32/eax -12409 # if (inouts->is-deref?) t = t->right # TODO: check that t->left is an addr -12410 81 7/subop/compare *(ecx+0x10) 0/imm32/false # Stmt-var-is-deref -12411 { -12412 74/jump-if-= break/disp8 -12413 (lookup *(ebx+0xc) *(ebx+0x10)) # Type-tree-right Type-tree-right => eax -12414 89/<- %ebx 0/r32/eax -12415 # if t->right is null, t = t->left -12416 81 7/subop/compare *(ebx+0xc) 0/imm32 # Type-tree-right -12417 75/jump-if-!= break/disp8 -12418 (lookup *(ebx+4) *(ebx+8)) # Type-tree-left Type-tree-left => eax -12419 89/<- %ebx 0/r32/eax -12420 } -12421 # var v2/eax: (addr v) = lookup(expected->value) -12422 (lookup *edx *(edx+4)) # List-value List-value => eax -12423 # var t2/eax: (addr type-tree) = lookup(v2->type) -12424 (lookup *(eax+8) *(eax+0xc)) # Var-type Var-type => eax -12425 # if (t != t2) error -12426 (type-match? %eax %ebx *(ebp-4)) # => eax -12427 3d/compare-eax-and 0/imm32/false -12428 { -12429 0f 85/jump-if-!= break/disp32 -12430 (write-buffered *(ebp+0x14) "fn ") -12431 8b/-> *(ebp+0x10) 0/r32/eax -12432 (lookup *eax *(eax+4)) # Function-name Function-name => eax -12433 (write-buffered *(ebp+0x14) %eax) -12434 (write-buffered *(ebp+0x14) ": call ") -12435 (lookup *edi *(edi+4)) # Function-name Function-name => eax -12436 (write-buffered *(ebp+0x14) %eax) -12437 (write-buffered *(ebp+0x14) ": type for inout '") -12438 (lookup *ecx *(ecx+4)) # Stmt-var-value Stmt-var-value => eax -12439 (lookup *eax *(eax+4)) # Var-name Var-name => eax -12440 (write-buffered *(ebp+0x14) %eax) -12441 (write-buffered *(ebp+0x14) "' is not right\n") -12442 (flush *(ebp+0x14)) -12443 (stop *(ebp+0x18) 1) -12444 } -12445 $check-mu-call:continue-to-next-inout: -12446 # inouts = lookup(inouts->next) -12447 (lookup *(ecx+8) *(ecx+0xc)) # Stmt-var-next Stmt-var-next => eax -12448 89/<- %ecx 0/r32/eax -12449 # expected = lookup(expected->next) -12450 (lookup *(edx+8) *(edx+0xc)) # List-next List-next => eax -12451 89/<- %edx 0/r32/eax -12452 # -12453 e9/jump loop/disp32 -12454 } -12455 $check-mu-call:check-inout-count: -12456 # if (inouts == expected) proceed -12457 39/compare %ecx 2/r32/edx -12458 { -12459 0f 84/jump-if-= break/disp32 -12460 # exactly one of the two is null -12461 # if (inouts == 0) error("too many inouts") -12462 { -12463 81 7/subop/compare %ecx 0/imm32 -12464 0f 84/jump-if-= break/disp32 -12465 (write-buffered *(ebp+0x14) "fn ") -12466 8b/-> *(ebp+0x10) 0/r32/eax -12467 (lookup *eax *(eax+4)) # Function-name Function-name => eax -12468 (write-buffered *(ebp+0x14) %eax) -12469 (write-buffered *(ebp+0x14) ": call ") -12470 (lookup *edi *(edi+4)) # Function-name Function-name => eax -12471 (write-buffered *(ebp+0x14) %eax) -12472 (write-buffered *(ebp+0x14) ": too many inouts\n") -12473 (flush *(ebp+0x14)) -12474 (stop *(ebp+0x18) 1) -12475 } -12476 # if (expected == 0) error("too few inouts") -12477 { -12478 81 7/subop/compare %edx 0/imm32 -12479 0f 84/jump-if-= break/disp32 -12480 (write-buffered *(ebp+0x14) "fn ") -12481 8b/-> *(ebp+0x10) 0/r32/eax -12482 (lookup *eax *(eax+4)) # Function-name Function-name => eax -12483 (write-buffered *(ebp+0x14) %eax) -12484 (write-buffered *(ebp+0x14) ": call ") -12485 (lookup *edi *(edi+4)) # Function-name Function-name => eax -12486 (write-buffered *(ebp+0x14) %eax) -12487 (write-buffered *(ebp+0x14) ": too few inouts\n") -12488 (flush *(ebp+0x14)) -12489 (stop *(ebp+0x18) 1) -12490 } -12491 } -12492 $check-mu-call:check-outputs: -12493 # var outputs/ecx: (addr stmt-var) = lookup(stmt->outputs) -12494 (lookup *(esi+0x14) *(esi+0x18)) # Stmt1-outputs Stmt1-outputs => eax -12495 89/<- %ecx 0/r32/eax -12496 # var expected/edx: (addr list var) = lookup(f->outputs) -12497 (lookup *(edi+0x10) *(edi+0x14)) # Function-outputs Function-outputs => eax -12498 89/<- %edx 0/r32/eax -12499 { -12500 $check-mu-call:check-for-outputs: -12501 # if (outputs == 0) break -12502 81 7/subop/compare %ecx 0/imm32 -12503 0f 84/jump-if-= break/disp32 -12504 # if (expected == 0) error -12505 81 7/subop/compare %edx 0/imm32 -12506 0f 84/jump-if-= break/disp32 -12507 $check-mu-call:check-output-type: -12508 # var v/eax: (addr v) = lookup(outputs->value) -12509 (lookup *ecx *(ecx+4)) # Stmt-var-value Stmt-var-value => eax -12510 # var t/ebx: (addr type-tree) = lookup(v->type) -12511 (lookup *(eax+8) *(eax+0xc)) # Var-type Var-type => eax -12512 89/<- %ebx 0/r32/eax -12513 # if (outputs->is-deref?) t = t->right # TODO: check that t->left is an addr -12514 81 7/subop/compare *(ecx+0x10) 0/imm32/false # Stmt-var-is-deref -12515 { -12516 74/jump-if-= break/disp8 -12517 (lookup *(ebx+0xc) *(ebx+0x10)) # Type-tree-right Type-tree-right => eax -12518 89/<- %ebx 0/r32/eax -12519 } -12520 # var v2/eax: (addr v) = lookup(expected->value) -12521 (lookup *edx *(edx+4)) # List-value List-value => eax -12522 # var t2/eax: (addr type-tree) = lookup(v2->type) -12523 (lookup *(eax+8) *(eax+0xc)) # Var-type Var-type => eax -12524 # if (t != t2) error -12525 (type-match? %eax %ebx *(ebp-4)) # => eax -12526 3d/compare-eax-and 0/imm32/false -12527 { -12528 0f 85/jump-if-!= break/disp32 -12529 (write-buffered *(ebp+0x14) "fn ") -12530 8b/-> *(ebp+0x10) 0/r32/eax -12531 (lookup *eax *(eax+4)) # Function-name Function-name => eax -12532 (write-buffered *(ebp+0x14) %eax) -12533 (write-buffered *(ebp+0x14) ": call ") -12534 (lookup *edi *(edi+4)) # Function-name Function-name => eax -12535 (write-buffered *(ebp+0x14) %eax) -12536 (write-buffered *(ebp+0x14) ": type for output '") -12537 (lookup *ecx *(ecx+4)) # Stmt-var-value Stmt-var-value => eax -12538 (lookup *eax *(eax+4)) # Var-name Var-name => eax -12539 (write-buffered *(ebp+0x14) %eax) -12540 (write-buffered *(ebp+0x14) "' is not right\n") -12541 (flush *(ebp+0x14)) -12542 (stop *(ebp+0x18) 1) -12543 } -12544 $check-mu-call:check-output-register: -12545 # var v/eax: (addr v) = lookup(outputs->value) -12546 (lookup *ecx *(ecx+4)) # Stmt-var-value Stmt-var-value => eax -12547 # var r/ebx: (addr array byte) = lookup(v->register) -12548 (lookup *(eax+18) *(eax+0x1c)) # Var-register Var-register => eax -12549 89/<- %ebx 0/r32/eax -12550 # var v2/eax: (addr v) = lookup(expected->value) -12551 (lookup *edx *(edx+4)) # Stmt-var-value Stmt-var-value => eax -12552 # var r2/eax: (addr array byte) = lookup(v2->register) -12553 (lookup *(eax+18) *(eax+0x1c)) # Var-register Var-register => eax -12554 # if (r != r2) error -12555 (string-equal? %eax %ebx) # => eax -12556 3d/compare-eax-and 0/imm32/false -12557 { -12558 0f 85/jump-if-!= break/disp32 -12559 (write-buffered *(ebp+0x14) "fn ") -12560 8b/-> *(ebp+0x10) 0/r32/eax -12561 (lookup *eax *(eax+4)) # Function-name Function-name => eax -12562 (write-buffered *(ebp+0x14) %eax) -12563 (write-buffered *(ebp+0x14) ": call ") -12564 (lookup *edi *(edi+4)) # Function-name Function-name => eax -12565 (write-buffered *(ebp+0x14) %eax) -12566 (write-buffered *(ebp+0x14) ": register for output '") -12567 (lookup *ecx *(ecx+4)) # Stmt-var-value Stmt-var-value => eax -12568 (lookup *eax *(eax+4)) # Var-name Var-name => eax -12569 (write-buffered *(ebp+0x14) %eax) -12570 (write-buffered *(ebp+0x14) "' is not right\n") -12571 (flush *(ebp+0x14)) -12572 (stop *(ebp+0x18) 1) -12573 } -12574 $check-mu-call:continue-to-next-output: -12575 # outputs = lookup(outputs->next) -12576 (lookup *(ecx+8) *(ecx+0xc)) # Stmt-var-next Stmt-var-next => eax -12577 89/<- %ecx 0/r32/eax -12578 # expected = lookup(expected->next) -12579 (lookup *(edx+8) *(edx+0xc)) # List-next List-next => eax -12580 89/<- %edx 0/r32/eax -12581 # -12582 e9/jump loop/disp32 -12583 } -12584 $check-mu-call:check-output-count: -12585 # if (outputs == expected) proceed -12586 39/compare %ecx 2/r32/edx -12587 { -12588 0f 84/jump-if-= break/disp32 -12589 # exactly one of the two is null -12590 # if (outputs == 0) error("too many outputs") -12591 { -12592 81 7/subop/compare %ecx 0/imm32 -12593 0f 84/jump-if-= break/disp32 -12594 (write-buffered *(ebp+0x14) "fn ") -12595 8b/-> *(ebp+0x10) 0/r32/eax -12596 (lookup *eax *(eax+4)) # Function-name Function-name => eax -12597 (write-buffered *(ebp+0x14) %eax) -12598 (write-buffered *(ebp+0x14) ": call ") -12599 (lookup *edi *(edi+4)) # Function-name Function-name => eax -12600 (write-buffered *(ebp+0x14) %eax) -12601 (write-buffered *(ebp+0x14) ": too many outputs\n") -12602 (flush *(ebp+0x14)) -12603 (stop *(ebp+0x18) 1) -12604 } -12605 # if (expected == 0) error("too few outputs") -12606 { -12607 81 7/subop/compare %edx 0/imm32 -12608 0f 84/jump-if-= break/disp32 -12609 (write-buffered *(ebp+0x14) "fn ") -12610 8b/-> *(ebp+0x10) 0/r32/eax -12611 (lookup *eax *(eax+4)) # Function-name Function-name => eax -12612 (write-buffered *(ebp+0x14) %eax) -12613 (write-buffered *(ebp+0x14) ": call ") -12614 (lookup *edi *(edi+4)) # Function-name Function-name => eax -12615 (write-buffered *(ebp+0x14) %eax) -12616 (write-buffered *(ebp+0x14) ": too few outputs\n") -12617 (flush *(ebp+0x14)) -12618 (stop *(ebp+0x18) 1) -12619 } -12620 } -12621 $check-mu-call:end: -12622 # . restore registers -12623 5f/pop-to-edi -12624 5e/pop-to-esi -12625 5b/pop-to-ebx -12626 5a/pop-to-edx -12627 59/pop-to-ecx -12628 58/pop-to-eax -12629 # . reclaim locals exclusively on the stack -12630 81 0/subop/add %esp 0x70/imm32 -12631 # . epilogue -12632 89/<- %esp 5/r32/ebp -12633 5d/pop-to-ebp -12634 c3/return -12635 -12636 # like type-equal? but takes literals into account -12637 type-match?: # def: (addr type-tree), call: (addr type-tree), type-parameters: (addr table (handle array byte) (addr type-tree)) -> result/eax: boolean -12638 # . prologue -12639 55/push-ebp -12640 89/<- %ebp 4/r32/esp -12641 # if (call == literal) return true # TODO: more precise -12642 (is-simple-mu-type? *(ebp+0xc) 0) # literal => eax -12643 3d/compare-eax-and 0/imm32/false -12644 b8/copy-to-eax 1/imm32/true -12645 75/jump-if-!= $type-match?:end/disp8 -12646 $type-match?:baseline: -12647 # otherwise fall back -12648 (type-component-match? *(ebp+8) *(ebp+0xc) *(ebp+0x10)) # => eax -12649 $type-match?:end: -12650 # . epilogue -12651 89/<- %esp 5/r32/ebp -12652 5d/pop-to-ebp -12653 c3/return -12654 -12655 type-component-match?: # def: (addr type-tree), call: (addr type-tree), type-parameters: (addr table (handle array byte) (addr type-tree)) -> result/eax: boolean -12656 # . prologue -12657 55/push-ebp -12658 89/<- %ebp 4/r32/esp -12659 # . save registers -12660 51/push-ecx -12661 52/push-edx -12662 53/push-ebx -12663 # ecx = def -12664 8b/-> *(ebp+8) 1/r32/ecx -12665 # edx = call -12666 8b/-> *(ebp+0xc) 2/r32/edx -12667 $type-component-match?:compare-addr: -12668 # if (def == call) return true -12669 8b/-> %ecx 0/r32/eax # Var-type -12670 39/compare %edx 0/r32/eax # Var-type -12671 b8/copy-to-eax 1/imm32/true -12672 0f 84/jump-if-= $type-component-match?:end/disp32 -12673 # if def is a type parameter, return true -12674 { -12675 $type-component-match?:check-type-parameter: -12676 81 7/subop/compare *ecx 0/imm32/false # Type-tree-is-atom -12677 74/jump-if-= break/disp8 -12678 81 7/subop/compare *(ecx+4) 0xa/imm32/type-parameter # Type-tree-value -12679 75/jump-if-!= break/disp8 -12680 $type-component-match?:type-parameter: -12681 (type-parameter-match? *(ecx+8) *(ecx+0xc) %edx *(ebp+0x10)) # => eax -12682 e9/jump $type-component-match?:end/disp32 -12683 } -12684 $type-component-match?:compare-atom-state: -12685 # if (def->is-atom? != call->is-atom?) return false -12686 8b/-> *ecx 3/r32/ebx # Type-tree-is-atom -12687 39/compare *edx 3/r32/ebx # Type-tree-is-atom -12688 b8/copy-to-eax 0/imm32/false -12689 0f 85/jump-if-!= $type-component-match?:end/disp32 -12690 # if def->is-atom? return (def->value == call->value) -12691 { -12692 $type-component-match?:check-atom: -12693 81 7/subop/compare %ebx 0/imm32/false -12694 74/jump-if-= break/disp8 -12695 $type-component-match?:is-atom: -12696 8b/-> *(ecx+4) 0/r32/eax # Type-tree-value -12697 39/compare *(edx+4) 0/r32/eax # Type-tree-value -12698 0f 94/set-if-= %al -12699 81 4/subop/and %eax 0xff/imm32 -12700 e9/jump $type-component-match?:end/disp32 -12701 } -12702 $type-component-match?:check-left: -12703 # if (!type-component-match?(def->left, call->left)) return false -12704 (lookup *(ecx+4) *(ecx+8)) # Type-tree-left Type-tree-left => eax -12705 89/<- %ebx 0/r32/eax -12706 (lookup *(edx+4) *(edx+8)) # Type-tree-left Type-tree-left => eax -12707 (type-component-match? %ebx %eax *(ebp+0x10)) # => eax -12708 3d/compare-eax-and 0/imm32/false -12709 74/jump-if-= $type-component-match?:end/disp8 -12710 $type-component-match?:check-right: -12711 # return type-component-match?(def->right, call->right) -12712 (lookup *(ecx+0xc) *(ecx+0x10)) # Type-tree-right Type-tree-right => eax -12713 89/<- %ebx 0/r32/eax -12714 (lookup *(edx+0xc) *(edx+0x10)) # Type-tree-right Type-tree-right => eax -12715 (type-component-match? %ebx %eax *(ebp+0x10)) # => eax -12716 $type-component-match?:end: -12717 # . restore registers -12718 5b/pop-to-ebx -12719 5a/pop-to-edx -12720 59/pop-to-ecx -12721 # . epilogue -12722 89/<- %esp 5/r32/ebp -12723 5d/pop-to-ebp -12724 c3/return -12725 -12726 type-parameter-match?: # type-parameter-name: (handle array byte), type: (addr type-tree), type-parameters: (addr table (handle array byte) (addr type-tree)) -> result/eax: boolean -12727 # . prologue -12728 55/push-ebp -12729 89/<- %ebp 4/r32/esp -12730 # . save registers -12731 51/push-ecx -12732 # -12733 (get-or-insert-handle *(ebp+0x14) *(ebp+8) *(ebp+0xc) 0xc) # => eax -12734 # if parameter wasn't saved, save it -12735 { -12736 81 7/subop/compare *eax 0/imm32 -12737 75/jump-if-!= break/disp8 -12738 8b/-> *(ebp+0x10) 1/r32/ecx -12739 89/<- *eax 1/r32/ecx -12740 } -12741 # -12742 (type-equal? *(ebp+0x10) *eax) # => eax -12743 $type-parameter-match?:end: -12744 # . restore registers -12745 59/pop-to-ecx -12746 # . epilogue -12747 89/<- %esp 5/r32/ebp -12748 5d/pop-to-ebp -12749 c3/return -12750 -12751 size-of: # v: (addr var) -> result/eax: int -12752 # . prologue -12753 55/push-ebp -12754 89/<- %ebp 4/r32/esp -12755 # . save registers -12756 51/push-ecx -12757 # var t/ecx: (addr type-tree) = lookup(v->type) -12758 8b/-> *(ebp+8) 1/r32/ecx -12759 #? (write-buffered Stderr "size-of ") -12760 #? (write-int32-hex-buffered Stderr %ecx) -12761 #? (write-buffered Stderr Newline) -12762 #? (write-buffered Stderr "type allocid: ") -12763 #? (write-int32-hex-buffered Stderr *(ecx+8)) -12764 #? (write-buffered Stderr Newline) -12765 #? (flush Stderr) -12766 (lookup *(ecx+8) *(ecx+0xc)) # Var-type Var-type => eax -12767 89/<- %ecx 0/r32/eax -12768 # if is-mu-array?(t) return size-of-array(t) -12769 { -12770 (is-mu-array? %ecx) # => eax -12771 3d/compare-eax-and 0/imm32/false -12772 74/jump-if-= break/disp8 -12773 (size-of-array %ecx) # => eax -12774 eb/jump $size-of:end/disp8 -12775 } -12776 # if (!t->is-atom?) t = lookup(t->left) -12777 { -12778 81 7/subop/compare *ecx 0/imm32/false # Type-tree-is-atom -12779 75/jump-if-!= break/disp8 -12780 (lookup *(ecx+4) *(ecx+8)) # Type-tree-left Type-tree-left => eax -12781 89/<- %ecx 0/r32/eax -12782 } -12783 # TODO: assert t->is-atom? -12784 (size-of-type-id *(ecx+4)) # Type-tree-value => eax -12785 $size-of:end: -12786 # . restore registers -12787 59/pop-to-ecx -12788 # . epilogue -12789 89/<- %esp 5/r32/ebp -12790 5d/pop-to-ebp -12791 c3/return -12792 -12793 size-of-deref: # v: (addr var) -> result/eax: int -12794 # . prologue -12795 55/push-ebp -12796 89/<- %ebp 4/r32/esp -12797 # . save registers -12798 51/push-ecx -12799 # var t/ecx: (addr type-tree) = lookup(v->type) -12800 8b/-> *(ebp+8) 1/r32/ecx -12801 (lookup *(ecx+8) *(ecx+0xc)) # Var-type Var-type => eax -12802 89/<- %ecx 0/r32/eax -12803 # TODO: assert(t is an addr) -12804 # t = lookup(t->right) -12805 (lookup *(ecx+0xc) *(ecx+0x10)) # Type-tree-right Type-tree-right => eax -12806 89/<- %ecx 0/r32/eax -12807 # if is-mu-array?(t) return size-of-array(t) -12808 { -12809 (is-mu-array? %ecx) # => eax -12810 3d/compare-eax-and 0/imm32/false -12811 74/jump-if-= break/disp8 -12812 (size-of-array %ecx) # => eax -12813 eb/jump $size-of:end/disp8 -12814 } -12815 # if (!t->is-atom?) t = lookup(t->left) -12816 { -12817 81 7/subop/compare *ecx 0/imm32/false # Type-tree-is-atom -12818 75/jump-if-!= break/disp8 -12819 (lookup *(ecx+4) *(ecx+8)) # Type-tree-left Type-tree-left => eax -12820 89/<- %ecx 0/r32/eax -12821 } -12822 # TODO: assert t->is-atom? -12823 (size-of-type-id *(ecx+4)) # Type-tree-value => eax -12824 $size-of-deref:end: -12825 # . restore registers -12826 59/pop-to-ecx -12827 # . epilogue -12828 89/<- %esp 5/r32/ebp -12829 5d/pop-to-ebp -12830 c3/return -12831 -12832 is-mu-array?: # t: (addr type-tree) -> result/eax: boolean -12833 # . prologue -12834 55/push-ebp -12835 89/<- %ebp 4/r32/esp -12836 # . save registers -12837 51/push-ecx -12838 # ecx = t -12839 8b/-> *(ebp+8) 1/r32/ecx -12840 # if t->is-atom?, return false -12841 81 7/subop/compare *ecx 0/imm32/false # Type-tree-is-atom -12842 75/jump-if-!= $is-mu-array?:return-false/disp8 -12843 # if !t->left->is-atom?, return false -12844 (lookup *(ecx+4) *(ecx+8)) # Type-tree-left Type-tree-left => eax -12845 81 7/subop/compare *eax 0/imm32/false # Type-tree-is-atom -12846 74/jump-if-= $is-mu-array?:return-false/disp8 -12847 # return t->left->value == array -12848 81 7/subop/compare *(eax+4) 3/imm32/array-type-id # Type-tree-value -12849 0f 94/set-if-= %al -12850 81 4/subop/and %eax 0xff/imm32 -12851 eb/jump $is-mu-array?:end/disp8 -12852 $is-mu-array?:return-false: -12853 b8/copy-to-eax 0/imm32/false -12854 $is-mu-array?:end: -12855 # . restore registers -12856 59/pop-to-ecx -12857 # . epilogue -12858 89/<- %esp 5/r32/ebp -12859 5d/pop-to-ebp -12860 c3/return -12861 -12862 size-of-array: # a: (addr type-tree) -> result/eax: int -12863 # . prologue -12864 55/push-ebp -12865 89/<- %ebp 4/r32/esp -12866 # . save registers -12867 51/push-ecx -12868 52/push-edx -12869 # -12870 8b/-> *(ebp+8) 1/r32/ecx -12871 # TODO: assert that a->left is 'array' -12872 (lookup *(ecx+0xc) *(ecx+0x10)) # Type-tree-right Type-tree-right => eax -12873 89/<- %ecx 0/r32/eax -12874 # var elem-type/edx: type-id = a->right->left->value -12875 (lookup *(ecx+4) *(ecx+8)) # Type-tree-left Type-tree-left => eax -12876 8b/-> *(eax+4) 2/r32/edx # Type-tree-value -12877 # TODO: assert that a->right->right->left->value == size -12878 # var array-size/ecx: int = a->right->right->left->value-size -12879 (lookup *(ecx+0xc) *(ecx+0x10)) # Type-tree-right Type-tree-right => eax -12880 (lookup *(eax+4) *(eax+8)) # Type-tree-left Type-tree-left => eax -12881 8b/-> *(eax+8) 1/r32/ecx # Type-tree-value-size -12882 # return array-size * size-of(elem-type) -12883 (size-of-type-id-as-array-element %edx) # => eax -12884 f7 4/subop/multiply-into-eax %ecx -12885 05/add-to-eax 4/imm32 # for array size -12886 $size-of-array:end: -12887 # . restore registers -12888 5a/pop-to-edx -12889 59/pop-to-ecx -12890 # . epilogue -12891 89/<- %esp 5/r32/ebp -12892 5d/pop-to-ebp -12893 c3/return -12894 -12895 size-of-type-id: # t: type-id -> result/eax: int -12896 # . prologue -12897 55/push-ebp -12898 89/<- %ebp 4/r32/esp -12899 # . save registers -12900 51/push-ecx -12901 # var out/ecx: (handle typeinfo) -12902 68/push 0/imm32 -12903 68/push 0/imm32 -12904 89/<- %ecx 4/r32/esp -12905 # eax = t -12906 8b/-> *(ebp+8) 0/r32/eax -12907 # if t is a literal, return 0 -12908 3d/compare-eax-and 0/imm32 -12909 0f 84/jump-if-= $size-of-type-id:end/disp32 # eax changes type from type-id to int -12910 # if t is a byte, return 4 (because we don't really support non-multiples of 4) -12911 3d/compare-eax-and 8/imm32/byte -12912 { -12913 75/jump-if-!= break/disp8 -12914 b8/copy-to-eax 4/imm32 -12915 eb/jump $size-of-type-id:end/disp8 -12916 } -12917 # if t is a handle, return 8 -12918 3d/compare-eax-and 4/imm32/handle -12919 { -12920 75/jump-if-!= break/disp8 -12921 b8/copy-to-eax 8/imm32 -12922 eb/jump $size-of-type-id:end/disp8 # eax changes type from type-id to int -12923 } -12924 # if t is a user-defined type, return its size -12925 # TODO: support non-atom type -12926 (find-typeinfo %eax %ecx) -12927 { -12928 81 7/subop/compare *ecx 0/imm32 +12340 $check-mu-get-stmt:error-output-not-in-register: +12341 (write-buffered *(ebp+0x10) "fn ") +12342 8b/-> *(ebp+0xc) 0/r32/eax +12343 (lookup *eax *(eax+4)) # Function-name Function-name => eax +12344 (write-buffered *(ebp+0x10) %eax) +12345 (write-buffered *(ebp+0x10) ": stmt get: output '") +12346 (lookup *edi *(edi+4)) # Var-name Var-name => eax +12347 (write-buffered *(ebp+0x10) %eax) +12348 (write-buffered *(ebp+0x10) "' is not in a register\n") +12349 (flush *(ebp+0x10)) +12350 (stop *(ebp+0x14) 1) +12351 # never gets here +12352 +12353 $check-mu-get-stmt:error-output-type-not-address: +12354 (write-buffered *(ebp+0x10) "fn ") +12355 8b/-> *(ebp+0xc) 0/r32/eax +12356 (lookup *eax *(eax+4)) # Function-name Function-name => eax +12357 (write-buffered *(ebp+0x10) %eax) +12358 (write-buffered *(ebp+0x10) ": stmt get: output must be an address\n") +12359 (flush *(ebp+0x10)) +12360 (stop *(ebp+0x14) 1) +12361 # never gets here +12362 +12363 $check-mu-get-stmt:error-bad-output-type: +12364 (write-buffered *(ebp+0x10) "fn ") +12365 8b/-> *(ebp+0xc) 0/r32/eax +12366 (lookup *eax *(eax+4)) # Function-name Function-name => eax +12367 (write-buffered *(ebp+0x10) %eax) +12368 (write-buffered *(ebp+0x10) ": stmt get: wrong output type for member '") +12369 (write-buffered *(ebp+0x10) %ecx) +12370 (write-buffered *(ebp+0x10) "' of type '") +12371 bf/copy-to-edi Type-id/imm32 +12372 (write-buffered *(ebp+0x10) *(edi+ebx<<2+0xc)) +12373 (write-buffered *(ebp+0x10) "'\n") +12374 (flush *(ebp+0x10)) +12375 (stop *(ebp+0x14) 1) +12376 # never gets here +12377 +12378 check-mu-index-stmt: # stmt: (addr stmt), fn: (addr function), err: (addr buffered-file), ed: (addr exit-descriptor) +12379 # . prologue +12380 55/push-ebp +12381 89/<- %ebp 4/r32/esp +12382 # . save registers +12383 $check-mu-index-stmt:end: +12384 # . restore registers +12385 # . epilogue +12386 89/<- %esp 5/r32/ebp +12387 5d/pop-to-ebp +12388 c3/return +12389 +12390 check-mu-length-stmt: # stmt: (addr stmt), fn: (addr function), err: (addr buffered-file), ed: (addr exit-descriptor) +12391 # . prologue +12392 55/push-ebp +12393 89/<- %ebp 4/r32/esp +12394 # . save registers +12395 $check-mu-length-stmt:end: +12396 # . restore registers +12397 # . epilogue +12398 89/<- %esp 5/r32/ebp +12399 5d/pop-to-ebp +12400 c3/return +12401 +12402 check-mu-compute-offset-stmt: # stmt: (addr stmt), fn: (addr function), err: (addr buffered-file), ed: (addr exit-descriptor) +12403 # . prologue +12404 55/push-ebp +12405 89/<- %ebp 4/r32/esp +12406 # . save registers +12407 $check-mu-compute-offset-stmt:end: +12408 # . restore registers +12409 # . epilogue +12410 89/<- %esp 5/r32/ebp +12411 5d/pop-to-ebp +12412 c3/return +12413 +12414 check-mu-allocate-stmt: # stmt: (addr stmt), fn: (addr function), err: (addr buffered-file), ed: (addr exit-descriptor) +12415 # . prologue +12416 55/push-ebp +12417 89/<- %ebp 4/r32/esp +12418 # . save registers +12419 $check-mu-allocate-stmt:end: +12420 # . restore registers +12421 # . epilogue +12422 89/<- %esp 5/r32/ebp +12423 5d/pop-to-ebp +12424 c3/return +12425 +12426 check-mu-populate-stmt: # stmt: (addr stmt), fn: (addr function), err: (addr buffered-file), ed: (addr exit-descriptor) +12427 # . prologue +12428 55/push-ebp +12429 89/<- %ebp 4/r32/esp +12430 # . save registers +12431 $check-mu-populate-stmt:end: +12432 # . restore registers +12433 # . epilogue +12434 89/<- %esp 5/r32/ebp +12435 5d/pop-to-ebp +12436 c3/return +12437 +12438 check-mu-populate-stream-stmt: # stmt: (addr stmt), fn: (addr function), err: (addr buffered-file), ed: (addr exit-descriptor) +12439 # . prologue +12440 55/push-ebp +12441 89/<- %ebp 4/r32/esp +12442 # . save registers +12443 $check-mu-populate-stream-stmt:end: +12444 # . restore registers +12445 # . epilogue +12446 89/<- %esp 5/r32/ebp +12447 5d/pop-to-ebp +12448 c3/return +12449 +12450 check-mu-read-from-stream-stmt: # stmt: (addr stmt), fn: (addr function), err: (addr buffered-file), ed: (addr exit-descriptor) +12451 # . prologue +12452 55/push-ebp +12453 89/<- %ebp 4/r32/esp +12454 # . save registers +12455 $check-mu-read-from-stream-stmt:end: +12456 # . restore registers +12457 # . epilogue +12458 89/<- %esp 5/r32/ebp +12459 5d/pop-to-ebp +12460 c3/return +12461 +12462 check-mu-write-to-stream-stmt: # stmt: (addr stmt), fn: (addr function), err: (addr buffered-file), ed: (addr exit-descriptor) +12463 # . prologue +12464 55/push-ebp +12465 89/<- %ebp 4/r32/esp +12466 # . save registers +12467 $check-mu-write-to-stream-stmt:end: +12468 # . restore registers +12469 # . epilogue +12470 89/<- %esp 5/r32/ebp +12471 5d/pop-to-ebp +12472 c3/return +12473 +12474 check-mu-call: # stmt: (addr stmt), callee: (addr function), fn: (addr function), err: (addr buffered-file), ed: (addr exit-descriptor) +12475 # . prologue +12476 55/push-ebp +12477 89/<- %ebp 4/r32/esp +12478 # var type-parameters: (addr table (handle array byte) (addr type-tree) 8) +12479 68/push 0/imm32 +12480 # var type-parameters-storage: (table (handle array byte) (addr type-tree) 8) +12481 81 5/subop/subtract %esp 0x60/imm32 +12482 68/push 0x60/imm32/size +12483 68/push 0/imm32/read +12484 68/push 0/imm32/write +12485 # save a pointer to type-parameters-storage at type-parameters +12486 89/<- *(ebp-4) 4/r32/esp +12487 (clear-stream *(ebp-4)) +12488 # . save registers +12489 50/push-eax +12490 51/push-ecx +12491 52/push-edx +12492 53/push-ebx +12493 56/push-esi +12494 57/push-edi +12495 # esi = stmt +12496 8b/-> *(ebp+8) 6/r32/esi +12497 # edi = callee +12498 8b/-> *(ebp+0xc) 7/r32/edi +12499 # var inouts/ecx: (addr stmt-var) = lookup(stmt->inouts) +12500 (lookup *(esi+0xc) *(esi+0x10)) # Stmt1-inouts Stmt1-inouts => eax +12501 89/<- %ecx 0/r32/eax +12502 # var expected/edx: (addr list var) = lookup(f->inouts) +12503 (lookup *(edi+8) *(edi+0xc)) # Function-inouts Function-inouts => eax +12504 89/<- %edx 0/r32/eax +12505 { +12506 $check-mu-call:check-for-inouts: +12507 # if (inouts == 0) break +12508 81 7/subop/compare %ecx 0/imm32 +12509 0f 84/jump-if-= break/disp32 +12510 # if (expected == 0) error +12511 81 7/subop/compare %edx 0/imm32 +12512 0f 84/jump-if-= break/disp32 +12513 $check-mu-call:check-inout-type: +12514 # var v/eax: (addr v) = lookup(inouts->value) +12515 (lookup *ecx *(ecx+4)) # Stmt-var-value Stmt-var-value => eax +12516 # var t/ebx: (addr type-tree) = lookup(v->type) +12517 (lookup *(eax+8) *(eax+0xc)) # Var-type Var-type => eax +12518 89/<- %ebx 0/r32/eax +12519 # if (inouts->is-deref?) t = t->right # TODO: check that t->left is an addr +12520 81 7/subop/compare *(ecx+0x10) 0/imm32/false # Stmt-var-is-deref +12521 { +12522 74/jump-if-= break/disp8 +12523 (lookup *(ebx+0xc) *(ebx+0x10)) # Type-tree-right Type-tree-right => eax +12524 89/<- %ebx 0/r32/eax +12525 # if t->right is null, t = t->left +12526 81 7/subop/compare *(ebx+0xc) 0/imm32 # Type-tree-right +12527 75/jump-if-!= break/disp8 +12528 (lookup *(ebx+4) *(ebx+8)) # Type-tree-left Type-tree-left => eax +12529 89/<- %ebx 0/r32/eax +12530 } +12531 # var v2/eax: (addr v) = lookup(expected->value) +12532 (lookup *edx *(edx+4)) # List-value List-value => eax +12533 # var t2/eax: (addr type-tree) = lookup(v2->type) +12534 (lookup *(eax+8) *(eax+0xc)) # Var-type Var-type => eax +12535 # if (t != t2) error +12536 (type-match? %eax %ebx *(ebp-4)) # => eax +12537 3d/compare-eax-and 0/imm32/false +12538 { +12539 0f 85/jump-if-!= break/disp32 +12540 (write-buffered *(ebp+0x14) "fn ") +12541 8b/-> *(ebp+0x10) 0/r32/eax +12542 (lookup *eax *(eax+4)) # Function-name Function-name => eax +12543 (write-buffered *(ebp+0x14) %eax) +12544 (write-buffered *(ebp+0x14) ": call ") +12545 (lookup *edi *(edi+4)) # Function-name Function-name => eax +12546 (write-buffered *(ebp+0x14) %eax) +12547 (write-buffered *(ebp+0x14) ": type for inout '") +12548 (lookup *ecx *(ecx+4)) # Stmt-var-value Stmt-var-value => eax +12549 (lookup *eax *(eax+4)) # Var-name Var-name => eax +12550 (write-buffered *(ebp+0x14) %eax) +12551 (write-buffered *(ebp+0x14) "' is not right\n") +12552 (flush *(ebp+0x14)) +12553 (stop *(ebp+0x18) 1) +12554 } +12555 $check-mu-call:continue-to-next-inout: +12556 # inouts = lookup(inouts->next) +12557 (lookup *(ecx+8) *(ecx+0xc)) # Stmt-var-next Stmt-var-next => eax +12558 89/<- %ecx 0/r32/eax +12559 # expected = lookup(expected->next) +12560 (lookup *(edx+8) *(edx+0xc)) # List-next List-next => eax +12561 89/<- %edx 0/r32/eax +12562 # +12563 e9/jump loop/disp32 +12564 } +12565 $check-mu-call:check-inout-count: +12566 # if (inouts == expected) proceed +12567 39/compare %ecx 2/r32/edx +12568 { +12569 0f 84/jump-if-= break/disp32 +12570 # exactly one of the two is null +12571 # if (inouts == 0) error("too many inouts") +12572 { +12573 81 7/subop/compare %ecx 0/imm32 +12574 0f 84/jump-if-= break/disp32 +12575 (write-buffered *(ebp+0x14) "fn ") +12576 8b/-> *(ebp+0x10) 0/r32/eax +12577 (lookup *eax *(eax+4)) # Function-name Function-name => eax +12578 (write-buffered *(ebp+0x14) %eax) +12579 (write-buffered *(ebp+0x14) ": call ") +12580 (lookup *edi *(edi+4)) # Function-name Function-name => eax +12581 (write-buffered *(ebp+0x14) %eax) +12582 (write-buffered *(ebp+0x14) ": too many inouts\n") +12583 (flush *(ebp+0x14)) +12584 (stop *(ebp+0x18) 1) +12585 } +12586 # if (expected == 0) error("too few inouts") +12587 { +12588 81 7/subop/compare %edx 0/imm32 +12589 0f 84/jump-if-= break/disp32 +12590 (write-buffered *(ebp+0x14) "fn ") +12591 8b/-> *(ebp+0x10) 0/r32/eax +12592 (lookup *eax *(eax+4)) # Function-name Function-name => eax +12593 (write-buffered *(ebp+0x14) %eax) +12594 (write-buffered *(ebp+0x14) ": call ") +12595 (lookup *edi *(edi+4)) # Function-name Function-name => eax +12596 (write-buffered *(ebp+0x14) %eax) +12597 (write-buffered *(ebp+0x14) ": too few inouts\n") +12598 (flush *(ebp+0x14)) +12599 (stop *(ebp+0x18) 1) +12600 } +12601 } +12602 $check-mu-call:check-outputs: +12603 # var outputs/ecx: (addr stmt-var) = lookup(stmt->outputs) +12604 (lookup *(esi+0x14) *(esi+0x18)) # Stmt1-outputs Stmt1-outputs => eax +12605 89/<- %ecx 0/r32/eax +12606 # var expected/edx: (addr list var) = lookup(f->outputs) +12607 (lookup *(edi+0x10) *(edi+0x14)) # Function-outputs Function-outputs => eax +12608 89/<- %edx 0/r32/eax +12609 { +12610 $check-mu-call:check-for-outputs: +12611 # if (outputs == 0) break +12612 81 7/subop/compare %ecx 0/imm32 +12613 0f 84/jump-if-= break/disp32 +12614 # if (expected == 0) error +12615 81 7/subop/compare %edx 0/imm32 +12616 0f 84/jump-if-= break/disp32 +12617 $check-mu-call:check-output-type: +12618 # var v/eax: (addr v) = lookup(outputs->value) +12619 (lookup *ecx *(ecx+4)) # Stmt-var-value Stmt-var-value => eax +12620 # var t/ebx: (addr type-tree) = lookup(v->type) +12621 (lookup *(eax+8) *(eax+0xc)) # Var-type Var-type => eax +12622 89/<- %ebx 0/r32/eax +12623 # if (outputs->is-deref?) t = t->right # TODO: check that t->left is an addr +12624 81 7/subop/compare *(ecx+0x10) 0/imm32/false # Stmt-var-is-deref +12625 { +12626 74/jump-if-= break/disp8 +12627 (lookup *(ebx+0xc) *(ebx+0x10)) # Type-tree-right Type-tree-right => eax +12628 89/<- %ebx 0/r32/eax +12629 } +12630 # var v2/eax: (addr v) = lookup(expected->value) +12631 (lookup *edx *(edx+4)) # List-value List-value => eax +12632 # var t2/eax: (addr type-tree) = lookup(v2->type) +12633 (lookup *(eax+8) *(eax+0xc)) # Var-type Var-type => eax +12634 # if (t != t2) error +12635 (type-match? %eax %ebx *(ebp-4)) # => eax +12636 3d/compare-eax-and 0/imm32/false +12637 { +12638 0f 85/jump-if-!= break/disp32 +12639 (write-buffered *(ebp+0x14) "fn ") +12640 8b/-> *(ebp+0x10) 0/r32/eax +12641 (lookup *eax *(eax+4)) # Function-name Function-name => eax +12642 (write-buffered *(ebp+0x14) %eax) +12643 (write-buffered *(ebp+0x14) ": call ") +12644 (lookup *edi *(edi+4)) # Function-name Function-name => eax +12645 (write-buffered *(ebp+0x14) %eax) +12646 (write-buffered *(ebp+0x14) ": type for output '") +12647 (lookup *ecx *(ecx+4)) # Stmt-var-value Stmt-var-value => eax +12648 (lookup *eax *(eax+4)) # Var-name Var-name => eax +12649 (write-buffered *(ebp+0x14) %eax) +12650 (write-buffered *(ebp+0x14) "' is not right\n") +12651 (flush *(ebp+0x14)) +12652 (stop *(ebp+0x18) 1) +12653 } +12654 $check-mu-call:check-output-register: +12655 # var v/eax: (addr v) = lookup(outputs->value) +12656 (lookup *ecx *(ecx+4)) # Stmt-var-value Stmt-var-value => eax +12657 # var r/ebx: (addr array byte) = lookup(v->register) +12658 (lookup *(eax+18) *(eax+0x1c)) # Var-register Var-register => eax +12659 89/<- %ebx 0/r32/eax +12660 # var v2/eax: (addr v) = lookup(expected->value) +12661 (lookup *edx *(edx+4)) # Stmt-var-value Stmt-var-value => eax +12662 # var r2/eax: (addr array byte) = lookup(v2->register) +12663 (lookup *(eax+18) *(eax+0x1c)) # Var-register Var-register => eax +12664 # if (r != r2) error +12665 (string-equal? %eax %ebx) # => eax +12666 3d/compare-eax-and 0/imm32/false +12667 { +12668 0f 85/jump-if-!= break/disp32 +12669 (write-buffered *(ebp+0x14) "fn ") +12670 8b/-> *(ebp+0x10) 0/r32/eax +12671 (lookup *eax *(eax+4)) # Function-name Function-name => eax +12672 (write-buffered *(ebp+0x14) %eax) +12673 (write-buffered *(ebp+0x14) ": call ") +12674 (lookup *edi *(edi+4)) # Function-name Function-name => eax +12675 (write-buffered *(ebp+0x14) %eax) +12676 (write-buffered *(ebp+0x14) ": register for output '") +12677 (lookup *ecx *(ecx+4)) # Stmt-var-value Stmt-var-value => eax +12678 (lookup *eax *(eax+4)) # Var-name Var-name => eax +12679 (write-buffered *(ebp+0x14) %eax) +12680 (write-buffered *(ebp+0x14) "' is not right\n") +12681 (flush *(ebp+0x14)) +12682 (stop *(ebp+0x18) 1) +12683 } +12684 $check-mu-call:continue-to-next-output: +12685 # outputs = lookup(outputs->next) +12686 (lookup *(ecx+8) *(ecx+0xc)) # Stmt-var-next Stmt-var-next => eax +12687 89/<- %ecx 0/r32/eax +12688 # expected = lookup(expected->next) +12689 (lookup *(edx+8) *(edx+0xc)) # List-next List-next => eax +12690 89/<- %edx 0/r32/eax +12691 # +12692 e9/jump loop/disp32 +12693 } +12694 $check-mu-call:check-output-count: +12695 # if (outputs == expected) proceed +12696 39/compare %ecx 2/r32/edx +12697 { +12698 0f 84/jump-if-= break/disp32 +12699 # exactly one of the two is null +12700 # if (outputs == 0) error("too many outputs") +12701 { +12702 81 7/subop/compare %ecx 0/imm32 +12703 0f 84/jump-if-= break/disp32 +12704 (write-buffered *(ebp+0x14) "fn ") +12705 8b/-> *(ebp+0x10) 0/r32/eax +12706 (lookup *eax *(eax+4)) # Function-name Function-name => eax +12707 (write-buffered *(ebp+0x14) %eax) +12708 (write-buffered *(ebp+0x14) ": call ") +12709 (lookup *edi *(edi+4)) # Function-name Function-name => eax +12710 (write-buffered *(ebp+0x14) %eax) +12711 (write-buffered *(ebp+0x14) ": too many outputs\n") +12712 (flush *(ebp+0x14)) +12713 (stop *(ebp+0x18) 1) +12714 } +12715 # if (expected == 0) error("too few outputs") +12716 { +12717 81 7/subop/compare %edx 0/imm32 +12718 0f 84/jump-if-= break/disp32 +12719 (write-buffered *(ebp+0x14) "fn ") +12720 8b/-> *(ebp+0x10) 0/r32/eax +12721 (lookup *eax *(eax+4)) # Function-name Function-name => eax +12722 (write-buffered *(ebp+0x14) %eax) +12723 (write-buffered *(ebp+0x14) ": call ") +12724 (lookup *edi *(edi+4)) # Function-name Function-name => eax +12725 (write-buffered *(ebp+0x14) %eax) +12726 (write-buffered *(ebp+0x14) ": too few outputs\n") +12727 (flush *(ebp+0x14)) +12728 (stop *(ebp+0x18) 1) +12729 } +12730 } +12731 $check-mu-call:end: +12732 # . restore registers +12733 5f/pop-to-edi +12734 5e/pop-to-esi +12735 5b/pop-to-ebx +12736 5a/pop-to-edx +12737 59/pop-to-ecx +12738 58/pop-to-eax +12739 # . reclaim locals exclusively on the stack +12740 81 0/subop/add %esp 0x70/imm32 +12741 # . epilogue +12742 89/<- %esp 5/r32/ebp +12743 5d/pop-to-ebp +12744 c3/return +12745 +12746 # like type-equal? but takes literals into account +12747 type-match?: # def: (addr type-tree), call: (addr type-tree), type-parameters: (addr table (handle array byte) (addr type-tree)) -> result/eax: boolean +12748 # . prologue +12749 55/push-ebp +12750 89/<- %ebp 4/r32/esp +12751 # if (call == literal) return true # TODO: more precise +12752 (is-simple-mu-type? *(ebp+0xc) 0) # literal => eax +12753 3d/compare-eax-and 0/imm32/false +12754 b8/copy-to-eax 1/imm32/true +12755 75/jump-if-!= $type-match?:end/disp8 +12756 $type-match?:baseline: +12757 # otherwise fall back +12758 (type-component-match? *(ebp+8) *(ebp+0xc) *(ebp+0x10)) # => eax +12759 $type-match?:end: +12760 # . epilogue +12761 89/<- %esp 5/r32/ebp +12762 5d/pop-to-ebp +12763 c3/return +12764 +12765 type-component-match?: # def: (addr type-tree), call: (addr type-tree), type-parameters: (addr table (handle array byte) (addr type-tree)) -> result/eax: boolean +12766 # . prologue +12767 55/push-ebp +12768 89/<- %ebp 4/r32/esp +12769 # . save registers +12770 51/push-ecx +12771 52/push-edx +12772 53/push-ebx +12773 # ecx = def +12774 8b/-> *(ebp+8) 1/r32/ecx +12775 # edx = call +12776 8b/-> *(ebp+0xc) 2/r32/edx +12777 $type-component-match?:compare-addr: +12778 # if (def == call) return true +12779 8b/-> %ecx 0/r32/eax # Var-type +12780 39/compare %edx 0/r32/eax # Var-type +12781 b8/copy-to-eax 1/imm32/true +12782 0f 84/jump-if-= $type-component-match?:end/disp32 +12783 # if def is a type parameter, return true +12784 { +12785 $type-component-match?:check-type-parameter: +12786 81 7/subop/compare *ecx 0/imm32/false # Type-tree-is-atom +12787 74/jump-if-= break/disp8 +12788 81 7/subop/compare *(ecx+4) 0xa/imm32/type-parameter # Type-tree-value +12789 75/jump-if-!= break/disp8 +12790 $type-component-match?:type-parameter: +12791 (type-parameter-match? *(ecx+8) *(ecx+0xc) %edx *(ebp+0x10)) # => eax +12792 e9/jump $type-component-match?:end/disp32 +12793 } +12794 $type-component-match?:compare-atom-state: +12795 # if (def->is-atom? != call->is-atom?) return false +12796 8b/-> *ecx 3/r32/ebx # Type-tree-is-atom +12797 39/compare *edx 3/r32/ebx # Type-tree-is-atom +12798 b8/copy-to-eax 0/imm32/false +12799 0f 85/jump-if-!= $type-component-match?:end/disp32 +12800 # if def->is-atom? return (def->value == call->value) +12801 { +12802 $type-component-match?:check-atom: +12803 81 7/subop/compare %ebx 0/imm32/false +12804 74/jump-if-= break/disp8 +12805 $type-component-match?:is-atom: +12806 8b/-> *(ecx+4) 0/r32/eax # Type-tree-value +12807 39/compare *(edx+4) 0/r32/eax # Type-tree-value +12808 0f 94/set-if-= %al +12809 81 4/subop/and %eax 0xff/imm32 +12810 e9/jump $type-component-match?:end/disp32 +12811 } +12812 $type-component-match?:check-left: +12813 # if (!type-component-match?(def->left, call->left)) return false +12814 (lookup *(ecx+4) *(ecx+8)) # Type-tree-left Type-tree-left => eax +12815 89/<- %ebx 0/r32/eax +12816 (lookup *(edx+4) *(edx+8)) # Type-tree-left Type-tree-left => eax +12817 (type-component-match? %ebx %eax *(ebp+0x10)) # => eax +12818 3d/compare-eax-and 0/imm32/false +12819 74/jump-if-= $type-component-match?:end/disp8 +12820 $type-component-match?:check-right: +12821 # return type-component-match?(def->right, call->right) +12822 (lookup *(ecx+0xc) *(ecx+0x10)) # Type-tree-right Type-tree-right => eax +12823 89/<- %ebx 0/r32/eax +12824 (lookup *(edx+0xc) *(edx+0x10)) # Type-tree-right Type-tree-right => eax +12825 (type-component-match? %ebx %eax *(ebp+0x10)) # => eax +12826 $type-component-match?:end: +12827 # . restore registers +12828 5b/pop-to-ebx +12829 5a/pop-to-edx +12830 59/pop-to-ecx +12831 # . epilogue +12832 89/<- %esp 5/r32/ebp +12833 5d/pop-to-ebp +12834 c3/return +12835 +12836 type-parameter-match?: # type-parameter-name: (handle array byte), type: (addr type-tree), type-parameters: (addr table (handle array byte) (addr type-tree)) -> result/eax: boolean +12837 # . prologue +12838 55/push-ebp +12839 89/<- %ebp 4/r32/esp +12840 # . save registers +12841 51/push-ecx +12842 # +12843 (get-or-insert-handle *(ebp+0x14) *(ebp+8) *(ebp+0xc) 0xc) # => eax +12844 # if parameter wasn't saved, save it +12845 { +12846 81 7/subop/compare *eax 0/imm32 +12847 75/jump-if-!= break/disp8 +12848 8b/-> *(ebp+0x10) 1/r32/ecx +12849 89/<- *eax 1/r32/ecx +12850 } +12851 # +12852 (type-equal? *(ebp+0x10) *eax) # => eax +12853 $type-parameter-match?:end: +12854 # . restore registers +12855 59/pop-to-ecx +12856 # . epilogue +12857 89/<- %esp 5/r32/ebp +12858 5d/pop-to-ebp +12859 c3/return +12860 +12861 size-of: # v: (addr var) -> result/eax: int +12862 # . prologue +12863 55/push-ebp +12864 89/<- %ebp 4/r32/esp +12865 # . save registers +12866 51/push-ecx +12867 # var t/ecx: (addr type-tree) = lookup(v->type) +12868 8b/-> *(ebp+8) 1/r32/ecx +12869 #? (write-buffered Stderr "size-of ") +12870 #? (write-int32-hex-buffered Stderr %ecx) +12871 #? (write-buffered Stderr Newline) +12872 #? (write-buffered Stderr "type allocid: ") +12873 #? (write-int32-hex-buffered Stderr *(ecx+8)) +12874 #? (write-buffered Stderr Newline) +12875 #? (flush Stderr) +12876 (lookup *(ecx+8) *(ecx+0xc)) # Var-type Var-type => eax +12877 89/<- %ecx 0/r32/eax +12878 # if is-mu-array?(t) return size-of-array(t) +12879 { +12880 (is-mu-array? %ecx) # => eax +12881 3d/compare-eax-and 0/imm32/false +12882 74/jump-if-= break/disp8 +12883 (size-of-array %ecx) # => eax +12884 eb/jump $size-of:end/disp8 +12885 } +12886 # if is-mu-stream?(t) return size-of-stream(t) +12887 { +12888 (is-mu-stream? %ecx) # => eax +12889 3d/compare-eax-and 0/imm32/false +12890 74/jump-if-= break/disp8 +12891 (size-of-stream %ecx) # => eax +12892 eb/jump $size-of:end/disp8 +12893 } +12894 # if (!t->is-atom?) t = lookup(t->left) +12895 { +12896 81 7/subop/compare *ecx 0/imm32/false # Type-tree-is-atom +12897 75/jump-if-!= break/disp8 +12898 (lookup *(ecx+4) *(ecx+8)) # Type-tree-left Type-tree-left => eax +12899 89/<- %ecx 0/r32/eax +12900 } +12901 # TODO: assert t->is-atom? +12902 (size-of-type-id *(ecx+4)) # Type-tree-value => eax +12903 $size-of:end: +12904 # . restore registers +12905 59/pop-to-ecx +12906 # . epilogue +12907 89/<- %esp 5/r32/ebp +12908 5d/pop-to-ebp +12909 c3/return +12910 +12911 size-of-deref: # v: (addr var) -> result/eax: int +12912 # . prologue +12913 55/push-ebp +12914 89/<- %ebp 4/r32/esp +12915 # . save registers +12916 51/push-ecx +12917 # var t/ecx: (addr type-tree) = lookup(v->type) +12918 8b/-> *(ebp+8) 1/r32/ecx +12919 (lookup *(ecx+8) *(ecx+0xc)) # Var-type Var-type => eax +12920 89/<- %ecx 0/r32/eax +12921 # TODO: assert(t is an addr) +12922 # t = lookup(t->right) +12923 (lookup *(ecx+0xc) *(ecx+0x10)) # Type-tree-right Type-tree-right => eax +12924 89/<- %ecx 0/r32/eax +12925 # if is-mu-array?(t) return size-of-array(t) +12926 { +12927 (is-mu-array? %ecx) # => eax +12928 3d/compare-eax-and 0/imm32/false 12929 74/jump-if-= break/disp8 -12930 $size-of-type-id:user-defined: -12931 (lookup *ecx *(ecx+4)) # => eax -12932 8b/-> *(eax+0xc) 0/r32/eax # Typeinfo-total-size-in-bytes -12933 eb/jump $size-of-type-id:end/disp8 -12934 } -12935 # otherwise return the word size -12936 b8/copy-to-eax 4/imm32 -12937 $size-of-type-id:end: -12938 # . reclaim locals -12939 81 0/subop/add %esp 8/imm32 -12940 # . restore registers -12941 59/pop-to-ecx -12942 # . epilogue -12943 89/<- %esp 5/r32/ebp -12944 5d/pop-to-ebp -12945 c3/return -12946 -12947 type-equal?: # a: (addr type-tree), b: (addr type-tree) -> result/eax: boolean -12948 # . prologue -12949 55/push-ebp -12950 89/<- %ebp 4/r32/esp -12951 # . save registers -12952 51/push-ecx -12953 52/push-edx -12954 53/push-ebx -12955 # ecx = a -12956 8b/-> *(ebp+8) 1/r32/ecx -12957 # edx = b -12958 8b/-> *(ebp+0xc) 2/r32/edx -12959 $type-equal?:compare-addr: -12960 # if (a == b) return true -12961 8b/-> %ecx 0/r32/eax # Var-type -12962 39/compare %edx 0/r32/eax # Var-type -12963 b8/copy-to-eax 1/imm32/true -12964 0f 84/jump-if-= $type-equal?:end/disp32 -12965 $type-equal?:compare-atom-state: -12966 # if (a->is-atom? != b->is-atom?) return false -12967 8b/-> *ecx 3/r32/ebx # Type-tree-is-atom -12968 39/compare *edx 3/r32/ebx # Type-tree-is-atom -12969 b8/copy-to-eax 0/imm32/false -12970 0f 85/jump-if-!= $type-equal?:end/disp32 -12971 # if a->is-atom? return (a->value == b->value) -12972 { -12973 $type-equal?:check-atom: -12974 81 7/subop/compare %ebx 0/imm32/false -12975 74/jump-if-= break/disp8 -12976 $type-equal?:is-atom: -12977 8b/-> *(ecx+4) 0/r32/eax # Type-tree-value -12978 39/compare *(edx+4) 0/r32/eax # Type-tree-value -12979 0f 94/set-if-= %al -12980 81 4/subop/and %eax 0xff/imm32 -12981 e9/jump $type-equal?:end/disp32 -12982 } -12983 $type-equal?:check-left: -12984 # if (!type-equal?(a->left, b->left)) return false -12985 (lookup *(ecx+4) *(ecx+8)) # Type-tree-left Type-tree-left => eax -12986 89/<- %ebx 0/r32/eax -12987 (lookup *(edx+4) *(edx+8)) # Type-tree-left Type-tree-left => eax -12988 (type-equal? %eax %ebx) # => eax -12989 3d/compare-eax-and 0/imm32/false -12990 74/jump-if-= $type-equal?:end/disp8 -12991 $type-equal?:check-right: -12992 # return type-equal?(a->right, b->right) -12993 (lookup *(ecx+0xc) *(ecx+0x10)) # Type-tree-right Type-tree-right => eax -12994 89/<- %ebx 0/r32/eax -12995 (lookup *(edx+0xc) *(edx+0x10)) # Type-tree-right Type-tree-right => eax -12996 (type-equal? %eax %ebx) # => eax -12997 $type-equal?:end: -12998 # . restore registers -12999 5b/pop-to-ebx -13000 5a/pop-to-edx -13001 59/pop-to-ecx -13002 # . epilogue -13003 89/<- %esp 5/r32/ebp -13004 5d/pop-to-ebp -13005 c3/return -13006 -13007 ####################################################### -13008 # Code-generation -13009 ####################################################### -13010 -13011 == data -13012 -13013 # Global state added to each var record when performing code-generation. -13014 Curr-local-stack-offset: # (addr int) -13015 0/imm32 -13016 -13017 == code -13018 -13019 emit-subx: # out: (addr buffered-file), err: (addr buffered-file), ed: (addr exit-descriptor) -13020 # . prologue -13021 55/push-ebp -13022 89/<- %ebp 4/r32/esp -13023 # . save registers -13024 50/push-eax -13025 # var curr/eax: (addr function) = *Program->functions -13026 (lookup *_Program-functions *_Program-functions->payload) # => eax -13027 { -13028 # if (curr == null) break -13029 3d/compare-eax-and 0/imm32 -13030 0f 84/jump-if-= break/disp32 -13031 (emit-subx-function *(ebp+8) %eax *(ebp+0xc) *(ebp+0x10)) -13032 # curr = lookup(curr->next) -13033 (lookup *(eax+0x20) *(eax+0x24)) # Function-next Function-next => eax -13034 e9/jump loop/disp32 -13035 } -13036 $emit-subx:end: -13037 # . restore registers -13038 58/pop-to-eax -13039 # . epilogue -13040 89/<- %esp 5/r32/ebp -13041 5d/pop-to-ebp -13042 c3/return -13043 -13044 emit-subx-function: # out: (addr buffered-file), f: (addr function), err: (addr buffered-file), ed: (addr exit-descriptor) -13045 # . prologue -13046 55/push-ebp -13047 89/<- %ebp 4/r32/esp -13048 # some preprocessing -13049 (populate-mu-type-offsets-in-inouts *(ebp+0xc)) -13050 # . save registers -13051 50/push-eax -13052 51/push-ecx -13053 52/push-edx -13054 # initialize some global state -13055 c7 0/subop/copy *Curr-block-depth 1/imm32 # Important: keep this in sync with the parse phase -13056 c7 0/subop/copy *Curr-local-stack-offset 0/imm32 -13057 # ecx = f -13058 8b/-> *(ebp+0xc) 1/r32/ecx -13059 # var vars/edx: (stack (addr var) 256) -13060 81 5/subop/subtract %esp 0xc00/imm32 -13061 68/push 0xc00/imm32/size -13062 68/push 0/imm32/top -13063 89/<- %edx 4/r32/esp -13064 # var name/eax: (addr array byte) = lookup(f->name) -13065 (lookup *ecx *(ecx+4)) # Function-name Function-name => eax -13066 # -13067 (write-buffered *(ebp+8) %eax) -13068 (write-buffered *(ebp+8) ":\n") -13069 (emit-subx-prologue *(ebp+8)) -13070 # var body/eax: (addr block) = lookup(f->body) -13071 (lookup *(ecx+0x18) *(ecx+0x1c)) # Function-body Function-body => eax -13072 # -13073 (emit-subx-block *(ebp+8) %eax %edx *(ebp+0xc) *(ebp+0x10) *(ebp+0x14)) -13074 (emit-subx-epilogue *(ebp+8)) -13075 # TODO: validate that *Curr-block-depth and *Curr-local-stack-offset have -13076 # been cleaned up -13077 $emit-subx-function:end: -13078 # . reclaim locals -13079 81 0/subop/add %esp 0xc08/imm32 -13080 # . restore registers -13081 5a/pop-to-edx -13082 59/pop-to-ecx -13083 58/pop-to-eax -13084 # . epilogue -13085 89/<- %esp 5/r32/ebp -13086 5d/pop-to-ebp -13087 c3/return -13088 -13089 populate-mu-type-offsets-in-inouts: # f: (addr function) -13090 # . prologue -13091 55/push-ebp -13092 89/<- %ebp 4/r32/esp -13093 # . save registers -13094 50/push-eax -13095 51/push-ecx -13096 52/push-edx -13097 53/push-ebx -13098 57/push-edi -13099 # var next-offset/edx: int = 8 -13100 ba/copy-to-edx 8/imm32 -13101 # var curr/ecx: (addr list var) = lookup(f->inouts) -13102 8b/-> *(ebp+8) 1/r32/ecx -13103 (lookup *(ecx+8) *(ecx+0xc)) # Function-inouts Function-inouts => eax -13104 89/<- %ecx 0/r32/eax -13105 { -13106 $populate-mu-type-offsets-in-inouts:loop: -13107 81 7/subop/compare %ecx 0/imm32 -13108 74/jump-if-= break/disp8 -13109 # var v/ebx: (addr var) = lookup(curr->value) -13110 (lookup *ecx *(ecx+4)) # List-value List-value => eax -13111 89/<- %ebx 0/r32/eax -13112 #? (lookup *ebx *(ebx+4)) -13113 #? (write-buffered Stderr "setting offset of fn inout ") -13114 #? (write-buffered Stderr %eax) -13115 #? (write-buffered Stderr "@") -13116 #? (write-int32-hex-buffered Stderr %ebx) -13117 #? (write-buffered Stderr " to ") -13118 #? (write-int32-hex-buffered Stderr %edx) -13119 #? (write-buffered Stderr Newline) -13120 #? (flush Stderr) -13121 # v->offset = next-offset -13122 89/<- *(ebx+0x14) 2/r32/edx # Var-offset -13123 # next-offset += size-of(v) -13124 (size-of %ebx) # => eax -13125 01/add-to %edx 0/r32/eax -13126 # curr = lookup(curr->next) -13127 (lookup *(ecx+8) *(ecx+0xc)) # List-next List-next => eax -13128 89/<- %ecx 0/r32/eax -13129 # -13130 eb/jump loop/disp8 -13131 } -13132 $populate-mu-type-offsets-in-inouts:end: -13133 # . restore registers -13134 5f/pop-to-edi -13135 5b/pop-to-ebx -13136 5a/pop-to-edx -13137 59/pop-to-ecx -13138 58/pop-to-eax -13139 # . epilogue -13140 89/<- %esp 5/r32/ebp -13141 5d/pop-to-ebp -13142 c3/return -13143 -13144 emit-subx-stmt-list: # out: (addr buffered-file), stmts: (addr list stmt), vars: (addr stack live-var), fn: (addr function), err: (addr buffered-file), ed: (addr exit-descriptor) -13145 # . prologue -13146 55/push-ebp -13147 89/<- %ebp 4/r32/esp -13148 # . save registers -13149 50/push-eax -13150 51/push-ecx -13151 53/push-ebx -13152 56/push-esi -13153 # esi = stmts -13154 8b/-> *(ebp+0xc) 6/r32/esi -13155 # -13156 { -13157 $emit-subx-stmt-list:loop: -13158 81 7/subop/compare %esi 0/imm32 -13159 0f 84/jump-if-= break/disp32 -13160 # var curr-stmt/ecx: (addr stmt) = lookup(stmts->value) -13161 (lookup *esi *(esi+4)) # List-value List-value => eax -13162 89/<- %ecx 0/r32/eax -13163 { -13164 $emit-subx-stmt-list:check-for-block: -13165 81 7/subop/compare *ecx 0/imm32/block # Stmt-tag -13166 75/jump-if-!= break/disp8 -13167 $emit-subx-stmt-list:block: -13168 (emit-subx-block *(ebp+8) %ecx *(ebp+0x10) *(ebp+0x14) *(ebp+0x18) *(ebp+0x1c)) -13169 } -13170 { -13171 $emit-subx-stmt-list:check-for-stmt: -13172 81 7/subop/compare *ecx 1/imm32/stmt1 # Stmt-tag -13173 0f 85/jump-if-!= break/disp32 -13174 $emit-subx-stmt-list:stmt1: -13175 { -13176 (is-mu-branch? %ecx) # => eax -13177 3d/compare-eax-and 0/imm32/false -13178 0f 84/jump-if-= break/disp32 -13179 $emit-subx-stmt-list:branch-stmt: -13180 +-- 27 lines: # unconditional loops -------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- -13207 +-- 16 lines: # unconditional breaks ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- -13223 +-- 38 lines: # simple conditional branches without a target ------------------------------------------------------------------------------------------------------------------------------------------------------- -13261 +-- 19 lines: # conditional branches with an explicit target ------------------------------------------------------------------------------------------------------------------------------------------------------- -13280 } -13281 $emit-subx-stmt-list:1-to-1: -13282 (emit-subx-stmt *(ebp+8) %ecx Primitives *(ebp+0x18) *(ebp+0x1c)) -13283 e9/jump $emit-subx-stmt-list:continue/disp32 -13284 } -13285 { -13286 $emit-subx-stmt-list:check-for-var-def: -13287 81 7/subop/compare *ecx 2/imm32/var-def # Stmt-tag -13288 75/jump-if-!= break/disp8 -13289 $emit-subx-stmt-list:var-def: -13290 (emit-subx-var-def *(ebp+8) %ecx) -13291 (push *(ebp+0x10) *(ecx+4)) # Vardef-var -13292 (push *(ebp+0x10) *(ecx+8)) # Vardef-var -13293 (push *(ebp+0x10) 0) # Live-var-register-spilled = 0 for vars on the stack -13294 # -13295 eb/jump $emit-subx-stmt-list:continue/disp8 -13296 } -13297 { -13298 $emit-subx-stmt-list:check-for-reg-var-def: -13299 81 7/subop/compare *ecx 3/imm32/reg-var-def # Stmt-tag -13300 0f 85/jump-if-!= break/disp32 -13301 $emit-subx-stmt-list:reg-var-def: -13302 # TODO: ensure that there's exactly one output -13303 (push-output-and-maybe-emit-spill *(ebp+8) %ecx *(ebp+0x10) %esi *(ebp+0x14) *(ebp+0x18) *(ebp+0x1c)) -13304 # emit the instruction as usual -13305 (emit-subx-stmt *(ebp+8) %ecx Primitives *(ebp+0x18) *(ebp+0x1c)) -13306 # -13307 eb/jump $emit-subx-stmt-list:continue/disp8 -13308 } -13309 $emit-subx-stmt-list:continue: -13310 # TODO: raise an error on unrecognized Stmt-tag -13311 (lookup *(esi+8) *(esi+0xc)) # List-next List-next => eax -13312 89/<- %esi 0/r32/eax -13313 e9/jump loop/disp32 -13314 } -13315 $emit-subx-stmt-list:emit-cleanup: -13316 (emit-cleanup-code-until-depth *(ebp+8) *(ebp+0x10) *Curr-block-depth) -13317 $emit-subx-stmt-list:clean-up: -13318 (clean-up-blocks *(ebp+0x10) *Curr-block-depth *(ebp+0x14)) -13319 $emit-subx-stmt-list:end: -13320 # . restore registers -13321 5e/pop-to-esi -13322 5b/pop-to-ebx -13323 59/pop-to-ecx -13324 58/pop-to-eax -13325 # . epilogue -13326 89/<- %esp 5/r32/ebp -13327 5d/pop-to-ebp -13328 c3/return -13329 -13330 # 'later-stmts' includes 'stmt', but will behave the same even without it; reg-var-def stmts are guaranteed not to write to function outputs. -13331 push-output-and-maybe-emit-spill: # out: (addr buffered-file), stmt: (addr reg-var-def), vars: (addr stack (handle var)), later-stmts: (addr list stmt), fn: (addr function), err: (addr buffered-file), ed: (addr exit-descriptor) -13332 # . prologue -13333 55/push-ebp -13334 89/<- %ebp 4/r32/esp -13335 # . save registers -13336 50/push-eax -13337 51/push-ecx -13338 52/push-edx -13339 # ecx = stmt -13340 8b/-> *(ebp+0xc) 1/r32/ecx -13341 # var sv/eax: (addr stmt-var) = lookup(curr-stmt->outputs) -13342 (lookup *(ecx+0x14) *(ecx+0x18)) # Regvardef-outputs Regvardef-outputs => eax -13343 # TODO: assert !sv->is-deref? -13344 # var v/ecx: (addr var) = lookup(sv->value) -13345 (lookup *eax *(eax+4)) # Stmt-var-value Stmt-var-value => eax -13346 89/<- %ecx 0/r32/eax -13347 # v->block-depth = *Curr-block-depth -13348 8b/-> *Curr-block-depth 0/r32/eax -13349 89/<- *(ecx+0x10) 0/r32/eax # Var-block-depth -13350 #? (write-buffered Stderr "var ") -13351 #? (lookup *ecx *(ecx+4)) -13352 #? (write-buffered Stderr %eax) -13353 #? (write-buffered Stderr " at depth ") -13354 #? (write-int32-hex-buffered Stderr *(ecx+0x10)) -13355 #? (write-buffered Stderr Newline) -13356 #? (flush Stderr) -13357 # ensure that v is in a register -13358 81 7/subop/compare *(ecx+0x18) 0/imm32 # Var-register -13359 0f 84/jump-if-= $push-output-and-maybe-emit-spill:abort/disp32 -13360 # var emit-spill?/edx: boolean = not-yet-spilled-this-block? && will-not-write-some-register?(fn) -13361 (not-yet-spilled-this-block? %ecx *(ebp+0x10)) # => eax -13362 89/<- %edx 0/r32/eax -13363 3d/compare-eax-and 0/imm32/false -13364 0f 84/jump-if-= $push-output-and-maybe-emit-spill:push/disp32 -13365 (will-not-write-some-register? %ecx *(ebp+0x14) *(ebp+0x18)) # => eax -13366 89/<- %edx 0/r32/eax -13367 # check emit-spill? -13368 3d/compare-eax-and 0/imm32/false -13369 0f 84/jump-if-= $push-output-and-maybe-emit-spill:push/disp32 -13370 # TODO: assert(size-of(output) == 4) -13371 # *Curr-local-stack-offset -= 4 -13372 81 5/subop/subtract *Curr-local-stack-offset 4/imm32 -13373 # emit spill -13374 (emit-indent *(ebp+8) *Curr-block-depth) -13375 (write-buffered *(ebp+8) "ff 6/subop/push %") -13376 (lookup *(ecx+0x18) *(ecx+0x1c)) # Var-register Var-register => eax -13377 (write-buffered *(ebp+8) %eax) -13378 (write-buffered *(ebp+8) Newline) -13379 $push-output-and-maybe-emit-spill:push: -13380 8b/-> *(ebp+0xc) 1/r32/ecx -13381 (lookup *(ecx+0x14) *(ecx+0x18)) # Regvardef-outputs Regvardef-outputs => eax -13382 # push(vars, {sv->value, emit-spill?}) -13383 (push *(ebp+0x10) *eax) # Stmt-var-value -13384 (push *(ebp+0x10) *(eax+4)) # Stmt-var-value -13385 (push *(ebp+0x10) %edx) -13386 $push-output-and-maybe-emit-spill:end: -13387 # . restore registers -13388 5a/pop-to-edx -13389 59/pop-to-ecx -13390 58/pop-to-eax -13391 # . epilogue -13392 89/<- %esp 5/r32/ebp -13393 5d/pop-to-ebp -13394 c3/return -13395 -13396 $push-output-and-maybe-emit-spill:abort: -13397 # error("var '" var->name "' initialized from an instruction must live in a register\n") -13398 (write-buffered *(ebp+0x1c) "var '") -13399 (write-buffered *(ebp+0x1c) *eax) # Var-name -13400 (write-buffered *(ebp+0x1c) "' initialized from an instruction must live in a register\n") -13401 (flush *(ebp+0x1c)) -13402 (stop *(ebp+0x20) 1) -13403 # never gets here -13404 -13405 emit-subx-cleanup-and-unconditional-nonlocal-branch: # out: (addr buffered-file), stmt: (addr stmt1), vars: (addr stack live-var) -13406 # . prologue -13407 55/push-ebp -13408 89/<- %ebp 4/r32/esp -13409 # . save registers -13410 50/push-eax -13411 51/push-ecx -13412 # ecx = stmt -13413 8b/-> *(ebp+0xc) 1/r32/ecx -13414 # var target/eax: (addr array byte) = curr-stmt->inouts->value->name -13415 (lookup *(ecx+0xc) *(ecx+0x10)) # Stmt1-inouts Stmt1-inouts => eax -13416 (lookup *eax *(eax+4)) # Stmt-var-value Stmt-var-value => eax -13417 (lookup *eax *(eax+4)) # Var-name Var-name => eax -13418 # clean up until target block -13419 (emit-cleanup-code-until-target *(ebp+8) *(ebp+0x10) %eax) -13420 # emit jump to target block -13421 (emit-indent *(ebp+8) *Curr-block-depth) -13422 (write-buffered *(ebp+8) "e9/jump ") -13423 (write-buffered *(ebp+8) %eax) -13424 (lookup *(ecx+4) *(ecx+8)) # Stmt1-operation Stmt1-operation => eax -13425 (string-starts-with? %eax "break") -13426 3d/compare-eax-and 0/imm32/false -13427 { -13428 74/jump-if-= break/disp8 -13429 (write-buffered *(ebp+8) ":break/disp32\n") -13430 } -13431 3d/compare-eax-and 0/imm32/false # just in case the function call modified flags -13432 { -13433 75/jump-if-!= break/disp8 -13434 (write-buffered *(ebp+8) ":loop/disp32\n") -13435 } -13436 $emit-subx-cleanup-and-unconditional-nonlocal-branch:end: -13437 # . restore registers -13438 59/pop-to-ecx -13439 58/pop-to-eax -13440 # . epilogue -13441 89/<- %esp 5/r32/ebp -13442 5d/pop-to-ebp -13443 c3/return -13444 -13445 is-mu-branch?: # stmt: (addr stmt1) -> result/eax: boolean -13446 # . prologue -13447 55/push-ebp -13448 89/<- %ebp 4/r32/esp -13449 # . save registers -13450 51/push-ecx -13451 # ecx = lookup(stmt->operation) -13452 8b/-> *(ebp+8) 1/r32/ecx -13453 (lookup *(ecx+4) *(ecx+8)) # Stmt1-operation Stmt1-operation => eax -13454 89/<- %ecx 0/r32/eax -13455 # if (stmt->operation starts with "loop") return true -13456 (string-starts-with? %ecx "loop") # => eax -13457 3d/compare-eax-and 0/imm32/false -13458 75/jump-if-not-equal $is-mu-branch?:end/disp8 -13459 # otherwise return (stmt->operation starts with "break") -13460 (string-starts-with? %ecx "break") # => eax -13461 $is-mu-branch?:end: -13462 # . restore registers -13463 59/pop-to-ecx -13464 # . epilogue -13465 89/<- %esp 5/r32/ebp -13466 5d/pop-to-ebp -13467 c3/return -13468 -13469 emit-reverse-break: # out: (addr buffered-file), stmt: (addr stmt1) -13470 # . prologue -13471 55/push-ebp -13472 89/<- %ebp 4/r32/esp -13473 # . save registers -13474 50/push-eax -13475 # eax = stmt -13476 8b/-> *(ebp+0xc) 0/r32/eax -13477 # -13478 (lookup *(eax+4) *(eax+8)) # Stmt1-operation Stmt1-operation => eax -13479 (get Reverse-branch %eax 0x10 "reverse-branch: ") # => eax: (addr handle array byte) -13480 (emit-indent *(ebp+8) *Curr-block-depth) -13481 (lookup *eax *(eax+4)) # => eax -13482 (write-buffered *(ebp+8) %eax) -13483 (write-buffered *(ebp+8) " break/disp32\n") -13484 $emit-reverse-break:end: -13485 # . restore registers -13486 58/pop-to-eax -13487 # . epilogue -13488 89/<- %esp 5/r32/ebp -13489 5d/pop-to-ebp -13490 c3/return -13491 -13492 == data -13493 -13494 # Table from Mu branch instructions to the reverse SubX opcodes for them. -13495 Reverse-branch: # (table (handle array byte) (handle array byte)) -13496 # a table is a stream -13497 0x140/imm32/write -13498 0/imm32/read -13499 0x140/imm32/size -13500 # data -13501 0x11/imm32/alloc-id _string-break-if-=/imm32 0x11/imm32/alloc-id _string_0f_85_jump_label/imm32 -13502 0x11/imm32/alloc-id _string-loop-if-=/imm32 0x11/imm32/alloc-id _string_0f_85_jump_label/imm32 -13503 0x11/imm32/alloc-id _string-break-if-!=/imm32 0x11/imm32/alloc-id _string_0f_84_jump_label/imm32 -13504 0x11/imm32/alloc-id _string-loop-if-!=/imm32 0x11/imm32/alloc-id _string_0f_84_jump_label/imm32 -13505 0x11/imm32/alloc-id _string-break-if-</imm32 0x11/imm32/alloc-id _string_0f_8d_jump_label/imm32 -13506 0x11/imm32/alloc-id _string-loop-if-</imm32 0x11/imm32/alloc-id _string_0f_8d_jump_label/imm32 -13507 0x11/imm32/alloc-id _string-break-if->/imm32 0x11/imm32/alloc-id _string_0f_8e_jump_label/imm32 -13508 0x11/imm32/alloc-id _string-loop-if->/imm32 0x11/imm32/alloc-id _string_0f_8e_jump_label/imm32 -13509 0x11/imm32/alloc-id _string-break-if-<=/imm32 0x11/imm32/alloc-id _string_0f_87_jump_label/imm32 -13510 0x11/imm32/alloc-id _string-loop-if-<=/imm32 0x11/imm32/alloc-id _string_0f_87_jump_label/imm32 -13511 0x11/imm32/alloc-id _string-break-if->=/imm32 0x11/imm32/alloc-id _string_0f_8c_jump_label/imm32 -13512 0x11/imm32/alloc-id _string-loop-if->=/imm32 0x11/imm32/alloc-id _string_0f_8c_jump_label/imm32 -13513 0x11/imm32/alloc-id _string-break-if-addr</imm32 0x11/imm32/alloc-id _string_0f_83_jump_label/imm32 -13514 0x11/imm32/alloc-id _string-loop-if-addr</imm32 0x11/imm32/alloc-id _string_0f_83_jump_label/imm32 -13515 0x11/imm32/alloc-id _string-break-if-addr>/imm32 0x11/imm32/alloc-id _string_0f_86_jump_label/imm32 -13516 0x11/imm32/alloc-id _string-loop-if-addr>/imm32 0x11/imm32/alloc-id _string_0f_86_jump_label/imm32 -13517 0x11/imm32/alloc-id _string-break-if-addr<=/imm32 0x11/imm32/alloc-id _string_0f_87_jump_label/imm32 -13518 0x11/imm32/alloc-id _string-loop-if-addr<=/imm32 0x11/imm32/alloc-id _string_0f_87_jump_label/imm32 -13519 0x11/imm32/alloc-id _string-break-if-addr>=/imm32 0x11/imm32/alloc-id _string_0f_82_jump_label/imm32 -13520 0x11/imm32/alloc-id _string-loop-if-addr>=/imm32 0x11/imm32/alloc-id _string_0f_82_jump_label/imm32 -13521 -13522 == code -13523 -13524 emit-unconditional-jump-to-depth: # out: (addr buffered-file), vars: (addr stack live-var), depth: int, label-suffix: (addr array byte) -13525 # . prologue -13526 55/push-ebp -13527 89/<- %ebp 4/r32/esp -13528 # . save registers -13529 50/push-eax -13530 51/push-ecx -13531 52/push-edx -13532 53/push-ebx -13533 56/push-esi -13534 # ecx = vars -13535 8b/-> *(ebp+0xc) 1/r32/ecx -13536 # var eax: int = vars->top -13537 8b/-> *ecx 0/r32/eax -13538 # var curr/esi: (addr handle var) = &vars->data[vars->top - 12] -13539 8d/copy-address *(ecx+eax-4) 6/r32/esi # vars + 8 + vars->top - 12/Live-var-size -13540 # var min/ecx: (addr handle var) = vars->data -13541 8d/copy-address *(ecx+8) 1/r32/ecx -13542 # edx = depth -13543 8b/-> *(ebp+0x10) 2/r32/edx -13544 { -13545 $emit-unconditional-jump-to-depth:loop: -13546 # if (curr < min) break -13547 39/compare %esi 1/r32/ecx -13548 0f 82/jump-if-addr< break/disp32 -13549 # var v/ebx: (addr var) = lookup(*curr) -13550 (lookup *esi *(esi+4)) # => eax -13551 89/<- %ebx 0/r32/eax -13552 # if (v->block-depth < until-block-depth) break -13553 39/compare *(ebx+0x10) 2/r32/edx # Var-block-depth -13554 0f 8c/jump-if-< break/disp32 -13555 { -13556 $emit-unconditional-jump-to-depth:check: -13557 # if v->block-depth != until-block-depth, continue -13558 39/compare *(ebx+0x10) 2/r32/edx # Var-block-depth -13559 0f 85/jump-if-!= break/disp32 -13560 $emit-unconditional-jump-to-depth:depth-found: -13561 # if v is not a literal, continue -13562 (size-of %ebx) # => eax -13563 3d/compare-eax-and 0/imm32 -13564 0f 85/jump-if-!= break/disp32 -13565 $emit-unconditional-jump-to-depth:label-found: -13566 # emit unconditional jump, then return -13567 (emit-indent *(ebp+8) *Curr-block-depth) -13568 (write-buffered *(ebp+8) "e9/jump ") -13569 (lookup *ebx *(ebx+4)) # Var-name Var-name => eax -13570 (write-buffered *(ebp+8) %eax) -13571 (write-buffered *(ebp+8) ":") -13572 (write-buffered *(ebp+8) *(ebp+0x14)) -13573 (write-buffered *(ebp+8) "/disp32\n") -13574 eb/jump $emit-unconditional-jump-to-depth:end/disp8 -13575 } -13576 # curr -= 12 -13577 81 5/subop/subtract %esi 0xc/imm32 -13578 e9/jump loop/disp32 -13579 } -13580 # TODO: error if no label at 'depth' was found -13581 $emit-unconditional-jump-to-depth:end: -13582 # . restore registers -13583 5e/pop-to-esi -13584 5b/pop-to-ebx -13585 5a/pop-to-edx -13586 59/pop-to-ecx -13587 58/pop-to-eax -13588 # . epilogue -13589 89/<- %esp 5/r32/ebp -13590 5d/pop-to-ebp -13591 c3/return -13592 -13593 # emit clean-up code for 'vars' until some block depth -13594 # doesn't actually modify 'vars' so we need traverse manually inside the stack -13595 emit-cleanup-code-until-depth: # out: (addr buffered-file), vars: (addr stack live-var), until-block-depth: int -13596 # . prologue -13597 55/push-ebp -13598 89/<- %ebp 4/r32/esp -13599 # . save registers -13600 50/push-eax -13601 51/push-ecx -13602 52/push-edx -13603 53/push-ebx -13604 56/push-esi -13605 #? (write-buffered Stderr "--- cleanup\n") -13606 #? (flush Stderr) -13607 # ecx = vars -13608 8b/-> *(ebp+0xc) 1/r32/ecx -13609 # var esi: int = vars->top -13610 8b/-> *ecx 6/r32/esi -13611 # var curr/esi: (addr handle var) = &vars->data[vars->top - 12] -13612 8d/copy-address *(ecx+esi-4) 6/r32/esi # vars + 8 + vars->top - 12/Live-var-size -13613 # var min/ecx: (addr handle var) = vars->data -13614 81 0/subop/add %ecx 8/imm32 -13615 # edx = until-block-depth -13616 8b/-> *(ebp+0x10) 2/r32/edx -13617 { -13618 $emit-cleanup-code-until-depth:loop: -13619 # if (curr < min) break -13620 39/compare %esi 1/r32/ecx -13621 0f 82/jump-if-addr< break/disp32 -13622 # var v/ebx: (addr var) = lookup(*curr) -13623 (lookup *esi *(esi+4)) # => eax -13624 89/<- %ebx 0/r32/eax -13625 #? (lookup *ebx *(ebx+4)) # Var-name -13626 #? (write-buffered Stderr "var ") -13627 #? (write-buffered Stderr %eax) -13628 #? (write-buffered Stderr Newline) -13629 #? (flush Stderr) -13630 # if (v->block-depth < until-block-depth) break -13631 39/compare *(ebx+0x10) 2/r32/edx # Var-block-depth -13632 0f 8c/jump-if-< break/disp32 -13633 # if v is in a register -13634 81 7/subop/compare *(ebx+0x18) 0/imm32 # Var-register -13635 { -13636 0f 84/jump-if-= break/disp32 -13637 { -13638 $emit-cleanup-code-until-depth:check-for-previous-spill: -13639 8b/-> *(esi+8) 0/r32/eax # Live-var-register-spilled -13640 3d/compare-eax-and 0/imm32/false -13641 74/jump-if-= break/disp8 -13642 $emit-cleanup-code-until-depth:reclaim-var-in-register: -13643 (emit-indent *(ebp+8) *Curr-block-depth) -13644 (write-buffered *(ebp+8) "8f 0/subop/pop %") -13645 (lookup *(ebx+0x18) *(ebx+0x1c)) # Var-register Var-register => eax -13646 (write-buffered *(ebp+8) %eax) -13647 (write-buffered *(ebp+8) Newline) -13648 } -13649 eb/jump $emit-cleanup-code-until-depth:continue/disp8 -13650 } -13651 # otherwise v is on the stack -13652 { -13653 75/jump-if-!= break/disp8 -13654 $emit-cleanup-code-until-depth:var-on-stack: -13655 (size-of %ebx) # => eax -13656 # don't emit code for labels -13657 3d/compare-eax-and 0/imm32 -13658 74/jump-if-= break/disp8 -13659 $emit-cleanup-code-until-depth:reclaim-var-on-stack: -13660 (emit-indent *(ebp+8) *Curr-block-depth) -13661 (write-buffered *(ebp+8) "81 0/subop/add %esp ") -13662 (write-int32-hex-buffered *(ebp+8) %eax) -13663 (write-buffered *(ebp+8) "/imm32\n") -13664 } -13665 $emit-cleanup-code-until-depth:continue: -13666 # curr -= 12 -13667 81 5/subop/subtract %esi 0xc/imm32 -13668 e9/jump loop/disp32 -13669 } -13670 $emit-cleanup-code-until-depth:end: -13671 # . restore registers -13672 5e/pop-to-esi -13673 5b/pop-to-ebx -13674 5a/pop-to-edx -13675 59/pop-to-ecx -13676 58/pop-to-eax -13677 # . epilogue -13678 89/<- %esp 5/r32/ebp -13679 5d/pop-to-ebp -13680 c3/return -13681 -13682 # emit clean-up code for 'vars' until a given label is encountered -13683 # doesn't actually modify 'vars' so we need traverse manually inside the stack -13684 emit-cleanup-code-until-target: # out: (addr buffered-file), vars: (addr stack live-var), until-block-label: (addr array byte) -13685 # . prologue -13686 55/push-ebp -13687 89/<- %ebp 4/r32/esp -13688 # . save registers -13689 50/push-eax -13690 51/push-ecx -13691 52/push-edx -13692 53/push-ebx -13693 # ecx = vars -13694 8b/-> *(ebp+0xc) 1/r32/ecx -13695 # var eax: int = vars->top -13696 8b/-> *ecx 0/r32/eax -13697 # var curr/edx: (addr handle var) = &vars->data[vars->top - 12] -13698 8d/copy-address *(ecx+eax-4) 2/r32/edx # vars + 8 + vars->top - 12/Live-var-size -13699 # var min/ecx: (addr handle var) = vars->data -13700 81 0/subop/add %ecx 8/imm32 -13701 { -13702 $emit-cleanup-code-until-target:loop: -13703 # if (curr < min) break -13704 39/compare %edx 1/r32/ecx -13705 0f 82/jump-if-addr< break/disp32 -13706 # var v/ebx: (handle var) = lookup(*curr) -13707 (lookup *edx *(edx+4)) # => eax -13708 89/<- %ebx 0/r32/eax -13709 # if (v->name == until-block-label) break -13710 (lookup *ebx *(ebx+4)) # Var-name Var-name => eax -13711 (string-equal? %eax *(ebp+0x10)) # => eax -13712 3d/compare-eax-and 0/imm32/false -13713 0f 85/jump-if-!= break/disp32 -13714 # if v is in a register -13715 81 7/subop/compare *(ebx+0x18) 0/imm32 # Var-register -13716 { -13717 0f 84/jump-if-= break/disp32 -13718 { -13719 $emit-cleanup-code-until-target:check-for-previous-spill: -13720 8b/-> *(edx+8) 0/r32/eax # Live-var-register-spilled -13721 3d/compare-eax-and 0/imm32/false -13722 74/jump-if-= break/disp8 -13723 $emit-cleanup-code-until-target:reclaim-var-in-register: -13724 (emit-indent *(ebp+8) *Curr-block-depth) -13725 (write-buffered *(ebp+8) "8f 0/subop/pop %") -13726 (lookup *(ebx+0x18) *(ebx+0x1c)) # Var-register Var-register => eax -13727 (write-buffered *(ebp+8) %eax) -13728 (write-buffered *(ebp+8) Newline) -13729 } -13730 eb/jump $emit-cleanup-code-until-target:continue/disp8 -13731 } -13732 # otherwise v is on the stack -13733 { -13734 75/jump-if-!= break/disp8 -13735 $emit-cleanup-code-until-target:reclaim-var-on-stack: -13736 (size-of %ebx) # => eax -13737 # don't emit code for labels -13738 3d/compare-eax-and 0/imm32 -13739 74/jump-if-= break/disp8 -13740 # -13741 (emit-indent *(ebp+8) *Curr-block-depth) -13742 (write-buffered *(ebp+8) "81 0/subop/add %esp ") -13743 (write-int32-hex-buffered *(ebp+8) %eax) -13744 (write-buffered *(ebp+8) "/imm32\n") -13745 } -13746 $emit-cleanup-code-until-target:continue: +12930 (size-of-array %ecx) # => eax +12931 eb/jump $size-of-deref:end/disp8 +12932 } +12933 # if is-mu-stream?(t) return size-of-stream(t) +12934 { +12935 (is-mu-stream? %ecx) # => eax +12936 3d/compare-eax-and 0/imm32/false +12937 74/jump-if-= break/disp8 +12938 (size-of-stream %ecx) # => eax +12939 eb/jump $size-of-deref:end/disp8 +12940 } +12941 # if (!t->is-atom?) t = lookup(t->left) +12942 { +12943 81 7/subop/compare *ecx 0/imm32/false # Type-tree-is-atom +12944 75/jump-if-!= break/disp8 +12945 (lookup *(ecx+4) *(ecx+8)) # Type-tree-left Type-tree-left => eax +12946 89/<- %ecx 0/r32/eax +12947 } +12948 # TODO: assert t->is-atom? +12949 (size-of-type-id *(ecx+4)) # Type-tree-value => eax +12950 $size-of-deref:end: +12951 # . restore registers +12952 59/pop-to-ecx +12953 # . epilogue +12954 89/<- %esp 5/r32/ebp +12955 5d/pop-to-ebp +12956 c3/return +12957 +12958 is-mu-array?: # t: (addr type-tree) -> result/eax: boolean +12959 # . prologue +12960 55/push-ebp +12961 89/<- %ebp 4/r32/esp +12962 # . save registers +12963 51/push-ecx +12964 # ecx = t +12965 8b/-> *(ebp+8) 1/r32/ecx +12966 # if t->is-atom?, return false +12967 81 7/subop/compare *ecx 0/imm32/false # Type-tree-is-atom +12968 75/jump-if-!= $is-mu-array?:return-false/disp8 +12969 # if !t->left->is-atom?, return false +12970 (lookup *(ecx+4) *(ecx+8)) # Type-tree-left Type-tree-left => eax +12971 81 7/subop/compare *eax 0/imm32/false # Type-tree-is-atom +12972 74/jump-if-= $is-mu-array?:return-false/disp8 +12973 # return t->left->value == array +12974 81 7/subop/compare *(eax+4) 3/imm32/array-type-id # Type-tree-value +12975 0f 94/set-if-= %al +12976 81 4/subop/and %eax 0xff/imm32 +12977 eb/jump $is-mu-array?:end/disp8 +12978 $is-mu-array?:return-false: +12979 b8/copy-to-eax 0/imm32/false +12980 $is-mu-array?:end: +12981 # . restore registers +12982 59/pop-to-ecx +12983 # . epilogue +12984 89/<- %esp 5/r32/ebp +12985 5d/pop-to-ebp +12986 c3/return +12987 +12988 # size of a statically allocated array where the size is part of the type expression +12989 size-of-array: # a: (addr type-tree) -> result/eax: int +12990 # . prologue +12991 55/push-ebp +12992 89/<- %ebp 4/r32/esp +12993 # . save registers +12994 51/push-ecx +12995 52/push-edx +12996 # +12997 8b/-> *(ebp+8) 1/r32/ecx +12998 # TODO: assert that a->left is 'array' +12999 (lookup *(ecx+0xc) *(ecx+0x10)) # Type-tree-right Type-tree-right => eax +13000 89/<- %ecx 0/r32/eax +13001 # var elem-type/edx: type-id = a->right->left->value +13002 (lookup *(ecx+4) *(ecx+8)) # Type-tree-left Type-tree-left => eax +13003 8b/-> *(eax+4) 2/r32/edx # Type-tree-value +13004 # TODO: assert that a->right->right->left->value == size +13005 # var array-size/ecx: int = a->right->right->left->value-size +13006 (lookup *(ecx+0xc) *(ecx+0x10)) # Type-tree-right Type-tree-right => eax +13007 (lookup *(eax+4) *(eax+8)) # Type-tree-left Type-tree-left => eax +13008 8b/-> *(eax+8) 1/r32/ecx # Type-tree-value-size +13009 # return 4 + array-size * size-of(elem-type) +13010 (size-of-type-id-as-array-element %edx) # => eax +13011 f7 4/subop/multiply-into-eax %ecx +13012 05/add-to-eax 4/imm32 # for array size +13013 $size-of-array:end: +13014 # . restore registers +13015 5a/pop-to-edx +13016 59/pop-to-ecx +13017 # . epilogue +13018 89/<- %esp 5/r32/ebp +13019 5d/pop-to-ebp +13020 c3/return +13021 +13022 is-mu-stream?: # t: (addr type-tree) -> result/eax: boolean +13023 # . prologue +13024 55/push-ebp +13025 89/<- %ebp 4/r32/esp +13026 # . save registers +13027 51/push-ecx +13028 # ecx = t +13029 8b/-> *(ebp+8) 1/r32/ecx +13030 # if t->is-atom?, return false +13031 81 7/subop/compare *ecx 0/imm32/false # Type-tree-is-atom +13032 75/jump-if-!= $is-mu-stream?:return-false/disp8 +13033 # if !t->left->is-atom?, return false +13034 (lookup *(ecx+4) *(ecx+8)) # Type-tree-left Type-tree-left => eax +13035 81 7/subop/compare *eax 0/imm32/false # Type-tree-is-atom +13036 74/jump-if-= $is-mu-stream?:return-false/disp8 +13037 # return t->left->value == stream +13038 81 7/subop/compare *(eax+4) 0xb/imm32/stream-type-id # Type-tree-value +13039 0f 94/set-if-= %al +13040 81 4/subop/and %eax 0xff/imm32 +13041 eb/jump $is-mu-stream?:end/disp8 +13042 $is-mu-stream?:return-false: +13043 b8/copy-to-eax 0/imm32/false +13044 $is-mu-stream?:end: +13045 # . restore registers +13046 59/pop-to-ecx +13047 # . epilogue +13048 89/<- %esp 5/r32/ebp +13049 5d/pop-to-ebp +13050 c3/return +13051 +13052 # size of a statically allocated stream where the size is part of the type expression +13053 size-of-stream: # a: (addr type-tree) -> result/eax: int +13054 # . prologue +13055 55/push-ebp +13056 89/<- %ebp 4/r32/esp +13057 # +13058 (size-of-array *(ebp+8)) # assumes we ignore the actual type name 'array' in the type +13059 05/add-to-eax 8/imm32 # for read/write pointers +13060 $size-of-stream:end: +13061 # . epilogue +13062 89/<- %esp 5/r32/ebp +13063 5d/pop-to-ebp +13064 c3/return +13065 +13066 size-of-type-id: # t: type-id -> result/eax: int +13067 # . prologue +13068 55/push-ebp +13069 89/<- %ebp 4/r32/esp +13070 # . save registers +13071 51/push-ecx +13072 # var out/ecx: (handle typeinfo) +13073 68/push 0/imm32 +13074 68/push 0/imm32 +13075 89/<- %ecx 4/r32/esp +13076 # eax = t +13077 8b/-> *(ebp+8) 0/r32/eax +13078 # if t is a literal, return 0 +13079 3d/compare-eax-and 0/imm32 +13080 0f 84/jump-if-= $size-of-type-id:end/disp32 # eax changes type from type-id to int +13081 # if t is a byte, return 4 (because we don't really support non-multiples of 4) +13082 3d/compare-eax-and 8/imm32/byte +13083 { +13084 75/jump-if-!= break/disp8 +13085 b8/copy-to-eax 4/imm32 +13086 eb/jump $size-of-type-id:end/disp8 +13087 } +13088 # if t is a handle, return 8 +13089 3d/compare-eax-and 4/imm32/handle +13090 { +13091 75/jump-if-!= break/disp8 +13092 b8/copy-to-eax 8/imm32 +13093 eb/jump $size-of-type-id:end/disp8 # eax changes type from type-id to int +13094 } +13095 # if t is a user-defined type, return its size +13096 # TODO: support non-atom type +13097 (find-typeinfo %eax %ecx) +13098 { +13099 81 7/subop/compare *ecx 0/imm32 +13100 74/jump-if-= break/disp8 +13101 $size-of-type-id:user-defined: +13102 (lookup *ecx *(ecx+4)) # => eax +13103 8b/-> *(eax+0xc) 0/r32/eax # Typeinfo-total-size-in-bytes +13104 eb/jump $size-of-type-id:end/disp8 +13105 } +13106 # otherwise return the word size +13107 b8/copy-to-eax 4/imm32 +13108 $size-of-type-id:end: +13109 # . reclaim locals +13110 81 0/subop/add %esp 8/imm32 +13111 # . restore registers +13112 59/pop-to-ecx +13113 # . epilogue +13114 89/<- %esp 5/r32/ebp +13115 5d/pop-to-ebp +13116 c3/return +13117 +13118 type-equal?: # a: (addr type-tree), b: (addr type-tree) -> result/eax: boolean +13119 # . prologue +13120 55/push-ebp +13121 89/<- %ebp 4/r32/esp +13122 # . save registers +13123 51/push-ecx +13124 52/push-edx +13125 53/push-ebx +13126 # ecx = a +13127 8b/-> *(ebp+8) 1/r32/ecx +13128 # edx = b +13129 8b/-> *(ebp+0xc) 2/r32/edx +13130 $type-equal?:compare-addr: +13131 # if (a == b) return true +13132 8b/-> %ecx 0/r32/eax # Var-type +13133 39/compare %edx 0/r32/eax # Var-type +13134 b8/copy-to-eax 1/imm32/true +13135 0f 84/jump-if-= $type-equal?:end/disp32 +13136 $type-equal?:compare-atom-state: +13137 # if (a->is-atom? != b->is-atom?) return false +13138 8b/-> *ecx 3/r32/ebx # Type-tree-is-atom +13139 39/compare *edx 3/r32/ebx # Type-tree-is-atom +13140 b8/copy-to-eax 0/imm32/false +13141 0f 85/jump-if-!= $type-equal?:end/disp32 +13142 # if a->is-atom? return (a->value == b->value) +13143 { +13144 $type-equal?:check-atom: +13145 81 7/subop/compare %ebx 0/imm32/false +13146 74/jump-if-= break/disp8 +13147 $type-equal?:is-atom: +13148 8b/-> *(ecx+4) 0/r32/eax # Type-tree-value +13149 39/compare *(edx+4) 0/r32/eax # Type-tree-value +13150 0f 94/set-if-= %al +13151 81 4/subop/and %eax 0xff/imm32 +13152 e9/jump $type-equal?:end/disp32 +13153 } +13154 $type-equal?:check-left: +13155 # if (!type-equal?(a->left, b->left)) return false +13156 (lookup *(ecx+4) *(ecx+8)) # Type-tree-left Type-tree-left => eax +13157 89/<- %ebx 0/r32/eax +13158 (lookup *(edx+4) *(edx+8)) # Type-tree-left Type-tree-left => eax +13159 (type-equal? %eax %ebx) # => eax +13160 3d/compare-eax-and 0/imm32/false +13161 74/jump-if-= $type-equal?:end/disp8 +13162 $type-equal?:check-right: +13163 # return type-equal?(a->right, b->right) +13164 (lookup *(ecx+0xc) *(ecx+0x10)) # Type-tree-right Type-tree-right => eax +13165 89/<- %ebx 0/r32/eax +13166 (lookup *(edx+0xc) *(edx+0x10)) # Type-tree-right Type-tree-right => eax +13167 (type-equal? %eax %ebx) # => eax +13168 $type-equal?:end: +13169 # . restore registers +13170 5b/pop-to-ebx +13171 5a/pop-to-edx +13172 59/pop-to-ecx +13173 # . epilogue +13174 89/<- %esp 5/r32/ebp +13175 5d/pop-to-ebp +13176 c3/return +13177 +13178 ####################################################### +13179 # Code-generation +13180 ####################################################### +13181 +13182 == data +13183 +13184 # Global state added to each var record when performing code-generation. +13185 Curr-local-stack-offset: # (addr int) +13186 0/imm32 +13187 +13188 == code +13189 +13190 emit-subx: # out: (addr buffered-file), err: (addr buffered-file), ed: (addr exit-descriptor) +13191 # . prologue +13192 55/push-ebp +13193 89/<- %ebp 4/r32/esp +13194 # . save registers +13195 50/push-eax +13196 # var curr/eax: (addr function) = *Program->functions +13197 (lookup *_Program-functions *_Program-functions->payload) # => eax +13198 { +13199 # if (curr == null) break +13200 3d/compare-eax-and 0/imm32 +13201 0f 84/jump-if-= break/disp32 +13202 (emit-subx-function *(ebp+8) %eax *(ebp+0xc) *(ebp+0x10)) +13203 # curr = lookup(curr->next) +13204 (lookup *(eax+0x20) *(eax+0x24)) # Function-next Function-next => eax +13205 e9/jump loop/disp32 +13206 } +13207 $emit-subx:end: +13208 # . restore registers +13209 58/pop-to-eax +13210 # . epilogue +13211 89/<- %esp 5/r32/ebp +13212 5d/pop-to-ebp +13213 c3/return +13214 +13215 emit-subx-function: # out: (addr buffered-file), f: (addr function), err: (addr buffered-file), ed: (addr exit-descriptor) +13216 # . prologue +13217 55/push-ebp +13218 89/<- %ebp 4/r32/esp +13219 # some preprocessing +13220 (populate-mu-type-offsets-in-inouts *(ebp+0xc)) +13221 # . save registers +13222 50/push-eax +13223 51/push-ecx +13224 52/push-edx +13225 # initialize some global state +13226 c7 0/subop/copy *Curr-block-depth 1/imm32 # Important: keep this in sync with the parse phase +13227 c7 0/subop/copy *Curr-local-stack-offset 0/imm32 +13228 # ecx = f +13229 8b/-> *(ebp+0xc) 1/r32/ecx +13230 # var vars/edx: (stack (addr var) 256) +13231 81 5/subop/subtract %esp 0xc00/imm32 +13232 68/push 0xc00/imm32/size +13233 68/push 0/imm32/top +13234 89/<- %edx 4/r32/esp +13235 # var name/eax: (addr array byte) = lookup(f->name) +13236 (lookup *ecx *(ecx+4)) # Function-name Function-name => eax +13237 # +13238 (write-buffered *(ebp+8) %eax) +13239 (write-buffered *(ebp+8) ":\n") +13240 (emit-subx-prologue *(ebp+8)) +13241 # var body/eax: (addr block) = lookup(f->body) +13242 (lookup *(ecx+0x18) *(ecx+0x1c)) # Function-body Function-body => eax +13243 # +13244 (emit-subx-block *(ebp+8) %eax %edx *(ebp+0xc) *(ebp+0x10) *(ebp+0x14)) +13245 (emit-subx-epilogue *(ebp+8)) +13246 # TODO: validate that *Curr-block-depth and *Curr-local-stack-offset have +13247 # been cleaned up +13248 $emit-subx-function:end: +13249 # . reclaim locals +13250 81 0/subop/add %esp 0xc08/imm32 +13251 # . restore registers +13252 5a/pop-to-edx +13253 59/pop-to-ecx +13254 58/pop-to-eax +13255 # . epilogue +13256 89/<- %esp 5/r32/ebp +13257 5d/pop-to-ebp +13258 c3/return +13259 +13260 populate-mu-type-offsets-in-inouts: # f: (addr function) +13261 # . prologue +13262 55/push-ebp +13263 89/<- %ebp 4/r32/esp +13264 # . save registers +13265 50/push-eax +13266 51/push-ecx +13267 52/push-edx +13268 53/push-ebx +13269 57/push-edi +13270 # var next-offset/edx: int = 8 +13271 ba/copy-to-edx 8/imm32 +13272 # var curr/ecx: (addr list var) = lookup(f->inouts) +13273 8b/-> *(ebp+8) 1/r32/ecx +13274 (lookup *(ecx+8) *(ecx+0xc)) # Function-inouts Function-inouts => eax +13275 89/<- %ecx 0/r32/eax +13276 { +13277 $populate-mu-type-offsets-in-inouts:loop: +13278 81 7/subop/compare %ecx 0/imm32 +13279 74/jump-if-= break/disp8 +13280 # var v/ebx: (addr var) = lookup(curr->value) +13281 (lookup *ecx *(ecx+4)) # List-value List-value => eax +13282 89/<- %ebx 0/r32/eax +13283 #? (lookup *ebx *(ebx+4)) +13284 #? (write-buffered Stderr "setting offset of fn inout ") +13285 #? (write-buffered Stderr %eax) +13286 #? (write-buffered Stderr "@") +13287 #? (write-int32-hex-buffered Stderr %ebx) +13288 #? (write-buffered Stderr " to ") +13289 #? (write-int32-hex-buffered Stderr %edx) +13290 #? (write-buffered Stderr Newline) +13291 #? (flush Stderr) +13292 # v->offset = next-offset +13293 89/<- *(ebx+0x14) 2/r32/edx # Var-offset +13294 # next-offset += size-of(v) +13295 (size-of %ebx) # => eax +13296 01/add-to %edx 0/r32/eax +13297 # curr = lookup(curr->next) +13298 (lookup *(ecx+8) *(ecx+0xc)) # List-next List-next => eax +13299 89/<- %ecx 0/r32/eax +13300 # +13301 eb/jump loop/disp8 +13302 } +13303 $populate-mu-type-offsets-in-inouts:end: +13304 # . restore registers +13305 5f/pop-to-edi +13306 5b/pop-to-ebx +13307 5a/pop-to-edx +13308 59/pop-to-ecx +13309 58/pop-to-eax +13310 # . epilogue +13311 89/<- %esp 5/r32/ebp +13312 5d/pop-to-ebp +13313 c3/return +13314 +13315 emit-subx-stmt-list: # out: (addr buffered-file), stmts: (addr list stmt), vars: (addr stack live-var), fn: (addr function), err: (addr buffered-file), ed: (addr exit-descriptor) +13316 # . prologue +13317 55/push-ebp +13318 89/<- %ebp 4/r32/esp +13319 # . save registers +13320 50/push-eax +13321 51/push-ecx +13322 53/push-ebx +13323 56/push-esi +13324 # esi = stmts +13325 8b/-> *(ebp+0xc) 6/r32/esi +13326 # +13327 { +13328 $emit-subx-stmt-list:loop: +13329 81 7/subop/compare %esi 0/imm32 +13330 0f 84/jump-if-= break/disp32 +13331 # var curr-stmt/ecx: (addr stmt) = lookup(stmts->value) +13332 (lookup *esi *(esi+4)) # List-value List-value => eax +13333 89/<- %ecx 0/r32/eax +13334 { +13335 $emit-subx-stmt-list:check-for-block: +13336 81 7/subop/compare *ecx 0/imm32/block # Stmt-tag +13337 75/jump-if-!= break/disp8 +13338 $emit-subx-stmt-list:block: +13339 (emit-subx-block *(ebp+8) %ecx *(ebp+0x10) *(ebp+0x14) *(ebp+0x18) *(ebp+0x1c)) +13340 } +13341 { +13342 $emit-subx-stmt-list:check-for-stmt: +13343 81 7/subop/compare *ecx 1/imm32/stmt1 # Stmt-tag +13344 0f 85/jump-if-!= break/disp32 +13345 $emit-subx-stmt-list:stmt1: +13346 { +13347 (is-mu-branch? %ecx) # => eax +13348 3d/compare-eax-and 0/imm32/false +13349 0f 84/jump-if-= break/disp32 +13350 $emit-subx-stmt-list:branch-stmt: +13351 +-- 27 lines: # unconditional loops ----------------------------------------------------------------------------------------------------------------------------------------------------- +13378 +-- 16 lines: # unconditional breaks ---------------------------------------------------------------------------------------------------------------------------------------------------- +13394 +-- 38 lines: # simple conditional branches without a target ---------------------------------------------------------------------------------------------------------------------------- +13432 +-- 19 lines: # conditional branches with an explicit target ---------------------------------------------------------------------------------------------------------------------------- +13451 } +13452 $emit-subx-stmt-list:1-to-1: +13453 (emit-subx-stmt *(ebp+8) %ecx Primitives *(ebp+0x18) *(ebp+0x1c)) +13454 e9/jump $emit-subx-stmt-list:continue/disp32 +13455 } +13456 { +13457 $emit-subx-stmt-list:check-for-var-def: +13458 81 7/subop/compare *ecx 2/imm32/var-def # Stmt-tag +13459 75/jump-if-!= break/disp8 +13460 $emit-subx-stmt-list:var-def: +13461 (emit-subx-var-def *(ebp+8) %ecx) +13462 (push *(ebp+0x10) *(ecx+4)) # Vardef-var +13463 (push *(ebp+0x10) *(ecx+8)) # Vardef-var +13464 (push *(ebp+0x10) 0) # Live-var-register-spilled = 0 for vars on the stack +13465 # +13466 eb/jump $emit-subx-stmt-list:continue/disp8 +13467 } +13468 { +13469 $emit-subx-stmt-list:check-for-reg-var-def: +13470 81 7/subop/compare *ecx 3/imm32/reg-var-def # Stmt-tag +13471 0f 85/jump-if-!= break/disp32 +13472 $emit-subx-stmt-list:reg-var-def: +13473 # TODO: ensure that there's exactly one output +13474 (push-output-and-maybe-emit-spill *(ebp+8) %ecx *(ebp+0x10) %esi *(ebp+0x14) *(ebp+0x18) *(ebp+0x1c)) +13475 # emit the instruction as usual +13476 (emit-subx-stmt *(ebp+8) %ecx Primitives *(ebp+0x18) *(ebp+0x1c)) +13477 # +13478 eb/jump $emit-subx-stmt-list:continue/disp8 +13479 } +13480 $emit-subx-stmt-list:continue: +13481 # TODO: raise an error on unrecognized Stmt-tag +13482 (lookup *(esi+8) *(esi+0xc)) # List-next List-next => eax +13483 89/<- %esi 0/r32/eax +13484 e9/jump loop/disp32 +13485 } +13486 $emit-subx-stmt-list:emit-cleanup: +13487 (emit-cleanup-code-until-depth *(ebp+8) *(ebp+0x10) *Curr-block-depth) +13488 $emit-subx-stmt-list:clean-up: +13489 (clean-up-blocks *(ebp+0x10) *Curr-block-depth *(ebp+0x14)) +13490 $emit-subx-stmt-list:end: +13491 # . restore registers +13492 5e/pop-to-esi +13493 5b/pop-to-ebx +13494 59/pop-to-ecx +13495 58/pop-to-eax +13496 # . epilogue +13497 89/<- %esp 5/r32/ebp +13498 5d/pop-to-ebp +13499 c3/return +13500 +13501 # 'later-stmts' includes 'stmt', but will behave the same even without it; reg-var-def stmts are guaranteed not to write to function outputs. +13502 push-output-and-maybe-emit-spill: # out: (addr buffered-file), stmt: (addr reg-var-def), vars: (addr stack (handle var)), later-stmts: (addr list stmt), fn: (addr function), err: (addr buffered-file), ed: (addr exit-descriptor) +13503 # . prologue +13504 55/push-ebp +13505 89/<- %ebp 4/r32/esp +13506 # . save registers +13507 50/push-eax +13508 51/push-ecx +13509 52/push-edx +13510 # ecx = stmt +13511 8b/-> *(ebp+0xc) 1/r32/ecx +13512 # var sv/eax: (addr stmt-var) = lookup(curr-stmt->outputs) +13513 (lookup *(ecx+0x14) *(ecx+0x18)) # Regvardef-outputs Regvardef-outputs => eax +13514 # TODO: assert !sv->is-deref? +13515 # var v/ecx: (addr var) = lookup(sv->value) +13516 (lookup *eax *(eax+4)) # Stmt-var-value Stmt-var-value => eax +13517 89/<- %ecx 0/r32/eax +13518 # v->block-depth = *Curr-block-depth +13519 8b/-> *Curr-block-depth 0/r32/eax +13520 89/<- *(ecx+0x10) 0/r32/eax # Var-block-depth +13521 #? (write-buffered Stderr "var ") +13522 #? (lookup *ecx *(ecx+4)) +13523 #? (write-buffered Stderr %eax) +13524 #? (write-buffered Stderr " at depth ") +13525 #? (write-int32-hex-buffered Stderr *(ecx+0x10)) +13526 #? (write-buffered Stderr Newline) +13527 #? (flush Stderr) +13528 # ensure that v is in a register +13529 81 7/subop/compare *(ecx+0x18) 0/imm32 # Var-register +13530 0f 84/jump-if-= $push-output-and-maybe-emit-spill:abort/disp32 +13531 # var emit-spill?/edx: boolean = not-yet-spilled-this-block? && will-not-write-some-register?(fn) +13532 (not-yet-spilled-this-block? %ecx *(ebp+0x10)) # => eax +13533 89/<- %edx 0/r32/eax +13534 3d/compare-eax-and 0/imm32/false +13535 0f 84/jump-if-= $push-output-and-maybe-emit-spill:push/disp32 +13536 (will-not-write-some-register? %ecx *(ebp+0x14) *(ebp+0x18)) # => eax +13537 89/<- %edx 0/r32/eax +13538 # check emit-spill? +13539 3d/compare-eax-and 0/imm32/false +13540 0f 84/jump-if-= $push-output-and-maybe-emit-spill:push/disp32 +13541 # TODO: assert(size-of(output) == 4) +13542 # *Curr-local-stack-offset -= 4 +13543 81 5/subop/subtract *Curr-local-stack-offset 4/imm32 +13544 # emit spill +13545 (emit-indent *(ebp+8) *Curr-block-depth) +13546 (write-buffered *(ebp+8) "ff 6/subop/push %") +13547 (lookup *(ecx+0x18) *(ecx+0x1c)) # Var-register Var-register => eax +13548 (write-buffered *(ebp+8) %eax) +13549 (write-buffered *(ebp+8) Newline) +13550 $push-output-and-maybe-emit-spill:push: +13551 8b/-> *(ebp+0xc) 1/r32/ecx +13552 (lookup *(ecx+0x14) *(ecx+0x18)) # Regvardef-outputs Regvardef-outputs => eax +13553 # push(vars, {sv->value, emit-spill?}) +13554 (push *(ebp+0x10) *eax) # Stmt-var-value +13555 (push *(ebp+0x10) *(eax+4)) # Stmt-var-value +13556 (push *(ebp+0x10) %edx) +13557 $push-output-and-maybe-emit-spill:end: +13558 # . restore registers +13559 5a/pop-to-edx +13560 59/pop-to-ecx +13561 58/pop-to-eax +13562 # . epilogue +13563 89/<- %esp 5/r32/ebp +13564 5d/pop-to-ebp +13565 c3/return +13566 +13567 $push-output-and-maybe-emit-spill:abort: +13568 # error("var '" var->name "' initialized from an instruction must live in a register\n") +13569 (write-buffered *(ebp+0x1c) "var '") +13570 (write-buffered *(ebp+0x1c) *eax) # Var-name +13571 (write-buffered *(ebp+0x1c) "' initialized from an instruction must live in a register\n") +13572 (flush *(ebp+0x1c)) +13573 (stop *(ebp+0x20) 1) +13574 # never gets here +13575 +13576 emit-subx-cleanup-and-unconditional-nonlocal-branch: # out: (addr buffered-file), stmt: (addr stmt1), vars: (addr stack live-var) +13577 # . prologue +13578 55/push-ebp +13579 89/<- %ebp 4/r32/esp +13580 # . save registers +13581 50/push-eax +13582 51/push-ecx +13583 # ecx = stmt +13584 8b/-> *(ebp+0xc) 1/r32/ecx +13585 # var target/eax: (addr array byte) = curr-stmt->inouts->value->name +13586 (lookup *(ecx+0xc) *(ecx+0x10)) # Stmt1-inouts Stmt1-inouts => eax +13587 (lookup *eax *(eax+4)) # Stmt-var-value Stmt-var-value => eax +13588 (lookup *eax *(eax+4)) # Var-name Var-name => eax +13589 # clean up until target block +13590 (emit-cleanup-code-until-target *(ebp+8) *(ebp+0x10) %eax) +13591 # emit jump to target block +13592 (emit-indent *(ebp+8) *Curr-block-depth) +13593 (write-buffered *(ebp+8) "e9/jump ") +13594 (write-buffered *(ebp+8) %eax) +13595 (lookup *(ecx+4) *(ecx+8)) # Stmt1-operation Stmt1-operation => eax +13596 (string-starts-with? %eax "break") +13597 3d/compare-eax-and 0/imm32/false +13598 { +13599 74/jump-if-= break/disp8 +13600 (write-buffered *(ebp+8) ":break/disp32\n") +13601 } +13602 3d/compare-eax-and 0/imm32/false # just in case the function call modified flags +13603 { +13604 75/jump-if-!= break/disp8 +13605 (write-buffered *(ebp+8) ":loop/disp32\n") +13606 } +13607 $emit-subx-cleanup-and-unconditional-nonlocal-branch:end: +13608 # . restore registers +13609 59/pop-to-ecx +13610 58/pop-to-eax +13611 # . epilogue +13612 89/<- %esp 5/r32/ebp +13613 5d/pop-to-ebp +13614 c3/return +13615 +13616 is-mu-branch?: # stmt: (addr stmt1) -> result/eax: boolean +13617 # . prologue +13618 55/push-ebp +13619 89/<- %ebp 4/r32/esp +13620 # . save registers +13621 51/push-ecx +13622 # ecx = lookup(stmt->operation) +13623 8b/-> *(ebp+8) 1/r32/ecx +13624 (lookup *(ecx+4) *(ecx+8)) # Stmt1-operation Stmt1-operation => eax +13625 89/<- %ecx 0/r32/eax +13626 # if (stmt->operation starts with "loop") return true +13627 (string-starts-with? %ecx "loop") # => eax +13628 3d/compare-eax-and 0/imm32/false +13629 75/jump-if-not-equal $is-mu-branch?:end/disp8 +13630 # otherwise return (stmt->operation starts with "break") +13631 (string-starts-with? %ecx "break") # => eax +13632 $is-mu-branch?:end: +13633 # . restore registers +13634 59/pop-to-ecx +13635 # . epilogue +13636 89/<- %esp 5/r32/ebp +13637 5d/pop-to-ebp +13638 c3/return +13639 +13640 emit-reverse-break: # out: (addr buffered-file), stmt: (addr stmt1) +13641 # . prologue +13642 55/push-ebp +13643 89/<- %ebp 4/r32/esp +13644 # . save registers +13645 50/push-eax +13646 # eax = stmt +13647 8b/-> *(ebp+0xc) 0/r32/eax +13648 # +13649 (lookup *(eax+4) *(eax+8)) # Stmt1-operation Stmt1-operation => eax +13650 (get Reverse-branch %eax 0x10 "reverse-branch: ") # => eax: (addr handle array byte) +13651 (emit-indent *(ebp+8) *Curr-block-depth) +13652 (lookup *eax *(eax+4)) # => eax +13653 (write-buffered *(ebp+8) %eax) +13654 (write-buffered *(ebp+8) " break/disp32\n") +13655 $emit-reverse-break:end: +13656 # . restore registers +13657 58/pop-to-eax +13658 # . epilogue +13659 89/<- %esp 5/r32/ebp +13660 5d/pop-to-ebp +13661 c3/return +13662 +13663 == data +13664 +13665 # Table from Mu branch instructions to the reverse SubX opcodes for them. +13666 Reverse-branch: # (table (handle array byte) (handle array byte)) +13667 # a table is a stream +13668 0x140/imm32/write +13669 0/imm32/read +13670 0x140/imm32/size +13671 # data +13672 0x11/imm32/alloc-id _string-break-if-=/imm32 0x11/imm32/alloc-id _string_0f_85_jump_label/imm32 +13673 0x11/imm32/alloc-id _string-loop-if-=/imm32 0x11/imm32/alloc-id _string_0f_85_jump_label/imm32 +13674 0x11/imm32/alloc-id _string-break-if-!=/imm32 0x11/imm32/alloc-id _string_0f_84_jump_label/imm32 +13675 0x11/imm32/alloc-id _string-loop-if-!=/imm32 0x11/imm32/alloc-id _string_0f_84_jump_label/imm32 +13676 0x11/imm32/alloc-id _string-break-if-</imm32 0x11/imm32/alloc-id _string_0f_8d_jump_label/imm32 +13677 0x11/imm32/alloc-id _string-loop-if-</imm32 0x11/imm32/alloc-id _string_0f_8d_jump_label/imm32 +13678 0x11/imm32/alloc-id _string-break-if->/imm32 0x11/imm32/alloc-id _string_0f_8e_jump_label/imm32 +13679 0x11/imm32/alloc-id _string-loop-if->/imm32 0x11/imm32/alloc-id _string_0f_8e_jump_label/imm32 +13680 0x11/imm32/alloc-id _string-break-if-<=/imm32 0x11/imm32/alloc-id _string_0f_87_jump_label/imm32 +13681 0x11/imm32/alloc-id _string-loop-if-<=/imm32 0x11/imm32/alloc-id _string_0f_87_jump_label/imm32 +13682 0x11/imm32/alloc-id _string-break-if->=/imm32 0x11/imm32/alloc-id _string_0f_8c_jump_label/imm32 +13683 0x11/imm32/alloc-id _string-loop-if->=/imm32 0x11/imm32/alloc-id _string_0f_8c_jump_label/imm32 +13684 0x11/imm32/alloc-id _string-break-if-addr</imm32 0x11/imm32/alloc-id _string_0f_83_jump_label/imm32 +13685 0x11/imm32/alloc-id _string-loop-if-addr</imm32 0x11/imm32/alloc-id _string_0f_83_jump_label/imm32 +13686 0x11/imm32/alloc-id _string-break-if-addr>/imm32 0x11/imm32/alloc-id _string_0f_86_jump_label/imm32 +13687 0x11/imm32/alloc-id _string-loop-if-addr>/imm32 0x11/imm32/alloc-id _string_0f_86_jump_label/imm32 +13688 0x11/imm32/alloc-id _string-break-if-addr<=/imm32 0x11/imm32/alloc-id _string_0f_87_jump_label/imm32 +13689 0x11/imm32/alloc-id _string-loop-if-addr<=/imm32 0x11/imm32/alloc-id _string_0f_87_jump_label/imm32 +13690 0x11/imm32/alloc-id _string-break-if-addr>=/imm32 0x11/imm32/alloc-id _string_0f_82_jump_label/imm32 +13691 0x11/imm32/alloc-id _string-loop-if-addr>=/imm32 0x11/imm32/alloc-id _string_0f_82_jump_label/imm32 +13692 +13693 == code +13694 +13695 emit-unconditional-jump-to-depth: # out: (addr buffered-file), vars: (addr stack live-var), depth: int, label-suffix: (addr array byte) +13696 # . prologue +13697 55/push-ebp +13698 89/<- %ebp 4/r32/esp +13699 # . save registers +13700 50/push-eax +13701 51/push-ecx +13702 52/push-edx +13703 53/push-ebx +13704 56/push-esi +13705 # ecx = vars +13706 8b/-> *(ebp+0xc) 1/r32/ecx +13707 # var eax: int = vars->top +13708 8b/-> *ecx 0/r32/eax +13709 # var curr/esi: (addr handle var) = &vars->data[vars->top - 12] +13710 8d/copy-address *(ecx+eax-4) 6/r32/esi # vars + 8 + vars->top - 12/Live-var-size +13711 # var min/ecx: (addr handle var) = vars->data +13712 8d/copy-address *(ecx+8) 1/r32/ecx +13713 # edx = depth +13714 8b/-> *(ebp+0x10) 2/r32/edx +13715 { +13716 $emit-unconditional-jump-to-depth:loop: +13717 # if (curr < min) break +13718 39/compare %esi 1/r32/ecx +13719 0f 82/jump-if-addr< break/disp32 +13720 # var v/ebx: (addr var) = lookup(*curr) +13721 (lookup *esi *(esi+4)) # => eax +13722 89/<- %ebx 0/r32/eax +13723 # if (v->block-depth < until-block-depth) break +13724 39/compare *(ebx+0x10) 2/r32/edx # Var-block-depth +13725 0f 8c/jump-if-< break/disp32 +13726 { +13727 $emit-unconditional-jump-to-depth:check: +13728 # if v->block-depth != until-block-depth, continue +13729 39/compare *(ebx+0x10) 2/r32/edx # Var-block-depth +13730 0f 85/jump-if-!= break/disp32 +13731 $emit-unconditional-jump-to-depth:depth-found: +13732 # if v is not a literal, continue +13733 (size-of %ebx) # => eax +13734 3d/compare-eax-and 0/imm32 +13735 0f 85/jump-if-!= break/disp32 +13736 $emit-unconditional-jump-to-depth:label-found: +13737 # emit unconditional jump, then return +13738 (emit-indent *(ebp+8) *Curr-block-depth) +13739 (write-buffered *(ebp+8) "e9/jump ") +13740 (lookup *ebx *(ebx+4)) # Var-name Var-name => eax +13741 (write-buffered *(ebp+8) %eax) +13742 (write-buffered *(ebp+8) ":") +13743 (write-buffered *(ebp+8) *(ebp+0x14)) +13744 (write-buffered *(ebp+8) "/disp32\n") +13745 eb/jump $emit-unconditional-jump-to-depth:end/disp8 +13746 } 13747 # curr -= 12 -13748 81 5/subop/subtract %edx 0xc/imm32 +13748 81 5/subop/subtract %esi 0xc/imm32 13749 e9/jump loop/disp32 13750 } -13751 $emit-cleanup-code-until-target:end: -13752 # . restore registers -13753 5b/pop-to-ebx -13754 5a/pop-to-edx -13755 59/pop-to-ecx -13756 58/pop-to-eax -13757 # . epilogue -13758 89/<- %esp 5/r32/ebp -13759 5d/pop-to-ebp -13760 c3/return -13761 -13762 # Return true if there isn't a variable in 'vars' with the same block-depth -13763 # and register as 'v'. -13764 # 'v' is guaranteed not to be within 'vars'. -13765 not-yet-spilled-this-block?: # v: (addr var), vars: (addr stack live-var) -> result/eax: boolean -13766 # . prologue -13767 55/push-ebp -13768 89/<- %ebp 4/r32/esp -13769 # . save registers -13770 51/push-ecx -13771 52/push-edx -13772 53/push-ebx -13773 56/push-esi -13774 57/push-edi -13775 # ecx = vars -13776 8b/-> *(ebp+0xc) 1/r32/ecx -13777 # var eax: int = vars->top -13778 8b/-> *ecx 0/r32/eax -13779 # var curr/edx: (addr handle var) = &vars->data[vars->top - 12] -13780 8d/copy-address *(ecx+eax-4) 2/r32/edx # vars + 8 + vars->top - 12/Live-var-size -13781 # var min/ecx: (addr handle var) = vars->data -13782 8d/copy-address *(ecx+8) 1/r32/ecx -13783 # var depth/ebx: int = v->block-depth -13784 8b/-> *(ebp+8) 3/r32/ebx -13785 8b/-> *(ebx+0x10) 3/r32/ebx # Var-block-depth -13786 # var needle/esi: (addr array byte) = v->register -13787 8b/-> *(ebp+8) 6/r32/esi -13788 (lookup *(esi+0x18) *(esi+0x1c)) # Var-register Var-register => eax -13789 89/<- %esi 0/r32/eax -13790 { -13791 $not-yet-spilled-this-block?:loop: -13792 # if (curr < min) break -13793 39/compare %edx 1/r32/ecx -13794 0f 82/jump-if-addr< break/disp32 -13795 # var cand/edi: (addr var) = lookup(*curr) -13796 (lookup *edx *(edx+4)) # => eax -13797 89/<- %edi 0/r32/eax -13798 # if (cand->block-depth < depth) break -13799 39/compare *(edi+0x10) 3/r32/ebx # Var-block-depth -13800 0f 8c/jump-if-< break/disp32 -13801 # var cand-reg/edi: (array array byte) = cand->reg -13802 (lookup *(edi+0x18) *(edi+0x1c)) # Var-register Var-register => eax -13803 89/<- %edi 0/r32/eax -13804 # if (cand-reg == null) continue -13805 { -13806 $not-yet-spilled-this-block?:check-reg: -13807 81 7/subop/compare %edi 0/imm32 -13808 0f 84/jump-if-= break/disp32 -13809 # if (cand-reg == needle) return true -13810 (string-equal? %esi %edi) # => eax -13811 3d/compare-eax-and 0/imm32/false -13812 74/jump-if-= break/disp8 -13813 $not-yet-spilled-this-block?:return-false: -13814 b8/copy-to-eax 0/imm32/false -13815 eb/jump $not-yet-spilled-this-block?:end/disp8 -13816 } -13817 $not-yet-spilled-this-block?:continue: -13818 # curr -= 12 -13819 81 5/subop/subtract %edx 0xc/imm32 -13820 e9/jump loop/disp32 -13821 } -13822 $not-yet-spilled-this-block?:return-true: -13823 # return true -13824 b8/copy-to-eax 1/imm32/true -13825 $not-yet-spilled-this-block?:end: -13826 # . restore registers -13827 5f/pop-to-edi -13828 5e/pop-to-esi -13829 5b/pop-to-ebx -13830 5a/pop-to-edx -13831 59/pop-to-ecx -13832 # . epilogue -13833 89/<- %esp 5/r32/ebp -13834 5d/pop-to-ebp -13835 c3/return -13836 -13837 # could the register of 'v' ever be written to by one of the vars in fn-outputs? -13838 will-not-write-some-register?: # v: (addr var), stmts: (addr list stmt), fn: (addr function) -> result/eax: boolean -13839 # . prologue -13840 55/push-ebp -13841 89/<- %ebp 4/r32/esp -13842 # eax = v -13843 8b/-> *(ebp+8) 0/r32/eax -13844 # var reg/eax: (addr array byte) = lookup(v->register) -13845 (lookup *(eax+0x18) *(eax+0x1c)) # Var-register Var-register => eax -13846 # var target/eax: (addr var) = find-register(fn-outputs, reg) -13847 (find-register *(ebp+0x10) %eax) # => eax -13848 # if (target == 0) return true -13849 { -13850 3d/compare-eax-and 0/imm32 -13851 75/jump-if-!= break/disp8 -13852 b8/copy-to-eax 1/imm32/true -13853 eb/jump $will-not-write-some-register?:end/disp8 -13854 } -13855 # return !assigns-in-stmts?(stmts, target) -13856 (assigns-in-stmts? *(ebp+0xc) %eax) # => eax -13857 3d/compare-eax-and 0/imm32/false -13858 # assume: true = 1, so no need to mask with 0x000000ff -13859 0f 94/set-if-= %al -13860 $will-not-write-some-register?:end: -13861 # . epilogue -13862 89/<- %esp 5/r32/ebp -13863 5d/pop-to-ebp -13864 c3/return -13865 -13866 # return fn output with matching register -13867 # always returns false if 'reg' is null -13868 find-register: # fn: (addr function), reg: (addr array byte) -> result/eax: (addr var) -13869 # . prologue -13870 55/push-ebp -13871 89/<- %ebp 4/r32/esp -13872 # . save registers -13873 51/push-ecx -13874 # var curr/ecx: (addr list var) = lookup(fn->outputs) -13875 8b/-> *(ebp+8) 1/r32/ecx -13876 (lookup *(ecx+0x10) *(ecx+0x14)) # Function-outputs Function-outputs => eax -13877 89/<- %ecx 0/r32/eax -13878 { -13879 $find-register:loop: -13880 # if (curr == 0) break -13881 81 7/subop/compare %ecx 0/imm32 -13882 74/jump-if-= break/disp8 -13883 # eax = curr->value->register -13884 (lookup *ecx *(ecx+4)) # List-value List-value => eax -13885 (lookup *(eax+0x18) *(eax+0x1c)) # Var-register Var-register => eax -13886 # if (eax == reg) return curr->value -13887 $find-register:compare: -13888 (string-equal? *(ebp+0xc) %eax) # => eax -13889 { -13890 3d/compare-eax-and 0/imm32/false -13891 74/jump-if-= break/disp8 -13892 $find-register:found: -13893 (lookup *ecx *(ecx+4)) # List-value List-value => eax -13894 eb/jump $find-register:end/disp8 -13895 } -13896 # curr = lookup(curr->next) -13897 (lookup *(ecx+8) *(ecx+0xc)) # List-next List-next => eax -13898 89/<- %ecx 0/r32/eax -13899 # -13900 eb/jump loop/disp8 -13901 } -13902 $find-register:end: -13903 # . restore registers -13904 59/pop-to-ecx -13905 # . epilogue -13906 89/<- %esp 5/r32/ebp -13907 5d/pop-to-ebp -13908 c3/return -13909 -13910 assigns-in-stmts?: # stmts: (addr list stmt), v: (addr var) -> result/eax: boolean -13911 # . prologue -13912 55/push-ebp -13913 89/<- %ebp 4/r32/esp -13914 # . save registers -13915 51/push-ecx -13916 # var curr/ecx: (addr list stmt) = stmts -13917 8b/-> *(ebp+8) 1/r32/ecx -13918 { -13919 # if (curr == 0) break -13920 81 7/subop/compare %ecx 0/imm32 -13921 74/jump-if-= break/disp8 -13922 # if assigns-in-stmt?(curr->value, v) return true -13923 (lookup *ecx *(ecx+4)) # List-value List-value => eax -13924 (assigns-in-stmt? %eax *(ebp+0xc)) # => eax -13925 3d/compare-eax-and 0/imm32/false -13926 75/jump-if-!= break/disp8 -13927 # curr = lookup(curr->next) -13928 (lookup *(ecx+8) *(ecx+0xc)) # List-next List-next => eax -13929 89/<- %ecx 0/r32/eax -13930 # -13931 eb/jump loop/disp8 -13932 } -13933 $assigns-in-stmts?:end: -13934 # . restore registers -13935 59/pop-to-ecx -13936 # . epilogue -13937 89/<- %esp 5/r32/ebp -13938 5d/pop-to-ebp -13939 c3/return -13940 -13941 assigns-in-stmt?: # stmt: (addr stmt), v: (addr var) -> result/eax: boolean -13942 # . prologue -13943 55/push-ebp -13944 89/<- %ebp 4/r32/esp -13945 # . save registers -13946 51/push-ecx -13947 # ecx = stmt -13948 8b/-> *(ebp+8) 1/r32/ecx -13949 # if stmt is a stmt1, return assigns-in-stmt-vars?(stmt->outputs, v) -13950 { -13951 81 7/subop/compare *ecx 1/imm32/stmt1 # Stmt-tag -13952 75/jump-if-!= break/disp8 -13953 (lookup *(ecx+0x14) *(ecx+0x18)) # Stmt1-outputs Stmt1-outputs => eax -13954 (assigns-in-stmt-vars? %eax *(ebp+0xc)) # => eax -13955 eb/jump $assigns-in-stmt?:end/disp8 -13956 } -13957 # if stmt is a block, return assigns-in-stmts?(stmt->stmts, v) -13958 { -13959 81 7/subop/compare *ecx 0/imm32/block # Stmt-tag -13960 75/jump-if-!= break/disp8 -13961 (lookup *(ecx+4) *(ecx+8)) # Block-stmts Block-stmts => eax -13962 (assigns-in-stmts? %eax *(ebp+0xc)) # => eax -13963 eb/jump $assigns-in-stmt?:end/disp8 -13964 } -13965 # otherwise return false -13966 b8/copy 0/imm32/false -13967 $assigns-in-stmt?:end: -13968 # . restore registers -13969 59/pop-to-ecx -13970 # . epilogue -13971 89/<- %esp 5/r32/ebp -13972 5d/pop-to-ebp -13973 c3/return -13974 -13975 assigns-in-stmt-vars?: # stmt-var: (addr stmt-var), v: (addr var) -> result/eax: boolean -13976 # . prologue -13977 55/push-ebp -13978 89/<- %ebp 4/r32/esp -13979 # . save registers -13980 51/push-ecx -13981 # var curr/ecx: (addr stmt-var) = stmt-var -13982 8b/-> *(ebp+8) 1/r32/ecx -13983 { -13984 # if (curr == 0) break -13985 81 7/subop/compare %ecx 0/imm32 -13986 74/jump-if-= break/disp8 -13987 # eax = lookup(curr->value) -13988 (lookup *ecx *(ecx+4)) # Stmt-var-value Stmt-var-value => eax -13989 # if (eax == v && curr->is-deref? == false) return true -13990 { -13991 39/compare *(ebp+0xc) 0/r32/eax -13992 75/jump-if-!= break/disp8 -13993 81 7/subop/compare *(ecx+0x10) 0/imm32/false # Stmt-var-is-deref -13994 75/jump-if-!= break/disp8 -13995 b8/copy-to-eax 1/imm32/true -13996 eb/jump $assigns-in-stmt-vars?:end/disp8 -13997 } -13998 # curr = lookup(curr->next) -13999 (lookup *(ecx+8) *(ecx+0xc)) # Stmt-var-next Stmt-var-next => eax -14000 89/<- %ecx 0/r32/eax -14001 # -14002 eb/jump loop/disp8 -14003 } -14004 $assigns-in-stmt-vars?:end: -14005 # . restore registers -14006 59/pop-to-ecx -14007 # . epilogue -14008 89/<- %esp 5/r32/ebp -14009 5d/pop-to-ebp -14010 c3/return -14011 -14012 # is there a var before 'v' with the same block-depth and register on the 'vars' stack? -14013 # v is guaranteed to be within vars -14014 # 'start' is provided as an optimization, a pointer within vars -14015 # *start == v -14016 same-register-spilled-before?: # v: (addr var), vars: (addr stack (handle var)), start: (addr var) -> result/eax: boolean -14017 # . prologue -14018 55/push-ebp -14019 89/<- %ebp 4/r32/esp -14020 # . save registers -14021 51/push-ecx -14022 52/push-edx -14023 53/push-ebx -14024 56/push-esi -14025 57/push-edi -14026 # ecx = v -14027 8b/-> *(ebp+8) 1/r32/ecx -14028 # var reg/edx: (addr array byte) = lookup(v->register) -14029 (lookup *(ecx+0x18) *(ecx+0x1c)) # Var-register Var-register => eax -14030 89/<- %edx 0/r32/eax -14031 # var depth/ebx: int = v->block-depth -14032 8b/-> *(ecx+0x10) 3/r32/ebx # Var-block-depth -14033 # var min/ecx: (addr handle var) = vars->data -14034 8b/-> *(ebp+0xc) 1/r32/ecx -14035 81 0/subop/add %ecx 8/imm32 -14036 # TODO: check that start >= min and start < &vars->data[top] -14037 # TODO: check that *start == v -14038 # var curr/esi: (addr handle var) = start -14039 8b/-> *(ebp+0x10) 6/r32/esi -14040 # curr -= 8 -14041 81 5/subop/subtract %esi 8/imm32 -14042 { -14043 $same-register-spilled-before?:loop: -14044 # if (curr < min) break -14045 39/compare %esi 1/r32/ecx -14046 0f 82/jump-if-addr< break/disp32 -14047 # var x/eax: (addr var) = lookup(*curr) -14048 (lookup *esi *(esi+4)) # => eax -14049 # if (x->block-depth < depth) break -14050 39/compare *(eax+0x10) 3/r32/ebx # Var-block-depth -14051 0f 8c/jump-if-< break/disp32 -14052 # if (x->register == 0) continue -14053 81 7/subop/compare *(eax+0x18) 0/imm32 # Var-register -14054 74/jump-if-= $same-register-spilled-before?:continue/disp8 -14055 # if (x->register == reg) return true +13751 # TODO: error if no label at 'depth' was found +13752 $emit-unconditional-jump-to-depth:end: +13753 # . restore registers +13754 5e/pop-to-esi +13755 5b/pop-to-ebx +13756 5a/pop-to-edx +13757 59/pop-to-ecx +13758 58/pop-to-eax +13759 # . epilogue +13760 89/<- %esp 5/r32/ebp +13761 5d/pop-to-ebp +13762 c3/return +13763 +13764 # emit clean-up code for 'vars' until some block depth +13765 # doesn't actually modify 'vars' so we need traverse manually inside the stack +13766 emit-cleanup-code-until-depth: # out: (addr buffered-file), vars: (addr stack live-var), until-block-depth: int +13767 # . prologue +13768 55/push-ebp +13769 89/<- %ebp 4/r32/esp +13770 # . save registers +13771 50/push-eax +13772 51/push-ecx +13773 52/push-edx +13774 53/push-ebx +13775 56/push-esi +13776 #? (write-buffered Stderr "--- cleanup\n") +13777 #? (flush Stderr) +13778 # ecx = vars +13779 8b/-> *(ebp+0xc) 1/r32/ecx +13780 # var esi: int = vars->top +13781 8b/-> *ecx 6/r32/esi +13782 # var curr/esi: (addr handle var) = &vars->data[vars->top - 12] +13783 8d/copy-address *(ecx+esi-4) 6/r32/esi # vars + 8 + vars->top - 12/Live-var-size +13784 # var min/ecx: (addr handle var) = vars->data +13785 81 0/subop/add %ecx 8/imm32 +13786 # edx = until-block-depth +13787 8b/-> *(ebp+0x10) 2/r32/edx +13788 { +13789 $emit-cleanup-code-until-depth:loop: +13790 # if (curr < min) break +13791 39/compare %esi 1/r32/ecx +13792 0f 82/jump-if-addr< break/disp32 +13793 # var v/ebx: (addr var) = lookup(*curr) +13794 (lookup *esi *(esi+4)) # => eax +13795 89/<- %ebx 0/r32/eax +13796 #? (lookup *ebx *(ebx+4)) # Var-name +13797 #? (write-buffered Stderr "var ") +13798 #? (write-buffered Stderr %eax) +13799 #? (write-buffered Stderr Newline) +13800 #? (flush Stderr) +13801 # if (v->block-depth < until-block-depth) break +13802 39/compare *(ebx+0x10) 2/r32/edx # Var-block-depth +13803 0f 8c/jump-if-< break/disp32 +13804 # if v is in a register +13805 81 7/subop/compare *(ebx+0x18) 0/imm32 # Var-register +13806 { +13807 0f 84/jump-if-= break/disp32 +13808 { +13809 $emit-cleanup-code-until-depth:check-for-previous-spill: +13810 8b/-> *(esi+8) 0/r32/eax # Live-var-register-spilled +13811 3d/compare-eax-and 0/imm32/false +13812 74/jump-if-= break/disp8 +13813 $emit-cleanup-code-until-depth:reclaim-var-in-register: +13814 (emit-indent *(ebp+8) *Curr-block-depth) +13815 (write-buffered *(ebp+8) "8f 0/subop/pop %") +13816 (lookup *(ebx+0x18) *(ebx+0x1c)) # Var-register Var-register => eax +13817 (write-buffered *(ebp+8) %eax) +13818 (write-buffered *(ebp+8) Newline) +13819 } +13820 eb/jump $emit-cleanup-code-until-depth:continue/disp8 +13821 } +13822 # otherwise v is on the stack +13823 { +13824 75/jump-if-!= break/disp8 +13825 $emit-cleanup-code-until-depth:var-on-stack: +13826 (size-of %ebx) # => eax +13827 # don't emit code for labels +13828 3d/compare-eax-and 0/imm32 +13829 74/jump-if-= break/disp8 +13830 $emit-cleanup-code-until-depth:reclaim-var-on-stack: +13831 (emit-indent *(ebp+8) *Curr-block-depth) +13832 (write-buffered *(ebp+8) "81 0/subop/add %esp ") +13833 (write-int32-hex-buffered *(ebp+8) %eax) +13834 (write-buffered *(ebp+8) "/imm32\n") +13835 } +13836 $emit-cleanup-code-until-depth:continue: +13837 # curr -= 12 +13838 81 5/subop/subtract %esi 0xc/imm32 +13839 e9/jump loop/disp32 +13840 } +13841 $emit-cleanup-code-until-depth:end: +13842 # . restore registers +13843 5e/pop-to-esi +13844 5b/pop-to-ebx +13845 5a/pop-to-edx +13846 59/pop-to-ecx +13847 58/pop-to-eax +13848 # . epilogue +13849 89/<- %esp 5/r32/ebp +13850 5d/pop-to-ebp +13851 c3/return +13852 +13853 # emit clean-up code for 'vars' until a given label is encountered +13854 # doesn't actually modify 'vars' so we need traverse manually inside the stack +13855 emit-cleanup-code-until-target: # out: (addr buffered-file), vars: (addr stack live-var), until-block-label: (addr array byte) +13856 # . prologue +13857 55/push-ebp +13858 89/<- %ebp 4/r32/esp +13859 # . save registers +13860 50/push-eax +13861 51/push-ecx +13862 52/push-edx +13863 53/push-ebx +13864 # ecx = vars +13865 8b/-> *(ebp+0xc) 1/r32/ecx +13866 # var eax: int = vars->top +13867 8b/-> *ecx 0/r32/eax +13868 # var curr/edx: (addr handle var) = &vars->data[vars->top - 12] +13869 8d/copy-address *(ecx+eax-4) 2/r32/edx # vars + 8 + vars->top - 12/Live-var-size +13870 # var min/ecx: (addr handle var) = vars->data +13871 81 0/subop/add %ecx 8/imm32 +13872 { +13873 $emit-cleanup-code-until-target:loop: +13874 # if (curr < min) break +13875 39/compare %edx 1/r32/ecx +13876 0f 82/jump-if-addr< break/disp32 +13877 # var v/ebx: (handle var) = lookup(*curr) +13878 (lookup *edx *(edx+4)) # => eax +13879 89/<- %ebx 0/r32/eax +13880 # if (v->name == until-block-label) break +13881 (lookup *ebx *(ebx+4)) # Var-name Var-name => eax +13882 (string-equal? %eax *(ebp+0x10)) # => eax +13883 3d/compare-eax-and 0/imm32/false +13884 0f 85/jump-if-!= break/disp32 +13885 # if v is in a register +13886 81 7/subop/compare *(ebx+0x18) 0/imm32 # Var-register +13887 { +13888 0f 84/jump-if-= break/disp32 +13889 { +13890 $emit-cleanup-code-until-target:check-for-previous-spill: +13891 8b/-> *(edx+8) 0/r32/eax # Live-var-register-spilled +13892 3d/compare-eax-and 0/imm32/false +13893 74/jump-if-= break/disp8 +13894 $emit-cleanup-code-until-target:reclaim-var-in-register: +13895 (emit-indent *(ebp+8) *Curr-block-depth) +13896 (write-buffered *(ebp+8) "8f 0/subop/pop %") +13897 (lookup *(ebx+0x18) *(ebx+0x1c)) # Var-register Var-register => eax +13898 (write-buffered *(ebp+8) %eax) +13899 (write-buffered *(ebp+8) Newline) +13900 } +13901 eb/jump $emit-cleanup-code-until-target:continue/disp8 +13902 } +13903 # otherwise v is on the stack +13904 { +13905 75/jump-if-!= break/disp8 +13906 $emit-cleanup-code-until-target:reclaim-var-on-stack: +13907 (size-of %ebx) # => eax +13908 # don't emit code for labels +13909 3d/compare-eax-and 0/imm32 +13910 74/jump-if-= break/disp8 +13911 # +13912 (emit-indent *(ebp+8) *Curr-block-depth) +13913 (write-buffered *(ebp+8) "81 0/subop/add %esp ") +13914 (write-int32-hex-buffered *(ebp+8) %eax) +13915 (write-buffered *(ebp+8) "/imm32\n") +13916 } +13917 $emit-cleanup-code-until-target:continue: +13918 # curr -= 12 +13919 81 5/subop/subtract %edx 0xc/imm32 +13920 e9/jump loop/disp32 +13921 } +13922 $emit-cleanup-code-until-target:end: +13923 # . restore registers +13924 5b/pop-to-ebx +13925 5a/pop-to-edx +13926 59/pop-to-ecx +13927 58/pop-to-eax +13928 # . epilogue +13929 89/<- %esp 5/r32/ebp +13930 5d/pop-to-ebp +13931 c3/return +13932 +13933 # Return true if there isn't a variable in 'vars' with the same block-depth +13934 # and register as 'v'. +13935 # 'v' is guaranteed not to be within 'vars'. +13936 not-yet-spilled-this-block?: # v: (addr var), vars: (addr stack live-var) -> result/eax: boolean +13937 # . prologue +13938 55/push-ebp +13939 89/<- %ebp 4/r32/esp +13940 # . save registers +13941 51/push-ecx +13942 52/push-edx +13943 53/push-ebx +13944 56/push-esi +13945 57/push-edi +13946 # ecx = vars +13947 8b/-> *(ebp+0xc) 1/r32/ecx +13948 # var eax: int = vars->top +13949 8b/-> *ecx 0/r32/eax +13950 # var curr/edx: (addr handle var) = &vars->data[vars->top - 12] +13951 8d/copy-address *(ecx+eax-4) 2/r32/edx # vars + 8 + vars->top - 12/Live-var-size +13952 # var min/ecx: (addr handle var) = vars->data +13953 8d/copy-address *(ecx+8) 1/r32/ecx +13954 # var depth/ebx: int = v->block-depth +13955 8b/-> *(ebp+8) 3/r32/ebx +13956 8b/-> *(ebx+0x10) 3/r32/ebx # Var-block-depth +13957 # var needle/esi: (addr array byte) = v->register +13958 8b/-> *(ebp+8) 6/r32/esi +13959 (lookup *(esi+0x18) *(esi+0x1c)) # Var-register Var-register => eax +13960 89/<- %esi 0/r32/eax +13961 { +13962 $not-yet-spilled-this-block?:loop: +13963 # if (curr < min) break +13964 39/compare %edx 1/r32/ecx +13965 0f 82/jump-if-addr< break/disp32 +13966 # var cand/edi: (addr var) = lookup(*curr) +13967 (lookup *edx *(edx+4)) # => eax +13968 89/<- %edi 0/r32/eax +13969 # if (cand->block-depth < depth) break +13970 39/compare *(edi+0x10) 3/r32/ebx # Var-block-depth +13971 0f 8c/jump-if-< break/disp32 +13972 # var cand-reg/edi: (array array byte) = cand->reg +13973 (lookup *(edi+0x18) *(edi+0x1c)) # Var-register Var-register => eax +13974 89/<- %edi 0/r32/eax +13975 # if (cand-reg == null) continue +13976 { +13977 $not-yet-spilled-this-block?:check-reg: +13978 81 7/subop/compare %edi 0/imm32 +13979 0f 84/jump-if-= break/disp32 +13980 # if (cand-reg == needle) return true +13981 (string-equal? %esi %edi) # => eax +13982 3d/compare-eax-and 0/imm32/false +13983 74/jump-if-= break/disp8 +13984 $not-yet-spilled-this-block?:return-false: +13985 b8/copy-to-eax 0/imm32/false +13986 eb/jump $not-yet-spilled-this-block?:end/disp8 +13987 } +13988 $not-yet-spilled-this-block?:continue: +13989 # curr -= 12 +13990 81 5/subop/subtract %edx 0xc/imm32 +13991 e9/jump loop/disp32 +13992 } +13993 $not-yet-spilled-this-block?:return-true: +13994 # return true +13995 b8/copy-to-eax 1/imm32/true +13996 $not-yet-spilled-this-block?:end: +13997 # . restore registers +13998 5f/pop-to-edi +13999 5e/pop-to-esi +14000 5b/pop-to-ebx +14001 5a/pop-to-edx +14002 59/pop-to-ecx +14003 # . epilogue +14004 89/<- %esp 5/r32/ebp +14005 5d/pop-to-ebp +14006 c3/return +14007 +14008 # could the register of 'v' ever be written to by one of the vars in fn-outputs? +14009 will-not-write-some-register?: # v: (addr var), stmts: (addr list stmt), fn: (addr function) -> result/eax: boolean +14010 # . prologue +14011 55/push-ebp +14012 89/<- %ebp 4/r32/esp +14013 # eax = v +14014 8b/-> *(ebp+8) 0/r32/eax +14015 # var reg/eax: (addr array byte) = lookup(v->register) +14016 (lookup *(eax+0x18) *(eax+0x1c)) # Var-register Var-register => eax +14017 # var target/eax: (addr var) = find-register(fn-outputs, reg) +14018 (find-register *(ebp+0x10) %eax) # => eax +14019 # if (target == 0) return true +14020 { +14021 3d/compare-eax-and 0/imm32 +14022 75/jump-if-!= break/disp8 +14023 b8/copy-to-eax 1/imm32/true +14024 eb/jump $will-not-write-some-register?:end/disp8 +14025 } +14026 # return !assigns-in-stmts?(stmts, target) +14027 (assigns-in-stmts? *(ebp+0xc) %eax) # => eax +14028 3d/compare-eax-and 0/imm32/false +14029 # assume: true = 1, so no need to mask with 0x000000ff +14030 0f 94/set-if-= %al +14031 $will-not-write-some-register?:end: +14032 # . epilogue +14033 89/<- %esp 5/r32/ebp +14034 5d/pop-to-ebp +14035 c3/return +14036 +14037 # return fn output with matching register +14038 # always returns false if 'reg' is null +14039 find-register: # fn: (addr function), reg: (addr array byte) -> result/eax: (addr var) +14040 # . prologue +14041 55/push-ebp +14042 89/<- %ebp 4/r32/esp +14043 # . save registers +14044 51/push-ecx +14045 # var curr/ecx: (addr list var) = lookup(fn->outputs) +14046 8b/-> *(ebp+8) 1/r32/ecx +14047 (lookup *(ecx+0x10) *(ecx+0x14)) # Function-outputs Function-outputs => eax +14048 89/<- %ecx 0/r32/eax +14049 { +14050 $find-register:loop: +14051 # if (curr == 0) break +14052 81 7/subop/compare %ecx 0/imm32 +14053 74/jump-if-= break/disp8 +14054 # eax = curr->value->register +14055 (lookup *ecx *(ecx+4)) # List-value List-value => eax 14056 (lookup *(eax+0x18) *(eax+0x1c)) # Var-register Var-register => eax -14057 (string-equal? %eax %edx) # => eax -14058 3d/compare-eax-and 0/imm32/false -14059 b8/copy-to-eax 1/imm32/true -14060 75/jump-if-!= $same-register-spilled-before?:end/disp8 -14061 $same-register-spilled-before?:continue: -14062 # curr -= 8 -14063 81 5/subop/subtract %esi 8/imm32 -14064 e9/jump loop/disp32 -14065 } -14066 $same-register-spilled-before?:false: -14067 b8/copy-to-eax 0/imm32/false -14068 $same-register-spilled-before?:end: -14069 # . restore registers -14070 5f/pop-to-edi -14071 5e/pop-to-esi -14072 5b/pop-to-ebx -14073 5a/pop-to-edx -14074 59/pop-to-ecx -14075 # . epilogue -14076 89/<- %esp 5/r32/ebp -14077 5d/pop-to-ebp -14078 c3/return -14079 -14080 # Clean up global state for 'vars' until some block depth (inclusive). -14081 # -14082 # This would be a simple series of pops, if it wasn't for fn outputs, which -14083 # can occur anywhere in the stack. -14084 # So we have to _compact_ the entire array underlying the stack. -14085 # -14086 # We want to allow a fn output register to be written to by locals before the -14087 # output is set. -14088 # So fn outputs can't just be pushed at the start of the function. -14089 # -14090 # We want to allow other locals to shadow a fn output register after the -14091 # output is set. -14092 # So the output can't just always override anything in the stack. Sequence matters. -14093 clean-up-blocks: # vars: (addr stack live-var), until-block-depth: int, fn: (addr function) -14094 # pseudocode: -14095 # to = vars->top (which points outside the stack) -14096 # while true -14097 # if to <= 0 -14098 # break -14099 # var v = vars->data[to-1] -14100 # if v.depth < until and !in-function-outputs?(fn, v) -14101 # break -14102 # --to -14103 # from = to -14104 # while true -14105 # if from >= vars->top -14106 # break -14107 # assert(from >= to) -14108 # v = vars->data[from] -14109 # if in-function-outputs?(fn, v) -14110 # if from > to -14111 # vars->data[to] = vars->data[from] -14112 # ++to -14113 # ++from -14114 # vars->top = to -14115 # -14116 # . prologue -14117 55/push-ebp -14118 89/<- %ebp 4/r32/esp -14119 # . save registers -14120 50/push-eax -14121 52/push-edx -14122 53/push-ebx -14123 56/push-esi -14124 57/push-edi -14125 # ebx = vars -14126 8b/-> *(ebp+8) 3/r32/ebx -14127 # edx = until-block-depth -14128 8b/-> *(ebp+0xc) 2/r32/edx -14129 $clean-up-blocks:phase1: -14130 # var to/edi: int = vars->top -14131 8b/-> *ebx 7/r32/edi -14132 { -14133 $clean-up-blocks:loop1: -14134 # if (to <= 0) break -14135 81 7/subop/compare %edi 0/imm32 -14136 7e/jump-if-<= break/disp8 -14137 # var v/eax: (addr var) = lookup(vars->data[to-1]->var) -14138 8d/copy-address *(ebx+edi-4) 0/r32/eax # vars + 8 + to - 12 -14139 (lookup *eax *(eax+4)) # => eax -14140 # if (v->block-depth >= until-block-depth) continue -14141 39/compare *(eax+0x10) 2/r32/edx # Var-block-depth -14142 { -14143 7d/jump-if->= break/disp8 -14144 # if (!in-function-outputs?(fn, v)) break -14145 (in-function-outputs? *(ebp+0x10) %eax) # => eax -14146 3d/compare-eax-and 0/imm32/false -14147 74/jump-if-= $clean-up-blocks:phase2/disp8 -14148 } -14149 $clean-up-blocks:loop1-continue: -14150 # --to -14151 81 5/subop/subtract %edi 0xc/imm32 -14152 # -14153 eb/jump loop/disp8 -14154 } -14155 $clean-up-blocks:phase2: -14156 # var from/esi: int = to -14157 89/<- %esi 7/r32/edi -14158 { -14159 $clean-up-blocks:loop2: -14160 # if (from >= vars->top) break -14161 3b/compare 6/r32/esi *ebx -14162 7d/jump-if->= break/disp8 -14163 # var v/eax: (addr var) = lookup(vars->data[from]->var) -14164 8d/copy-address *(ebx+esi+8) 0/r32/eax -14165 (lookup *eax *(eax+4)) # => eax -14166 # if !in-function-outputs?(fn, v) continue -14167 (in-function-outputs? *(ebp+0x10) %eax) # => eax -14168 3d/compare-eax-and 0/imm32/false -14169 74/jump-if-= $clean-up-blocks:loop2-continue/disp8 -14170 # invariant: from >= to -14171 # if (from > to) vars->data[to] = vars->data[from] -14172 { -14173 39/compare %esi 7/r32/edi -14174 7e/jump-if-<= break/disp8 -14175 56/push-esi -14176 57/push-edi -14177 # . var from/esi: (addr byte) = &vars->data[from] -14178 8d/copy-address *(ebx+esi+8) 6/r32/esi -14179 # . var to/edi: (addr byte) = &vars->data[to] -14180 8d/copy-address *(ebx+edi+8) 7/r32/edi -14181 # . -14182 8b/-> *esi 0/r32/eax -14183 89/<- *edi 0/r32/eax -14184 8b/-> *(esi+4) 0/r32/eax -14185 89/<- *(edi+4) 0/r32/eax -14186 8b/-> *(esi+8) 0/r32/eax -14187 89/<- *(edi+8) 0/r32/eax -14188 5f/pop-to-edi -14189 5e/pop-to-esi -14190 } -14191 # ++to -14192 81 0/subop/add %edi 0xc/imm32 -14193 $clean-up-blocks:loop2-continue: -14194 # ++from -14195 81 0/subop/add %esi 0xc/imm32 -14196 # -14197 eb/jump loop/disp8 -14198 } -14199 89/<- *ebx 7/r32/edi -14200 $clean-up-blocks:end: -14201 # . restore registers -14202 5f/pop-to-edi -14203 5e/pop-to-esi -14204 5b/pop-to-ebx -14205 5a/pop-to-edx -14206 58/pop-to-eax -14207 # . epilogue -14208 89/<- %esp 5/r32/ebp -14209 5d/pop-to-ebp -14210 c3/return -14211 -14212 in-function-outputs?: # fn: (addr function), target: (addr var) -> result/eax: boolean -14213 # . prologue -14214 55/push-ebp -14215 89/<- %ebp 4/r32/esp -14216 # . save registers -14217 51/push-ecx -14218 # var curr/ecx: (addr list var) = lookup(fn->outputs) -14219 8b/-> *(ebp+8) 1/r32/ecx -14220 (lookup *(ecx+0x10) *(ecx+0x14)) # Function-outputs Function-outputs => eax -14221 89/<- %ecx 0/r32/eax -14222 # while curr != null -14223 { -14224 81 7/subop/compare %ecx 0/imm32 -14225 74/jump-if-= break/disp8 -14226 # var v/eax: (addr var) = lookup(curr->value) -14227 (lookup *ecx *(ecx+4)) # List-value List-value => eax -14228 # if (v == target) return true -14229 39/compare *(ebp+0xc) 0/r32/eax +14057 # if (eax == reg) return curr->value +14058 $find-register:compare: +14059 (string-equal? *(ebp+0xc) %eax) # => eax +14060 { +14061 3d/compare-eax-and 0/imm32/false +14062 74/jump-if-= break/disp8 +14063 $find-register:found: +14064 (lookup *ecx *(ecx+4)) # List-value List-value => eax +14065 eb/jump $find-register:end/disp8 +14066 } +14067 # curr = lookup(curr->next) +14068 (lookup *(ecx+8) *(ecx+0xc)) # List-next List-next => eax +14069 89/<- %ecx 0/r32/eax +14070 # +14071 eb/jump loop/disp8 +14072 } +14073 $find-register:end: +14074 # . restore registers +14075 59/pop-to-ecx +14076 # . epilogue +14077 89/<- %esp 5/r32/ebp +14078 5d/pop-to-ebp +14079 c3/return +14080 +14081 assigns-in-stmts?: # stmts: (addr list stmt), v: (addr var) -> result/eax: boolean +14082 # . prologue +14083 55/push-ebp +14084 89/<- %ebp 4/r32/esp +14085 # . save registers +14086 51/push-ecx +14087 # var curr/ecx: (addr list stmt) = stmts +14088 8b/-> *(ebp+8) 1/r32/ecx +14089 { +14090 # if (curr == 0) break +14091 81 7/subop/compare %ecx 0/imm32 +14092 74/jump-if-= break/disp8 +14093 # if assigns-in-stmt?(curr->value, v) return true +14094 (lookup *ecx *(ecx+4)) # List-value List-value => eax +14095 (assigns-in-stmt? %eax *(ebp+0xc)) # => eax +14096 3d/compare-eax-and 0/imm32/false +14097 75/jump-if-!= break/disp8 +14098 # curr = lookup(curr->next) +14099 (lookup *(ecx+8) *(ecx+0xc)) # List-next List-next => eax +14100 89/<- %ecx 0/r32/eax +14101 # +14102 eb/jump loop/disp8 +14103 } +14104 $assigns-in-stmts?:end: +14105 # . restore registers +14106 59/pop-to-ecx +14107 # . epilogue +14108 89/<- %esp 5/r32/ebp +14109 5d/pop-to-ebp +14110 c3/return +14111 +14112 assigns-in-stmt?: # stmt: (addr stmt), v: (addr var) -> result/eax: boolean +14113 # . prologue +14114 55/push-ebp +14115 89/<- %ebp 4/r32/esp +14116 # . save registers +14117 51/push-ecx +14118 # ecx = stmt +14119 8b/-> *(ebp+8) 1/r32/ecx +14120 # if stmt is a stmt1, return assigns-in-stmt-vars?(stmt->outputs, v) +14121 { +14122 81 7/subop/compare *ecx 1/imm32/stmt1 # Stmt-tag +14123 75/jump-if-!= break/disp8 +14124 (lookup *(ecx+0x14) *(ecx+0x18)) # Stmt1-outputs Stmt1-outputs => eax +14125 (assigns-in-stmt-vars? %eax *(ebp+0xc)) # => eax +14126 eb/jump $assigns-in-stmt?:end/disp8 +14127 } +14128 # if stmt is a block, return assigns-in-stmts?(stmt->stmts, v) +14129 { +14130 81 7/subop/compare *ecx 0/imm32/block # Stmt-tag +14131 75/jump-if-!= break/disp8 +14132 (lookup *(ecx+4) *(ecx+8)) # Block-stmts Block-stmts => eax +14133 (assigns-in-stmts? %eax *(ebp+0xc)) # => eax +14134 eb/jump $assigns-in-stmt?:end/disp8 +14135 } +14136 # otherwise return false +14137 b8/copy 0/imm32/false +14138 $assigns-in-stmt?:end: +14139 # . restore registers +14140 59/pop-to-ecx +14141 # . epilogue +14142 89/<- %esp 5/r32/ebp +14143 5d/pop-to-ebp +14144 c3/return +14145 +14146 assigns-in-stmt-vars?: # stmt-var: (addr stmt-var), v: (addr var) -> result/eax: boolean +14147 # . prologue +14148 55/push-ebp +14149 89/<- %ebp 4/r32/esp +14150 # . save registers +14151 51/push-ecx +14152 # var curr/ecx: (addr stmt-var) = stmt-var +14153 8b/-> *(ebp+8) 1/r32/ecx +14154 { +14155 # if (curr == 0) break +14156 81 7/subop/compare %ecx 0/imm32 +14157 74/jump-if-= break/disp8 +14158 # eax = lookup(curr->value) +14159 (lookup *ecx *(ecx+4)) # Stmt-var-value Stmt-var-value => eax +14160 # if (eax == v && curr->is-deref? == false) return true +14161 { +14162 39/compare *(ebp+0xc) 0/r32/eax +14163 75/jump-if-!= break/disp8 +14164 81 7/subop/compare *(ecx+0x10) 0/imm32/false # Stmt-var-is-deref +14165 75/jump-if-!= break/disp8 +14166 b8/copy-to-eax 1/imm32/true +14167 eb/jump $assigns-in-stmt-vars?:end/disp8 +14168 } +14169 # curr = lookup(curr->next) +14170 (lookup *(ecx+8) *(ecx+0xc)) # Stmt-var-next Stmt-var-next => eax +14171 89/<- %ecx 0/r32/eax +14172 # +14173 eb/jump loop/disp8 +14174 } +14175 $assigns-in-stmt-vars?:end: +14176 # . restore registers +14177 59/pop-to-ecx +14178 # . epilogue +14179 89/<- %esp 5/r32/ebp +14180 5d/pop-to-ebp +14181 c3/return +14182 +14183 # is there a var before 'v' with the same block-depth and register on the 'vars' stack? +14184 # v is guaranteed to be within vars +14185 # 'start' is provided as an optimization, a pointer within vars +14186 # *start == v +14187 same-register-spilled-before?: # v: (addr var), vars: (addr stack (handle var)), start: (addr var) -> result/eax: boolean +14188 # . prologue +14189 55/push-ebp +14190 89/<- %ebp 4/r32/esp +14191 # . save registers +14192 51/push-ecx +14193 52/push-edx +14194 53/push-ebx +14195 56/push-esi +14196 57/push-edi +14197 # ecx = v +14198 8b/-> *(ebp+8) 1/r32/ecx +14199 # var reg/edx: (addr array byte) = lookup(v->register) +14200 (lookup *(ecx+0x18) *(ecx+0x1c)) # Var-register Var-register => eax +14201 89/<- %edx 0/r32/eax +14202 # var depth/ebx: int = v->block-depth +14203 8b/-> *(ecx+0x10) 3/r32/ebx # Var-block-depth +14204 # var min/ecx: (addr handle var) = vars->data +14205 8b/-> *(ebp+0xc) 1/r32/ecx +14206 81 0/subop/add %ecx 8/imm32 +14207 # TODO: check that start >= min and start < &vars->data[top] +14208 # TODO: check that *start == v +14209 # var curr/esi: (addr handle var) = start +14210 8b/-> *(ebp+0x10) 6/r32/esi +14211 # curr -= 8 +14212 81 5/subop/subtract %esi 8/imm32 +14213 { +14214 $same-register-spilled-before?:loop: +14215 # if (curr < min) break +14216 39/compare %esi 1/r32/ecx +14217 0f 82/jump-if-addr< break/disp32 +14218 # var x/eax: (addr var) = lookup(*curr) +14219 (lookup *esi *(esi+4)) # => eax +14220 # if (x->block-depth < depth) break +14221 39/compare *(eax+0x10) 3/r32/ebx # Var-block-depth +14222 0f 8c/jump-if-< break/disp32 +14223 # if (x->register == 0) continue +14224 81 7/subop/compare *(eax+0x18) 0/imm32 # Var-register +14225 74/jump-if-= $same-register-spilled-before?:continue/disp8 +14226 # if (x->register == reg) return true +14227 (lookup *(eax+0x18) *(eax+0x1c)) # Var-register Var-register => eax +14228 (string-equal? %eax %edx) # => eax +14229 3d/compare-eax-and 0/imm32/false 14230 b8/copy-to-eax 1/imm32/true -14231 74/jump-if-= $in-function-outputs?:end/disp8 -14232 # curr = curr->next -14233 (lookup *(ecx+8) *(ecx+0xc)) # List-next List-next => eax -14234 89/<- %ecx 0/r32/eax -14235 # -14236 eb/jump loop/disp8 -14237 } -14238 b8/copy-to-eax 0/imm32 -14239 $in-function-outputs?:end: +14231 75/jump-if-!= $same-register-spilled-before?:end/disp8 +14232 $same-register-spilled-before?:continue: +14233 # curr -= 8 +14234 81 5/subop/subtract %esi 8/imm32 +14235 e9/jump loop/disp32 +14236 } +14237 $same-register-spilled-before?:false: +14238 b8/copy-to-eax 0/imm32/false +14239 $same-register-spilled-before?:end: 14240 # . restore registers -14241 59/pop-to-ecx -14242 # . epilogue -14243 89/<- %esp 5/r32/ebp -14244 5d/pop-to-ebp -14245 c3/return -14246 -14247 emit-subx-var-def: # out: (addr buffered-file), stmt: (addr stmt) -14248 # . prologue -14249 55/push-ebp -14250 89/<- %ebp 4/r32/esp -14251 # . save registers -14252 50/push-eax -14253 51/push-ecx -14254 52/push-edx -14255 # eax = stmt -14256 8b/-> *(ebp+0xc) 0/r32/eax -14257 # var v/ecx: (addr var) -14258 (lookup *(eax+4) *(eax+8)) # Vardef-var Vardef-var => eax -14259 89/<- %ecx 0/r32/eax -14260 # v->block-depth = *Curr-block-depth -14261 8b/-> *Curr-block-depth 0/r32/eax -14262 89/<- *(ecx+0x10) 0/r32/eax # Var-block-depth -14263 # var n/edx: int = size-of(stmt->var) -14264 (size-of %ecx) # => eax -14265 89/<- %edx 0/r32/eax -14266 # *Curr-local-stack-offset -= n -14267 29/subtract-from *Curr-local-stack-offset 2/r32/edx -14268 # v->offset = *Curr-local-stack-offset -14269 8b/-> *Curr-local-stack-offset 0/r32/eax -14270 89/<- *(ecx+0x14) 0/r32/eax # Var-offset -14271 # if v is an array, do something special -14272 { -14273 (lookup *(ecx+8) *(ecx+0xc)) # Var-type Var-type => eax -14274 (is-mu-array? %eax) # => eax -14275 3d/compare-eax-and 0/imm32/false -14276 0f 84/jump-if-= break/disp32 -14277 # var array-size-without-size/edx: int = n-4 -14278 81 5/subop/subtract %edx 4/imm32 -14279 (emit-indent *(ebp+8) *Curr-block-depth) -14280 (write-buffered *(ebp+8) "(push-n-zero-bytes ") -14281 (write-int32-hex-buffered *(ebp+8) %edx) -14282 (write-buffered *(ebp+8) ")\n") -14283 (emit-indent *(ebp+8) *Curr-block-depth) -14284 (write-buffered *(ebp+8) "68/push ") -14285 (write-int32-hex-buffered *(ebp+8) %edx) -14286 (write-buffered *(ebp+8) "/imm32\n") -14287 eb/jump $emit-subx-var-def:end/disp8 -14288 } -14289 # while n > 0 -14290 { -14291 81 7/subop/compare %edx 0/imm32 -14292 7e/jump-if-<= break/disp8 -14293 (emit-indent *(ebp+8) *Curr-block-depth) -14294 (write-buffered *(ebp+8) "68/push 0/imm32\n") -14295 # n -= 4 -14296 81 5/subop/subtract %edx 4/imm32 -14297 # -14298 eb/jump loop/disp8 -14299 } -14300 $emit-subx-var-def:end: -14301 # . restore registers -14302 5a/pop-to-edx -14303 59/pop-to-ecx -14304 58/pop-to-eax -14305 # . epilogue -14306 89/<- %esp 5/r32/ebp -14307 5d/pop-to-ebp -14308 c3/return -14309 -14310 emit-subx-stmt: # out: (addr buffered-file), stmt: (addr stmt), primitives: (addr primitive), err: (addr buffered-file), ed: (addr exit-descriptor) -14311 # . prologue -14312 55/push-ebp -14313 89/<- %ebp 4/r32/esp -14314 # . save registers -14315 50/push-eax -14316 51/push-ecx -14317 # - some special-case primitives that don't actually use the 'primitives' data structure -14318 # var op/ecx: (addr array byte) = lookup(stmt->operation) -14319 8b/-> *(ebp+0xc) 1/r32/ecx -14320 (lookup *(ecx+4) *(ecx+8)) # Stmt1-operation Stmt1-operation => eax -14321 89/<- %ecx 0/r32/eax -14322 # array size -14323 { -14324 # if (!string-equal?(stmt->operation, "length")) break -14325 (string-equal? %ecx "length") # => eax -14326 3d/compare-eax-and 0/imm32 -14327 0f 84/jump-if-= break/disp32 -14328 (translate-mu-length-stmt *(ebp+8) *(ebp+0xc) *(ebp+0x14) *(ebp+0x18)) -14329 e9/jump $emit-subx-stmt:end/disp32 -14330 } -14331 # index into array -14332 { -14333 # if (!string-equal?(stmt->operation, "index")) break -14334 (string-equal? %ecx "index") # => eax -14335 3d/compare-eax-and 0/imm32 -14336 0f 84/jump-if-= break/disp32 -14337 (translate-mu-index-stmt *(ebp+8) *(ebp+0xc) *(ebp+0x14) *(ebp+0x18)) -14338 e9/jump $emit-subx-stmt:end/disp32 -14339 } -14340 # compute-offset for index into array -14341 { -14342 # if (!string-equal?(stmt->operation, "compute-offset")) break -14343 (string-equal? %ecx "compute-offset") # => eax -14344 3d/compare-eax-and 0/imm32 -14345 0f 84/jump-if-= break/disp32 -14346 (translate-mu-compute-index-stmt *(ebp+8) *(ebp+0xc) *(ebp+0x14) *(ebp+0x18)) -14347 e9/jump $emit-subx-stmt:end/disp32 -14348 } -14349 # get field from record -14350 { -14351 # if (!string-equal?(stmt->operation, "get")) break -14352 (string-equal? %ecx "get") # => eax -14353 3d/compare-eax-and 0/imm32 -14354 0f 84/jump-if-= break/disp32 -14355 (translate-mu-get-stmt *(ebp+8) *(ebp+0xc)) -14356 e9/jump $emit-subx-stmt:end/disp32 -14357 } -14358 # allocate scalar -14359 { -14360 # if (!string-equal?(stmt->operation, "allocate")) break -14361 (string-equal? %ecx "allocate") # => eax -14362 3d/compare-eax-and 0/imm32 -14363 0f 84/jump-if-= break/disp32 -14364 (translate-mu-allocate-stmt *(ebp+8) *(ebp+0xc) *(ebp+0x14) *(ebp+0x18)) -14365 e9/jump $emit-subx-stmt:end/disp32 -14366 } -14367 # allocate array -14368 { -14369 # if (!string-equal?(stmt->operation, "populate")) break -14370 (string-equal? %ecx "populate") # => eax -14371 3d/compare-eax-and 0/imm32 -14372 0f 84/jump-if-= break/disp32 -14373 (translate-mu-populate-stmt *(ebp+8) *(ebp+0xc) *(ebp+0x14) *(ebp+0x18)) -14374 e9/jump $emit-subx-stmt:end/disp32 -14375 } -14376 # - if stmt matches a primitive, emit it -14377 { -14378 $emit-subx-stmt:check-for-primitive: -14379 # var curr/eax: (addr primitive) -14380 (find-matching-primitive *(ebp+0x10) *(ebp+0xc)) # primitives, stmt => eax -14381 3d/compare-eax-and 0/imm32 -14382 74/jump-if-= break/disp8 -14383 $emit-subx-stmt:primitive: -14384 (emit-subx-primitive *(ebp+8) *(ebp+0xc) %eax) # out, stmt, curr -14385 e9/jump $emit-subx-stmt:end/disp32 -14386 } -14387 # - otherwise emit a call -14388 # TODO: type-checking -14389 $emit-subx-stmt:call: -14390 (emit-call *(ebp+8) *(ebp+0xc)) -14391 $emit-subx-stmt:end: -14392 # . restore registers -14393 59/pop-to-ecx -14394 58/pop-to-eax -14395 # . epilogue -14396 89/<- %esp 5/r32/ebp -14397 5d/pop-to-ebp -14398 c3/return -14399 -14400 translate-mu-length-stmt: # out: (addr buffered-file), stmt: (addr stmt), err: (addr buffered-file), ed: (addr exit-descriptor) -14401 # . prologue -14402 55/push-ebp -14403 89/<- %ebp 4/r32/esp -14404 # . save registers -14405 50/push-eax -14406 51/push-ecx -14407 52/push-edx -14408 53/push-ebx -14409 56/push-esi -14410 # esi = stmt -14411 8b/-> *(ebp+0xc) 6/r32/esi -14412 # var base/ebx: (addr var) = stmt->inouts[0]->value -14413 (lookup *(esi+0xc) *(esi+0x10)) # Stmt1-inouts Stmt1-inouts => eax -14414 (lookup *eax *(eax+4)) # Stmt-var-value Stmt-var-value => eax -14415 89/<- %ebx 0/r32/eax -14416 # var elemsize/ecx: int = array-element-size(base) -14417 (array-element-size %ebx *(ebp+0x10) *(ebp+0x14)) # => eax -14418 89/<- %ecx 0/r32/eax -14419 # var outreg/edx: (addr array byte) = stmt->outputs[0]->value->register -14420 (lookup *(esi+0x14) *(esi+0x18)) # Stmt1-outputs Stmt1-outputs => eax -14421 (lookup *eax *(eax+4)) # Stmt-var-value Stmt-var-value => eax -14422 (lookup *(eax+0x18) *(eax+0x1c)) # Var-register Var-register => eax -14423 89/<- %edx 0/r32/eax -14424 # if elemsize == 1 -14425 { -14426 81 7/subop/compare %ecx 1/imm32 -14427 75/jump-if-!= break/disp8 -14428 $translate-mu-length-stmt:size-1: -14429 (emit-save-size-to *(ebp+8) %ebx %edx) -14430 e9/jump $translate-mu-length-stmt:end/disp32 -14431 } -14432 # if elemsize is a power of 2 less than 256 -14433 { -14434 (power-of-2? %ecx *(ebp+0x10) *(ebp+0x14)) # => eax -14435 3d/compare-eax-and 0/imm32/false -14436 74/jump-if-= break/disp8 -14437 81 7/subop/compare %ecx 0xff/imm32 -14438 7f/jump-if-> break/disp8 -14439 $translate-mu-length-stmt:size-power-of-2: -14440 (emit-save-size-to *(ebp+8) %ebx %edx) -14441 (emit-divide-by-shift-right *(ebp+8) %edx %ecx) -14442 e9/jump $translate-mu-length-stmt:end/disp32 -14443 } -14444 # otherwise, the complex case -14445 # . emit register spills -14446 { -14447 $translate-mu-length-stmt:complex: -14448 (string-equal? %edx "eax") # => eax -14449 3d/compare-eax-and 0/imm32/false -14450 75/break-if-!= break/disp8 -14451 (emit-indent *(ebp+8) *Curr-block-depth) -14452 (write-buffered *(ebp+8) "50/push-eax\n") +14241 5f/pop-to-edi +14242 5e/pop-to-esi +14243 5b/pop-to-ebx +14244 5a/pop-to-edx +14245 59/pop-to-ecx +14246 # . epilogue +14247 89/<- %esp 5/r32/ebp +14248 5d/pop-to-ebp +14249 c3/return +14250 +14251 # Clean up global state for 'vars' until some block depth (inclusive). +14252 # +14253 # This would be a simple series of pops, if it wasn't for fn outputs, which +14254 # can occur anywhere in the stack. +14255 # So we have to _compact_ the entire array underlying the stack. +14256 # +14257 # We want to allow a fn output register to be written to by locals before the +14258 # output is set. +14259 # So fn outputs can't just be pushed at the start of the function. +14260 # +14261 # We want to allow other locals to shadow a fn output register after the +14262 # output is set. +14263 # So the output can't just always override anything in the stack. Sequence matters. +14264 clean-up-blocks: # vars: (addr stack live-var), until-block-depth: int, fn: (addr function) +14265 # pseudocode: +14266 # to = vars->top (which points outside the stack) +14267 # while true +14268 # if to <= 0 +14269 # break +14270 # var v = vars->data[to-1] +14271 # if v.depth < until and !in-function-outputs?(fn, v) +14272 # break +14273 # --to +14274 # from = to +14275 # while true +14276 # if from >= vars->top +14277 # break +14278 # assert(from >= to) +14279 # v = vars->data[from] +14280 # if in-function-outputs?(fn, v) +14281 # if from > to +14282 # vars->data[to] = vars->data[from] +14283 # ++to +14284 # ++from +14285 # vars->top = to +14286 # +14287 # . prologue +14288 55/push-ebp +14289 89/<- %ebp 4/r32/esp +14290 # . save registers +14291 50/push-eax +14292 52/push-edx +14293 53/push-ebx +14294 56/push-esi +14295 57/push-edi +14296 # ebx = vars +14297 8b/-> *(ebp+8) 3/r32/ebx +14298 # edx = until-block-depth +14299 8b/-> *(ebp+0xc) 2/r32/edx +14300 $clean-up-blocks:phase1: +14301 # var to/edi: int = vars->top +14302 8b/-> *ebx 7/r32/edi +14303 { +14304 $clean-up-blocks:loop1: +14305 # if (to <= 0) break +14306 81 7/subop/compare %edi 0/imm32 +14307 7e/jump-if-<= break/disp8 +14308 # var v/eax: (addr var) = lookup(vars->data[to-1]->var) +14309 8d/copy-address *(ebx+edi-4) 0/r32/eax # vars + 8 + to - 12 +14310 (lookup *eax *(eax+4)) # => eax +14311 # if (v->block-depth >= until-block-depth) continue +14312 39/compare *(eax+0x10) 2/r32/edx # Var-block-depth +14313 { +14314 7d/jump-if->= break/disp8 +14315 # if (!in-function-outputs?(fn, v)) break +14316 (in-function-outputs? *(ebp+0x10) %eax) # => eax +14317 3d/compare-eax-and 0/imm32/false +14318 74/jump-if-= $clean-up-blocks:phase2/disp8 +14319 } +14320 $clean-up-blocks:loop1-continue: +14321 # --to +14322 81 5/subop/subtract %edi 0xc/imm32 +14323 # +14324 eb/jump loop/disp8 +14325 } +14326 $clean-up-blocks:phase2: +14327 # var from/esi: int = to +14328 89/<- %esi 7/r32/edi +14329 { +14330 $clean-up-blocks:loop2: +14331 # if (from >= vars->top) break +14332 3b/compare 6/r32/esi *ebx +14333 7d/jump-if->= break/disp8 +14334 # var v/eax: (addr var) = lookup(vars->data[from]->var) +14335 8d/copy-address *(ebx+esi+8) 0/r32/eax +14336 (lookup *eax *(eax+4)) # => eax +14337 # if !in-function-outputs?(fn, v) continue +14338 (in-function-outputs? *(ebp+0x10) %eax) # => eax +14339 3d/compare-eax-and 0/imm32/false +14340 74/jump-if-= $clean-up-blocks:loop2-continue/disp8 +14341 # invariant: from >= to +14342 # if (from > to) vars->data[to] = vars->data[from] +14343 { +14344 39/compare %esi 7/r32/edi +14345 7e/jump-if-<= break/disp8 +14346 56/push-esi +14347 57/push-edi +14348 # . var from/esi: (addr byte) = &vars->data[from] +14349 8d/copy-address *(ebx+esi+8) 6/r32/esi +14350 # . var to/edi: (addr byte) = &vars->data[to] +14351 8d/copy-address *(ebx+edi+8) 7/r32/edi +14352 # . +14353 8b/-> *esi 0/r32/eax +14354 89/<- *edi 0/r32/eax +14355 8b/-> *(esi+4) 0/r32/eax +14356 89/<- *(edi+4) 0/r32/eax +14357 8b/-> *(esi+8) 0/r32/eax +14358 89/<- *(edi+8) 0/r32/eax +14359 5f/pop-to-edi +14360 5e/pop-to-esi +14361 } +14362 # ++to +14363 81 0/subop/add %edi 0xc/imm32 +14364 $clean-up-blocks:loop2-continue: +14365 # ++from +14366 81 0/subop/add %esi 0xc/imm32 +14367 # +14368 eb/jump loop/disp8 +14369 } +14370 89/<- *ebx 7/r32/edi +14371 $clean-up-blocks:end: +14372 # . restore registers +14373 5f/pop-to-edi +14374 5e/pop-to-esi +14375 5b/pop-to-ebx +14376 5a/pop-to-edx +14377 58/pop-to-eax +14378 # . epilogue +14379 89/<- %esp 5/r32/ebp +14380 5d/pop-to-ebp +14381 c3/return +14382 +14383 in-function-outputs?: # fn: (addr function), target: (addr var) -> result/eax: boolean +14384 # . prologue +14385 55/push-ebp +14386 89/<- %ebp 4/r32/esp +14387 # . save registers +14388 51/push-ecx +14389 # var curr/ecx: (addr list var) = lookup(fn->outputs) +14390 8b/-> *(ebp+8) 1/r32/ecx +14391 (lookup *(ecx+0x10) *(ecx+0x14)) # Function-outputs Function-outputs => eax +14392 89/<- %ecx 0/r32/eax +14393 # while curr != null +14394 { +14395 81 7/subop/compare %ecx 0/imm32 +14396 74/jump-if-= break/disp8 +14397 # var v/eax: (addr var) = lookup(curr->value) +14398 (lookup *ecx *(ecx+4)) # List-value List-value => eax +14399 # if (v == target) return true +14400 39/compare *(ebp+0xc) 0/r32/eax +14401 b8/copy-to-eax 1/imm32/true +14402 74/jump-if-= $in-function-outputs?:end/disp8 +14403 # curr = curr->next +14404 (lookup *(ecx+8) *(ecx+0xc)) # List-next List-next => eax +14405 89/<- %ecx 0/r32/eax +14406 # +14407 eb/jump loop/disp8 +14408 } +14409 b8/copy-to-eax 0/imm32 +14410 $in-function-outputs?:end: +14411 # . restore registers +14412 59/pop-to-ecx +14413 # . epilogue +14414 89/<- %esp 5/r32/ebp +14415 5d/pop-to-ebp +14416 c3/return +14417 +14418 emit-subx-var-def: # out: (addr buffered-file), stmt: (addr stmt) +14419 # . prologue +14420 55/push-ebp +14421 89/<- %ebp 4/r32/esp +14422 # . save registers +14423 50/push-eax +14424 51/push-ecx +14425 52/push-edx +14426 # eax = stmt +14427 8b/-> *(ebp+0xc) 0/r32/eax +14428 # var v/ecx: (addr var) +14429 (lookup *(eax+4) *(eax+8)) # Vardef-var Vardef-var => eax +14430 89/<- %ecx 0/r32/eax +14431 # v->block-depth = *Curr-block-depth +14432 8b/-> *Curr-block-depth 0/r32/eax +14433 89/<- *(ecx+0x10) 0/r32/eax # Var-block-depth +14434 # var n/edx: int = size-of(stmt->var) +14435 (size-of %ecx) # => eax +14436 89/<- %edx 0/r32/eax +14437 # *Curr-local-stack-offset -= n +14438 29/subtract-from *Curr-local-stack-offset 2/r32/edx +14439 # v->offset = *Curr-local-stack-offset +14440 8b/-> *Curr-local-stack-offset 0/r32/eax +14441 89/<- *(ecx+0x14) 0/r32/eax # Var-offset +14442 # if v is an array, do something special to initialize it +14443 { +14444 (lookup *(ecx+8) *(ecx+0xc)) # Var-type Var-type => eax +14445 (is-mu-array? %eax) # => eax +14446 3d/compare-eax-and 0/imm32/false +14447 0f 84/jump-if-= break/disp32 +14448 # var array-size-without-size/edx: int = n-4 +14449 81 5/subop/subtract %edx 4/imm32 +14450 # +14451 (emit-array-data-initialization *(ebp+8) %edx) +14452 e9/jump $emit-subx-var-def:end/disp32 14453 } -14454 { -14455 (string-equal? %edx "ecx") # => eax -14456 3d/compare-eax-and 0/imm32/false -14457 75/break-if-!= break/disp8 -14458 (emit-indent *(ebp+8) *Curr-block-depth) -14459 (write-buffered *(ebp+8) "51/push-ecx\n") -14460 } -14461 { -14462 (string-equal? %edx "edx") # => eax -14463 3d/compare-eax-and 0/imm32/false -14464 75/break-if-!= break/disp8 -14465 (emit-indent *(ebp+8) *Curr-block-depth) -14466 (write-buffered *(ebp+8) "52/push-edx\n") -14467 } -14468 # . -14469 (emit-save-size-to *(ebp+8) %ebx "eax") -14470 (emit-indent *(ebp+8) *Curr-block-depth) -14471 (write-buffered *(ebp+8) "31/xor %edx 2/r32/edx\n") -14472 (emit-indent *(ebp+8) *Curr-block-depth) -14473 (write-buffered *(ebp+8) "b9/copy-to-ecx ") -14474 (write-int32-hex-buffered *(ebp+8) %ecx) -14475 (write-buffered *(ebp+8) "/imm32\n") -14476 (emit-indent *(ebp+8) *Curr-block-depth) -14477 (write-buffered *(ebp+8) "f7 7/subop/idiv-eax-edx-by %ecx\n") -14478 { -14479 (string-equal? %edx "eax") # => eax -14480 3d/compare-eax-and 0/imm32/false -14481 75/break-if-!= break/disp8 -14482 (emit-indent *(ebp+8) *Curr-block-depth) -14483 (write-buffered *(ebp+8) "89/<- %") -14484 (write-buffered *(ebp+8) %edx) -14485 (write-buffered *(ebp+8) " 0/r32/eax\n") -14486 } -14487 # . emit register restores -14488 { -14489 (string-equal? %edx "edx") # => eax -14490 3d/compare-eax-and 0/imm32/false -14491 75/break-if-!= break/disp8 -14492 (emit-indent *(ebp+8) *Curr-block-depth) -14493 (write-buffered *(ebp+8) "5a/pop-to-edx\n") -14494 } -14495 { -14496 (string-equal? %edx "ecx") # => eax -14497 3d/compare-eax-and 0/imm32/false -14498 75/break-if-!= break/disp8 -14499 (emit-indent *(ebp+8) *Curr-block-depth) -14500 (write-buffered *(ebp+8) "59/pop-to-ecx\n") -14501 } -14502 { -14503 (string-equal? %edx "eax") # => eax -14504 3d/compare-eax-and 0/imm32/false -14505 75/break-if-!= break/disp8 -14506 (emit-indent *(ebp+8) *Curr-block-depth) -14507 (write-buffered *(ebp+8) "58/pop-to-eax\n") -14508 } -14509 $translate-mu-length-stmt:end: -14510 # . restore registers -14511 5e/pop-to-esi -14512 5b/pop-to-ebx -14513 5a/pop-to-edx -14514 59/pop-to-ecx -14515 58/pop-to-eax -14516 # . epilogue -14517 89/<- %esp 5/r32/ebp -14518 5d/pop-to-ebp -14519 c3/return -14520 -14521 array-element-size: # arr: (addr var), err: (addr buffered-file), ed: (addr exit-descriptor) -> result/eax: int -14522 # . prologue -14523 55/push-ebp -14524 89/<- %ebp 4/r32/esp -14525 # -14526 (array-element-type-id *(ebp+8) *(ebp+0xc) *(ebp+0x10)) # => eax -14527 (size-of-type-id-as-array-element %eax) # => eax -14528 $array-element-size:end: -14529 # . epilogue -14530 89/<- %esp 5/r32/ebp -14531 5d/pop-to-ebp -14532 c3/return -14533 -14534 array-element-type-id: # v: (addr var), err: (addr buffered-file), ed: (addr exit-descriptor) -> result/eax: type-id -14535 # precondition: n is positive -14536 # . prologue -14537 55/push-ebp -14538 89/<- %ebp 4/r32/esp -14539 # -14540 8b/-> *(ebp+8) 0/r32/eax -14541 # var t/eax: (addr type-tree) -14542 (lookup *(eax+8) *(eax+0xc)) # Var-type Var-type => eax -14543 # if t == 0 abort -14544 3d/compare-eax-with 0/imm32 -14545 0f 84/jump-if-== $array-element-type-id:error0/disp32 -14546 # if t->is-atom? abort -14547 81 7/subop/compare *eax 0/imm32/false # Type-tree-is-atom -14548 0f 85/jump-if-!= $array-element-type-id:error1/disp32 -14549 # if (t->left == addr) t = t->right -14550 { -14551 50/push-eax -14552 (lookup *(eax+4) *(eax+8)) # Type-tree-left Type-tree-left => eax -14553 (is-simple-mu-type? %eax 2) # addr => eax -14554 3d/compare-eax-with 0/imm32/false -14555 58/pop-to-eax -14556 74/jump-if-= break/disp8 -14557 $array-element-type-id:skip-addr: -14558 (lookup *(eax+0xc) *(eax+0x10)) # Type-tree-right Type-tree-right => eax +14454 # another special-case for initializing streams +14455 # a stream is an array with 2 extra pointers +14456 { +14457 (lookup *(ecx+8) *(ecx+0xc)) # Var-type Var-type => eax +14458 (is-mu-stream? %eax) # => eax +14459 3d/compare-eax-and 0/imm32/false +14460 0f 84/jump-if-= break/disp32 +14461 # var array-size-without-size/edx: int = n-12 +14462 81 5/subop/subtract %edx 0xc/imm32 +14463 (emit-array-data-initialization *(ebp+8) %edx) +14464 # emit read and write pointers +14465 (emit-indent *(ebp+8) *Curr-block-depth) +14466 (write-buffered *(ebp+8) "68/push 0/imm32\n") +14467 (emit-indent *(ebp+8) *Curr-block-depth) +14468 (write-buffered *(ebp+8) "68/push 0/imm32\n") +14469 # +14470 eb/jump $emit-subx-var-def:end/disp8 +14471 } +14472 # while n > 0 +14473 { +14474 81 7/subop/compare %edx 0/imm32 +14475 7e/jump-if-<= break/disp8 +14476 (emit-indent *(ebp+8) *Curr-block-depth) +14477 (write-buffered *(ebp+8) "68/push 0/imm32\n") +14478 # n -= 4 +14479 81 5/subop/subtract %edx 4/imm32 +14480 # +14481 eb/jump loop/disp8 +14482 } +14483 $emit-subx-var-def:end: +14484 # . restore registers +14485 5a/pop-to-edx +14486 59/pop-to-ecx +14487 58/pop-to-eax +14488 # . epilogue +14489 89/<- %esp 5/r32/ebp +14490 5d/pop-to-ebp +14491 c3/return +14492 +14493 emit-array-data-initialization: # out: (addr buffered-file), n: int +14494 # . prologue +14495 55/push-ebp +14496 89/<- %ebp 4/r32/esp +14497 # +14498 (emit-indent *(ebp+8) *Curr-block-depth) +14499 (write-buffered *(ebp+8) "(push-n-zero-bytes ") +14500 (write-int32-hex-buffered *(ebp+8) *(ebp+0xc)) +14501 (write-buffered *(ebp+8) ")\n") +14502 (emit-indent *(ebp+8) *Curr-block-depth) +14503 (write-buffered *(ebp+8) "68/push ") +14504 (write-int32-hex-buffered *(ebp+8) *(ebp+0xc)) +14505 (write-buffered *(ebp+8) "/imm32\n") +14506 $emit-array-data-initialization:end: +14507 # . epilogue +14508 89/<- %esp 5/r32/ebp +14509 5d/pop-to-ebp +14510 c3/return +14511 +14512 emit-subx-stmt: # out: (addr buffered-file), stmt: (addr stmt), primitives: (addr primitive), err: (addr buffered-file), ed: (addr exit-descriptor) +14513 # . prologue +14514 55/push-ebp +14515 89/<- %ebp 4/r32/esp +14516 # . save registers +14517 50/push-eax +14518 51/push-ecx +14519 # - some special-case primitives that don't actually use the 'primitives' data structure +14520 # var op/ecx: (addr array byte) = lookup(stmt->operation) +14521 8b/-> *(ebp+0xc) 1/r32/ecx +14522 (lookup *(ecx+4) *(ecx+8)) # Stmt1-operation Stmt1-operation => eax +14523 89/<- %ecx 0/r32/eax +14524 # array size +14525 { +14526 # if (!string-equal?(stmt->operation, "length")) break +14527 (string-equal? %ecx "length") # => eax +14528 3d/compare-eax-and 0/imm32 +14529 0f 84/jump-if-= break/disp32 +14530 (translate-mu-length-stmt *(ebp+8) *(ebp+0xc) *(ebp+0x14) *(ebp+0x18)) +14531 e9/jump $emit-subx-stmt:end/disp32 +14532 } +14533 # index into array +14534 { +14535 # if (!string-equal?(stmt->operation, "index")) break +14536 (string-equal? %ecx "index") # => eax +14537 3d/compare-eax-and 0/imm32 +14538 0f 84/jump-if-= break/disp32 +14539 (translate-mu-index-stmt *(ebp+8) *(ebp+0xc) *(ebp+0x14) *(ebp+0x18)) +14540 e9/jump $emit-subx-stmt:end/disp32 +14541 } +14542 # compute-offset for index into array +14543 { +14544 # if (!string-equal?(stmt->operation, "compute-offset")) break +14545 (string-equal? %ecx "compute-offset") # => eax +14546 3d/compare-eax-and 0/imm32 +14547 0f 84/jump-if-= break/disp32 +14548 (translate-mu-compute-index-stmt *(ebp+8) *(ebp+0xc) *(ebp+0x14) *(ebp+0x18)) +14549 e9/jump $emit-subx-stmt:end/disp32 +14550 } +14551 # get field from record +14552 { +14553 # if (!string-equal?(stmt->operation, "get")) break +14554 (string-equal? %ecx "get") # => eax +14555 3d/compare-eax-and 0/imm32 +14556 0f 84/jump-if-= break/disp32 +14557 (translate-mu-get-stmt *(ebp+8) *(ebp+0xc)) +14558 e9/jump $emit-subx-stmt:end/disp32 14559 } -14560 # if t == 0 abort -14561 3d/compare-eax-with 0/imm32 -14562 0f 84/jump-if-= $array-element-type-id:error2/disp32 -14563 # if t->is-atom? abort -14564 81 7/subop/compare *eax 0/imm32/false # Type-tree-is-atom -14565 0f 85/jump-if-!= $array-element-type-id:error2/disp32 -14566 # if t->left != array abort -14567 { -14568 50/push-eax -14569 (lookup *(eax+4) *(eax+8)) # Type-tree-left Type-tree-left => eax -14570 (is-simple-mu-type? %eax 3) # array => eax -14571 3d/compare-eax-with 0/imm32/false -14572 58/pop-to-eax -14573 $array-element-type-id:no-array: -14574 0f 84/jump-if-= $array-element-type-id:error2/disp32 -14575 } -14576 $array-element-type-id:skip-array: -14577 # t = t->right -14578 (lookup *(eax+0xc) *(eax+0x10)) # Type-tree-right Type-tree-right => eax -14579 # if t == 0 abort -14580 3d/compare-eax-with 0/imm32 -14581 0f 84/jump-if-= $array-element-type-id:error2/disp32 -14582 # if t->is-atom? abort -14583 81 7/subop/compare *eax 0/imm32/false # Type-tree-is-atom -14584 0f 85/jump-if-!= $array-element-type-id:error2/disp32 -14585 # return t->left->value -14586 (lookup *(eax+4) *(eax+8)) # Type-tree-left Type-tree-left => eax -14587 8b/-> *(eax+4) 0/r32/eax # Type-tree-value -14588 $array-element-type-id:end: -14589 # . epilogue -14590 89/<- %esp 5/r32/ebp -14591 5d/pop-to-ebp -14592 c3/return -14593 -14594 $array-element-type-id:error0: -14595 (write-buffered *(ebp+0xc) "array-element-type-id: var '") -14596 50/push-eax -14597 8b/-> *(ebp+8) 0/r32/eax -14598 (lookup *eax *(eax+4)) # Var-name Var-name => eax -14599 (write-buffered *(ebp+0xc) %eax) -14600 58/pop-to-eax -14601 (write-buffered *(ebp+0xc) "' has no type\n") -14602 (flush *(ebp+0xc)) -14603 (stop *(ebp+0x10) 1) -14604 # never gets here -14605 -14606 $array-element-type-id:error1: -14607 (write-buffered *(ebp+0xc) "array-element-type-id: var '") -14608 50/push-eax -14609 8b/-> *(ebp+8) 0/r32/eax -14610 (lookup *eax *(eax+4)) # Var-name Var-name => eax -14611 (write-buffered *(ebp+0xc) %eax) -14612 58/pop-to-eax -14613 (write-buffered *(ebp+0xc) "' has atomic type ") -14614 (write-int32-hex-buffered *(ebp+0xc) *(eax+4)) # Type-tree-value -14615 (write-buffered *(ebp+0xc) Newline) -14616 (flush *(ebp+0xc)) -14617 (stop *(ebp+0x10) 1) -14618 # never gets here -14619 -14620 $array-element-type-id:error2: -14621 (write-buffered *(ebp+0xc) "array-element-type-id: var '") -14622 50/push-eax -14623 8b/-> *(ebp+8) 0/r32/eax -14624 (lookup *eax *(eax+4)) # Var-name Var-name => eax -14625 (write-buffered *(ebp+0xc) %eax) -14626 58/pop-to-eax -14627 (write-buffered *(ebp+0xc) "' has non-array type\n") -14628 (flush *(ebp+0xc)) -14629 (stop *(ebp+0x10) 1) -14630 # never gets here -14631 -14632 size-of-type-id-as-array-element: # t: type-id -> result/eax: int -14633 # . prologue -14634 55/push-ebp -14635 89/<- %ebp 4/r32/esp -14636 # eax = t -14637 8b/-> *(ebp+8) 0/r32/eax -14638 # if t is 'byte', size is 1 -14639 3d/compare-eax-and 8/imm32/byte -14640 { -14641 75/jump-if-!= break/disp8 -14642 b8/copy-to-eax 1/imm32 -14643 eb/jump $size-of-type-id-as-array-element:end/disp8 -14644 } -14645 # otherwise proceed as usual -14646 (size-of-type-id %eax) # => eax -14647 $size-of-type-id-as-array-element:end: -14648 # . epilogue -14649 89/<- %esp 5/r32/ebp -14650 5d/pop-to-ebp -14651 c3/return -14652 -14653 emit-save-size-to: # out: (addr buffered-file), base: (addr var), outreg: (addr array byte) -14654 # . prologue -14655 55/push-ebp -14656 89/<- %ebp 4/r32/esp -14657 # . save registers -14658 50/push-eax -14659 53/push-ebx -14660 # ebx = base -14661 8b/-> *(ebp+0xc) 3/r32/ebx -14662 (emit-indent *(ebp+8) *Curr-block-depth) -14663 (write-buffered *(ebp+8) "8b/-> *") -14664 # if base is an (addr array ...) in a register -14665 { -14666 81 7/subop/compare *(ebx+0x18)) 0/imm32 # Var-register -14667 74/jump-if-= break/disp8 -14668 $emit-save-size-to:emit-base-from-register: -14669 (lookup *(ebx+0x18) *(ebx+0x1c)) # Var-register Var-register => eax -14670 (write-buffered *(ebp+8) %eax) -14671 eb/jump $emit-save-size-to:emit-output/disp8 +14560 # allocate scalar +14561 { +14562 # if (!string-equal?(stmt->operation, "allocate")) break +14563 (string-equal? %ecx "allocate") # => eax +14564 3d/compare-eax-and 0/imm32 +14565 0f 84/jump-if-= break/disp32 +14566 (translate-mu-allocate-stmt *(ebp+8) *(ebp+0xc) *(ebp+0x14) *(ebp+0x18)) +14567 e9/jump $emit-subx-stmt:end/disp32 +14568 } +14569 # allocate array +14570 { +14571 # if (!string-equal?(stmt->operation, "populate")) break +14572 (string-equal? %ecx "populate") # => eax +14573 3d/compare-eax-and 0/imm32 +14574 0f 84/jump-if-= break/disp32 +14575 (translate-mu-populate-stmt *(ebp+8) *(ebp+0xc) *(ebp+0x14) *(ebp+0x18)) +14576 e9/jump $emit-subx-stmt:end/disp32 +14577 } +14578 # allocate stream +14579 { +14580 # if (!string-equal?(stmt->operation, "populate-stream")) break +14581 (string-equal? %ecx "populate-stream") # => eax +14582 3d/compare-eax-and 0/imm32 +14583 0f 84/jump-if-= break/disp32 +14584 (translate-mu-populate-stream-stmt *(ebp+8) *(ebp+0xc) *(ebp+0x14) *(ebp+0x18)) +14585 e9/jump $emit-subx-stmt:end/disp32 +14586 } +14587 # read from stream +14588 { +14589 # if (!string-equal?(stmt->operation, "read-from-stream")) break +14590 (string-equal? %ecx "read-from-stream") # => eax +14591 3d/compare-eax-and 0/imm32 +14592 0f 84/jump-if-= break/disp32 +14593 (translate-mu-read-from-stream-stmt *(ebp+8) *(ebp+0xc) *(ebp+0x14) *(ebp+0x18)) +14594 e9/jump $emit-subx-stmt:end/disp32 +14595 } +14596 # write to stream +14597 { +14598 # if (!string-equal?(stmt->operation, "write-to-stream")) break +14599 (string-equal? %ecx "write-to-stream") # => eax +14600 3d/compare-eax-and 0/imm32 +14601 0f 84/jump-if-= break/disp32 +14602 (translate-mu-write-to-stream-stmt *(ebp+8) *(ebp+0xc) *(ebp+0x14) *(ebp+0x18)) +14603 e9/jump $emit-subx-stmt:end/disp32 +14604 } +14605 # - if stmt matches a primitive, emit it +14606 { +14607 $emit-subx-stmt:check-for-primitive: +14608 # var curr/eax: (addr primitive) +14609 (find-matching-primitive *(ebp+0x10) *(ebp+0xc)) # primitives, stmt => eax +14610 3d/compare-eax-and 0/imm32 +14611 74/jump-if-= break/disp8 +14612 $emit-subx-stmt:primitive: +14613 (emit-subx-primitive *(ebp+8) *(ebp+0xc) %eax) # out, stmt, curr +14614 e9/jump $emit-subx-stmt:end/disp32 +14615 } +14616 # - otherwise emit a call +14617 # TODO: type-checking +14618 $emit-subx-stmt:call: +14619 (emit-call *(ebp+8) *(ebp+0xc)) +14620 $emit-subx-stmt:end: +14621 # . restore registers +14622 59/pop-to-ecx +14623 58/pop-to-eax +14624 # . epilogue +14625 89/<- %esp 5/r32/ebp +14626 5d/pop-to-ebp +14627 c3/return +14628 +14629 translate-mu-length-stmt: # out: (addr buffered-file), stmt: (addr stmt), err: (addr buffered-file), ed: (addr exit-descriptor) +14630 # . prologue +14631 55/push-ebp +14632 89/<- %ebp 4/r32/esp +14633 # . save registers +14634 50/push-eax +14635 51/push-ecx +14636 52/push-edx +14637 53/push-ebx +14638 56/push-esi +14639 # esi = stmt +14640 8b/-> *(ebp+0xc) 6/r32/esi +14641 # var base/ebx: (addr var) = stmt->inouts[0]->value +14642 (lookup *(esi+0xc) *(esi+0x10)) # Stmt1-inouts Stmt1-inouts => eax +14643 (lookup *eax *(eax+4)) # Stmt-var-value Stmt-var-value => eax +14644 89/<- %ebx 0/r32/eax +14645 # var elemsize/ecx: int = array-element-size(base) +14646 (array-element-size %ebx *(ebp+0x10) *(ebp+0x14)) # => eax +14647 89/<- %ecx 0/r32/eax +14648 # var outreg/edx: (addr array byte) = stmt->outputs[0]->value->register +14649 (lookup *(esi+0x14) *(esi+0x18)) # Stmt1-outputs Stmt1-outputs => eax +14650 (lookup *eax *(eax+4)) # Stmt-var-value Stmt-var-value => eax +14651 (lookup *(eax+0x18) *(eax+0x1c)) # Var-register Var-register => eax +14652 89/<- %edx 0/r32/eax +14653 # if elemsize == 1 +14654 { +14655 81 7/subop/compare %ecx 1/imm32 +14656 75/jump-if-!= break/disp8 +14657 $translate-mu-length-stmt:size-1: +14658 (emit-save-size-to *(ebp+8) %ebx %edx) +14659 e9/jump $translate-mu-length-stmt:end/disp32 +14660 } +14661 # if elemsize is a power of 2 less than 256 +14662 { +14663 (power-of-2? %ecx *(ebp+0x10) *(ebp+0x14)) # => eax +14664 3d/compare-eax-and 0/imm32/false +14665 74/jump-if-= break/disp8 +14666 81 7/subop/compare %ecx 0xff/imm32 +14667 7f/jump-if-> break/disp8 +14668 $translate-mu-length-stmt:size-power-of-2: +14669 (emit-save-size-to *(ebp+8) %ebx %edx) +14670 (emit-divide-by-shift-right *(ebp+8) %edx %ecx) +14671 e9/jump $translate-mu-length-stmt:end/disp32 14672 } -14673 # otherwise if base is an (array ...) on the stack -14674 { -14675 81 7/subop/compare *(ebx+0x14)) 0/imm32 # Var-offset -14676 74/jump-if-= break/disp8 -14677 $emit-save-size-to:emit-base-from-stack: -14678 (write-buffered *(ebp+8) "(ebp+") -14679 (write-int32-hex-buffered *(ebp+8) *(ebx+0x14)) # Var-offset -14680 (write-buffered *(ebp+8) ")") -14681 } -14682 $emit-save-size-to:emit-output: -14683 (write-buffered *(ebp+8) " ") -14684 (get Mu-registers *(ebp+0x10) 0xc "Mu-registers") # => eax -14685 (write-int32-hex-buffered *(ebp+8) *eax) -14686 (write-buffered *(ebp+8) "/r32\n") -14687 $emit-save-size-to:end: -14688 # . restore registers -14689 5b/pop-to-ebx -14690 58/pop-to-eax -14691 # . epilogue -14692 89/<- %esp 5/r32/ebp -14693 5d/pop-to-ebp -14694 c3/return -14695 -14696 emit-divide-by-shift-right: # out: (addr buffered-file), reg: (addr array byte), size: int -14697 # . prologue -14698 55/push-ebp -14699 89/<- %ebp 4/r32/esp -14700 # . save registers -14701 50/push-eax -14702 # -14703 (emit-indent *(ebp+8) *Curr-block-depth) -14704 (write-buffered *(ebp+8) "c1/shift 5/subop/>> %") -14705 (write-buffered *(ebp+8) *(ebp+0xc)) -14706 (write-buffered *(ebp+8) Space) -14707 (num-shift-rights *(ebp+0x10)) # => eax -14708 (write-int32-hex-buffered *(ebp+8) %eax) -14709 (write-buffered *(ebp+8) "/imm8\n") -14710 $emit-divide-by-shift-right:end: -14711 # . restore registers -14712 58/pop-to-eax -14713 # . epilogue -14714 89/<- %esp 5/r32/ebp -14715 5d/pop-to-ebp -14716 c3/return -14717 -14718 translate-mu-index-stmt: # out: (addr buffered-file), stmt: (addr stmt), err: (addr buffered-file), ed: (addr exit-descriptor) -14719 # . prologue -14720 55/push-ebp -14721 89/<- %ebp 4/r32/esp -14722 # . save registers -14723 51/push-ecx -14724 # ecx = stmt -14725 8b/-> *(ebp+0xc) 1/r32/ecx -14726 # var base/ecx: (addr var) = stmt->inouts[0] -14727 (lookup *(ecx+0xc) *(ecx+0x10)) # Stmt1-inouts Stmt1-inouts => eax -14728 (lookup *eax *(eax+4)) # Stmt-var-value Stmt-var-value => eax -14729 89/<- %ecx 0/r32/eax -14730 # if (var->register) do one thing +14673 # otherwise, the complex case +14674 # . emit register spills +14675 { +14676 $translate-mu-length-stmt:complex: +14677 (string-equal? %edx "eax") # => eax +14678 3d/compare-eax-and 0/imm32/false +14679 75/break-if-!= break/disp8 +14680 (emit-indent *(ebp+8) *Curr-block-depth) +14681 (write-buffered *(ebp+8) "50/push-eax\n") +14682 } +14683 { +14684 (string-equal? %edx "ecx") # => eax +14685 3d/compare-eax-and 0/imm32/false +14686 75/break-if-!= break/disp8 +14687 (emit-indent *(ebp+8) *Curr-block-depth) +14688 (write-buffered *(ebp+8) "51/push-ecx\n") +14689 } +14690 { +14691 (string-equal? %edx "edx") # => eax +14692 3d/compare-eax-and 0/imm32/false +14693 75/break-if-!= break/disp8 +14694 (emit-indent *(ebp+8) *Curr-block-depth) +14695 (write-buffered *(ebp+8) "52/push-edx\n") +14696 } +14697 # . +14698 (emit-save-size-to *(ebp+8) %ebx "eax") +14699 (emit-indent *(ebp+8) *Curr-block-depth) +14700 (write-buffered *(ebp+8) "31/xor %edx 2/r32/edx\n") +14701 (emit-indent *(ebp+8) *Curr-block-depth) +14702 (write-buffered *(ebp+8) "b9/copy-to-ecx ") +14703 (write-int32-hex-buffered *(ebp+8) %ecx) +14704 (write-buffered *(ebp+8) "/imm32\n") +14705 (emit-indent *(ebp+8) *Curr-block-depth) +14706 (write-buffered *(ebp+8) "f7 7/subop/idiv-eax-edx-by %ecx\n") +14707 { +14708 (string-equal? %edx "eax") # => eax +14709 3d/compare-eax-and 0/imm32/false +14710 75/break-if-!= break/disp8 +14711 (emit-indent *(ebp+8) *Curr-block-depth) +14712 (write-buffered *(ebp+8) "89/<- %") +14713 (write-buffered *(ebp+8) %edx) +14714 (write-buffered *(ebp+8) " 0/r32/eax\n") +14715 } +14716 # . emit register restores +14717 { +14718 (string-equal? %edx "edx") # => eax +14719 3d/compare-eax-and 0/imm32/false +14720 75/break-if-!= break/disp8 +14721 (emit-indent *(ebp+8) *Curr-block-depth) +14722 (write-buffered *(ebp+8) "5a/pop-to-edx\n") +14723 } +14724 { +14725 (string-equal? %edx "ecx") # => eax +14726 3d/compare-eax-and 0/imm32/false +14727 75/break-if-!= break/disp8 +14728 (emit-indent *(ebp+8) *Curr-block-depth) +14729 (write-buffered *(ebp+8) "59/pop-to-ecx\n") +14730 } 14731 { -14732 81 7/subop/compare *(ecx+0x18) 0/imm32 # Var-register -14733 74/jump-if-= break/disp8 -14734 # TODO: ensure there's no dereference -14735 (translate-mu-index-stmt-with-array-in-register *(ebp+8) *(ebp+0xc) *(ebp+0x10) *(ebp+0x14)) -14736 eb/jump $translate-mu-index-stmt:end/disp8 +14732 (string-equal? %edx "eax") # => eax +14733 3d/compare-eax-and 0/imm32/false +14734 75/break-if-!= break/disp8 +14735 (emit-indent *(ebp+8) *Curr-block-depth) +14736 (write-buffered *(ebp+8) "58/pop-to-eax\n") 14737 } -14738 # if (var->offset) do a different thing -14739 { -14740 81 7/subop/compare *(ecx+0x14) 0/imm32 # Var-offset -14741 74/jump-if-= break/disp8 -14742 # TODO: ensure there's no dereference -14743 (translate-mu-index-stmt-with-array-on-stack *(ebp+8) *(ebp+0xc) *(ebp+0x10) *(ebp+0x14)) -14744 eb/jump $translate-mu-index-stmt:end/disp8 -14745 } -14746 $translate-mu-index-stmt:end: -14747 # . restore registers -14748 59/pop-to-ecx -14749 # . epilogue -14750 89/<- %esp 5/r32/ebp -14751 5d/pop-to-ebp -14752 c3/return -14753 -14754 $translate-mu-index-stmt-with-array:error1: -14755 (write-buffered *(ebp+0x10) "couldn't translate an index instruction. second (index) input must either lie in a register or be a literal\n") -14756 (flush *(ebp+0x10)) -14757 (stop *(ebp+0x14) 1) -14758 # never gets here -14759 -14760 $translate-mu-index-stmt-with-array:error2: -14761 (write-buffered *(ebp+0x10) "couldn't translate an index instruction. second (index) input when in a register must be an int or offset\n") -14762 (flush *(ebp+0x10)) -14763 (stop *(ebp+0x14) 1) -14764 # never gets here -14765 -14766 translate-mu-index-stmt-with-array-in-register: # out: (addr buffered-file), stmt: (addr stmt), err: (addr buffered-file), ed: (addr exit-descriptor) -14767 # . prologue -14768 55/push-ebp -14769 89/<- %ebp 4/r32/esp -14770 # . save registers -14771 50/push-eax -14772 51/push-ecx -14773 52/push-edx -14774 53/push-ebx -14775 # -14776 (emit-indent *(ebp+8) *Curr-block-depth) -14777 (write-buffered *(ebp+8) "8d/copy-address *(") -14778 # TODO: ensure inouts[0] is in a register and not dereferenced -14779 $translate-mu-index-stmt-with-array-in-register:emit-base: -14780 # ecx = stmt -14781 8b/-> *(ebp+0xc) 1/r32/ecx -14782 # var base/ebx: (addr var) = inouts[0] -14783 (lookup *(ecx+0xc) *(ecx+0x10)) # Stmt1-inouts Stmt1-inouts => eax -14784 (lookup *eax *(eax+4)) # Stmt-var-value Stmt-var-value => eax -14785 89/<- %ebx 0/r32/eax -14786 # print base->register " + " -14787 (lookup *(ebx+0x18) *(ebx+0x1c)) # Var-register Var-register => eax -14788 (write-buffered *(ebp+8) %eax) -14789 (write-buffered *(ebp+8) " + ") -14790 # var index/edx: (addr var) = inouts[1] -14791 (lookup *(ecx+0xc) *(ecx+0x10)) # Stmt1-inouts Stmt1-inouts => eax -14792 (lookup *(eax+8) *(eax+0xc)) # Stmt-var-next Stmt-var-next => eax -14793 (lookup *eax *(eax+4)) # Stmt-var-value Stmt-var-value => eax -14794 89/<- %edx 0/r32/eax -14795 # if index->register -14796 81 7/subop/compare *(edx+0x18) 0/imm32 # Var-register -14797 { -14798 0f 84/jump-if-= break/disp32 -14799 $translate-mu-index-stmt-with-array-in-register:emit-register-index: -14800 # if index is an int -14801 (lookup *(edx+8) *(edx+0xc)) # Var-type Var-type => eax -14802 (is-simple-mu-type? %eax 1) # int => eax -14803 3d/compare-eax-and 0/imm32/false -14804 { -14805 0f 84/jump-if-= break/disp32 -14806 $translate-mu-index-stmt-with-array-in-register:emit-int-register-index: -14807 # print index->register "<<" log2(array-element-size(base)) " + 4) " -14808 # . index->register "<<" -14809 (lookup *(edx+0x18) *(edx+0x1c)) # Var-register Var-register => eax -14810 (write-buffered *(ebp+8) %eax) -14811 (write-buffered *(ebp+8) "<<") -14812 # . log2(array-element-size(base->type)) -14813 # TODO: ensure size is a power of 2 -14814 (array-element-size %ebx *(ebp+0x10) *(ebp+0x14)) # => eax -14815 (num-shift-rights %eax) # => eax -14816 (write-int32-hex-buffered *(ebp+8) %eax) -14817 e9/jump $translate-mu-index-stmt-with-array-in-register:emit-register-index-done/disp32 -14818 } -14819 # if index->type is any other atom, abort -14820 (lookup *(edx+8) *(edx+0xc)) # Var-type Var-type => eax -14821 81 7/subop/compare *eax 0/imm32/false # Type-tree-is-atom -14822 0f 85/jump-if-!= $translate-mu-index-stmt-with-array:error2/disp32 -14823 # if index has type (offset ...) -14824 (lookup *(eax+4) *(eax+8)) # Type-tree-left Type-tree-left => eax -14825 (is-simple-mu-type? %eax 7) # => eax -14826 3d/compare-eax-and 0/imm32/false -14827 { -14828 0f 84/jump-if-= break/disp32 -14829 # print index->register -14830 $translate-mu-index-stmt-with-array-in-register:emit-offset-register-index: -14831 (lookup *(edx+0x18) *(edx+0x1c)) # Var-register Var-register => eax -14832 (write-buffered *(ebp+8) %eax) -14833 } -14834 $translate-mu-index-stmt-with-array-in-register:emit-register-index-done: -14835 (write-buffered *(ebp+8) " + 4) ") -14836 e9/jump $translate-mu-index-stmt-with-array-in-register:emit-output/disp32 -14837 } -14838 # otherwise if index is a literal -14839 (lookup *(edx+8) *(edx+0xc)) # Var-type Var-type => eax -14840 (is-simple-mu-type? %eax 0) # => eax -14841 3d/compare-eax-and 0/imm32/false -14842 { -14843 0f 84/jump-if-= break/disp32 -14844 $translate-mu-index-stmt-with-array-in-register:emit-literal-index: -14845 # var index-value/edx: int = parse-hex-int(index->name) -14846 (lookup *edx *(edx+4)) # Var-name Var-name => eax -14847 (parse-hex-int %eax) # => eax -14848 89/<- %edx 0/r32/eax -14849 # offset = idx-value * array-element-size(base->type) -14850 (array-element-size %ebx *(ebp+0x10) *(ebp+0x14)) # => eax -14851 f7 4/subop/multiply-into-eax %edx # clobbers edx -14852 # offset += 4 for array size -14853 05/add-to-eax 4/imm32 -14854 # TODO: check edx for overflow -14855 # print offset -14856 (write-int32-hex-buffered *(ebp+8) %eax) -14857 (write-buffered *(ebp+8) ") ") -14858 e9/jump $translate-mu-index-stmt-with-array-in-register:emit-output/disp32 -14859 } -14860 # otherwise abort -14861 e9/jump $translate-mu-index-stmt-with-array:error1/disp32 -14862 $translate-mu-index-stmt-with-array-in-register:emit-output: -14863 # outputs[0] "/r32" -14864 8b/-> *(ebp+0xc) 1/r32/ecx -14865 (lookup *(ecx+0x14) *(ecx+0x18)) # Stmt1-outputs Stmt1-outputs => eax -14866 (lookup *eax *(eax+4)) # Stmt-var-value Stmt-var-value => eax -14867 (lookup *(eax+0x18) *(eax+0x1c)) # Var-register Var-register => eax -14868 (get Mu-registers %eax 0xc "Mu-registers") # => eax: (addr int) -14869 (write-int32-hex-buffered *(ebp+8) *eax) -14870 (write-buffered *(ebp+8) "/r32\n") -14871 $translate-mu-index-stmt-with-array-in-register:end: -14872 # . restore registers -14873 5b/pop-to-ebx -14874 5a/pop-to-edx -14875 59/pop-to-ecx -14876 58/pop-to-eax +14738 $translate-mu-length-stmt:end: +14739 # . restore registers +14740 5e/pop-to-esi +14741 5b/pop-to-ebx +14742 5a/pop-to-edx +14743 59/pop-to-ecx +14744 58/pop-to-eax +14745 # . epilogue +14746 89/<- %esp 5/r32/ebp +14747 5d/pop-to-ebp +14748 c3/return +14749 +14750 array-element-size: # arr: (addr var), err: (addr buffered-file), ed: (addr exit-descriptor) -> result/eax: int +14751 # . prologue +14752 55/push-ebp +14753 89/<- %ebp 4/r32/esp +14754 # +14755 (array-element-type-id *(ebp+8) *(ebp+0xc) *(ebp+0x10)) # => eax +14756 (size-of-type-id-as-array-element %eax) # => eax +14757 $array-element-size:end: +14758 # . epilogue +14759 89/<- %esp 5/r32/ebp +14760 5d/pop-to-ebp +14761 c3/return +14762 +14763 array-element-type-id: # v: (addr var), err: (addr buffered-file), ed: (addr exit-descriptor) -> result/eax: type-id +14764 # precondition: n is positive +14765 # . prologue +14766 55/push-ebp +14767 89/<- %ebp 4/r32/esp +14768 # +14769 8b/-> *(ebp+8) 0/r32/eax +14770 # var t/eax: (addr type-tree) +14771 (lookup *(eax+8) *(eax+0xc)) # Var-type Var-type => eax +14772 # if t == 0 abort +14773 3d/compare-eax-with 0/imm32 +14774 0f 84/jump-if-== $array-element-type-id:error0/disp32 +14775 # if t->is-atom? abort +14776 81 7/subop/compare *eax 0/imm32/false # Type-tree-is-atom +14777 0f 85/jump-if-!= $array-element-type-id:error1/disp32 +14778 # if (t->left == addr) t = t->right +14779 { +14780 50/push-eax +14781 (lookup *(eax+4) *(eax+8)) # Type-tree-left Type-tree-left => eax +14782 (is-simple-mu-type? %eax 2) # addr => eax +14783 3d/compare-eax-with 0/imm32/false +14784 58/pop-to-eax +14785 74/jump-if-= break/disp8 +14786 $array-element-type-id:skip-addr: +14787 (lookup *(eax+0xc) *(eax+0x10)) # Type-tree-right Type-tree-right => eax +14788 } +14789 # if t == 0 abort +14790 3d/compare-eax-with 0/imm32 +14791 0f 84/jump-if-= $array-element-type-id:error2/disp32 +14792 # if t->is-atom? abort +14793 81 7/subop/compare *eax 0/imm32/false # Type-tree-is-atom +14794 0f 85/jump-if-!= $array-element-type-id:error2/disp32 +14795 # if t->left != array abort +14796 { +14797 50/push-eax +14798 (lookup *(eax+4) *(eax+8)) # Type-tree-left Type-tree-left => eax +14799 (is-simple-mu-type? %eax 3) # array => eax +14800 3d/compare-eax-with 0/imm32/false +14801 58/pop-to-eax +14802 $array-element-type-id:no-array: +14803 0f 84/jump-if-= $array-element-type-id:error2/disp32 +14804 } +14805 $array-element-type-id:skip-array: +14806 # t = t->right +14807 (lookup *(eax+0xc) *(eax+0x10)) # Type-tree-right Type-tree-right => eax +14808 # if t == 0 abort +14809 3d/compare-eax-with 0/imm32 +14810 0f 84/jump-if-= $array-element-type-id:error2/disp32 +14811 # if t->is-atom? abort +14812 81 7/subop/compare *eax 0/imm32/false # Type-tree-is-atom +14813 0f 85/jump-if-!= $array-element-type-id:error2/disp32 +14814 # return t->left->value +14815 (lookup *(eax+4) *(eax+8)) # Type-tree-left Type-tree-left => eax +14816 8b/-> *(eax+4) 0/r32/eax # Type-tree-value +14817 $array-element-type-id:end: +14818 # . epilogue +14819 89/<- %esp 5/r32/ebp +14820 5d/pop-to-ebp +14821 c3/return +14822 +14823 $array-element-type-id:error0: +14824 (write-buffered *(ebp+0xc) "array-element-type-id: var '") +14825 50/push-eax +14826 8b/-> *(ebp+8) 0/r32/eax +14827 (lookup *eax *(eax+4)) # Var-name Var-name => eax +14828 (write-buffered *(ebp+0xc) %eax) +14829 58/pop-to-eax +14830 (write-buffered *(ebp+0xc) "' has no type\n") +14831 (flush *(ebp+0xc)) +14832 (stop *(ebp+0x10) 1) +14833 # never gets here +14834 +14835 $array-element-type-id:error1: +14836 (write-buffered *(ebp+0xc) "array-element-type-id: var '") +14837 50/push-eax +14838 8b/-> *(ebp+8) 0/r32/eax +14839 (lookup *eax *(eax+4)) # Var-name Var-name => eax +14840 (write-buffered *(ebp+0xc) %eax) +14841 58/pop-to-eax +14842 (write-buffered *(ebp+0xc) "' has atomic type ") +14843 (write-int32-hex-buffered *(ebp+0xc) *(eax+4)) # Type-tree-value +14844 (write-buffered *(ebp+0xc) Newline) +14845 (flush *(ebp+0xc)) +14846 (stop *(ebp+0x10) 1) +14847 # never gets here +14848 +14849 $array-element-type-id:error2: +14850 (write-buffered *(ebp+0xc) "array-element-type-id: var '") +14851 50/push-eax +14852 8b/-> *(ebp+8) 0/r32/eax +14853 (lookup *eax *(eax+4)) # Var-name Var-name => eax +14854 (write-buffered *(ebp+0xc) %eax) +14855 58/pop-to-eax +14856 (write-buffered *(ebp+0xc) "' has non-array type\n") +14857 (flush *(ebp+0xc)) +14858 (stop *(ebp+0x10) 1) +14859 # never gets here +14860 +14861 size-of-type-id-as-array-element: # t: type-id -> result/eax: int +14862 # . prologue +14863 55/push-ebp +14864 89/<- %ebp 4/r32/esp +14865 # eax = t +14866 8b/-> *(ebp+8) 0/r32/eax +14867 # if t is 'byte', size is 1 +14868 3d/compare-eax-and 8/imm32/byte +14869 { +14870 75/jump-if-!= break/disp8 +14871 b8/copy-to-eax 1/imm32 +14872 eb/jump $size-of-type-id-as-array-element:end/disp8 +14873 } +14874 # otherwise proceed as usual +14875 (size-of-type-id %eax) # => eax +14876 $size-of-type-id-as-array-element:end: 14877 # . epilogue 14878 89/<- %esp 5/r32/ebp 14879 5d/pop-to-ebp 14880 c3/return 14881 -14882 translate-mu-index-stmt-with-array-on-stack: # out: (addr buffered-file), stmt: (addr stmt), err: (addr buffered-file), ed: (addr exit-descriptor) +14882 emit-save-size-to: # out: (addr buffered-file), base: (addr var), outreg: (addr array byte) 14883 # . prologue 14884 55/push-ebp 14885 89/<- %ebp 4/r32/esp 14886 # . save registers 14887 50/push-eax -14888 51/push-ecx -14889 52/push-edx -14890 53/push-ebx -14891 # -14892 (emit-indent *(ebp+8) *Curr-block-depth) -14893 (write-buffered *(ebp+8) "8d/copy-address *(ebp + ") -14894 # var curr/edx: (addr stmt-var) = lookup(stmt->inouts) -14895 8b/-> *(ebp+0xc) 0/r32/eax -14896 (lookup *(eax+0xc) *(eax+0x10)) # Stmt1-inouts Stmt1-inouts => eax -14897 89/<- %edx 0/r32/eax -14898 # var base/ecx: (addr var) = lookup(curr->value) -14899 (lookup *eax *(eax+4)) # Stmt-var-value Stmt-var-value => eax -14900 89/<- %ecx 0/r32/eax -14901 # var curr2/eax: (addr stmt-var) = lookup(curr->next) -14902 (lookup *(edx+8) *(edx+0xc)) # Stmt-var-next Stmt-var-next => eax -14903 # var index/edx: (handle var) = curr2->value -14904 (lookup *eax *(eax+4)) # Stmt-var-value Stmt-var-value => eax -14905 89/<- %edx 0/r32/eax -14906 # if index->register -14907 81 7/subop/compare *(edx+0x18) 0/imm32 # Var-register -14908 { -14909 0f 84/jump-if-= break/disp32 -14910 $translate-mu-index-stmt-with-array-on-stack:emit-register-index: -14911 # if index is an int -14912 (lookup *(edx+8) *(edx+0xc)) # Var-type Var-type => eax -14913 (is-simple-mu-type? %eax 1) # int => eax -14914 3d/compare-eax-and 0/imm32/false -14915 { -14916 0f 84/jump-if-= break/disp32 -14917 $translate-mu-index-stmt-with-array-on-stack:emit-int-register-index: -14918 # print index->register "<<" log2(array-element-size(base)) " + " base->offset+4 -14919 # . inouts[1]->register "<<" -14920 (lookup *(edx+0x18) *(edx+0x1c)) # Var-register Var-register => eax -14921 (write-buffered *(ebp+8) %eax) -14922 (write-buffered *(ebp+8) "<<") -14923 # . log2(array-element-size(base)) -14924 # TODO: ensure size is a power of 2 -14925 (array-element-size %ecx *(ebp+0x10) *(ebp+0x14)) # => eax -14926 (num-shift-rights %eax) # => eax -14927 (write-int32-hex-buffered *(ebp+8) %eax) -14928 # -14929 (write-buffered *(ebp+8) " + ") -14930 # -14931 8b/-> *(ecx+0x14) 0/r32/eax # Var-offset -14932 05/add-to-eax 4/imm32 # for array length -14933 (write-int32-hex-buffered *(ebp+8) %eax) -14934 e9/jump $translate-mu-index-stmt-with-array-on-stack:emit-register-index-done/disp32 -14935 } -14936 # if index->type is any other atom, abort -14937 (lookup *(edx+8) *(edx+0xc)) # Var-type Var-type => eax -14938 81 7/subop/compare *eax 0/imm32/false # Type-tree-is-atom -14939 0f 85/jump-if-!= $translate-mu-index-stmt-with-array:error2/disp32 -14940 # if index has type (offset ...) -14941 (lookup *(eax+4) *(eax+8)) # Type-tree-left Type-tree-left => eax -14942 (is-simple-mu-type? %eax 7) # => eax -14943 3d/compare-eax-and 0/imm32/false -14944 { -14945 0f 84/jump-if-= break/disp32 -14946 # print index->register -14947 $translate-mu-index-stmt-with-array-on-stack:emit-offset-register-index: -14948 (lookup *(edx+0x18) *(edx+0x1c)) # Var-register Var-register => eax -14949 (write-buffered *(ebp+8) %eax) -14950 } -14951 $translate-mu-index-stmt-with-array-on-stack:emit-register-index-done: -14952 (write-buffered *(ebp+8) ") ") -14953 e9/jump $translate-mu-index-stmt-with-array-on-stack:emit-output/disp32 -14954 } -14955 # otherwise if index is a literal -14956 (lookup *(edx+8) *(edx+0xc)) # Var-type Var-type => eax -14957 (is-simple-mu-type? %eax 0) # => eax -14958 3d/compare-eax-and 0/imm32/false -14959 { -14960 0f 84/jump-if-= break/disp32 -14961 $translate-mu-index-stmt-with-array-on-stack:emit-literal-index: -14962 # var idx-value/edx: int = parse-hex-int(index->name) -14963 (lookup *edx *(edx+4)) # Var-name Var-name => eax -14964 (parse-hex-int %eax) # Var-name => eax -14965 89/<- %edx 0/r32/eax -14966 # offset = idx-value * array-element-size(base) -14967 (array-element-size %ecx *(ebp+0x10) *(ebp+0x14)) # => eax -14968 f7 4/subop/multiply-into-eax %edx # clobbers edx -14969 # offset += base->offset -14970 03/add *(ecx+0x14) 0/r32/eax # Var-offset -14971 # offset += 4 for array size -14972 05/add-to-eax 4/imm32 -14973 # TODO: check edx for overflow -14974 # print offset -14975 (write-int32-hex-buffered *(ebp+8) %eax) -14976 (write-buffered *(ebp+8) ") ") -14977 e9/jump $translate-mu-index-stmt-with-array-on-stack:emit-output/disp32 -14978 } -14979 # otherwise abort -14980 e9/jump $translate-mu-index-stmt-with-array:error1/disp32 -14981 $translate-mu-index-stmt-with-array-on-stack:emit-output: -14982 # outputs[0] "/r32" -14983 8b/-> *(ebp+0xc) 0/r32/eax -14984 (lookup *(eax+0x14) *(eax+0x18)) # Stmt1-outputs Stmt1-outputs => eax -14985 (lookup *eax *(eax+4)) # Stmt-var-value Stmt-var-value => eax -14986 (lookup *(eax+0x18) *(eax+0x1c)) # Var-register Var-register => eax -14987 (get Mu-registers %eax 0xc "Mu-registers") # => eax: (addr int) -14988 (write-int32-hex-buffered *(ebp+8) *eax) -14989 (write-buffered *(ebp+8) "/r32\n") -14990 $translate-mu-index-stmt-with-array-on-stack:end: -14991 # . restore registers -14992 5b/pop-to-ebx -14993 5a/pop-to-edx -14994 59/pop-to-ecx -14995 58/pop-to-eax -14996 # . epilogue -14997 89/<- %esp 5/r32/ebp -14998 5d/pop-to-ebp -14999 c3/return -15000 -15001 translate-mu-compute-index-stmt: # out: (addr buffered-file), stmt: (addr stmt), err: (addr buffered-file), ed: (addr exit-descriptor) -15002 # . prologue -15003 55/push-ebp -15004 89/<- %ebp 4/r32/esp -15005 # . save registers -15006 50/push-eax -15007 51/push-ecx -15008 52/push-edx -15009 53/push-ebx -15010 # -15011 (emit-indent *(ebp+8) *Curr-block-depth) -15012 (write-buffered *(ebp+8) "69/multiply") -15013 # ecx = stmt -15014 8b/-> *(ebp+0xc) 1/r32/ecx -15015 # var first-inout/ebx: (addr stmt-var) = stmt->inouts[0] -15016 (lookup *(ecx+0xc) *(ecx+0x10)) # Stmt1-inouts Stmt1-inouts => eax -15017 89/<- %ebx 0/r32/eax -15018 $translate-mu-compute-index-stmt:emit-index: -15019 (lookup *(ebx+8) *(ebx+0xc)) # Stmt-var-next Stmt-var-next => eax -15020 (emit-subx-var-as-rm32 *(ebp+8) %eax) -15021 (write-buffered *(ebp+8) Space) -15022 $translate-mu-compute-index-stmt:emit-elem-size: -15023 # var base/ebx: (addr var) -15024 (lookup *ebx *(ebx+4)) # Stmt-var-value Stmt-var-value => eax -15025 89/<- %ebx 0/r32/eax -15026 # print array-element-size(base) -15027 (array-element-size %ebx *(ebp+0x10) *(ebp+0x14)) # => eax -15028 (write-int32-hex-buffered *(ebp+8) %eax) -15029 (write-buffered *(ebp+8) "/imm32 ") -15030 $translate-mu-compute-index-stmt:emit-output: -15031 # outputs[0] "/r32" -15032 (lookup *(ecx+0x14) *(ecx+0x18)) # Stmt1-outputs Stmt1-outputs => eax -15033 (lookup *eax *(eax+4)) # Stmt-var-value Stmt-var-value => eax -15034 (lookup *(eax+0x18) *(eax+0x1c)) # Var-register Var-register => eax -15035 (get Mu-registers %eax 0xc "Mu-registers") # => eax: (addr int) -15036 (write-int32-hex-buffered *(ebp+8) *eax) -15037 (write-buffered *(ebp+8) "/r32\n") -15038 $translate-mu-compute-index-stmt:end: -15039 # . restore registers -15040 5b/pop-to-ebx -15041 5a/pop-to-edx -15042 59/pop-to-ecx -15043 58/pop-to-eax -15044 # . epilogue -15045 89/<- %esp 5/r32/ebp -15046 5d/pop-to-ebp -15047 c3/return -15048 -15049 translate-mu-get-stmt: # out: (addr buffered-file), stmt: (addr stmt) -15050 # . prologue -15051 55/push-ebp -15052 89/<- %ebp 4/r32/esp -15053 # . save registers -15054 50/push-eax -15055 51/push-ecx -15056 52/push-edx -15057 # -15058 (emit-indent *(ebp+8) *Curr-block-depth) -15059 (write-buffered *(ebp+8) "8d/copy-address ") -15060 # ecx = stmt -15061 8b/-> *(ebp+0xc) 1/r32/ecx -15062 # var offset/edx: int = get offset of stmt -15063 (mu-get-offset %ecx) # => eax -15064 89/<- %edx 0/r32/eax -15065 # var base/eax: (addr var) = stmt->inouts->value -15066 (lookup *(ecx+0xc) *(ecx+0x10)) # Stmt1-inouts Stmt1-inouts => eax -15067 (lookup *eax *(eax+4)) # Stmt-var-value Stmt-var-value => eax -15068 # if base is in a register -15069 81 7/subop/compare *(eax+0x18) 0/imm32 # Var-register -15070 { -15071 0f 84/jump-if-= break/disp32 -15072 $translate-mu-get-stmt:emit-register-input: -15073 # emit "*(" base->register " + " offset ") " -15074 (write-buffered *(ebp+8) "*(") -15075 (lookup *(eax+0x18) *(eax+0x1c)) # Var-register Var-register => eax -15076 (write-buffered *(ebp+8) %eax) -15077 (write-buffered *(ebp+8) " + ") -15078 (write-int32-hex-buffered *(ebp+8) %edx) -15079 (write-buffered *(ebp+8) ") ") -15080 e9/jump $translate-mu-get-stmt:emit-output/disp32 -15081 } -15082 # otherwise base is on the stack -15083 { -15084 $translate-mu-get-stmt:emit-stack-input: -15085 # emit "*(ebp + " inouts[0]->stack-offset + offset ") " -15086 (write-buffered *(ebp+8) "*(ebp+") -15087 03/add *(eax+0x14) 2/r32/edx # Var-offset -15088 (write-int32-hex-buffered *(ebp+8) %edx) -15089 (write-buffered *(ebp+8) ") ") -15090 eb/jump $translate-mu-get-stmt:emit-output/disp8 -15091 } -15092 $translate-mu-get-stmt:emit-output: -15093 # var output/eax: (addr var) = stmt->outputs->value +14888 53/push-ebx +14889 # ebx = base +14890 8b/-> *(ebp+0xc) 3/r32/ebx +14891 (emit-indent *(ebp+8) *Curr-block-depth) +14892 (write-buffered *(ebp+8) "8b/-> *") +14893 # if base is an (addr array ...) in a register +14894 { +14895 81 7/subop/compare *(ebx+0x18)) 0/imm32 # Var-register +14896 74/jump-if-= break/disp8 +14897 $emit-save-size-to:emit-base-from-register: +14898 (lookup *(ebx+0x18) *(ebx+0x1c)) # Var-register Var-register => eax +14899 (write-buffered *(ebp+8) %eax) +14900 eb/jump $emit-save-size-to:emit-output/disp8 +14901 } +14902 # otherwise if base is an (array ...) on the stack +14903 { +14904 81 7/subop/compare *(ebx+0x14)) 0/imm32 # Var-offset +14905 74/jump-if-= break/disp8 +14906 $emit-save-size-to:emit-base-from-stack: +14907 (write-buffered *(ebp+8) "(ebp+") +14908 (write-int32-hex-buffered *(ebp+8) *(ebx+0x14)) # Var-offset +14909 (write-buffered *(ebp+8) ")") +14910 } +14911 $emit-save-size-to:emit-output: +14912 (write-buffered *(ebp+8) " ") +14913 (get Mu-registers *(ebp+0x10) 0xc "Mu-registers") # => eax +14914 (write-int32-hex-buffered *(ebp+8) *eax) +14915 (write-buffered *(ebp+8) "/r32\n") +14916 $emit-save-size-to:end: +14917 # . restore registers +14918 5b/pop-to-ebx +14919 58/pop-to-eax +14920 # . epilogue +14921 89/<- %esp 5/r32/ebp +14922 5d/pop-to-ebp +14923 c3/return +14924 +14925 emit-divide-by-shift-right: # out: (addr buffered-file), reg: (addr array byte), size: int +14926 # . prologue +14927 55/push-ebp +14928 89/<- %ebp 4/r32/esp +14929 # . save registers +14930 50/push-eax +14931 # +14932 (emit-indent *(ebp+8) *Curr-block-depth) +14933 (write-buffered *(ebp+8) "c1/shift 5/subop/>> %") +14934 (write-buffered *(ebp+8) *(ebp+0xc)) +14935 (write-buffered *(ebp+8) Space) +14936 (num-shift-rights *(ebp+0x10)) # => eax +14937 (write-int32-hex-buffered *(ebp+8) %eax) +14938 (write-buffered *(ebp+8) "/imm8\n") +14939 $emit-divide-by-shift-right:end: +14940 # . restore registers +14941 58/pop-to-eax +14942 # . epilogue +14943 89/<- %esp 5/r32/ebp +14944 5d/pop-to-ebp +14945 c3/return +14946 +14947 translate-mu-index-stmt: # out: (addr buffered-file), stmt: (addr stmt), err: (addr buffered-file), ed: (addr exit-descriptor) +14948 # . prologue +14949 55/push-ebp +14950 89/<- %ebp 4/r32/esp +14951 # . save registers +14952 51/push-ecx +14953 # ecx = stmt +14954 8b/-> *(ebp+0xc) 1/r32/ecx +14955 # var base/ecx: (addr var) = stmt->inouts[0] +14956 (lookup *(ecx+0xc) *(ecx+0x10)) # Stmt1-inouts Stmt1-inouts => eax +14957 (lookup *eax *(eax+4)) # Stmt-var-value Stmt-var-value => eax +14958 89/<- %ecx 0/r32/eax +14959 # if (var->register) do one thing +14960 { +14961 81 7/subop/compare *(ecx+0x18) 0/imm32 # Var-register +14962 74/jump-if-= break/disp8 +14963 # TODO: ensure there's no dereference +14964 (translate-mu-index-stmt-with-array-in-register *(ebp+8) *(ebp+0xc) *(ebp+0x10) *(ebp+0x14)) +14965 eb/jump $translate-mu-index-stmt:end/disp8 +14966 } +14967 # if (var->offset) do a different thing +14968 { +14969 81 7/subop/compare *(ecx+0x14) 0/imm32 # Var-offset +14970 74/jump-if-= break/disp8 +14971 # TODO: ensure there's no dereference +14972 (translate-mu-index-stmt-with-array-on-stack *(ebp+8) *(ebp+0xc) *(ebp+0x10) *(ebp+0x14)) +14973 eb/jump $translate-mu-index-stmt:end/disp8 +14974 } +14975 $translate-mu-index-stmt:end: +14976 # . restore registers +14977 59/pop-to-ecx +14978 # . epilogue +14979 89/<- %esp 5/r32/ebp +14980 5d/pop-to-ebp +14981 c3/return +14982 +14983 $translate-mu-index-stmt-with-array:error1: +14984 (write-buffered *(ebp+0x10) "couldn't translate an index instruction. second (index) input must either lie in a register or be a literal\n") +14985 (flush *(ebp+0x10)) +14986 (stop *(ebp+0x14) 1) +14987 # never gets here +14988 +14989 $translate-mu-index-stmt-with-array:error2: +14990 (write-buffered *(ebp+0x10) "couldn't translate an index instruction. second (index) input when in a register must be an int or offset\n") +14991 (flush *(ebp+0x10)) +14992 (stop *(ebp+0x14) 1) +14993 # never gets here +14994 +14995 translate-mu-index-stmt-with-array-in-register: # out: (addr buffered-file), stmt: (addr stmt), err: (addr buffered-file), ed: (addr exit-descriptor) +14996 # . prologue +14997 55/push-ebp +14998 89/<- %ebp 4/r32/esp +14999 # . save registers +15000 50/push-eax +15001 51/push-ecx +15002 52/push-edx +15003 53/push-ebx +15004 # +15005 (emit-indent *(ebp+8) *Curr-block-depth) +15006 (write-buffered *(ebp+8) "8d/copy-address *(") +15007 # TODO: ensure inouts[0] is in a register and not dereferenced +15008 $translate-mu-index-stmt-with-array-in-register:emit-base: +15009 # ecx = stmt +15010 8b/-> *(ebp+0xc) 1/r32/ecx +15011 # var base/ebx: (addr var) = inouts[0] +15012 (lookup *(ecx+0xc) *(ecx+0x10)) # Stmt1-inouts Stmt1-inouts => eax +15013 (lookup *eax *(eax+4)) # Stmt-var-value Stmt-var-value => eax +15014 89/<- %ebx 0/r32/eax +15015 # print base->register " + " +15016 (lookup *(ebx+0x18) *(ebx+0x1c)) # Var-register Var-register => eax +15017 (write-buffered *(ebp+8) %eax) +15018 (write-buffered *(ebp+8) " + ") +15019 # var index/edx: (addr var) = inouts[1] +15020 (lookup *(ecx+0xc) *(ecx+0x10)) # Stmt1-inouts Stmt1-inouts => eax +15021 (lookup *(eax+8) *(eax+0xc)) # Stmt-var-next Stmt-var-next => eax +15022 (lookup *eax *(eax+4)) # Stmt-var-value Stmt-var-value => eax +15023 89/<- %edx 0/r32/eax +15024 # if index->register +15025 81 7/subop/compare *(edx+0x18) 0/imm32 # Var-register +15026 { +15027 0f 84/jump-if-= break/disp32 +15028 $translate-mu-index-stmt-with-array-in-register:emit-register-index: +15029 # if index is an int +15030 (lookup *(edx+8) *(edx+0xc)) # Var-type Var-type => eax +15031 (is-simple-mu-type? %eax 1) # int => eax +15032 3d/compare-eax-and 0/imm32/false +15033 { +15034 0f 84/jump-if-= break/disp32 +15035 $translate-mu-index-stmt-with-array-in-register:emit-int-register-index: +15036 # print index->register "<<" log2(array-element-size(base)) " + 4) " +15037 # . index->register "<<" +15038 (lookup *(edx+0x18) *(edx+0x1c)) # Var-register Var-register => eax +15039 (write-buffered *(ebp+8) %eax) +15040 (write-buffered *(ebp+8) "<<") +15041 # . log2(array-element-size(base->type)) +15042 # TODO: ensure size is a power of 2 +15043 (array-element-size %ebx *(ebp+0x10) *(ebp+0x14)) # => eax +15044 (num-shift-rights %eax) # => eax +15045 (write-int32-hex-buffered *(ebp+8) %eax) +15046 e9/jump $translate-mu-index-stmt-with-array-in-register:emit-register-index-done/disp32 +15047 } +15048 # if index->type is any other atom, abort +15049 (lookup *(edx+8) *(edx+0xc)) # Var-type Var-type => eax +15050 81 7/subop/compare *eax 0/imm32/false # Type-tree-is-atom +15051 0f 85/jump-if-!= $translate-mu-index-stmt-with-array:error2/disp32 +15052 # if index has type (offset ...) +15053 (lookup *(eax+4) *(eax+8)) # Type-tree-left Type-tree-left => eax +15054 (is-simple-mu-type? %eax 7) # => eax +15055 3d/compare-eax-and 0/imm32/false +15056 { +15057 0f 84/jump-if-= break/disp32 +15058 # print index->register +15059 $translate-mu-index-stmt-with-array-in-register:emit-offset-register-index: +15060 (lookup *(edx+0x18) *(edx+0x1c)) # Var-register Var-register => eax +15061 (write-buffered *(ebp+8) %eax) +15062 } +15063 $translate-mu-index-stmt-with-array-in-register:emit-register-index-done: +15064 (write-buffered *(ebp+8) " + 4) ") +15065 e9/jump $translate-mu-index-stmt-with-array-in-register:emit-output/disp32 +15066 } +15067 # otherwise if index is a literal +15068 (lookup *(edx+8) *(edx+0xc)) # Var-type Var-type => eax +15069 (is-simple-mu-type? %eax 0) # => eax +15070 3d/compare-eax-and 0/imm32/false +15071 { +15072 0f 84/jump-if-= break/disp32 +15073 $translate-mu-index-stmt-with-array-in-register:emit-literal-index: +15074 # var index-value/edx: int = parse-hex-int(index->name) +15075 (lookup *edx *(edx+4)) # Var-name Var-name => eax +15076 (parse-hex-int %eax) # => eax +15077 89/<- %edx 0/r32/eax +15078 # offset = idx-value * array-element-size(base->type) +15079 (array-element-size %ebx *(ebp+0x10) *(ebp+0x14)) # => eax +15080 f7 4/subop/multiply-into-eax %edx # clobbers edx +15081 # offset += 4 for array size +15082 05/add-to-eax 4/imm32 +15083 # TODO: check edx for overflow +15084 # print offset +15085 (write-int32-hex-buffered *(ebp+8) %eax) +15086 (write-buffered *(ebp+8) ") ") +15087 e9/jump $translate-mu-index-stmt-with-array-in-register:emit-output/disp32 +15088 } +15089 # otherwise abort +15090 e9/jump $translate-mu-index-stmt-with-array:error1/disp32 +15091 $translate-mu-index-stmt-with-array-in-register:emit-output: +15092 # outputs[0] "/r32" +15093 8b/-> *(ebp+0xc) 1/r32/ecx 15094 (lookup *(ecx+0x14) *(ecx+0x18)) # Stmt1-outputs Stmt1-outputs => eax 15095 (lookup *eax *(eax+4)) # Stmt-var-value Stmt-var-value => eax -15096 # emit offset->register "/r32" -15097 (lookup *(eax+0x18) *(eax+0x1c)) # Var-register Var-register => eax -15098 (get Mu-registers %eax 0xc "Mu-registers") # => eax: (addr int) -15099 (write-int32-hex-buffered *(ebp+8) *eax) -15100 (write-buffered *(ebp+8) "/r32\n") -15101 $translate-mu-get-stmt:end: -15102 # . restore registers +15096 (lookup *(eax+0x18) *(eax+0x1c)) # Var-register Var-register => eax +15097 (get Mu-registers %eax 0xc "Mu-registers") # => eax: (addr int) +15098 (write-int32-hex-buffered *(ebp+8) *eax) +15099 (write-buffered *(ebp+8) "/r32\n") +15100 $translate-mu-index-stmt-with-array-in-register:end: +15101 # . restore registers +15102 5b/pop-to-ebx 15103 5a/pop-to-edx 15104 59/pop-to-ecx 15105 58/pop-to-eax @@ -14467,6834 +14467,7228 @@ if ('onhashchange' in window) { 15108 5d/pop-to-ebp 15109 c3/return 15110 -15111 translate-mu-allocate-stmt: # out: (addr buffered-file), stmt: (addr stmt), err: (addr buffered-file), ed: (addr exit-descriptor) +15111 translate-mu-index-stmt-with-array-on-stack: # out: (addr buffered-file), stmt: (addr stmt), err: (addr buffered-file), ed: (addr exit-descriptor) 15112 # . prologue 15113 55/push-ebp 15114 89/<- %ebp 4/r32/esp 15115 # . save registers 15116 50/push-eax -15117 56/push-esi -15118 57/push-edi -15119 # esi = stmt -15120 8b/-> *(ebp+0xc) 6/r32/esi -15121 # var target/edi: (addr stmt-var) = stmt->inouts[0] -15122 (lookup *(esi+0xc) *(esi+0x10)) # Stmt1-inouts Stmt1-inouts => eax -15123 89/<- %edi 0/r32/eax -15124 # -15125 (emit-indent *(ebp+8) *Curr-block-depth) -15126 (write-buffered *(ebp+8) "(allocate Heap ") -15127 (addr-handle-payload-size %edi *(ebp+0x10) *(ebp+0x14)) # => eax -15128 (write-int32-hex-buffered *(ebp+8) %eax) -15129 (emit-subx-call-operand *(ebp+8) %edi) -15130 (write-buffered *(ebp+8) ")\n") -15131 $translate-mu-allocate-stmt:end: -15132 # . restore registers -15133 5f/pop-to-edi -15134 5e/pop-to-esi -15135 58/pop-to-eax -15136 # . epilogue -15137 89/<- %esp 5/r32/ebp -15138 5d/pop-to-ebp -15139 c3/return -15140 -15141 addr-handle-payload-size: # s: (addr stmt-var), err: (addr buffered-file), ed: (addr exit-descriptor) -> result/eax: int -15142 # . prologue -15143 55/push-ebp -15144 89/<- %ebp 4/r32/esp -15145 # var t/eax: (addr type-tree) = s->value->type -15146 8b/-> *(ebp+8) 0/r32/eax -15147 (lookup *eax *(eax+4)) # Stmt-var-value Stmt-var-value => eax -15148 (lookup *(eax+8) *(eax+0xc)) # Var-type Var-type => eax -15149 # TODO: check eax != 0 -15150 # TODO: check !t->is-atom? -15151 # TODO: check t->left == addr -15152 # t = t->right -15153 $addr-handle-payload-size:skip-addr: -15154 (lookup *(eax+0xc) *(eax+0x10)) # Type-tree-right Type-tree-right => eax -15155 # TODO: check eax != 0 -15156 # TODO: check !t->is-atom? -15157 # TODO: check t->left == handle -15158 # t = t->right -15159 $addr-handle-payload-size:skip-handle: -15160 (lookup *(eax+0xc) *(eax+0x10)) # Type-tree-right Type-tree-right => eax -15161 # TODO: check eax != 0 -15162 # if !t->is-atom? t = t->left -15163 81 7/subop/compare *eax 0/imm32/false -15164 { -15165 75/jump-if-!= break/disp8 -15166 (lookup *(eax+4) *(eax+8)) # Type-tree-left Type-tree-left => eax -15167 } -15168 # TODO: check t->is-atom? -15169 # return size(t->value) -15170 (size-of-type-id *(eax+4)) # Type-tree-value => eax -15171 $addr-handle-payload-size:end: -15172 # . epilogue -15173 89/<- %esp 5/r32/ebp -15174 5d/pop-to-ebp -15175 c3/return -15176 -15177 translate-mu-populate-stmt: # out: (addr buffered-file), stmt: (addr stmt), err: (addr buffered-file), ed: (addr exit-descriptor) -15178 # . prologue -15179 55/push-ebp -15180 89/<- %ebp 4/r32/esp -15181 # . save registers -15182 50/push-eax -15183 51/push-ecx -15184 56/push-esi -15185 57/push-edi -15186 # esi = stmt -15187 8b/-> *(ebp+0xc) 6/r32/esi -15188 # var target/edi: (addr stmt-var) = stmt->inouts[0] -15189 (lookup *(esi+0xc) *(esi+0x10)) # Stmt1-inouts Stmt1-inouts => eax -15190 89/<- %edi 0/r32/eax -15191 # var len/ecx: (addr stmt-var) = stmt->inouts[1] -15192 (lookup *(edi+8) *(edi+0xc)) # Stmt-var-next Stmt-var-next => eax -15193 89/<- %ecx 0/r32/eax -15194 # -15195 (emit-indent *(ebp+8) *Curr-block-depth) -15196 (write-buffered *(ebp+8) "(allocate-array2 Heap ") -15197 (addr-handle-array-payload-size %edi *(ebp+0x10) *(ebp+0x14)) # => eax -15198 (write-int32-hex-buffered *(ebp+8) %eax) -15199 (emit-subx-call-operand *(ebp+8) %ecx) -15200 (emit-subx-call-operand *(ebp+8) %edi) -15201 (write-buffered *(ebp+8) ")\n") -15202 $translate-mu-populate-stmt:end: -15203 # . restore registers -15204 5f/pop-to-edi -15205 5e/pop-to-esi -15206 59/pop-to-ecx -15207 58/pop-to-eax -15208 # . epilogue -15209 89/<- %esp 5/r32/ebp -15210 5d/pop-to-ebp -15211 c3/return -15212 -15213 addr-handle-array-payload-size: # s: (addr stmt-var), err: (addr buffered-file), ed: (addr exit-descriptor) -> result/eax: int -15214 # . prologue -15215 55/push-ebp -15216 89/<- %ebp 4/r32/esp -15217 # var t/eax: (addr type-tree) = s->value->type -15218 8b/-> *(ebp+8) 0/r32/eax -15219 (lookup *eax *(eax+4)) # Stmt-var-value Stmt-var-value => eax -15220 (lookup *(eax+8) *(eax+0xc)) # Var-type Var-type => eax -15221 # TODO: check eax != 0 -15222 # TODO: check !t->is-atom? -15223 # TODO: check t->left == addr -15224 # t = t->right -15225 $addr-handle-array-payload-size:skip-addr: -15226 (lookup *(eax+0xc) *(eax+0x10)) # Type-tree-right Type-tree-right => eax -15227 # TODO: check eax != 0 -15228 # TODO: check !t->is-atom? -15229 # TODO: check t->left == handle -15230 # t = t->right -15231 $addr-handle-array-payload-size:skip-handle: -15232 (lookup *(eax+0xc) *(eax+0x10)) # Type-tree-right Type-tree-right => eax -15233 # TODO: check eax != 0 -15234 # TODO: check !t->is-atom? -15235 # TODO: check t->left == array -15236 # t = t->right -15237 $addr-handle-array-payload-size:skip-array: -15238 (lookup *(eax+0xc) *(eax+0x10)) # Type-tree-right Type-tree-right => eax -15239 # TODO: check eax != 0 -15240 # if !t->is-atom? t = t->left -15241 81 7/subop/compare *eax 0/imm32/false -15242 { -15243 75/jump-if-!= break/disp8 -15244 (lookup *(eax+4) *(eax+8)) # Type-tree-left Type-tree-left => eax -15245 } -15246 $addr-handle-array-payload-size:compute-size: -15247 # TODO: check t->is-atom? -15248 # return size(t->value) -15249 (size-of-type-id-as-array-element *(eax+4)) # Type-tree-value => eax -15250 $addr-handle-array-payload-size:end: -15251 # . epilogue -15252 89/<- %esp 5/r32/ebp -15253 5d/pop-to-ebp -15254 c3/return -15255 -15256 power-of-2?: # n: int, err: (addr buffered-file), ed: (addr exit-descriptor) -> result/eax: boolean -15257 # precondition: n is positive -15258 # . prologue -15259 55/push-ebp -15260 89/<- %ebp 4/r32/esp -15261 # eax = n -15262 8b/-> *(ebp+8) 0/r32/eax -15263 # if (n < 0) abort -15264 3d/compare-eax-with 0/imm32 -15265 0f 8c/jump-if-< $power-of-2?:abort/disp32 -15266 # var tmp/eax: int = n-1 -15267 48/decrement-eax -15268 # var tmp2/eax: int = n & tmp -15269 23/and-> *(ebp+8) 0/r32/eax -15270 # return (tmp2 == 0) -15271 3d/compare-eax-and 0/imm32 -15272 0f 94/set-byte-if-= %al -15273 81 4/subop/and %eax 0xff/imm32 -15274 $power-of-2?:end: -15275 # . epilogue -15276 89/<- %esp 5/r32/ebp -15277 5d/pop-to-ebp -15278 c3/return -15279 -15280 $power-of-2?:abort: -15281 (write-buffered *(ebp+0xc) "power-of-2?: negative number\n") -15282 (flush *(ebp+0xc)) -15283 (stop *(ebp+0x10) 1) -15284 # never gets here -15285 -15286 num-shift-rights: # n: int -> result/eax: int -15287 # precondition: n is a positive power of 2 -15288 # . prologue -15289 55/push-ebp -15290 89/<- %ebp 4/r32/esp -15291 # . save registers -15292 51/push-ecx -15293 # var curr/ecx: int = n -15294 8b/-> *(ebp+8) 1/r32/ecx -15295 # result = 0 -15296 b8/copy-to-eax 0/imm32 -15297 { -15298 # if (curr <= 1) break -15299 81 7/subop/compare %ecx 1/imm32 -15300 7e/jump-if-<= break/disp8 -15301 40/increment-eax -15302 c1/shift 5/subop/arithmetic-right %ecx 1/imm8 -15303 eb/jump loop/disp8 -15304 } -15305 $num-shift-rights:end: -15306 # . restore registers -15307 59/pop-to-ecx -15308 # . epilogue -15309 89/<- %esp 5/r32/ebp -15310 5d/pop-to-ebp -15311 c3/return -15312 -15313 mu-get-offset: # stmt: (addr stmt) -> result/eax: int -15314 # . prologue -15315 55/push-ebp -15316 89/<- %ebp 4/r32/esp -15317 # var second-inout/eax: (addr stmt-var) = stmt->inouts->next -15318 8b/-> *(ebp+8) 0/r32/eax -15319 (lookup *(eax+0xc) *(eax+0x10)) # Stmt1-inouts Stmt1-inouts => eax -15320 (lookup *(eax+8) *(eax+0xc)) # Stmt-var-next Stmt-var-next => eax -15321 # var output-var/eax: (addr var) = second-inout->value -15322 (lookup *eax *(eax+4)) # Stmt-var-value Stmt-var-value => eax -15323 #? (write-buffered Stderr "mu-get-offset: ") -15324 #? (write-int32-hex-buffered Stderr %eax) -15325 #? (write-buffered Stderr " name: ") -15326 #? 50/push-eax -15327 #? (lookup *eax *(eax+4)) # Var-name -15328 #? (write-buffered Stderr %eax) -15329 #? 58/pop-to-eax -15330 #? (write-buffered Stderr Newline) -15331 #? (flush Stderr) -15332 # return output-var->stack-offset -15333 8b/-> *(eax+0x14) 0/r32/eax # Var-offset -15334 #? (write-buffered Stderr "=> ") -15335 #? (write-int32-hex-buffered Stderr %eax) -15336 #? (write-buffered Stderr Newline) -15337 #? (flush Stderr) -15338 $emit-get-offset:end: -15339 # . epilogue -15340 89/<- %esp 5/r32/ebp -15341 5d/pop-to-ebp -15342 c3/return -15343 -15344 emit-subx-block: # out: (addr buffered-file), block: (addr block), vars: (addr stack live-var), fn: (addr function), err: (addr buffered-file), ed: (addr exit-descriptor) -15345 # . prologue -15346 55/push-ebp -15347 89/<- %ebp 4/r32/esp -15348 # . save registers -15349 50/push-eax -15350 51/push-ecx -15351 56/push-esi -15352 # esi = block -15353 8b/-> *(ebp+0xc) 6/r32/esi -15354 # block->var->block-depth = *Curr-block-depth -15355 (lookup *(esi+0xc) *(esi+0x10)) # Block-var Block-var => eax -15356 8b/-> *Curr-block-depth 1/r32/ecx -15357 89/<- *(eax+0x10) 1/r32/ecx # Var-block-depth -15358 # var stmts/eax: (addr list stmt) = lookup(block->statements) -15359 (lookup *(esi+4) *(esi+8)) # Block-stmts Block-stmts => eax -15360 # -15361 { -15362 $emit-subx-block:check-empty: -15363 3d/compare-eax-and 0/imm32 -15364 0f 84/jump-if-= break/disp32 -15365 (emit-indent *(ebp+8) *Curr-block-depth) -15366 (write-buffered *(ebp+8) "{\n") -15367 # var v/ecx: (addr var) = lookup(block->var) -15368 (lookup *(esi+0xc) *(esi+0x10)) # Block-var Block-var => eax -15369 89/<- %ecx 0/r32/eax -15370 # -15371 (lookup *ecx *(ecx+4)) # Var-name Var-name => eax -15372 (write-buffered *(ebp+8) %eax) -15373 (write-buffered *(ebp+8) ":loop:\n") -15374 ff 0/subop/increment *Curr-block-depth -15375 (push *(ebp+0x10) *(esi+0xc)) # Block-var -15376 (push *(ebp+0x10) *(esi+0x10)) # Block-var -15377 (push *(ebp+0x10) 0) # false -15378 # emit block->statements -15379 (lookup *(esi+4) *(esi+8)) # Block-stmts Block-stmts => eax -15380 (emit-subx-stmt-list *(ebp+8) %eax *(ebp+0x10) *(ebp+0x14) *(ebp+0x18) *(ebp+0x1c)) -15381 (pop *(ebp+0x10)) # => eax -15382 (pop *(ebp+0x10)) # => eax -15383 (pop *(ebp+0x10)) # => eax -15384 ff 1/subop/decrement *Curr-block-depth -15385 (emit-indent *(ebp+8) *Curr-block-depth) -15386 (write-buffered *(ebp+8) "}\n") -15387 (lookup *ecx *(ecx+4)) # Var-name Var-name => eax -15388 (write-buffered *(ebp+8) %eax) -15389 (write-buffered *(ebp+8) ":break:\n") -15390 } -15391 $emit-subx-block:end: -15392 # . restore registers -15393 5e/pop-to-esi -15394 59/pop-to-ecx -15395 58/pop-to-eax -15396 # . epilogue -15397 89/<- %esp 5/r32/ebp -15398 5d/pop-to-ebp -15399 c3/return -15400 -15401 # Primitives supported -15402 # See mu_instructions for a summary of this linked-list data structure. -15403 # -15404 # For each operation, put variants with hard-coded registers before flexible ones. -15405 # -15406 # Unfortunately, our restrictions on addresses require that various fields in -15407 # primitives be handles, which complicates these definitions. -15408 # - we need to insert dummy fields all over the place for fake alloc-ids -15409 # - we can't use our syntax sugar of quoted literals for string fields -15410 # -15411 # Fake alloc-ids are needed because our type definitions up top require -15412 # handles but it's clearer to statically allocate these long-lived objects. -15413 # Fake alloc-ids are perfectly safe, but they can't be reclaimed. -15414 # -15415 # Every 'object' below starts with a fake alloc-id. It may also contain other -15416 # fake alloc-ids for various handle fields. -15417 # -15418 # I think of objects starting with a fake alloc-id as having type 'payload'. -15419 # It's not really intended to be created dynamically; for that use `allocate` -15420 # as usual. -15421 # -15422 # Idea for a notation to simplify such definitions: -15423 # _Primitive-increment-eax: # (payload primitive) -15424 # 0x11/alloc-id:fake:payload -15425 # 0x11 @(0x11 "increment") # name -15426 # 0 0 # inouts -15427 # 0x11 @(0x11/payload -15428 # 0x11 @(0x11/payload # List-value -15429 # 0 0 # Var-name -15430 # 0x11 @(0x11 # Var-type -15431 # 1/is-atom -15432 # 1/value 0/unused # Type-tree-left -15433 # 0 0 # Type-tree-right -15434 # ) -15435 # 1 # block-depth -15436 # 0 # stack-offset -15437 # 0x11 @(0x11 "eax") # Var-register -15438 # ) -15439 # 0 0) # List-next -15440 # ... -15441 # _Primitive-increment-ecx/imm32/next -15442 # ... -15443 # Awfully complex and non-obvious. But also clearly signals there's something -15444 # to learn here, so may be worth trying. -15445 # -15446 # '@' is just an initial thought. Punctuation used so far in Mu: () * % # / " -15447 # -15448 # For now we'll continue to just use comments and manually ensure they stay up -15449 # to date. -15450 == data -15451 Primitives: # (addr primitive) -15452 # - increment/decrement -15453 _Primitive-increment-eax: # (addr primitive) -15454 # var/eax <- increment => 40/increment-eax -15455 0x11/imm32/alloc-id:fake -15456 _string-increment/imm32/name -15457 0/imm32/no-inouts -15458 0/imm32/no-inouts -15459 0x11/imm32/alloc-id:fake -15460 Single-int-var-in-eax/imm32/outputs -15461 0x11/imm32/alloc-id:fake -15462 _string_40_increment_eax/imm32/subx-name -15463 0/imm32/no-rm32 -15464 0/imm32/no-r32 -15465 0/imm32/no-imm32 -15466 0/imm32/no-imm8 -15467 0/imm32/no-disp32 -15468 0/imm32/output-is-write-only -15469 0x11/imm32/alloc-id:fake -15470 _Primitive-increment-ecx/imm32/next -15471 _Primitive-increment-ecx: # (payload primitive) -15472 0x11/imm32/alloc-id:fake:payload -15473 # var/ecx <- increment => 41/increment-ecx -15474 0x11/imm32/alloc-id:fake -15475 _string-increment/imm32/name -15476 0/imm32/no-inouts -15477 0/imm32/no-inouts -15478 0x11/imm32/alloc-id:fake -15479 Single-int-var-in-ecx/imm32/outputs -15480 0x11/imm32/alloc-id:fake -15481 _string_41_increment_ecx/imm32/subx-name -15482 0/imm32/no-rm32 -15483 0/imm32/no-r32 -15484 0/imm32/no-imm32 -15485 0/imm32/no-imm8 -15486 0/imm32/no-disp32 -15487 0/imm32/output-is-write-only -15488 0x11/imm32/alloc-id:fake -15489 _Primitive-increment-edx/imm32/next -15490 _Primitive-increment-edx: # (payload primitive) -15491 0x11/imm32/alloc-id:fake:payload -15492 # var/edx <- increment => 42/increment-edx -15493 0x11/imm32/alloc-id:fake -15494 _string-increment/imm32/name -15495 0/imm32/no-inouts -15496 0/imm32/no-inouts -15497 0x11/imm32/alloc-id:fake -15498 Single-int-var-in-edx/imm32/outputs -15499 0x11/imm32/alloc-id:fake -15500 _string_42_increment_edx/imm32/subx-name -15501 0/imm32/no-rm32 -15502 0/imm32/no-r32 -15503 0/imm32/no-imm32 -15504 0/imm32/no-imm8 -15505 0/imm32/no-disp32 -15506 0/imm32/output-is-write-only -15507 0x11/imm32/alloc-id:fake -15508 _Primitive-increment-ebx/imm32/next -15509 _Primitive-increment-ebx: # (payload primitive) -15510 0x11/imm32/alloc-id:fake:payload -15511 # var/ebx <- increment => 43/increment-ebx -15512 0x11/imm32/alloc-id:fake -15513 _string-increment/imm32/name -15514 0/imm32/no-inouts -15515 0/imm32/no-inouts -15516 0x11/imm32/alloc-id:fake -15517 Single-int-var-in-ebx/imm32/outputs -15518 0x11/imm32/alloc-id:fake -15519 _string_43_increment_ebx/imm32/subx-name -15520 0/imm32/no-rm32 -15521 0/imm32/no-r32 -15522 0/imm32/no-imm32 -15523 0/imm32/no-imm8 -15524 0/imm32/no-disp32 -15525 0/imm32/output-is-write-only -15526 0x11/imm32/alloc-id:fake -15527 _Primitive-increment-esi/imm32/next -15528 _Primitive-increment-esi: # (payload primitive) -15529 0x11/imm32/alloc-id:fake:payload -15530 # var/esi <- increment => 46/increment-esi -15531 0x11/imm32/alloc-id:fake -15532 _string-increment/imm32/name -15533 0/imm32/no-inouts -15534 0/imm32/no-inouts -15535 0x11/imm32/alloc-id:fake -15536 Single-int-var-in-esi/imm32/outputs -15537 0x11/imm32/alloc-id:fake -15538 _string_46_increment_esi/imm32/subx-name -15539 0/imm32/no-rm32 -15540 0/imm32/no-r32 -15541 0/imm32/no-imm32 -15542 0/imm32/no-imm8 -15543 0/imm32/no-disp32 -15544 0/imm32/output-is-write-only -15545 0x11/imm32/alloc-id:fake -15546 _Primitive-increment-edi/imm32/next -15547 _Primitive-increment-edi: # (payload primitive) -15548 0x11/imm32/alloc-id:fake:payload -15549 # var/edi <- increment => 47/increment-edi -15550 0x11/imm32/alloc-id:fake -15551 _string-increment/imm32/name -15552 0/imm32/no-inouts -15553 0/imm32/no-inouts -15554 0x11/imm32/alloc-id:fake -15555 Single-int-var-in-edi/imm32/outputs -15556 0x11/imm32/alloc-id:fake -15557 _string_47_increment_edi/imm32/subx-name -15558 0/imm32/no-rm32 -15559 0/imm32/no-r32 -15560 0/imm32/no-imm32 -15561 0/imm32/no-imm8 -15562 0/imm32/no-disp32 -15563 0/imm32/output-is-write-only -15564 0x11/imm32/alloc-id:fake -15565 _Primitive-decrement-eax/imm32/next -15566 _Primitive-decrement-eax: # (payload primitive) -15567 0x11/imm32/alloc-id:fake:payload -15568 # var/eax <- decrement => 48/decrement-eax -15569 0x11/imm32/alloc-id:fake -15570 _string-decrement/imm32/name -15571 0/imm32/no-inouts -15572 0/imm32/no-inouts -15573 0x11/imm32/alloc-id:fake -15574 Single-int-var-in-eax/imm32/outputs -15575 0x11/imm32/alloc-id:fake -15576 _string_48_decrement_eax/imm32/subx-name -15577 0/imm32/no-rm32 -15578 0/imm32/no-r32 -15579 0/imm32/no-imm32 -15580 0/imm32/no-imm8 -15581 0/imm32/no-disp32 -15582 0/imm32/output-is-write-only -15583 0x11/imm32/alloc-id:fake -15584 _Primitive-decrement-ecx/imm32/next -15585 _Primitive-decrement-ecx: # (payload primitive) -15586 0x11/imm32/alloc-id:fake:payload -15587 # var/ecx <- decrement => 49/decrement-ecx -15588 0x11/imm32/alloc-id:fake -15589 _string-decrement/imm32/name -15590 0/imm32/no-inouts -15591 0/imm32/no-inouts -15592 0x11/imm32/alloc-id:fake -15593 Single-int-var-in-ecx/imm32/outputs -15594 0x11/imm32/alloc-id:fake -15595 _string_49_decrement_ecx/imm32/subx-name -15596 0/imm32/no-rm32 -15597 0/imm32/no-r32 -15598 0/imm32/no-imm32 -15599 0/imm32/no-imm8 -15600 0/imm32/no-disp32 -15601 0/imm32/output-is-write-only -15602 0x11/imm32/alloc-id:fake -15603 _Primitive-decrement-edx/imm32/next -15604 _Primitive-decrement-edx: # (payload primitive) -15605 0x11/imm32/alloc-id:fake:payload -15606 # var/edx <- decrement => 4a/decrement-edx -15607 0x11/imm32/alloc-id:fake -15608 _string-decrement/imm32/name -15609 0/imm32/no-inouts -15610 0/imm32/no-inouts -15611 0x11/imm32/alloc-id:fake -15612 Single-int-var-in-edx/imm32/outputs -15613 0x11/imm32/alloc-id:fake -15614 _string_4a_decrement_edx/imm32/subx-name -15615 0/imm32/no-rm32 -15616 0/imm32/no-r32 -15617 0/imm32/no-imm32 -15618 0/imm32/no-imm8 -15619 0/imm32/no-disp32 -15620 0/imm32/output-is-write-only -15621 0x11/imm32/alloc-id:fake -15622 _Primitive-decrement-ebx/imm32/next -15623 _Primitive-decrement-ebx: # (payload primitive) -15624 0x11/imm32/alloc-id:fake:payload -15625 # var/ebx <- decrement => 4b/decrement-ebx -15626 0x11/imm32/alloc-id:fake -15627 _string-decrement/imm32/name -15628 0/imm32/no-inouts -15629 0/imm32/no-inouts -15630 0x11/imm32/alloc-id:fake -15631 Single-int-var-in-ebx/imm32/outputs -15632 0x11/imm32/alloc-id:fake -15633 _string_4b_decrement_ebx/imm32/subx-name -15634 0/imm32/no-rm32 -15635 0/imm32/no-r32 -15636 0/imm32/no-imm32 -15637 0/imm32/no-imm8 -15638 0/imm32/no-disp32 -15639 0/imm32/output-is-write-only -15640 0x11/imm32/alloc-id:fake -15641 _Primitive-decrement-esi/imm32/next -15642 _Primitive-decrement-esi: # (payload primitive) -15643 0x11/imm32/alloc-id:fake:payload -15644 # var/esi <- decrement => 4e/decrement-esi -15645 0x11/imm32/alloc-id:fake -15646 _string-decrement/imm32/name -15647 0/imm32/no-inouts -15648 0/imm32/no-inouts -15649 0x11/imm32/alloc-id:fake -15650 Single-int-var-in-esi/imm32/outputs -15651 0x11/imm32/alloc-id:fake -15652 _string_4e_decrement_esi/imm32/subx-name -15653 0/imm32/no-rm32 -15654 0/imm32/no-r32 -15655 0/imm32/no-imm32 -15656 0/imm32/no-imm8 -15657 0/imm32/no-disp32 -15658 0/imm32/output-is-write-only -15659 0x11/imm32/alloc-id:fake -15660 _Primitive-decrement-edi/imm32/next -15661 _Primitive-decrement-edi: # (payload primitive) -15662 0x11/imm32/alloc-id:fake:payload -15663 # var/edi <- decrement => 4f/decrement-edi -15664 0x11/imm32/alloc-id:fake -15665 _string-decrement/imm32/name -15666 0/imm32/no-inouts -15667 0/imm32/no-inouts -15668 0x11/imm32/alloc-id:fake -15669 Single-int-var-in-edi/imm32/outputs -15670 0x11/imm32/alloc-id:fake -15671 _string_4f_decrement_edi/imm32/subx-name -15672 0/imm32/no-rm32 -15673 0/imm32/no-r32 -15674 0/imm32/no-imm32 -15675 0/imm32/no-imm8 -15676 0/imm32/no-disp32 -15677 0/imm32/output-is-write-only -15678 0x11/imm32/alloc-id:fake -15679 _Primitive-increment-mem/imm32/next -15680 _Primitive-increment-mem: # (payload primitive) -15681 0x11/imm32/alloc-id:fake:payload -15682 # increment var => ff 0/subop/increment *(ebp+__) -15683 0x11/imm32/alloc-id:fake -15684 _string-increment/imm32/name -15685 0x11/imm32/alloc-id:fake -15686 Single-int-var-in-mem/imm32/inouts -15687 0/imm32/no-outputs -15688 0/imm32/no-outputs -15689 0x11/imm32/alloc-id:fake -15690 _string_ff_subop_increment/imm32/subx-name -15691 1/imm32/rm32-is-first-inout -15692 0/imm32/no-r32 -15693 0/imm32/no-imm32 -15694 0/imm32/no-imm8 -15695 0/imm32/no-disp32 -15696 0/imm32/output-is-write-only -15697 0x11/imm32/alloc-id:fake -15698 _Primitive-increment-reg/imm32/next -15699 _Primitive-increment-reg: # (payload primitive) -15700 0x11/imm32/alloc-id:fake:payload -15701 # var/reg <- increment => ff 0/subop/increment %__ -15702 0x11/imm32/alloc-id:fake -15703 _string-increment/imm32/name -15704 0/imm32/no-inouts -15705 0/imm32/no-inouts -15706 0x11/imm32/alloc-id:fake -15707 Single-int-var-in-some-register/imm32/outputs -15708 0x11/imm32/alloc-id:fake -15709 _string_ff_subop_increment/imm32/subx-name -15710 3/imm32/rm32-is-first-output -15711 0/imm32/no-r32 -15712 0/imm32/no-imm32 -15713 0/imm32/no-imm8 -15714 0/imm32/no-disp32 -15715 0/imm32/output-is-write-only -15716 0x11/imm32/alloc-id:fake -15717 _Primitive-decrement-mem/imm32/next -15718 _Primitive-decrement-mem: # (payload primitive) -15719 0x11/imm32/alloc-id:fake:payload -15720 # decrement var => ff 1/subop/decrement *(ebp+__) -15721 0x11/imm32/alloc-id:fake -15722 _string-decrement/imm32/name -15723 0x11/imm32/alloc-id:fake -15724 Single-int-var-in-mem/imm32/inouts -15725 0/imm32/no-outputs -15726 0/imm32/no-outputs -15727 0x11/imm32/alloc-id:fake -15728 _string_ff_subop_decrement/imm32/subx-name -15729 1/imm32/rm32-is-first-inout -15730 0/imm32/no-r32 -15731 0/imm32/no-imm32 -15732 0/imm32/no-imm8 -15733 0/imm32/no-disp32 -15734 0/imm32/output-is-write-only -15735 0x11/imm32/alloc-id:fake -15736 _Primitive-decrement-reg/imm32/next -15737 _Primitive-decrement-reg: # (payload primitive) -15738 0x11/imm32/alloc-id:fake:payload -15739 # var/reg <- decrement => ff 1/subop/decrement %__ -15740 0x11/imm32/alloc-id:fake -15741 _string-decrement/imm32/name -15742 0/imm32/no-inouts -15743 0/imm32/no-inouts -15744 0x11/imm32/alloc-id:fake -15745 Single-int-var-in-some-register/imm32/outputs -15746 0x11/imm32/alloc-id:fake -15747 _string_ff_subop_decrement/imm32/subx-name -15748 3/imm32/rm32-is-first-output -15749 0/imm32/no-r32 -15750 0/imm32/no-imm32 -15751 0/imm32/no-imm8 -15752 0/imm32/no-disp32 -15753 0/imm32/output-is-write-only -15754 0x11/imm32/alloc-id:fake -15755 _Primitive-add-to-eax/imm32/next -15756 # - add -15757 _Primitive-add-to-eax: # (payload primitive) -15758 0x11/imm32/alloc-id:fake:payload -15759 # var/eax <- add lit => 05/add-to-eax lit/imm32 -15760 0x11/imm32/alloc-id:fake -15761 _string-add/imm32/name -15762 0x11/imm32/alloc-id:fake -15763 Single-lit-var/imm32/inouts -15764 0x11/imm32/alloc-id:fake -15765 Single-int-var-in-eax/imm32/outputs -15766 0x11/imm32/alloc-id:fake -15767 _string_05_add_to_eax/imm32/subx-name -15768 0/imm32/no-rm32 -15769 0/imm32/no-r32 -15770 1/imm32/imm32-is-first-inout -15771 0/imm32/no-imm8 -15772 0/imm32/no-disp32 -15773 0/imm32/output-is-write-only -15774 0x11/imm32/alloc-id:fake -15775 _Primitive-add-reg-to-reg/imm32/next -15776 _Primitive-add-reg-to-reg: # (payload primitive) -15777 0x11/imm32/alloc-id:fake:payload -15778 # var1/reg <- add var2/reg => 01/add-to var1/rm32 var2/r32 -15779 0x11/imm32/alloc-id:fake -15780 _string-add/imm32/name -15781 0x11/imm32/alloc-id:fake -15782 Single-int-var-in-some-register/imm32/inouts -15783 0x11/imm32/alloc-id:fake -15784 Single-int-var-in-some-register/imm32/outputs -15785 0x11/imm32/alloc-id:fake -15786 _string_01_add_to/imm32/subx-name -15787 3/imm32/rm32-is-first-output -15788 1/imm32/r32-is-first-inout -15789 0/imm32/no-imm32 -15790 0/imm32/no-imm8 -15791 0/imm32/no-disp32 -15792 0/imm32/output-is-write-only -15793 0x11/imm32/alloc-id:fake -15794 _Primitive-add-reg-to-mem/imm32/next -15795 _Primitive-add-reg-to-mem: # (payload primitive) -15796 0x11/imm32/alloc-id:fake:payload -15797 # add-to var1 var2/reg => 01/add-to var1 var2/r32 -15798 0x11/imm32/alloc-id:fake -15799 _string-add-to/imm32/name -15800 0x11/imm32/alloc-id:fake -15801 Two-args-int-stack-int-reg/imm32/inouts -15802 0/imm32/no-outputs -15803 0/imm32/no-outputs -15804 0x11/imm32/alloc-id:fake -15805 _string_01_add_to/imm32/subx-name -15806 1/imm32/rm32-is-first-inout -15807 2/imm32/r32-is-second-inout -15808 0/imm32/no-imm32 -15809 0/imm32/no-imm8 -15810 0/imm32/no-disp32 -15811 0/imm32/output-is-write-only -15812 0x11/imm32/alloc-id:fake -15813 _Primitive-add-mem-to-reg/imm32/next -15814 _Primitive-add-mem-to-reg: # (payload primitive) -15815 0x11/imm32/alloc-id:fake:payload -15816 # var1/reg <- add var2 => 03/add var2/rm32 var1/r32 -15817 0x11/imm32/alloc-id:fake -15818 _string-add/imm32/name -15819 0x11/imm32/alloc-id:fake -15820 Single-int-var-in-mem/imm32/inouts -15821 0x11/imm32/alloc-id:fake -15822 Single-int-var-in-some-register/imm32/outputs -15823 0x11/imm32/alloc-id:fake -15824 _string_03_add/imm32/subx-name -15825 1/imm32/rm32-is-first-inout -15826 3/imm32/r32-is-first-output -15827 0/imm32/no-imm32 -15828 0/imm32/no-imm8 -15829 0/imm32/no-disp32 -15830 0/imm32/output-is-write-only +15117 51/push-ecx +15118 52/push-edx +15119 53/push-ebx +15120 # +15121 (emit-indent *(ebp+8) *Curr-block-depth) +15122 (write-buffered *(ebp+8) "8d/copy-address *(ebp + ") +15123 # var curr/edx: (addr stmt-var) = lookup(stmt->inouts) +15124 8b/-> *(ebp+0xc) 0/r32/eax +15125 (lookup *(eax+0xc) *(eax+0x10)) # Stmt1-inouts Stmt1-inouts => eax +15126 89/<- %edx 0/r32/eax +15127 # var base/ecx: (addr var) = lookup(curr->value) +15128 (lookup *eax *(eax+4)) # Stmt-var-value Stmt-var-value => eax +15129 89/<- %ecx 0/r32/eax +15130 # var curr2/eax: (addr stmt-var) = lookup(curr->next) +15131 (lookup *(edx+8) *(edx+0xc)) # Stmt-var-next Stmt-var-next => eax +15132 # var index/edx: (handle var) = curr2->value +15133 (lookup *eax *(eax+4)) # Stmt-var-value Stmt-var-value => eax +15134 89/<- %edx 0/r32/eax +15135 # if index->register +15136 81 7/subop/compare *(edx+0x18) 0/imm32 # Var-register +15137 { +15138 0f 84/jump-if-= break/disp32 +15139 $translate-mu-index-stmt-with-array-on-stack:emit-register-index: +15140 # if index is an int +15141 (lookup *(edx+8) *(edx+0xc)) # Var-type Var-type => eax +15142 (is-simple-mu-type? %eax 1) # int => eax +15143 3d/compare-eax-and 0/imm32/false +15144 { +15145 0f 84/jump-if-= break/disp32 +15146 $translate-mu-index-stmt-with-array-on-stack:emit-int-register-index: +15147 # print index->register "<<" log2(array-element-size(base)) " + " base->offset+4 +15148 # . inouts[1]->register "<<" +15149 (lookup *(edx+0x18) *(edx+0x1c)) # Var-register Var-register => eax +15150 (write-buffered *(ebp+8) %eax) +15151 (write-buffered *(ebp+8) "<<") +15152 # . log2(array-element-size(base)) +15153 # TODO: ensure size is a power of 2 +15154 (array-element-size %ecx *(ebp+0x10) *(ebp+0x14)) # => eax +15155 (num-shift-rights %eax) # => eax +15156 (write-int32-hex-buffered *(ebp+8) %eax) +15157 # +15158 (write-buffered *(ebp+8) " + ") +15159 # +15160 8b/-> *(ecx+0x14) 0/r32/eax # Var-offset +15161 05/add-to-eax 4/imm32 # for array length +15162 (write-int32-hex-buffered *(ebp+8) %eax) +15163 e9/jump $translate-mu-index-stmt-with-array-on-stack:emit-register-index-done/disp32 +15164 } +15165 # if index->type is any other atom, abort +15166 (lookup *(edx+8) *(edx+0xc)) # Var-type Var-type => eax +15167 81 7/subop/compare *eax 0/imm32/false # Type-tree-is-atom +15168 0f 85/jump-if-!= $translate-mu-index-stmt-with-array:error2/disp32 +15169 # if index has type (offset ...) +15170 (lookup *(eax+4) *(eax+8)) # Type-tree-left Type-tree-left => eax +15171 (is-simple-mu-type? %eax 7) # => eax +15172 3d/compare-eax-and 0/imm32/false +15173 { +15174 0f 84/jump-if-= break/disp32 +15175 # print index->register +15176 $translate-mu-index-stmt-with-array-on-stack:emit-offset-register-index: +15177 (lookup *(edx+0x18) *(edx+0x1c)) # Var-register Var-register => eax +15178 (write-buffered *(ebp+8) %eax) +15179 } +15180 $translate-mu-index-stmt-with-array-on-stack:emit-register-index-done: +15181 (write-buffered *(ebp+8) ") ") +15182 e9/jump $translate-mu-index-stmt-with-array-on-stack:emit-output/disp32 +15183 } +15184 # otherwise if index is a literal +15185 (lookup *(edx+8) *(edx+0xc)) # Var-type Var-type => eax +15186 (is-simple-mu-type? %eax 0) # => eax +15187 3d/compare-eax-and 0/imm32/false +15188 { +15189 0f 84/jump-if-= break/disp32 +15190 $translate-mu-index-stmt-with-array-on-stack:emit-literal-index: +15191 # var idx-value/edx: int = parse-hex-int(index->name) +15192 (lookup *edx *(edx+4)) # Var-name Var-name => eax +15193 (parse-hex-int %eax) # Var-name => eax +15194 89/<- %edx 0/r32/eax +15195 # offset = idx-value * array-element-size(base) +15196 (array-element-size %ecx *(ebp+0x10) *(ebp+0x14)) # => eax +15197 f7 4/subop/multiply-into-eax %edx # clobbers edx +15198 # offset += base->offset +15199 03/add *(ecx+0x14) 0/r32/eax # Var-offset +15200 # offset += 4 for array size +15201 05/add-to-eax 4/imm32 +15202 # TODO: check edx for overflow +15203 # print offset +15204 (write-int32-hex-buffered *(ebp+8) %eax) +15205 (write-buffered *(ebp+8) ") ") +15206 e9/jump $translate-mu-index-stmt-with-array-on-stack:emit-output/disp32 +15207 } +15208 # otherwise abort +15209 e9/jump $translate-mu-index-stmt-with-array:error1/disp32 +15210 $translate-mu-index-stmt-with-array-on-stack:emit-output: +15211 # outputs[0] "/r32" +15212 8b/-> *(ebp+0xc) 0/r32/eax +15213 (lookup *(eax+0x14) *(eax+0x18)) # Stmt1-outputs Stmt1-outputs => eax +15214 (lookup *eax *(eax+4)) # Stmt-var-value Stmt-var-value => eax +15215 (lookup *(eax+0x18) *(eax+0x1c)) # Var-register Var-register => eax +15216 (get Mu-registers %eax 0xc "Mu-registers") # => eax: (addr int) +15217 (write-int32-hex-buffered *(ebp+8) *eax) +15218 (write-buffered *(ebp+8) "/r32\n") +15219 $translate-mu-index-stmt-with-array-on-stack:end: +15220 # . restore registers +15221 5b/pop-to-ebx +15222 5a/pop-to-edx +15223 59/pop-to-ecx +15224 58/pop-to-eax +15225 # . epilogue +15226 89/<- %esp 5/r32/ebp +15227 5d/pop-to-ebp +15228 c3/return +15229 +15230 translate-mu-compute-index-stmt: # out: (addr buffered-file), stmt: (addr stmt), err: (addr buffered-file), ed: (addr exit-descriptor) +15231 # . prologue +15232 55/push-ebp +15233 89/<- %ebp 4/r32/esp +15234 # . save registers +15235 50/push-eax +15236 51/push-ecx +15237 52/push-edx +15238 53/push-ebx +15239 # +15240 (emit-indent *(ebp+8) *Curr-block-depth) +15241 (write-buffered *(ebp+8) "69/multiply") +15242 # ecx = stmt +15243 8b/-> *(ebp+0xc) 1/r32/ecx +15244 # var first-inout/ebx: (addr stmt-var) = stmt->inouts[0] +15245 (lookup *(ecx+0xc) *(ecx+0x10)) # Stmt1-inouts Stmt1-inouts => eax +15246 89/<- %ebx 0/r32/eax +15247 $translate-mu-compute-index-stmt:emit-index: +15248 (lookup *(ebx+8) *(ebx+0xc)) # Stmt-var-next Stmt-var-next => eax +15249 (emit-subx-var-as-rm32 *(ebp+8) %eax) +15250 (write-buffered *(ebp+8) Space) +15251 $translate-mu-compute-index-stmt:emit-elem-size: +15252 # var base/ebx: (addr var) +15253 (lookup *ebx *(ebx+4)) # Stmt-var-value Stmt-var-value => eax +15254 89/<- %ebx 0/r32/eax +15255 # print array-element-size(base) +15256 (array-element-size %ebx *(ebp+0x10) *(ebp+0x14)) # => eax +15257 (write-int32-hex-buffered *(ebp+8) %eax) +15258 (write-buffered *(ebp+8) "/imm32 ") +15259 $translate-mu-compute-index-stmt:emit-output: +15260 # outputs[0] "/r32" +15261 (lookup *(ecx+0x14) *(ecx+0x18)) # Stmt1-outputs Stmt1-outputs => eax +15262 (lookup *eax *(eax+4)) # Stmt-var-value Stmt-var-value => eax +15263 (lookup *(eax+0x18) *(eax+0x1c)) # Var-register Var-register => eax +15264 (get Mu-registers %eax 0xc "Mu-registers") # => eax: (addr int) +15265 (write-int32-hex-buffered *(ebp+8) *eax) +15266 (write-buffered *(ebp+8) "/r32\n") +15267 $translate-mu-compute-index-stmt:end: +15268 # . restore registers +15269 5b/pop-to-ebx +15270 5a/pop-to-edx +15271 59/pop-to-ecx +15272 58/pop-to-eax +15273 # . epilogue +15274 89/<- %esp 5/r32/ebp +15275 5d/pop-to-ebp +15276 c3/return +15277 +15278 translate-mu-get-stmt: # out: (addr buffered-file), stmt: (addr stmt) +15279 # . prologue +15280 55/push-ebp +15281 89/<- %ebp 4/r32/esp +15282 # . save registers +15283 50/push-eax +15284 51/push-ecx +15285 52/push-edx +15286 # +15287 (emit-indent *(ebp+8) *Curr-block-depth) +15288 (write-buffered *(ebp+8) "8d/copy-address ") +15289 # ecx = stmt +15290 8b/-> *(ebp+0xc) 1/r32/ecx +15291 # var offset/edx: int = get offset of stmt +15292 (mu-get-offset %ecx) # => eax +15293 89/<- %edx 0/r32/eax +15294 # var base/eax: (addr var) = stmt->inouts->value +15295 (lookup *(ecx+0xc) *(ecx+0x10)) # Stmt1-inouts Stmt1-inouts => eax +15296 (lookup *eax *(eax+4)) # Stmt-var-value Stmt-var-value => eax +15297 # if base is in a register +15298 81 7/subop/compare *(eax+0x18) 0/imm32 # Var-register +15299 { +15300 0f 84/jump-if-= break/disp32 +15301 $translate-mu-get-stmt:emit-register-input: +15302 # emit "*(" base->register " + " offset ") " +15303 (write-buffered *(ebp+8) "*(") +15304 (lookup *(eax+0x18) *(eax+0x1c)) # Var-register Var-register => eax +15305 (write-buffered *(ebp+8) %eax) +15306 (write-buffered *(ebp+8) " + ") +15307 (write-int32-hex-buffered *(ebp+8) %edx) +15308 (write-buffered *(ebp+8) ") ") +15309 e9/jump $translate-mu-get-stmt:emit-output/disp32 +15310 } +15311 # otherwise base is on the stack +15312 { +15313 $translate-mu-get-stmt:emit-stack-input: +15314 # emit "*(ebp + " inouts[0]->stack-offset + offset ") " +15315 (write-buffered *(ebp+8) "*(ebp+") +15316 03/add *(eax+0x14) 2/r32/edx # Var-offset +15317 (write-int32-hex-buffered *(ebp+8) %edx) +15318 (write-buffered *(ebp+8) ") ") +15319 eb/jump $translate-mu-get-stmt:emit-output/disp8 +15320 } +15321 $translate-mu-get-stmt:emit-output: +15322 # var output/eax: (addr var) = stmt->outputs->value +15323 (lookup *(ecx+0x14) *(ecx+0x18)) # Stmt1-outputs Stmt1-outputs => eax +15324 (lookup *eax *(eax+4)) # Stmt-var-value Stmt-var-value => eax +15325 # emit offset->register "/r32" +15326 (lookup *(eax+0x18) *(eax+0x1c)) # Var-register Var-register => eax +15327 (get Mu-registers %eax 0xc "Mu-registers") # => eax: (addr int) +15328 (write-int32-hex-buffered *(ebp+8) *eax) +15329 (write-buffered *(ebp+8) "/r32\n") +15330 $translate-mu-get-stmt:end: +15331 # . restore registers +15332 5a/pop-to-edx +15333 59/pop-to-ecx +15334 58/pop-to-eax +15335 # . epilogue +15336 89/<- %esp 5/r32/ebp +15337 5d/pop-to-ebp +15338 c3/return +15339 +15340 translate-mu-allocate-stmt: # out: (addr buffered-file), stmt: (addr stmt), err: (addr buffered-file), ed: (addr exit-descriptor) +15341 # . prologue +15342 55/push-ebp +15343 89/<- %ebp 4/r32/esp +15344 # . save registers +15345 50/push-eax +15346 56/push-esi +15347 57/push-edi +15348 # esi = stmt +15349 8b/-> *(ebp+0xc) 6/r32/esi +15350 # var target/edi: (addr stmt-var) = stmt->inouts[0] +15351 (lookup *(esi+0xc) *(esi+0x10)) # Stmt1-inouts Stmt1-inouts => eax +15352 89/<- %edi 0/r32/eax +15353 # +15354 (emit-indent *(ebp+8) *Curr-block-depth) +15355 (write-buffered *(ebp+8) "(allocate Heap ") +15356 (addr-handle-payload-size %edi *(ebp+0x10) *(ebp+0x14)) # => eax +15357 (write-int32-hex-buffered *(ebp+8) %eax) +15358 (emit-subx-call-operand *(ebp+8) %edi) +15359 (write-buffered *(ebp+8) ")\n") +15360 $translate-mu-allocate-stmt:end: +15361 # . restore registers +15362 5f/pop-to-edi +15363 5e/pop-to-esi +15364 58/pop-to-eax +15365 # . epilogue +15366 89/<- %esp 5/r32/ebp +15367 5d/pop-to-ebp +15368 c3/return +15369 +15370 addr-handle-payload-size: # s: (addr stmt-var), err: (addr buffered-file), ed: (addr exit-descriptor) -> result/eax: int +15371 # . prologue +15372 55/push-ebp +15373 89/<- %ebp 4/r32/esp +15374 # var t/eax: (addr type-tree) = s->value->type +15375 8b/-> *(ebp+8) 0/r32/eax +15376 (lookup *eax *(eax+4)) # Stmt-var-value Stmt-var-value => eax +15377 (lookup *(eax+8) *(eax+0xc)) # Var-type Var-type => eax +15378 # TODO: check eax != 0 +15379 # TODO: check !t->is-atom? +15380 # TODO: check t->left == addr +15381 # t = t->right +15382 $addr-handle-payload-size:skip-addr: +15383 (lookup *(eax+0xc) *(eax+0x10)) # Type-tree-right Type-tree-right => eax +15384 # TODO: check eax != 0 +15385 # TODO: check !t->is-atom? +15386 # TODO: check t->left == handle +15387 # t = t->right +15388 $addr-handle-payload-size:skip-handle: +15389 (lookup *(eax+0xc) *(eax+0x10)) # Type-tree-right Type-tree-right => eax +15390 # TODO: check eax != 0 +15391 # if !t->is-atom? t = t->left +15392 81 7/subop/compare *eax 0/imm32/false +15393 { +15394 75/jump-if-!= break/disp8 +15395 (lookup *(eax+4) *(eax+8)) # Type-tree-left Type-tree-left => eax +15396 } +15397 # TODO: check t->is-atom? +15398 # return size(t->value) +15399 (size-of-type-id *(eax+4)) # Type-tree-value => eax +15400 $addr-handle-payload-size:end: +15401 # . epilogue +15402 89/<- %esp 5/r32/ebp +15403 5d/pop-to-ebp +15404 c3/return +15405 +15406 addr-payload-size: # s: (addr stmt-var), err: (addr buffered-file), ed: (addr exit-descriptor) -> result/eax: int +15407 # . prologue +15408 55/push-ebp +15409 89/<- %ebp 4/r32/esp +15410 # var t/eax: (addr type-tree) = s->value->type +15411 8b/-> *(ebp+8) 0/r32/eax +15412 (lookup *eax *(eax+4)) # Stmt-var-value Stmt-var-value => eax +15413 (lookup *(eax+8) *(eax+0xc)) # Var-type Var-type => eax +15414 # TODO: check eax != 0 +15415 # TODO: check !t->is-atom? +15416 # TODO: check t->left == addr +15417 # t = t->right +15418 $addr-payload-size:skip-addr: +15419 (lookup *(eax+0xc) *(eax+0x10)) # Type-tree-right Type-tree-right => eax +15420 # TODO: check eax != 0 +15421 # if !t->is-atom? t = t->left +15422 81 7/subop/compare *eax 0/imm32/false +15423 { +15424 75/jump-if-!= break/disp8 +15425 (lookup *(eax+4) *(eax+8)) # Type-tree-left Type-tree-left => eax +15426 } +15427 # TODO: check t->is-atom? +15428 # return size(t->value) +15429 (size-of-type-id *(eax+4)) # Type-tree-value => eax +15430 $addr-payload-size:end: +15431 # . epilogue +15432 89/<- %esp 5/r32/ebp +15433 5d/pop-to-ebp +15434 c3/return +15435 +15436 translate-mu-populate-stmt: # out: (addr buffered-file), stmt: (addr stmt), err: (addr buffered-file), ed: (addr exit-descriptor) +15437 # . prologue +15438 55/push-ebp +15439 89/<- %ebp 4/r32/esp +15440 # . save registers +15441 50/push-eax +15442 51/push-ecx +15443 56/push-esi +15444 57/push-edi +15445 # esi = stmt +15446 8b/-> *(ebp+0xc) 6/r32/esi +15447 # var target/edi: (addr stmt-var) = stmt->inouts[0] +15448 (lookup *(esi+0xc) *(esi+0x10)) # Stmt1-inouts Stmt1-inouts => eax +15449 89/<- %edi 0/r32/eax +15450 # var len/ecx: (addr stmt-var) = stmt->inouts[1] +15451 (lookup *(edi+8) *(edi+0xc)) # Stmt-var-next Stmt-var-next => eax +15452 89/<- %ecx 0/r32/eax +15453 # +15454 (emit-indent *(ebp+8) *Curr-block-depth) +15455 (write-buffered *(ebp+8) "(allocate-array2 Heap ") +15456 (addr-handle-array-payload-size %edi *(ebp+0x10) *(ebp+0x14)) # => eax +15457 (write-int32-hex-buffered *(ebp+8) %eax) +15458 (emit-subx-call-operand *(ebp+8) %ecx) +15459 (emit-subx-call-operand *(ebp+8) %edi) +15460 (write-buffered *(ebp+8) ")\n") +15461 $translate-mu-populate-stmt:end: +15462 # . restore registers +15463 5f/pop-to-edi +15464 5e/pop-to-esi +15465 59/pop-to-ecx +15466 58/pop-to-eax +15467 # . epilogue +15468 89/<- %esp 5/r32/ebp +15469 5d/pop-to-ebp +15470 c3/return +15471 +15472 translate-mu-populate-stream-stmt: # out: (addr buffered-file), stmt: (addr stmt), err: (addr buffered-file), ed: (addr exit-descriptor) +15473 # . prologue +15474 55/push-ebp +15475 89/<- %ebp 4/r32/esp +15476 # . save registers +15477 50/push-eax +15478 51/push-ecx +15479 56/push-esi +15480 57/push-edi +15481 # esi = stmt +15482 8b/-> *(ebp+0xc) 6/r32/esi +15483 # var target/edi: (addr stmt-var) = stmt->inouts[0] +15484 (lookup *(esi+0xc) *(esi+0x10)) # Stmt1-inouts Stmt1-inouts => eax +15485 89/<- %edi 0/r32/eax +15486 # var len/ecx: (addr stmt-var) = stmt->inouts[1] +15487 (lookup *(edi+8) *(edi+0xc)) # Stmt-var-next Stmt-var-next => eax +15488 89/<- %ecx 0/r32/eax +15489 # +15490 (emit-indent *(ebp+8) *Curr-block-depth) +15491 (write-buffered *(ebp+8) "(new-stream Heap ") +15492 (addr-handle-array-payload-size %edi *(ebp+0x10) *(ebp+0x14)) # => eax +15493 (write-int32-hex-buffered *(ebp+8) %eax) +15494 (emit-subx-call-operand *(ebp+8) %ecx) +15495 (emit-subx-call-operand *(ebp+8) %edi) +15496 (write-buffered *(ebp+8) ")\n") +15497 $translate-mu-populate-stream-stmt:end: +15498 # . restore registers +15499 5f/pop-to-edi +15500 5e/pop-to-esi +15501 59/pop-to-ecx +15502 58/pop-to-eax +15503 # . epilogue +15504 89/<- %esp 5/r32/ebp +15505 5d/pop-to-ebp +15506 c3/return +15507 +15508 translate-mu-read-from-stream-stmt: # out: (addr buffered-file), stmt: (addr stmt), err: (addr buffered-file), ed: (addr exit-descriptor) +15509 # . prologue +15510 55/push-ebp +15511 89/<- %ebp 4/r32/esp +15512 # . save registers +15513 50/push-eax +15514 51/push-ecx +15515 56/push-esi +15516 57/push-edi +15517 # esi = stmt +15518 8b/-> *(ebp+0xc) 6/r32/esi +15519 # var stream/ecx: (addr stmt-var) = stmt->inouts[0] +15520 (lookup *(esi+0xc) *(esi+0x10)) # Stmt1-inouts Stmt1-inouts => eax +15521 89/<- %ecx 0/r32/eax +15522 # var target/edi: (addr stmt-var) = stmt->inouts[1] +15523 (lookup *(ecx+8) *(ecx+0xc)) # Stmt-var-next Stmt-var-next => eax +15524 89/<- %edi 0/r32/eax +15525 # +15526 (emit-indent *(ebp+8) *Curr-block-depth) +15527 (write-buffered *(ebp+8) "(read-from-stream") +15528 (emit-subx-call-operand *(ebp+8) %ecx) +15529 (emit-subx-call-operand *(ebp+8) %edi) +15530 (write-buffered *(ebp+8) Space) +15531 (addr-payload-size %edi *(ebp+0x10) *(ebp+0x14)) # => eax +15532 (write-int32-hex-buffered *(ebp+8) %eax) +15533 (write-buffered *(ebp+8) ")\n") +15534 $translate-mu-read-from-stream-stmt:end: +15535 # . restore registers +15536 5f/pop-to-edi +15537 5e/pop-to-esi +15538 59/pop-to-ecx +15539 58/pop-to-eax +15540 # . epilogue +15541 89/<- %esp 5/r32/ebp +15542 5d/pop-to-ebp +15543 c3/return +15544 +15545 translate-mu-write-to-stream-stmt: # out: (addr buffered-file), stmt: (addr stmt), err: (addr buffered-file), ed: (addr exit-descriptor) +15546 # . prologue +15547 55/push-ebp +15548 89/<- %ebp 4/r32/esp +15549 # . save registers +15550 50/push-eax +15551 51/push-ecx +15552 56/push-esi +15553 57/push-edi +15554 # esi = stmt +15555 8b/-> *(ebp+0xc) 6/r32/esi +15556 # var stream/ecx: (addr stmt-var) = stmt->inouts[0] +15557 (lookup *(esi+0xc) *(esi+0x10)) # Stmt1-inouts Stmt1-inouts => eax +15558 89/<- %ecx 0/r32/eax +15559 # var target/edi: (addr stmt-var) = stmt->inouts[1] +15560 (lookup *(ecx+8) *(ecx+0xc)) # Stmt-var-next Stmt-var-next => eax +15561 89/<- %edi 0/r32/eax +15562 # +15563 (emit-indent *(ebp+8) *Curr-block-depth) +15564 (write-buffered *(ebp+8) "(write-to-stream") +15565 (emit-subx-call-operand *(ebp+8) %ecx) +15566 (flush *(ebp+8)) +15567 (emit-subx-call-operand *(ebp+8) %edi) +15568 (flush *(ebp+8)) +15569 (write-buffered *(ebp+8) Space) +15570 (flush *(ebp+8)) +15571 (addr-payload-size %edi *(ebp+0x10) *(ebp+0x14)) # => eax +15572 (write-int32-hex-buffered *(ebp+8) %eax) +15573 (write-buffered *(ebp+8) ")\n") +15574 $translate-mu-write-to-stream-stmt:end: +15575 # . restore registers +15576 5f/pop-to-edi +15577 5e/pop-to-esi +15578 59/pop-to-ecx +15579 58/pop-to-eax +15580 # . epilogue +15581 89/<- %esp 5/r32/ebp +15582 5d/pop-to-ebp +15583 c3/return +15584 +15585 addr-handle-array-payload-size: # s: (addr stmt-var), err: (addr buffered-file), ed: (addr exit-descriptor) -> result/eax: int +15586 # . prologue +15587 55/push-ebp +15588 89/<- %ebp 4/r32/esp +15589 # var t/eax: (addr type-tree) = s->value->type +15590 8b/-> *(ebp+8) 0/r32/eax +15591 (lookup *eax *(eax+4)) # Stmt-var-value Stmt-var-value => eax +15592 (lookup *(eax+8) *(eax+0xc)) # Var-type Var-type => eax +15593 # TODO: check eax != 0 +15594 # TODO: check !t->is-atom? +15595 # TODO: check t->left == addr +15596 # t = t->right +15597 $addr-handle-array-payload-size:skip-addr: +15598 (lookup *(eax+0xc) *(eax+0x10)) # Type-tree-right Type-tree-right => eax +15599 # TODO: check eax != 0 +15600 # TODO: check !t->is-atom? +15601 # TODO: check t->left == handle +15602 # t = t->right +15603 $addr-handle-array-payload-size:skip-handle: +15604 (lookup *(eax+0xc) *(eax+0x10)) # Type-tree-right Type-tree-right => eax +15605 # TODO: check eax != 0 +15606 # TODO: check !t->is-atom? +15607 # TODO: check t->left == array +15608 # t = t->right +15609 $addr-handle-array-payload-size:skip-array: +15610 (lookup *(eax+0xc) *(eax+0x10)) # Type-tree-right Type-tree-right => eax +15611 # TODO: check eax != 0 +15612 # if !t->is-atom? t = t->left +15613 81 7/subop/compare *eax 0/imm32/false +15614 { +15615 75/jump-if-!= break/disp8 +15616 (lookup *(eax+4) *(eax+8)) # Type-tree-left Type-tree-left => eax +15617 } +15618 $addr-handle-array-payload-size:compute-size: +15619 # TODO: check t->is-atom? +15620 # return size(t->value) +15621 (size-of-type-id-as-array-element *(eax+4)) # Type-tree-value => eax +15622 $addr-handle-array-payload-size:end: +15623 # . epilogue +15624 89/<- %esp 5/r32/ebp +15625 5d/pop-to-ebp +15626 c3/return +15627 +15628 power-of-2?: # n: int, err: (addr buffered-file), ed: (addr exit-descriptor) -> result/eax: boolean +15629 # precondition: n is positive +15630 # . prologue +15631 55/push-ebp +15632 89/<- %ebp 4/r32/esp +15633 # eax = n +15634 8b/-> *(ebp+8) 0/r32/eax +15635 # if (n < 0) abort +15636 3d/compare-eax-with 0/imm32 +15637 0f 8c/jump-if-< $power-of-2?:abort/disp32 +15638 # var tmp/eax: int = n-1 +15639 48/decrement-eax +15640 # var tmp2/eax: int = n & tmp +15641 23/and-> *(ebp+8) 0/r32/eax +15642 # return (tmp2 == 0) +15643 3d/compare-eax-and 0/imm32 +15644 0f 94/set-byte-if-= %al +15645 81 4/subop/and %eax 0xff/imm32 +15646 $power-of-2?:end: +15647 # . epilogue +15648 89/<- %esp 5/r32/ebp +15649 5d/pop-to-ebp +15650 c3/return +15651 +15652 $power-of-2?:abort: +15653 (write-buffered *(ebp+0xc) "power-of-2?: negative number\n") +15654 (flush *(ebp+0xc)) +15655 (stop *(ebp+0x10) 1) +15656 # never gets here +15657 +15658 num-shift-rights: # n: int -> result/eax: int +15659 # precondition: n is a positive power of 2 +15660 # . prologue +15661 55/push-ebp +15662 89/<- %ebp 4/r32/esp +15663 # . save registers +15664 51/push-ecx +15665 # var curr/ecx: int = n +15666 8b/-> *(ebp+8) 1/r32/ecx +15667 # result = 0 +15668 b8/copy-to-eax 0/imm32 +15669 { +15670 # if (curr <= 1) break +15671 81 7/subop/compare %ecx 1/imm32 +15672 7e/jump-if-<= break/disp8 +15673 40/increment-eax +15674 c1/shift 5/subop/arithmetic-right %ecx 1/imm8 +15675 eb/jump loop/disp8 +15676 } +15677 $num-shift-rights:end: +15678 # . restore registers +15679 59/pop-to-ecx +15680 # . epilogue +15681 89/<- %esp 5/r32/ebp +15682 5d/pop-to-ebp +15683 c3/return +15684 +15685 mu-get-offset: # stmt: (addr stmt) -> result/eax: int +15686 # . prologue +15687 55/push-ebp +15688 89/<- %ebp 4/r32/esp +15689 # var second-inout/eax: (addr stmt-var) = stmt->inouts->next +15690 8b/-> *(ebp+8) 0/r32/eax +15691 (lookup *(eax+0xc) *(eax+0x10)) # Stmt1-inouts Stmt1-inouts => eax +15692 (lookup *(eax+8) *(eax+0xc)) # Stmt-var-next Stmt-var-next => eax +15693 # var output-var/eax: (addr var) = second-inout->value +15694 (lookup *eax *(eax+4)) # Stmt-var-value Stmt-var-value => eax +15695 #? (write-buffered Stderr "mu-get-offset: ") +15696 #? (write-int32-hex-buffered Stderr %eax) +15697 #? (write-buffered Stderr " name: ") +15698 #? 50/push-eax +15699 #? (lookup *eax *(eax+4)) # Var-name +15700 #? (write-buffered Stderr %eax) +15701 #? 58/pop-to-eax +15702 #? (write-buffered Stderr Newline) +15703 #? (flush Stderr) +15704 # return output-var->stack-offset +15705 8b/-> *(eax+0x14) 0/r32/eax # Var-offset +15706 #? (write-buffered Stderr "=> ") +15707 #? (write-int32-hex-buffered Stderr %eax) +15708 #? (write-buffered Stderr Newline) +15709 #? (flush Stderr) +15710 $emit-get-offset:end: +15711 # . epilogue +15712 89/<- %esp 5/r32/ebp +15713 5d/pop-to-ebp +15714 c3/return +15715 +15716 emit-subx-block: # out: (addr buffered-file), block: (addr block), vars: (addr stack live-var), fn: (addr function), err: (addr buffered-file), ed: (addr exit-descriptor) +15717 # . prologue +15718 55/push-ebp +15719 89/<- %ebp 4/r32/esp +15720 # . save registers +15721 50/push-eax +15722 51/push-ecx +15723 56/push-esi +15724 # esi = block +15725 8b/-> *(ebp+0xc) 6/r32/esi +15726 # block->var->block-depth = *Curr-block-depth +15727 (lookup *(esi+0xc) *(esi+0x10)) # Block-var Block-var => eax +15728 8b/-> *Curr-block-depth 1/r32/ecx +15729 89/<- *(eax+0x10) 1/r32/ecx # Var-block-depth +15730 # var stmts/eax: (addr list stmt) = lookup(block->statements) +15731 (lookup *(esi+4) *(esi+8)) # Block-stmts Block-stmts => eax +15732 # +15733 { +15734 $emit-subx-block:check-empty: +15735 3d/compare-eax-and 0/imm32 +15736 0f 84/jump-if-= break/disp32 +15737 (emit-indent *(ebp+8) *Curr-block-depth) +15738 (write-buffered *(ebp+8) "{\n") +15739 # var v/ecx: (addr var) = lookup(block->var) +15740 (lookup *(esi+0xc) *(esi+0x10)) # Block-var Block-var => eax +15741 89/<- %ecx 0/r32/eax +15742 # +15743 (lookup *ecx *(ecx+4)) # Var-name Var-name => eax +15744 (write-buffered *(ebp+8) %eax) +15745 (write-buffered *(ebp+8) ":loop:\n") +15746 ff 0/subop/increment *Curr-block-depth +15747 (push *(ebp+0x10) *(esi+0xc)) # Block-var +15748 (push *(ebp+0x10) *(esi+0x10)) # Block-var +15749 (push *(ebp+0x10) 0) # false +15750 # emit block->statements +15751 (lookup *(esi+4) *(esi+8)) # Block-stmts Block-stmts => eax +15752 (emit-subx-stmt-list *(ebp+8) %eax *(ebp+0x10) *(ebp+0x14) *(ebp+0x18) *(ebp+0x1c)) +15753 (pop *(ebp+0x10)) # => eax +15754 (pop *(ebp+0x10)) # => eax +15755 (pop *(ebp+0x10)) # => eax +15756 ff 1/subop/decrement *Curr-block-depth +15757 (emit-indent *(ebp+8) *Curr-block-depth) +15758 (write-buffered *(ebp+8) "}\n") +15759 (lookup *ecx *(ecx+4)) # Var-name Var-name => eax +15760 (write-buffered *(ebp+8) %eax) +15761 (write-buffered *(ebp+8) ":break:\n") +15762 } +15763 $emit-subx-block:end: +15764 # . restore registers +15765 5e/pop-to-esi +15766 59/pop-to-ecx +15767 58/pop-to-eax +15768 # . epilogue +15769 89/<- %esp 5/r32/ebp +15770 5d/pop-to-ebp +15771 c3/return +15772 +15773 # Primitives supported +15774 # See mu_instructions for a summary of this linked-list data structure. +15775 # +15776 # For each operation, put variants with hard-coded registers before flexible ones. +15777 # +15778 # Unfortunately, our restrictions on addresses require that various fields in +15779 # primitives be handles, which complicates these definitions. +15780 # - we need to insert dummy fields all over the place for fake alloc-ids +15781 # - we can't use our syntax sugar of quoted literals for string fields +15782 # +15783 # Fake alloc-ids are needed because our type definitions up top require +15784 # handles but it's clearer to statically allocate these long-lived objects. +15785 # Fake alloc-ids are perfectly safe, but they can't be reclaimed. +15786 # +15787 # Every 'object' below starts with a fake alloc-id. It may also contain other +15788 # fake alloc-ids for various handle fields. +15789 # +15790 # I think of objects starting with a fake alloc-id as having type 'payload'. +15791 # It's not really intended to be created dynamically; for that use `allocate` +15792 # as usual. +15793 # +15794 # Idea for a notation to simplify such definitions: +15795 # _Primitive-increment-eax: # (payload primitive) +15796 # 0x11/alloc-id:fake:payload +15797 # 0x11 @(0x11 "increment") # name +15798 # 0 0 # inouts +15799 # 0x11 @(0x11/payload +15800 # 0x11 @(0x11/payload # List-value +15801 # 0 0 # Var-name +15802 # 0x11 @(0x11 # Var-type +15803 # 1/is-atom +15804 # 1/value 0/unused # Type-tree-left +15805 # 0 0 # Type-tree-right +15806 # ) +15807 # 1 # block-depth +15808 # 0 # stack-offset +15809 # 0x11 @(0x11 "eax") # Var-register +15810 # ) +15811 # 0 0) # List-next +15812 # ... +15813 # _Primitive-increment-ecx/imm32/next +15814 # ... +15815 # Awfully complex and non-obvious. But also clearly signals there's something +15816 # to learn here, so may be worth trying. +15817 # +15818 # '@' is just an initial thought. Punctuation used so far in Mu: () * % # / " +15819 # +15820 # For now we'll continue to just use comments and manually ensure they stay up +15821 # to date. +15822 == data +15823 Primitives: # (addr primitive) +15824 # - increment/decrement +15825 _Primitive-increment-eax: # (addr primitive) +15826 # var/eax <- increment => 40/increment-eax +15827 0x11/imm32/alloc-id:fake +15828 _string-increment/imm32/name +15829 0/imm32/no-inouts +15830 0/imm32/no-inouts 15831 0x11/imm32/alloc-id:fake -15832 _Primitive-add-lit-to-reg/imm32/next -15833 _Primitive-add-lit-to-reg: # (payload primitive) -15834 0x11/imm32/alloc-id:fake:payload -15835 # var1/reg <- add lit => 81 0/subop/add var1/rm32 lit/imm32 -15836 0x11/imm32/alloc-id:fake -15837 _string-add/imm32/name -15838 0x11/imm32/alloc-id:fake -15839 Single-lit-var/imm32/inouts -15840 0x11/imm32/alloc-id:fake -15841 Single-int-var-in-some-register/imm32/outputs -15842 0x11/imm32/alloc-id:fake -15843 _string_81_subop_add/imm32/subx-name -15844 3/imm32/rm32-is-first-output -15845 0/imm32/no-r32 -15846 1/imm32/imm32-is-first-inout -15847 0/imm32/no-imm8 -15848 0/imm32/no-disp32 -15849 0/imm32/output-is-write-only +15832 Single-int-var-in-eax/imm32/outputs +15833 0x11/imm32/alloc-id:fake +15834 _string_40_increment_eax/imm32/subx-name +15835 0/imm32/no-rm32 +15836 0/imm32/no-r32 +15837 0/imm32/no-imm32 +15838 0/imm32/no-imm8 +15839 0/imm32/no-disp32 +15840 0/imm32/output-is-write-only +15841 0x11/imm32/alloc-id:fake +15842 _Primitive-increment-ecx/imm32/next +15843 _Primitive-increment-ecx: # (payload primitive) +15844 0x11/imm32/alloc-id:fake:payload +15845 # var/ecx <- increment => 41/increment-ecx +15846 0x11/imm32/alloc-id:fake +15847 _string-increment/imm32/name +15848 0/imm32/no-inouts +15849 0/imm32/no-inouts 15850 0x11/imm32/alloc-id:fake -15851 _Primitive-add-lit-to-mem/imm32/next -15852 _Primitive-add-lit-to-mem: # (payload primitive) -15853 0x11/imm32/alloc-id:fake:payload -15854 # add-to var1, lit => 81 0/subop/add var1/rm32 lit/imm32 -15855 0x11/imm32/alloc-id:fake -15856 _string-add-to/imm32/name -15857 0x11/imm32/alloc-id:fake -15858 Int-var-and-literal/imm32/inouts -15859 0/imm32/no-outputs -15860 0/imm32/no-outputs -15861 0x11/imm32/alloc-id:fake -15862 _string_81_subop_add/imm32/subx-name -15863 1/imm32/rm32-is-first-inout -15864 0/imm32/no-r32 -15865 2/imm32/imm32-is-second-inout -15866 0/imm32/no-imm8 -15867 0/imm32/no-disp32 -15868 0/imm32/output-is-write-only +15851 Single-int-var-in-ecx/imm32/outputs +15852 0x11/imm32/alloc-id:fake +15853 _string_41_increment_ecx/imm32/subx-name +15854 0/imm32/no-rm32 +15855 0/imm32/no-r32 +15856 0/imm32/no-imm32 +15857 0/imm32/no-imm8 +15858 0/imm32/no-disp32 +15859 0/imm32/output-is-write-only +15860 0x11/imm32/alloc-id:fake +15861 _Primitive-increment-edx/imm32/next +15862 _Primitive-increment-edx: # (payload primitive) +15863 0x11/imm32/alloc-id:fake:payload +15864 # var/edx <- increment => 42/increment-edx +15865 0x11/imm32/alloc-id:fake +15866 _string-increment/imm32/name +15867 0/imm32/no-inouts +15868 0/imm32/no-inouts 15869 0x11/imm32/alloc-id:fake -15870 _Primitive-subtract-from-eax/imm32/next -15871 # - subtract -15872 _Primitive-subtract-from-eax: # (payload primitive) -15873 0x11/imm32/alloc-id:fake:payload -15874 # var/eax <- subtract lit => 2d/subtract-from-eax lit/imm32 -15875 0x11/imm32/alloc-id:fake -15876 _string-subtract/imm32/name -15877 0x11/imm32/alloc-id:fake -15878 Single-lit-var/imm32/inouts +15870 Single-int-var-in-edx/imm32/outputs +15871 0x11/imm32/alloc-id:fake +15872 _string_42_increment_edx/imm32/subx-name +15873 0/imm32/no-rm32 +15874 0/imm32/no-r32 +15875 0/imm32/no-imm32 +15876 0/imm32/no-imm8 +15877 0/imm32/no-disp32 +15878 0/imm32/output-is-write-only 15879 0x11/imm32/alloc-id:fake -15880 Single-int-var-in-eax/imm32/outputs -15881 0x11/imm32/alloc-id:fake -15882 _string_2d_subtract_from_eax/imm32/subx-name -15883 0/imm32/no-rm32 -15884 0/imm32/no-r32 -15885 1/imm32/imm32-is-first-inout -15886 0/imm32/no-imm8 -15887 0/imm32/no-disp32 -15888 0/imm32/output-is-write-only -15889 0x11/imm32/alloc-id:fake -15890 _Primitive-subtract-reg-from-reg/imm32/next -15891 _Primitive-subtract-reg-from-reg: # (payload primitive) -15892 0x11/imm32/alloc-id:fake:payload -15893 # var1/reg <- subtract var2/reg => 29/subtract-from var1/rm32 var2/r32 -15894 0x11/imm32/alloc-id:fake -15895 _string-subtract/imm32/name -15896 0x11/imm32/alloc-id:fake -15897 Single-int-var-in-some-register/imm32/inouts +15880 _Primitive-increment-ebx/imm32/next +15881 _Primitive-increment-ebx: # (payload primitive) +15882 0x11/imm32/alloc-id:fake:payload +15883 # var/ebx <- increment => 43/increment-ebx +15884 0x11/imm32/alloc-id:fake +15885 _string-increment/imm32/name +15886 0/imm32/no-inouts +15887 0/imm32/no-inouts +15888 0x11/imm32/alloc-id:fake +15889 Single-int-var-in-ebx/imm32/outputs +15890 0x11/imm32/alloc-id:fake +15891 _string_43_increment_ebx/imm32/subx-name +15892 0/imm32/no-rm32 +15893 0/imm32/no-r32 +15894 0/imm32/no-imm32 +15895 0/imm32/no-imm8 +15896 0/imm32/no-disp32 +15897 0/imm32/output-is-write-only 15898 0x11/imm32/alloc-id:fake -15899 Single-int-var-in-some-register/imm32/outputs -15900 0x11/imm32/alloc-id:fake -15901 _string_29_subtract_from/imm32/subx-name -15902 3/imm32/rm32-is-first-output -15903 1/imm32/r32-is-first-inout -15904 0/imm32/no-imm32 -15905 0/imm32/no-imm8 -15906 0/imm32/no-disp32 -15907 0/imm32/output-is-write-only -15908 0x11/imm32/alloc-id:fake -15909 _Primitive-subtract-reg-from-mem/imm32/next -15910 _Primitive-subtract-reg-from-mem: # (payload primitive) -15911 0x11/imm32/alloc-id:fake:payload -15912 # subtract-from var1 var2/reg => 29/subtract-from var1 var2/r32 -15913 0x11/imm32/alloc-id:fake -15914 _string-subtract-from/imm32/name -15915 0x11/imm32/alloc-id:fake -15916 Two-args-int-stack-int-reg/imm32/inouts -15917 0/imm32/no-outputs -15918 0/imm32/no-outputs -15919 0x11/imm32/alloc-id:fake -15920 _string_29_subtract_from/imm32/subx-name -15921 1/imm32/rm32-is-first-inout -15922 2/imm32/r32-is-second-inout -15923 0/imm32/no-imm32 -15924 0/imm32/no-imm8 -15925 0/imm32/no-disp32 -15926 0/imm32/output-is-write-only -15927 0x11/imm32/alloc-id:fake -15928 _Primitive-subtract-mem-from-reg/imm32/next -15929 _Primitive-subtract-mem-from-reg: # (payload primitive) -15930 0x11/imm32/alloc-id:fake:payload -15931 # var1/reg <- subtract var2 => 2b/subtract var2/rm32 var1/r32 -15932 0x11/imm32/alloc-id:fake -15933 _string-subtract/imm32/name -15934 0x11/imm32/alloc-id:fake -15935 Single-int-var-in-mem/imm32/inouts +15899 _Primitive-increment-esi/imm32/next +15900 _Primitive-increment-esi: # (payload primitive) +15901 0x11/imm32/alloc-id:fake:payload +15902 # var/esi <- increment => 46/increment-esi +15903 0x11/imm32/alloc-id:fake +15904 _string-increment/imm32/name +15905 0/imm32/no-inouts +15906 0/imm32/no-inouts +15907 0x11/imm32/alloc-id:fake +15908 Single-int-var-in-esi/imm32/outputs +15909 0x11/imm32/alloc-id:fake +15910 _string_46_increment_esi/imm32/subx-name +15911 0/imm32/no-rm32 +15912 0/imm32/no-r32 +15913 0/imm32/no-imm32 +15914 0/imm32/no-imm8 +15915 0/imm32/no-disp32 +15916 0/imm32/output-is-write-only +15917 0x11/imm32/alloc-id:fake +15918 _Primitive-increment-edi/imm32/next +15919 _Primitive-increment-edi: # (payload primitive) +15920 0x11/imm32/alloc-id:fake:payload +15921 # var/edi <- increment => 47/increment-edi +15922 0x11/imm32/alloc-id:fake +15923 _string-increment/imm32/name +15924 0/imm32/no-inouts +15925 0/imm32/no-inouts +15926 0x11/imm32/alloc-id:fake +15927 Single-int-var-in-edi/imm32/outputs +15928 0x11/imm32/alloc-id:fake +15929 _string_47_increment_edi/imm32/subx-name +15930 0/imm32/no-rm32 +15931 0/imm32/no-r32 +15932 0/imm32/no-imm32 +15933 0/imm32/no-imm8 +15934 0/imm32/no-disp32 +15935 0/imm32/output-is-write-only 15936 0x11/imm32/alloc-id:fake -15937 Single-int-var-in-some-register/imm32/outputs -15938 0x11/imm32/alloc-id:fake -15939 _string_2b_subtract/imm32/subx-name -15940 1/imm32/rm32-is-first-inout -15941 3/imm32/r32-is-first-output -15942 0/imm32/no-imm32 -15943 0/imm32/no-imm8 -15944 0/imm32/no-disp32 -15945 0/imm32/output-is-write-only -15946 0x11/imm32/alloc-id:fake -15947 _Primitive-subtract-lit-from-reg/imm32/next -15948 _Primitive-subtract-lit-from-reg: # (payload primitive) -15949 0x11/imm32/alloc-id:fake:payload -15950 # var1/reg <- subtract lit => 81 5/subop/subtract var1/rm32 lit/imm32 -15951 0x11/imm32/alloc-id:fake -15952 _string-subtract/imm32/name -15953 0x11/imm32/alloc-id:fake -15954 Single-lit-var/imm32/inouts +15937 _Primitive-decrement-eax/imm32/next +15938 _Primitive-decrement-eax: # (payload primitive) +15939 0x11/imm32/alloc-id:fake:payload +15940 # var/eax <- decrement => 48/decrement-eax +15941 0x11/imm32/alloc-id:fake +15942 _string-decrement/imm32/name +15943 0/imm32/no-inouts +15944 0/imm32/no-inouts +15945 0x11/imm32/alloc-id:fake +15946 Single-int-var-in-eax/imm32/outputs +15947 0x11/imm32/alloc-id:fake +15948 _string_48_decrement_eax/imm32/subx-name +15949 0/imm32/no-rm32 +15950 0/imm32/no-r32 +15951 0/imm32/no-imm32 +15952 0/imm32/no-imm8 +15953 0/imm32/no-disp32 +15954 0/imm32/output-is-write-only 15955 0x11/imm32/alloc-id:fake -15956 Single-int-var-in-some-register/imm32/outputs -15957 0x11/imm32/alloc-id:fake -15958 _string_81_subop_subtract/imm32/subx-name -15959 3/imm32/rm32-is-first-output -15960 0/imm32/no-r32 -15961 1/imm32/imm32-is-first-inout -15962 0/imm32/no-imm8 -15963 0/imm32/no-disp32 -15964 0/imm32/output-is-write-only -15965 0x11/imm32/alloc-id:fake -15966 _Primitive-subtract-lit-from-mem/imm32/next -15967 _Primitive-subtract-lit-from-mem: # (payload primitive) -15968 0x11/imm32/alloc-id:fake:payload -15969 # subtract-from var1, lit => 81 5/subop/subtract var1/rm32 lit/imm32 -15970 0x11/imm32/alloc-id:fake -15971 _string-subtract-from/imm32/name -15972 0x11/imm32/alloc-id:fake -15973 Int-var-and-literal/imm32/inouts -15974 0/imm32/no-outputs -15975 0/imm32/no-outputs -15976 0x11/imm32/alloc-id:fake -15977 _string_81_subop_subtract/imm32/subx-name -15978 1/imm32/rm32-is-first-inout -15979 0/imm32/no-r32 -15980 2/imm32/imm32-is-second-inout -15981 0/imm32/no-imm8 -15982 0/imm32/no-disp32 -15983 0/imm32/output-is-write-only -15984 0x11/imm32/alloc-id:fake -15985 _Primitive-and-with-eax/imm32/next -15986 # - and -15987 _Primitive-and-with-eax: # (payload primitive) -15988 0x11/imm32/alloc-id:fake:payload -15989 # var/eax <- and lit => 25/and-with-eax lit/imm32 -15990 0x11/imm32/alloc-id:fake -15991 _string-and/imm32/name -15992 0x11/imm32/alloc-id:fake -15993 Single-lit-var/imm32/inouts -15994 0x11/imm32/alloc-id:fake -15995 Single-int-var-in-eax/imm32/outputs -15996 0x11/imm32/alloc-id:fake -15997 _string_25_and_with_eax/imm32/subx-name -15998 0/imm32/no-rm32 -15999 0/imm32/no-r32 -16000 1/imm32/imm32-is-first-inout -16001 0/imm32/no-imm8 -16002 0/imm32/no-disp32 -16003 0/imm32/output-is-write-only +15956 _Primitive-decrement-ecx/imm32/next +15957 _Primitive-decrement-ecx: # (payload primitive) +15958 0x11/imm32/alloc-id:fake:payload +15959 # var/ecx <- decrement => 49/decrement-ecx +15960 0x11/imm32/alloc-id:fake +15961 _string-decrement/imm32/name +15962 0/imm32/no-inouts +15963 0/imm32/no-inouts +15964 0x11/imm32/alloc-id:fake +15965 Single-int-var-in-ecx/imm32/outputs +15966 0x11/imm32/alloc-id:fake +15967 _string_49_decrement_ecx/imm32/subx-name +15968 0/imm32/no-rm32 +15969 0/imm32/no-r32 +15970 0/imm32/no-imm32 +15971 0/imm32/no-imm8 +15972 0/imm32/no-disp32 +15973 0/imm32/output-is-write-only +15974 0x11/imm32/alloc-id:fake +15975 _Primitive-decrement-edx/imm32/next +15976 _Primitive-decrement-edx: # (payload primitive) +15977 0x11/imm32/alloc-id:fake:payload +15978 # var/edx <- decrement => 4a/decrement-edx +15979 0x11/imm32/alloc-id:fake +15980 _string-decrement/imm32/name +15981 0/imm32/no-inouts +15982 0/imm32/no-inouts +15983 0x11/imm32/alloc-id:fake +15984 Single-int-var-in-edx/imm32/outputs +15985 0x11/imm32/alloc-id:fake +15986 _string_4a_decrement_edx/imm32/subx-name +15987 0/imm32/no-rm32 +15988 0/imm32/no-r32 +15989 0/imm32/no-imm32 +15990 0/imm32/no-imm8 +15991 0/imm32/no-disp32 +15992 0/imm32/output-is-write-only +15993 0x11/imm32/alloc-id:fake +15994 _Primitive-decrement-ebx/imm32/next +15995 _Primitive-decrement-ebx: # (payload primitive) +15996 0x11/imm32/alloc-id:fake:payload +15997 # var/ebx <- decrement => 4b/decrement-ebx +15998 0x11/imm32/alloc-id:fake +15999 _string-decrement/imm32/name +16000 0/imm32/no-inouts +16001 0/imm32/no-inouts +16002 0x11/imm32/alloc-id:fake +16003 Single-int-var-in-ebx/imm32/outputs 16004 0x11/imm32/alloc-id:fake -16005 _Primitive-and-reg-with-reg/imm32/next -16006 _Primitive-and-reg-with-reg: # (payload primitive) -16007 0x11/imm32/alloc-id:fake:payload -16008 # var1/reg <- and var2/reg => 21/and-with var1/rm32 var2/r32 -16009 0x11/imm32/alloc-id:fake -16010 _string-and/imm32/name -16011 0x11/imm32/alloc-id:fake -16012 Single-int-var-in-some-register/imm32/inouts -16013 0x11/imm32/alloc-id:fake -16014 Single-int-var-in-some-register/imm32/outputs -16015 0x11/imm32/alloc-id:fake -16016 _string_21_and_with/imm32/subx-name -16017 3/imm32/rm32-is-first-output -16018 1/imm32/r32-is-first-inout -16019 0/imm32/no-imm32 -16020 0/imm32/no-imm8 -16021 0/imm32/no-disp32 -16022 0/imm32/output-is-write-only +16005 _string_4b_decrement_ebx/imm32/subx-name +16006 0/imm32/no-rm32 +16007 0/imm32/no-r32 +16008 0/imm32/no-imm32 +16009 0/imm32/no-imm8 +16010 0/imm32/no-disp32 +16011 0/imm32/output-is-write-only +16012 0x11/imm32/alloc-id:fake +16013 _Primitive-decrement-esi/imm32/next +16014 _Primitive-decrement-esi: # (payload primitive) +16015 0x11/imm32/alloc-id:fake:payload +16016 # var/esi <- decrement => 4e/decrement-esi +16017 0x11/imm32/alloc-id:fake +16018 _string-decrement/imm32/name +16019 0/imm32/no-inouts +16020 0/imm32/no-inouts +16021 0x11/imm32/alloc-id:fake +16022 Single-int-var-in-esi/imm32/outputs 16023 0x11/imm32/alloc-id:fake -16024 _Primitive-and-reg-with-mem/imm32/next -16025 _Primitive-and-reg-with-mem: # (payload primitive) -16026 0x11/imm32/alloc-id:fake:payload -16027 # and-with var1 var2/reg => 21/and-with var1 var2/r32 -16028 0x11/imm32/alloc-id:fake -16029 _string-and-with/imm32/name -16030 0x11/imm32/alloc-id:fake -16031 Two-args-int-stack-int-reg/imm32/inouts -16032 0/imm32/no-outputs -16033 0/imm32/no-outputs -16034 0x11/imm32/alloc-id:fake -16035 _string_21_and_with/imm32/subx-name -16036 1/imm32/rm32-is-first-inout -16037 2/imm32/r32-is-second-inout -16038 0/imm32/no-imm32 -16039 0/imm32/no-imm8 -16040 0/imm32/no-disp32 -16041 0/imm32/output-is-write-only +16024 _string_4e_decrement_esi/imm32/subx-name +16025 0/imm32/no-rm32 +16026 0/imm32/no-r32 +16027 0/imm32/no-imm32 +16028 0/imm32/no-imm8 +16029 0/imm32/no-disp32 +16030 0/imm32/output-is-write-only +16031 0x11/imm32/alloc-id:fake +16032 _Primitive-decrement-edi/imm32/next +16033 _Primitive-decrement-edi: # (payload primitive) +16034 0x11/imm32/alloc-id:fake:payload +16035 # var/edi <- decrement => 4f/decrement-edi +16036 0x11/imm32/alloc-id:fake +16037 _string-decrement/imm32/name +16038 0/imm32/no-inouts +16039 0/imm32/no-inouts +16040 0x11/imm32/alloc-id:fake +16041 Single-int-var-in-edi/imm32/outputs 16042 0x11/imm32/alloc-id:fake -16043 _Primitive-and-mem-with-reg/imm32/next -16044 _Primitive-and-mem-with-reg: # (payload primitive) -16045 0x11/imm32/alloc-id:fake:payload -16046 # var1/reg <- and var2 => 23/and var2/rm32 var1/r32 -16047 0x11/imm32/alloc-id:fake -16048 _string-and/imm32/name -16049 0x11/imm32/alloc-id:fake -16050 Single-int-var-in-mem/imm32/inouts -16051 0x11/imm32/alloc-id:fake -16052 Single-int-var-in-some-register/imm32/outputs -16053 0x11/imm32/alloc-id:fake -16054 _string_23_and/imm32/subx-name -16055 1/imm32/rm32-is-first-inout -16056 3/imm32/r32-is-first-output -16057 0/imm32/no-imm32 -16058 0/imm32/no-imm8 -16059 0/imm32/no-disp32 -16060 0/imm32/output-is-write-only +16043 _string_4f_decrement_edi/imm32/subx-name +16044 0/imm32/no-rm32 +16045 0/imm32/no-r32 +16046 0/imm32/no-imm32 +16047 0/imm32/no-imm8 +16048 0/imm32/no-disp32 +16049 0/imm32/output-is-write-only +16050 0x11/imm32/alloc-id:fake +16051 _Primitive-increment-mem/imm32/next +16052 _Primitive-increment-mem: # (payload primitive) +16053 0x11/imm32/alloc-id:fake:payload +16054 # increment var => ff 0/subop/increment *(ebp+__) +16055 0x11/imm32/alloc-id:fake +16056 _string-increment/imm32/name +16057 0x11/imm32/alloc-id:fake +16058 Single-int-var-in-mem/imm32/inouts +16059 0/imm32/no-outputs +16060 0/imm32/no-outputs 16061 0x11/imm32/alloc-id:fake -16062 _Primitive-and-lit-with-reg/imm32/next -16063 _Primitive-and-lit-with-reg: # (payload primitive) -16064 0x11/imm32/alloc-id:fake:payload -16065 # var1/reg <- and lit => 81 4/subop/and var1/rm32 lit/imm32 -16066 0x11/imm32/alloc-id:fake -16067 _string-and/imm32/name -16068 0x11/imm32/alloc-id:fake -16069 Single-lit-var/imm32/inouts -16070 0x11/imm32/alloc-id:fake -16071 Single-int-var-in-some-register/imm32/outputs -16072 0x11/imm32/alloc-id:fake -16073 _string_81_subop_and/imm32/subx-name -16074 3/imm32/rm32-is-first-output -16075 0/imm32/no-r32 -16076 1/imm32/imm32-is-first-inout -16077 0/imm32/no-imm8 -16078 0/imm32/no-disp32 -16079 0/imm32/output-is-write-only +16062 _string_ff_subop_increment/imm32/subx-name +16063 1/imm32/rm32-is-first-inout +16064 0/imm32/no-r32 +16065 0/imm32/no-imm32 +16066 0/imm32/no-imm8 +16067 0/imm32/no-disp32 +16068 0/imm32/output-is-write-only +16069 0x11/imm32/alloc-id:fake +16070 _Primitive-increment-reg/imm32/next +16071 _Primitive-increment-reg: # (payload primitive) +16072 0x11/imm32/alloc-id:fake:payload +16073 # var/reg <- increment => ff 0/subop/increment %__ +16074 0x11/imm32/alloc-id:fake +16075 _string-increment/imm32/name +16076 0/imm32/no-inouts +16077 0/imm32/no-inouts +16078 0x11/imm32/alloc-id:fake +16079 Single-int-var-in-some-register/imm32/outputs 16080 0x11/imm32/alloc-id:fake -16081 _Primitive-and-lit-with-mem/imm32/next -16082 _Primitive-and-lit-with-mem: # (payload primitive) -16083 0x11/imm32/alloc-id:fake:payload -16084 # and-with var1, lit => 81 4/subop/and var1/rm32 lit/imm32 -16085 0x11/imm32/alloc-id:fake -16086 _string-and-with/imm32/name -16087 0x11/imm32/alloc-id:fake -16088 Int-var-and-literal/imm32/inouts -16089 0/imm32/no-outputs -16090 0/imm32/no-outputs -16091 0x11/imm32/alloc-id:fake -16092 _string_81_subop_and/imm32/subx-name -16093 1/imm32/rm32-is-first-inout -16094 0/imm32/no-r32 -16095 2/imm32/imm32-is-second-inout -16096 0/imm32/no-imm8 -16097 0/imm32/no-disp32 -16098 0/imm32/output-is-write-only +16081 _string_ff_subop_increment/imm32/subx-name +16082 3/imm32/rm32-is-first-output +16083 0/imm32/no-r32 +16084 0/imm32/no-imm32 +16085 0/imm32/no-imm8 +16086 0/imm32/no-disp32 +16087 0/imm32/output-is-write-only +16088 0x11/imm32/alloc-id:fake +16089 _Primitive-decrement-mem/imm32/next +16090 _Primitive-decrement-mem: # (payload primitive) +16091 0x11/imm32/alloc-id:fake:payload +16092 # decrement var => ff 1/subop/decrement *(ebp+__) +16093 0x11/imm32/alloc-id:fake +16094 _string-decrement/imm32/name +16095 0x11/imm32/alloc-id:fake +16096 Single-int-var-in-mem/imm32/inouts +16097 0/imm32/no-outputs +16098 0/imm32/no-outputs 16099 0x11/imm32/alloc-id:fake -16100 _Primitive-or-with-eax/imm32/next -16101 # - or -16102 _Primitive-or-with-eax: # (payload primitive) -16103 0x11/imm32/alloc-id:fake:payload -16104 # var/eax <- or lit => 0d/or-with-eax lit/imm32 -16105 0x11/imm32/alloc-id:fake -16106 _string-or/imm32/name +16100 _string_ff_subop_decrement/imm32/subx-name +16101 1/imm32/rm32-is-first-inout +16102 0/imm32/no-r32 +16103 0/imm32/no-imm32 +16104 0/imm32/no-imm8 +16105 0/imm32/no-disp32 +16106 0/imm32/output-is-write-only 16107 0x11/imm32/alloc-id:fake -16108 Single-lit-var/imm32/inouts -16109 0x11/imm32/alloc-id:fake -16110 Single-int-var-in-eax/imm32/outputs -16111 0x11/imm32/alloc-id:fake -16112 _string_0d_or_with_eax/imm32/subx-name -16113 0/imm32/no-rm32 -16114 0/imm32/no-r32 -16115 1/imm32/imm32-is-first-inout -16116 0/imm32/no-imm8 -16117 0/imm32/no-disp32 -16118 0/imm32/output-is-write-only -16119 0x11/imm32/alloc-id:fake -16120 _Primitive-or-reg-with-reg/imm32/next -16121 _Primitive-or-reg-with-reg: # (payload primitive) -16122 0x11/imm32/alloc-id:fake:payload -16123 # var1/reg <- or var2/reg => 09/or-with var1/rm32 var2/r32 -16124 0x11/imm32/alloc-id:fake -16125 _string-or/imm32/name +16108 _Primitive-decrement-reg/imm32/next +16109 _Primitive-decrement-reg: # (payload primitive) +16110 0x11/imm32/alloc-id:fake:payload +16111 # var/reg <- decrement => ff 1/subop/decrement %__ +16112 0x11/imm32/alloc-id:fake +16113 _string-decrement/imm32/name +16114 0/imm32/no-inouts +16115 0/imm32/no-inouts +16116 0x11/imm32/alloc-id:fake +16117 Single-int-var-in-some-register/imm32/outputs +16118 0x11/imm32/alloc-id:fake +16119 _string_ff_subop_decrement/imm32/subx-name +16120 3/imm32/rm32-is-first-output +16121 0/imm32/no-r32 +16122 0/imm32/no-imm32 +16123 0/imm32/no-imm8 +16124 0/imm32/no-disp32 +16125 0/imm32/output-is-write-only 16126 0x11/imm32/alloc-id:fake -16127 Single-int-var-in-some-register/imm32/inouts -16128 0x11/imm32/alloc-id:fake -16129 Single-int-var-in-some-register/imm32/outputs -16130 0x11/imm32/alloc-id:fake -16131 _string_09_or_with/imm32/subx-name -16132 3/imm32/rm32-is-first-output -16133 1/imm32/r32-is-first-inout -16134 0/imm32/no-imm32 -16135 0/imm32/no-imm8 -16136 0/imm32/no-disp32 -16137 0/imm32/output-is-write-only +16127 _Primitive-add-to-eax/imm32/next +16128 # - add +16129 _Primitive-add-to-eax: # (payload primitive) +16130 0x11/imm32/alloc-id:fake:payload +16131 # var/eax <- add lit => 05/add-to-eax lit/imm32 +16132 0x11/imm32/alloc-id:fake +16133 _string-add/imm32/name +16134 0x11/imm32/alloc-id:fake +16135 Single-lit-var/imm32/inouts +16136 0x11/imm32/alloc-id:fake +16137 Single-int-var-in-eax/imm32/outputs 16138 0x11/imm32/alloc-id:fake -16139 _Primitive-or-reg-with-mem/imm32/next -16140 _Primitive-or-reg-with-mem: # (payload primitive) -16141 0x11/imm32/alloc-id:fake:payload -16142 # or-with var1 var2/reg => 09/or-with var1 var2/r32 -16143 0x11/imm32/alloc-id:fake -16144 _string-or-with/imm32/name -16145 0x11/imm32/alloc-id:fake -16146 Two-args-int-stack-int-reg/imm32/inouts -16147 0/imm32/no-outputs -16148 0/imm32/no-outputs -16149 0x11/imm32/alloc-id:fake -16150 _string_09_or_with/imm32/subx-name -16151 1/imm32/rm32-is-first-inout -16152 2/imm32/r32-is-second-inout -16153 0/imm32/no-imm32 -16154 0/imm32/no-imm8 -16155 0/imm32/no-disp32 -16156 0/imm32/output-is-write-only +16139 _string_05_add_to_eax/imm32/subx-name +16140 0/imm32/no-rm32 +16141 0/imm32/no-r32 +16142 1/imm32/imm32-is-first-inout +16143 0/imm32/no-imm8 +16144 0/imm32/no-disp32 +16145 0/imm32/output-is-write-only +16146 0x11/imm32/alloc-id:fake +16147 _Primitive-add-reg-to-reg/imm32/next +16148 _Primitive-add-reg-to-reg: # (payload primitive) +16149 0x11/imm32/alloc-id:fake:payload +16150 # var1/reg <- add var2/reg => 01/add-to var1/rm32 var2/r32 +16151 0x11/imm32/alloc-id:fake +16152 _string-add/imm32/name +16153 0x11/imm32/alloc-id:fake +16154 Single-int-var-in-some-register/imm32/inouts +16155 0x11/imm32/alloc-id:fake +16156 Single-int-var-in-some-register/imm32/outputs 16157 0x11/imm32/alloc-id:fake -16158 _Primitive-or-mem-with-reg/imm32/next -16159 _Primitive-or-mem-with-reg: # (payload primitive) -16160 0x11/imm32/alloc-id:fake:payload -16161 # var1/reg <- or var2 => 0b/or var2/rm32 var1/r32 -16162 0x11/imm32/alloc-id:fake -16163 _string-or/imm32/name -16164 0x11/imm32/alloc-id:fake -16165 Single-int-var-in-mem/imm32/inouts -16166 0x11/imm32/alloc-id:fake -16167 Single-int-var-in-some-register/imm32/outputs -16168 0x11/imm32/alloc-id:fake -16169 _string_0b_or/imm32/subx-name -16170 1/imm32/rm32-is-first-inout -16171 3/imm32/r32-is-first-output -16172 0/imm32/no-imm32 -16173 0/imm32/no-imm8 -16174 0/imm32/no-disp32 -16175 0/imm32/output-is-write-only +16158 _string_01_add_to/imm32/subx-name +16159 3/imm32/rm32-is-first-output +16160 1/imm32/r32-is-first-inout +16161 0/imm32/no-imm32 +16162 0/imm32/no-imm8 +16163 0/imm32/no-disp32 +16164 0/imm32/output-is-write-only +16165 0x11/imm32/alloc-id:fake +16166 _Primitive-add-reg-to-mem/imm32/next +16167 _Primitive-add-reg-to-mem: # (payload primitive) +16168 0x11/imm32/alloc-id:fake:payload +16169 # add-to var1 var2/reg => 01/add-to var1 var2/r32 +16170 0x11/imm32/alloc-id:fake +16171 _string-add-to/imm32/name +16172 0x11/imm32/alloc-id:fake +16173 Two-args-int-stack-int-reg/imm32/inouts +16174 0/imm32/no-outputs +16175 0/imm32/no-outputs 16176 0x11/imm32/alloc-id:fake -16177 _Primitive-or-lit-with-reg/imm32/next -16178 _Primitive-or-lit-with-reg: # (payload primitive) -16179 0x11/imm32/alloc-id:fake:payload -16180 # var1/reg <- or lit => 81 1/subop/or var1/rm32 lit/imm32 -16181 0x11/imm32/alloc-id:fake -16182 _string-or/imm32/name -16183 0x11/imm32/alloc-id:fake -16184 Single-lit-var/imm32/inouts -16185 0x11/imm32/alloc-id:fake -16186 Single-int-var-in-some-register/imm32/outputs -16187 0x11/imm32/alloc-id:fake -16188 _string_81_subop_or/imm32/subx-name -16189 3/imm32/rm32-is-first-output -16190 0/imm32/no-r32 -16191 1/imm32/imm32-is-first-inout -16192 0/imm32/no-imm8 -16193 0/imm32/no-disp32 -16194 0/imm32/output-is-write-only +16177 _string_01_add_to/imm32/subx-name +16178 1/imm32/rm32-is-first-inout +16179 2/imm32/r32-is-second-inout +16180 0/imm32/no-imm32 +16181 0/imm32/no-imm8 +16182 0/imm32/no-disp32 +16183 0/imm32/output-is-write-only +16184 0x11/imm32/alloc-id:fake +16185 _Primitive-add-mem-to-reg/imm32/next +16186 _Primitive-add-mem-to-reg: # (payload primitive) +16187 0x11/imm32/alloc-id:fake:payload +16188 # var1/reg <- add var2 => 03/add var2/rm32 var1/r32 +16189 0x11/imm32/alloc-id:fake +16190 _string-add/imm32/name +16191 0x11/imm32/alloc-id:fake +16192 Single-int-var-in-mem/imm32/inouts +16193 0x11/imm32/alloc-id:fake +16194 Single-int-var-in-some-register/imm32/outputs 16195 0x11/imm32/alloc-id:fake -16196 _Primitive-or-lit-with-mem/imm32/next -16197 _Primitive-or-lit-with-mem: # (payload primitive) -16198 0x11/imm32/alloc-id:fake:payload -16199 # or-with var1, lit => 81 1/subop/or var1/rm32 lit/imm32 -16200 0x11/imm32/alloc-id:fake -16201 _string-or-with/imm32/name -16202 0x11/imm32/alloc-id:fake -16203 Int-var-and-literal/imm32/inouts -16204 0/imm32/no-outputs -16205 0/imm32/no-outputs -16206 0x11/imm32/alloc-id:fake -16207 _string_81_subop_or/imm32/subx-name -16208 1/imm32/rm32-is-first-inout -16209 0/imm32/no-r32 -16210 2/imm32/imm32-is-second-inout -16211 0/imm32/no-imm8 -16212 0/imm32/no-disp32 -16213 0/imm32/output-is-write-only +16196 _string_03_add/imm32/subx-name +16197 1/imm32/rm32-is-first-inout +16198 3/imm32/r32-is-first-output +16199 0/imm32/no-imm32 +16200 0/imm32/no-imm8 +16201 0/imm32/no-disp32 +16202 0/imm32/output-is-write-only +16203 0x11/imm32/alloc-id:fake +16204 _Primitive-add-lit-to-reg/imm32/next +16205 _Primitive-add-lit-to-reg: # (payload primitive) +16206 0x11/imm32/alloc-id:fake:payload +16207 # var1/reg <- add lit => 81 0/subop/add var1/rm32 lit/imm32 +16208 0x11/imm32/alloc-id:fake +16209 _string-add/imm32/name +16210 0x11/imm32/alloc-id:fake +16211 Single-lit-var/imm32/inouts +16212 0x11/imm32/alloc-id:fake +16213 Single-int-var-in-some-register/imm32/outputs 16214 0x11/imm32/alloc-id:fake -16215 _Primitive-xor-with-eax/imm32/next -16216 # - xor -16217 _Primitive-xor-with-eax: # (payload primitive) -16218 0x11/imm32/alloc-id:fake:payload -16219 # var/eax <- xor lit => 35/xor-with-eax lit/imm32 -16220 0x11/imm32/alloc-id:fake -16221 _string-xor/imm32/name +16215 _string_81_subop_add/imm32/subx-name +16216 3/imm32/rm32-is-first-output +16217 0/imm32/no-r32 +16218 1/imm32/imm32-is-first-inout +16219 0/imm32/no-imm8 +16220 0/imm32/no-disp32 +16221 0/imm32/output-is-write-only 16222 0x11/imm32/alloc-id:fake -16223 Single-lit-var/imm32/inouts -16224 0x11/imm32/alloc-id:fake -16225 Single-int-var-in-eax/imm32/outputs -16226 0x11/imm32/alloc-id:fake -16227 _string_35_xor_with_eax/imm32/subx-name -16228 0/imm32/no-rm32 -16229 0/imm32/no-r32 -16230 1/imm32/imm32-is-first-inout -16231 0/imm32/no-imm8 -16232 0/imm32/no-disp32 -16233 0/imm32/output-is-write-only -16234 0x11/imm32/alloc-id:fake -16235 _Primitive-xor-reg-with-reg/imm32/next -16236 _Primitive-xor-reg-with-reg: # (payload primitive) -16237 0x11/imm32/alloc-id:fake:payload -16238 # var1/reg <- xor var2/reg => 31/xor-with var1/rm32 var2/r32 -16239 0x11/imm32/alloc-id:fake -16240 _string-xor/imm32/name +16223 _Primitive-add-lit-to-mem/imm32/next +16224 _Primitive-add-lit-to-mem: # (payload primitive) +16225 0x11/imm32/alloc-id:fake:payload +16226 # add-to var1, lit => 81 0/subop/add var1/rm32 lit/imm32 +16227 0x11/imm32/alloc-id:fake +16228 _string-add-to/imm32/name +16229 0x11/imm32/alloc-id:fake +16230 Int-var-and-literal/imm32/inouts +16231 0/imm32/no-outputs +16232 0/imm32/no-outputs +16233 0x11/imm32/alloc-id:fake +16234 _string_81_subop_add/imm32/subx-name +16235 1/imm32/rm32-is-first-inout +16236 0/imm32/no-r32 +16237 2/imm32/imm32-is-second-inout +16238 0/imm32/no-imm8 +16239 0/imm32/no-disp32 +16240 0/imm32/output-is-write-only 16241 0x11/imm32/alloc-id:fake -16242 Single-int-var-in-some-register/imm32/inouts -16243 0x11/imm32/alloc-id:fake -16244 Single-int-var-in-some-register/imm32/outputs -16245 0x11/imm32/alloc-id:fake -16246 _string_31_xor_with/imm32/subx-name -16247 3/imm32/rm32-is-first-output -16248 1/imm32/r32-is-first-inout -16249 0/imm32/no-imm32 -16250 0/imm32/no-imm8 -16251 0/imm32/no-disp32 -16252 0/imm32/output-is-write-only +16242 _Primitive-subtract-from-eax/imm32/next +16243 # - subtract +16244 _Primitive-subtract-from-eax: # (payload primitive) +16245 0x11/imm32/alloc-id:fake:payload +16246 # var/eax <- subtract lit => 2d/subtract-from-eax lit/imm32 +16247 0x11/imm32/alloc-id:fake +16248 _string-subtract/imm32/name +16249 0x11/imm32/alloc-id:fake +16250 Single-lit-var/imm32/inouts +16251 0x11/imm32/alloc-id:fake +16252 Single-int-var-in-eax/imm32/outputs 16253 0x11/imm32/alloc-id:fake -16254 _Primitive-xor-reg-with-mem/imm32/next -16255 _Primitive-xor-reg-with-mem: # (payload primitive) -16256 0x11/imm32/alloc-id:fake:payload -16257 # xor-with var1 var2/reg => 31/xor-with var1 var2/r32 -16258 0x11/imm32/alloc-id:fake -16259 _string-xor-with/imm32/name -16260 0x11/imm32/alloc-id:fake -16261 Two-args-int-stack-int-reg/imm32/inouts -16262 0/imm32/no-outputs -16263 0/imm32/no-outputs -16264 0x11/imm32/alloc-id:fake -16265 _string_31_xor_with/imm32/subx-name -16266 1/imm32/rm32-is-first-inout -16267 2/imm32/r32-is-second-inout -16268 0/imm32/no-imm32 -16269 0/imm32/no-imm8 -16270 0/imm32/no-disp32 -16271 0/imm32/output-is-write-only +16254 _string_2d_subtract_from_eax/imm32/subx-name +16255 0/imm32/no-rm32 +16256 0/imm32/no-r32 +16257 1/imm32/imm32-is-first-inout +16258 0/imm32/no-imm8 +16259 0/imm32/no-disp32 +16260 0/imm32/output-is-write-only +16261 0x11/imm32/alloc-id:fake +16262 _Primitive-subtract-reg-from-reg/imm32/next +16263 _Primitive-subtract-reg-from-reg: # (payload primitive) +16264 0x11/imm32/alloc-id:fake:payload +16265 # var1/reg <- subtract var2/reg => 29/subtract-from var1/rm32 var2/r32 +16266 0x11/imm32/alloc-id:fake +16267 _string-subtract/imm32/name +16268 0x11/imm32/alloc-id:fake +16269 Single-int-var-in-some-register/imm32/inouts +16270 0x11/imm32/alloc-id:fake +16271 Single-int-var-in-some-register/imm32/outputs 16272 0x11/imm32/alloc-id:fake -16273 _Primitive-xor-mem-with-reg/imm32/next -16274 _Primitive-xor-mem-with-reg: # (payload primitive) -16275 0x11/imm32/alloc-id:fake:payload -16276 # var1/reg <- xor var2 => 33/xor var2/rm32 var1/r32 -16277 0x11/imm32/alloc-id:fake -16278 _string-xor/imm32/name -16279 0x11/imm32/alloc-id:fake -16280 Single-int-var-in-mem/imm32/inouts -16281 0x11/imm32/alloc-id:fake -16282 Single-int-var-in-some-register/imm32/outputs -16283 0x11/imm32/alloc-id:fake -16284 _string_33_xor/imm32/subx-name -16285 1/imm32/rm32-is-first-inout -16286 3/imm32/r32-is-first-output -16287 0/imm32/no-imm32 -16288 0/imm32/no-imm8 -16289 0/imm32/no-disp32 -16290 0/imm32/output-is-write-only +16273 _string_29_subtract_from/imm32/subx-name +16274 3/imm32/rm32-is-first-output +16275 1/imm32/r32-is-first-inout +16276 0/imm32/no-imm32 +16277 0/imm32/no-imm8 +16278 0/imm32/no-disp32 +16279 0/imm32/output-is-write-only +16280 0x11/imm32/alloc-id:fake +16281 _Primitive-subtract-reg-from-mem/imm32/next +16282 _Primitive-subtract-reg-from-mem: # (payload primitive) +16283 0x11/imm32/alloc-id:fake:payload +16284 # subtract-from var1 var2/reg => 29/subtract-from var1 var2/r32 +16285 0x11/imm32/alloc-id:fake +16286 _string-subtract-from/imm32/name +16287 0x11/imm32/alloc-id:fake +16288 Two-args-int-stack-int-reg/imm32/inouts +16289 0/imm32/no-outputs +16290 0/imm32/no-outputs 16291 0x11/imm32/alloc-id:fake -16292 _Primitive-xor-lit-with-reg/imm32/next -16293 _Primitive-xor-lit-with-reg: # (payload primitive) -16294 0x11/imm32/alloc-id:fake:payload -16295 # var1/reg <- xor lit => 81 6/subop/xor var1/rm32 lit/imm32 -16296 0x11/imm32/alloc-id:fake -16297 _string-xor/imm32/name -16298 0x11/imm32/alloc-id:fake -16299 Single-lit-var/imm32/inouts -16300 0x11/imm32/alloc-id:fake -16301 Single-int-var-in-some-register/imm32/outputs -16302 0x11/imm32/alloc-id:fake -16303 _string_81_subop_xor/imm32/subx-name -16304 3/imm32/rm32-is-first-output -16305 0/imm32/no-r32 -16306 1/imm32/imm32-is-first-inout -16307 0/imm32/no-imm8 -16308 0/imm32/no-disp32 -16309 0/imm32/output-is-write-only +16292 _string_29_subtract_from/imm32/subx-name +16293 1/imm32/rm32-is-first-inout +16294 2/imm32/r32-is-second-inout +16295 0/imm32/no-imm32 +16296 0/imm32/no-imm8 +16297 0/imm32/no-disp32 +16298 0/imm32/output-is-write-only +16299 0x11/imm32/alloc-id:fake +16300 _Primitive-subtract-mem-from-reg/imm32/next +16301 _Primitive-subtract-mem-from-reg: # (payload primitive) +16302 0x11/imm32/alloc-id:fake:payload +16303 # var1/reg <- subtract var2 => 2b/subtract var2/rm32 var1/r32 +16304 0x11/imm32/alloc-id:fake +16305 _string-subtract/imm32/name +16306 0x11/imm32/alloc-id:fake +16307 Single-int-var-in-mem/imm32/inouts +16308 0x11/imm32/alloc-id:fake +16309 Single-int-var-in-some-register/imm32/outputs 16310 0x11/imm32/alloc-id:fake -16311 _Primitive-xor-lit-with-mem/imm32/next -16312 _Primitive-xor-lit-with-mem: # (payload primitive) -16313 0x11/imm32/alloc-id:fake:payload -16314 # xor-with var1, lit => 81 6/subop/xor var1/rm32 lit/imm32 -16315 0x11/imm32/alloc-id:fake -16316 _string-xor-with/imm32/name -16317 0x11/imm32/alloc-id:fake -16318 Int-var-and-literal/imm32/inouts -16319 0/imm32/no-outputs -16320 0/imm32/no-outputs -16321 0x11/imm32/alloc-id:fake -16322 _string_81_subop_xor/imm32/subx-name -16323 1/imm32/rm32-is-first-inout -16324 0/imm32/no-r32 -16325 2/imm32/imm32-is-second-inout -16326 0/imm32/no-imm8 -16327 0/imm32/no-disp32 -16328 0/imm32/output-is-write-only +16311 _string_2b_subtract/imm32/subx-name +16312 1/imm32/rm32-is-first-inout +16313 3/imm32/r32-is-first-output +16314 0/imm32/no-imm32 +16315 0/imm32/no-imm8 +16316 0/imm32/no-disp32 +16317 0/imm32/output-is-write-only +16318 0x11/imm32/alloc-id:fake +16319 _Primitive-subtract-lit-from-reg/imm32/next +16320 _Primitive-subtract-lit-from-reg: # (payload primitive) +16321 0x11/imm32/alloc-id:fake:payload +16322 # var1/reg <- subtract lit => 81 5/subop/subtract var1/rm32 lit/imm32 +16323 0x11/imm32/alloc-id:fake +16324 _string-subtract/imm32/name +16325 0x11/imm32/alloc-id:fake +16326 Single-lit-var/imm32/inouts +16327 0x11/imm32/alloc-id:fake +16328 Single-int-var-in-some-register/imm32/outputs 16329 0x11/imm32/alloc-id:fake -16330 _Primitive-shift-reg-left-by-lit/imm32/next -16331 _Primitive-shift-reg-left-by-lit: # (payload primitive) -16332 0x11/imm32/alloc-id:fake:payload -16333 # var1/reg <- shift-left lit => c1/shift 4/subop/left var1/rm32 lit/imm32 -16334 0x11/imm32/alloc-id:fake -16335 _string-shift-left/imm32/name -16336 0x11/imm32/alloc-id:fake -16337 Single-lit-var/imm32/inouts -16338 0x11/imm32/alloc-id:fake -16339 Single-int-var-in-some-register/imm32/outputs -16340 0x11/imm32/alloc-id:fake -16341 _string_c1_subop_shift_left/imm32/subx-name -16342 3/imm32/rm32-is-first-output -16343 0/imm32/no-r32 -16344 0/imm32/no-imm32 -16345 1/imm32/imm8-is-first-inout -16346 0/imm32/no-disp32 -16347 0/imm32/output-is-write-only +16330 _string_81_subop_subtract/imm32/subx-name +16331 3/imm32/rm32-is-first-output +16332 0/imm32/no-r32 +16333 1/imm32/imm32-is-first-inout +16334 0/imm32/no-imm8 +16335 0/imm32/no-disp32 +16336 0/imm32/output-is-write-only +16337 0x11/imm32/alloc-id:fake +16338 _Primitive-subtract-lit-from-mem/imm32/next +16339 _Primitive-subtract-lit-from-mem: # (payload primitive) +16340 0x11/imm32/alloc-id:fake:payload +16341 # subtract-from var1, lit => 81 5/subop/subtract var1/rm32 lit/imm32 +16342 0x11/imm32/alloc-id:fake +16343 _string-subtract-from/imm32/name +16344 0x11/imm32/alloc-id:fake +16345 Int-var-and-literal/imm32/inouts +16346 0/imm32/no-outputs +16347 0/imm32/no-outputs 16348 0x11/imm32/alloc-id:fake -16349 _Primitive-shift-reg-right-by-lit/imm32/next -16350 _Primitive-shift-reg-right-by-lit: # (payload primitive) -16351 0x11/imm32/alloc-id:fake:payload -16352 # var1/reg <- shift-right lit => c1/shift 5/subop/right var1/rm32 lit/imm32 -16353 0x11/imm32/alloc-id:fake -16354 _string-shift-right/imm32/name -16355 0x11/imm32/alloc-id:fake -16356 Single-lit-var/imm32/inouts -16357 0x11/imm32/alloc-id:fake -16358 Single-int-var-in-some-register/imm32/outputs -16359 0x11/imm32/alloc-id:fake -16360 _string_c1_subop_shift_right_padding_zeroes/imm32/subx-name -16361 3/imm32/rm32-is-first-output -16362 0/imm32/no-r32 -16363 0/imm32/no-imm32 -16364 1/imm32/imm8-is-first-inout -16365 0/imm32/no-disp32 -16366 0/imm32/output-is-write-only -16367 0x11/imm32/alloc-id:fake -16368 _Primitive-shift-reg-right-signed-by-lit/imm32/next -16369 _Primitive-shift-reg-right-signed-by-lit: # (payload primitive) -16370 0x11/imm32/alloc-id:fake:payload -16371 # var1/reg <- shift-right-signed lit => c1/shift 7/subop/right-preserving-sign var1/rm32 lit/imm32 -16372 0x11/imm32/alloc-id:fake -16373 _string-shift-right-signed/imm32/name -16374 0x11/imm32/alloc-id:fake -16375 Single-lit-var/imm32/inouts +16349 _string_81_subop_subtract/imm32/subx-name +16350 1/imm32/rm32-is-first-inout +16351 0/imm32/no-r32 +16352 2/imm32/imm32-is-second-inout +16353 0/imm32/no-imm8 +16354 0/imm32/no-disp32 +16355 0/imm32/output-is-write-only +16356 0x11/imm32/alloc-id:fake +16357 _Primitive-and-with-eax/imm32/next +16358 # - and +16359 _Primitive-and-with-eax: # (payload primitive) +16360 0x11/imm32/alloc-id:fake:payload +16361 # var/eax <- and lit => 25/and-with-eax lit/imm32 +16362 0x11/imm32/alloc-id:fake +16363 _string-and/imm32/name +16364 0x11/imm32/alloc-id:fake +16365 Single-lit-var/imm32/inouts +16366 0x11/imm32/alloc-id:fake +16367 Single-int-var-in-eax/imm32/outputs +16368 0x11/imm32/alloc-id:fake +16369 _string_25_and_with_eax/imm32/subx-name +16370 0/imm32/no-rm32 +16371 0/imm32/no-r32 +16372 1/imm32/imm32-is-first-inout +16373 0/imm32/no-imm8 +16374 0/imm32/no-disp32 +16375 0/imm32/output-is-write-only 16376 0x11/imm32/alloc-id:fake -16377 Single-int-var-in-some-register/imm32/outputs -16378 0x11/imm32/alloc-id:fake -16379 _string_c1_subop_shift_right_preserving_sign/imm32/subx-name -16380 3/imm32/rm32-is-first-output -16381 0/imm32/no-r32 -16382 0/imm32/no-imm32 -16383 1/imm32/imm8-is-first-inout -16384 0/imm32/no-disp32 -16385 0/imm32/output-is-write-only -16386 0x11/imm32/alloc-id:fake -16387 _Primitive-shift-mem-left-by-lit/imm32/next -16388 _Primitive-shift-mem-left-by-lit: # (payload primitive) -16389 0x11/imm32/alloc-id:fake:payload -16390 # shift-left var1, lit => c1/shift 4/subop/left var1/rm32 lit/imm32 -16391 0x11/imm32/alloc-id:fake -16392 _string-shift-left/imm32/name -16393 0x11/imm32/alloc-id:fake -16394 Int-var-and-literal/imm32/inouts -16395 0/imm32/no-outputs -16396 0/imm32/no-outputs -16397 0x11/imm32/alloc-id:fake -16398 _string_c1_subop_shift_left/imm32/subx-name -16399 1/imm32/rm32-is-first-inout -16400 0/imm32/no-r32 -16401 0/imm32/no-imm32 -16402 2/imm32/imm8-is-second-inout -16403 0/imm32/no-disp32 -16404 0/imm32/output-is-write-only -16405 0x11/imm32/alloc-id:fake -16406 _Primitive-shift-mem-right-by-lit/imm32/next -16407 _Primitive-shift-mem-right-by-lit: # (payload primitive) -16408 0x11/imm32/alloc-id:fake:payload -16409 # shift-right var1, lit => c1/shift 5/subop/right var1/rm32 lit/imm32 -16410 0x11/imm32/alloc-id:fake -16411 _string-shift-right/imm32/name -16412 0x11/imm32/alloc-id:fake -16413 Int-var-and-literal/imm32/inouts -16414 0/imm32/no-outputs -16415 0/imm32/no-outputs -16416 0x11/imm32/alloc-id:fake -16417 _string_c1_subop_shift_right_padding_zeroes/imm32/subx-name -16418 1/imm32/rm32-is-first-inout -16419 0/imm32/no-r32 -16420 0/imm32/no-imm32 -16421 2/imm32/imm8-is-second-inout -16422 0/imm32/no-disp32 -16423 0/imm32/output-is-write-only -16424 0x11/imm32/alloc-id:fake -16425 _Primitive-shift-mem-right-signed-by-lit/imm32/next -16426 _Primitive-shift-mem-right-signed-by-lit: # (payload primitive) -16427 0x11/imm32/alloc-id:fake:payload -16428 # shift-right-signed var1, lit => c1/shift 7/subop/right-preserving-sign var1/rm32 lit/imm32 -16429 0x11/imm32/alloc-id:fake -16430 _string-shift-right-signed/imm32/name -16431 0x11/imm32/alloc-id:fake -16432 Int-var-and-literal/imm32/inouts -16433 0/imm32/no-outputs -16434 0/imm32/no-outputs -16435 0x11/imm32/alloc-id:fake -16436 _string_c1_subop_shift_right_preserving_sign/imm32/subx-name -16437 1/imm32/rm32-is-first-inout -16438 0/imm32/no-r32 -16439 0/imm32/no-imm32 -16440 2/imm32/imm8-is-second-inout -16441 0/imm32/no-disp32 -16442 0/imm32/output-is-write-only -16443 0x11/imm32/alloc-id:fake -16444 _Primitive-copy-to-eax/imm32/next -16445 # - copy -16446 _Primitive-copy-to-eax: # (payload primitive) -16447 0x11/imm32/alloc-id:fake:payload -16448 # var/eax <- copy lit => b8/copy-to-eax lit/imm32 -16449 0x11/imm32/alloc-id:fake -16450 _string-copy/imm32/name -16451 0x11/imm32/alloc-id:fake -16452 Single-lit-var/imm32/inouts -16453 0x11/imm32/alloc-id:fake -16454 Single-int-var-in-eax/imm32/outputs -16455 0x11/imm32/alloc-id:fake -16456 _string_b8_copy_to_eax/imm32/subx-name -16457 0/imm32/no-rm32 -16458 0/imm32/no-r32 -16459 1/imm32/imm32-is-first-inout -16460 0/imm32/no-imm8 -16461 0/imm32/no-disp32 -16462 1/imm32/output-is-write-only +16377 _Primitive-and-reg-with-reg/imm32/next +16378 _Primitive-and-reg-with-reg: # (payload primitive) +16379 0x11/imm32/alloc-id:fake:payload +16380 # var1/reg <- and var2/reg => 21/and-with var1/rm32 var2/r32 +16381 0x11/imm32/alloc-id:fake +16382 _string-and/imm32/name +16383 0x11/imm32/alloc-id:fake +16384 Single-int-var-in-some-register/imm32/inouts +16385 0x11/imm32/alloc-id:fake +16386 Single-int-var-in-some-register/imm32/outputs +16387 0x11/imm32/alloc-id:fake +16388 _string_21_and_with/imm32/subx-name +16389 3/imm32/rm32-is-first-output +16390 1/imm32/r32-is-first-inout +16391 0/imm32/no-imm32 +16392 0/imm32/no-imm8 +16393 0/imm32/no-disp32 +16394 0/imm32/output-is-write-only +16395 0x11/imm32/alloc-id:fake +16396 _Primitive-and-reg-with-mem/imm32/next +16397 _Primitive-and-reg-with-mem: # (payload primitive) +16398 0x11/imm32/alloc-id:fake:payload +16399 # and-with var1 var2/reg => 21/and-with var1 var2/r32 +16400 0x11/imm32/alloc-id:fake +16401 _string-and-with/imm32/name +16402 0x11/imm32/alloc-id:fake +16403 Two-args-int-stack-int-reg/imm32/inouts +16404 0/imm32/no-outputs +16405 0/imm32/no-outputs +16406 0x11/imm32/alloc-id:fake +16407 _string_21_and_with/imm32/subx-name +16408 1/imm32/rm32-is-first-inout +16409 2/imm32/r32-is-second-inout +16410 0/imm32/no-imm32 +16411 0/imm32/no-imm8 +16412 0/imm32/no-disp32 +16413 0/imm32/output-is-write-only +16414 0x11/imm32/alloc-id:fake +16415 _Primitive-and-mem-with-reg/imm32/next +16416 _Primitive-and-mem-with-reg: # (payload primitive) +16417 0x11/imm32/alloc-id:fake:payload +16418 # var1/reg <- and var2 => 23/and var2/rm32 var1/r32 +16419 0x11/imm32/alloc-id:fake +16420 _string-and/imm32/name +16421 0x11/imm32/alloc-id:fake +16422 Single-int-var-in-mem/imm32/inouts +16423 0x11/imm32/alloc-id:fake +16424 Single-int-var-in-some-register/imm32/outputs +16425 0x11/imm32/alloc-id:fake +16426 _string_23_and/imm32/subx-name +16427 1/imm32/rm32-is-first-inout +16428 3/imm32/r32-is-first-output +16429 0/imm32/no-imm32 +16430 0/imm32/no-imm8 +16431 0/imm32/no-disp32 +16432 0/imm32/output-is-write-only +16433 0x11/imm32/alloc-id:fake +16434 _Primitive-and-lit-with-reg/imm32/next +16435 _Primitive-and-lit-with-reg: # (payload primitive) +16436 0x11/imm32/alloc-id:fake:payload +16437 # var1/reg <- and lit => 81 4/subop/and var1/rm32 lit/imm32 +16438 0x11/imm32/alloc-id:fake +16439 _string-and/imm32/name +16440 0x11/imm32/alloc-id:fake +16441 Single-lit-var/imm32/inouts +16442 0x11/imm32/alloc-id:fake +16443 Single-int-var-in-some-register/imm32/outputs +16444 0x11/imm32/alloc-id:fake +16445 _string_81_subop_and/imm32/subx-name +16446 3/imm32/rm32-is-first-output +16447 0/imm32/no-r32 +16448 1/imm32/imm32-is-first-inout +16449 0/imm32/no-imm8 +16450 0/imm32/no-disp32 +16451 0/imm32/output-is-write-only +16452 0x11/imm32/alloc-id:fake +16453 _Primitive-and-lit-with-mem/imm32/next +16454 _Primitive-and-lit-with-mem: # (payload primitive) +16455 0x11/imm32/alloc-id:fake:payload +16456 # and-with var1, lit => 81 4/subop/and var1/rm32 lit/imm32 +16457 0x11/imm32/alloc-id:fake +16458 _string-and-with/imm32/name +16459 0x11/imm32/alloc-id:fake +16460 Int-var-and-literal/imm32/inouts +16461 0/imm32/no-outputs +16462 0/imm32/no-outputs 16463 0x11/imm32/alloc-id:fake -16464 _Primitive-copy-to-ecx/imm32/next -16465 _Primitive-copy-to-ecx: # (payload primitive) -16466 0x11/imm32/alloc-id:fake:payload -16467 # var/ecx <- copy lit => b9/copy-to-ecx lit/imm32 -16468 0x11/imm32/alloc-id:fake -16469 _string-copy/imm32/name -16470 0x11/imm32/alloc-id:fake -16471 Single-lit-var/imm32/inouts -16472 0x11/imm32/alloc-id:fake -16473 Single-int-var-in-ecx/imm32/outputs -16474 0x11/imm32/alloc-id:fake -16475 _string_b9_copy_to_ecx/imm32/subx-name -16476 0/imm32/no-rm32 -16477 0/imm32/no-r32 -16478 1/imm32/imm32-is-first-inout -16479 0/imm32/no-imm8 -16480 0/imm32/no-disp32 -16481 1/imm32/output-is-write-only -16482 0x11/imm32/alloc-id:fake -16483 _Primitive-copy-to-edx/imm32/next -16484 _Primitive-copy-to-edx: # (payload primitive) -16485 0x11/imm32/alloc-id:fake:payload -16486 # var/edx <- copy lit => ba/copy-to-edx lit/imm32 -16487 0x11/imm32/alloc-id:fake -16488 _string-copy/imm32/name -16489 0x11/imm32/alloc-id:fake -16490 Single-lit-var/imm32/inouts +16464 _string_81_subop_and/imm32/subx-name +16465 1/imm32/rm32-is-first-inout +16466 0/imm32/no-r32 +16467 2/imm32/imm32-is-second-inout +16468 0/imm32/no-imm8 +16469 0/imm32/no-disp32 +16470 0/imm32/output-is-write-only +16471 0x11/imm32/alloc-id:fake +16472 _Primitive-or-with-eax/imm32/next +16473 # - or +16474 _Primitive-or-with-eax: # (payload primitive) +16475 0x11/imm32/alloc-id:fake:payload +16476 # var/eax <- or lit => 0d/or-with-eax lit/imm32 +16477 0x11/imm32/alloc-id:fake +16478 _string-or/imm32/name +16479 0x11/imm32/alloc-id:fake +16480 Single-lit-var/imm32/inouts +16481 0x11/imm32/alloc-id:fake +16482 Single-int-var-in-eax/imm32/outputs +16483 0x11/imm32/alloc-id:fake +16484 _string_0d_or_with_eax/imm32/subx-name +16485 0/imm32/no-rm32 +16486 0/imm32/no-r32 +16487 1/imm32/imm32-is-first-inout +16488 0/imm32/no-imm8 +16489 0/imm32/no-disp32 +16490 0/imm32/output-is-write-only 16491 0x11/imm32/alloc-id:fake -16492 Single-int-var-in-edx/imm32/outputs -16493 0x11/imm32/alloc-id:fake -16494 _string_ba_copy_to_edx/imm32/subx-name -16495 0/imm32/no-rm32 -16496 0/imm32/no-r32 -16497 1/imm32/imm32-is-first-inout -16498 0/imm32/no-imm8 -16499 0/imm32/no-disp32 -16500 1/imm32/output-is-write-only -16501 0x11/imm32/alloc-id:fake -16502 _Primitive-copy-to-ebx/imm32/next -16503 _Primitive-copy-to-ebx: # (payload primitive) -16504 0x11/imm32/alloc-id:fake:payload -16505 # var/ebx <- copy lit => bb/copy-to-ebx lit/imm32 -16506 0x11/imm32/alloc-id:fake -16507 _string-copy/imm32/name -16508 0x11/imm32/alloc-id:fake -16509 Single-lit-var/imm32/inouts +16492 _Primitive-or-reg-with-reg/imm32/next +16493 _Primitive-or-reg-with-reg: # (payload primitive) +16494 0x11/imm32/alloc-id:fake:payload +16495 # var1/reg <- or var2/reg => 09/or-with var1/rm32 var2/r32 +16496 0x11/imm32/alloc-id:fake +16497 _string-or/imm32/name +16498 0x11/imm32/alloc-id:fake +16499 Single-int-var-in-some-register/imm32/inouts +16500 0x11/imm32/alloc-id:fake +16501 Single-int-var-in-some-register/imm32/outputs +16502 0x11/imm32/alloc-id:fake +16503 _string_09_or_with/imm32/subx-name +16504 3/imm32/rm32-is-first-output +16505 1/imm32/r32-is-first-inout +16506 0/imm32/no-imm32 +16507 0/imm32/no-imm8 +16508 0/imm32/no-disp32 +16509 0/imm32/output-is-write-only 16510 0x11/imm32/alloc-id:fake -16511 Single-int-var-in-ebx/imm32/outputs -16512 0x11/imm32/alloc-id:fake -16513 _string_bb_copy_to_ebx/imm32/subx-name -16514 0/imm32/no-rm32 -16515 0/imm32/no-r32 -16516 1/imm32/imm32-is-first-inout -16517 0/imm32/no-imm8 -16518 0/imm32/no-disp32 -16519 1/imm32/output-is-write-only -16520 0x11/imm32/alloc-id:fake -16521 _Primitive-copy-to-esi/imm32/next -16522 _Primitive-copy-to-esi: # (payload primitive) -16523 0x11/imm32/alloc-id:fake:payload -16524 # var/esi <- copy lit => be/copy-to-esi lit/imm32 -16525 0x11/imm32/alloc-id:fake -16526 _string-copy/imm32/name -16527 0x11/imm32/alloc-id:fake -16528 Single-lit-var/imm32/inouts +16511 _Primitive-or-reg-with-mem/imm32/next +16512 _Primitive-or-reg-with-mem: # (payload primitive) +16513 0x11/imm32/alloc-id:fake:payload +16514 # or-with var1 var2/reg => 09/or-with var1 var2/r32 +16515 0x11/imm32/alloc-id:fake +16516 _string-or-with/imm32/name +16517 0x11/imm32/alloc-id:fake +16518 Two-args-int-stack-int-reg/imm32/inouts +16519 0/imm32/no-outputs +16520 0/imm32/no-outputs +16521 0x11/imm32/alloc-id:fake +16522 _string_09_or_with/imm32/subx-name +16523 1/imm32/rm32-is-first-inout +16524 2/imm32/r32-is-second-inout +16525 0/imm32/no-imm32 +16526 0/imm32/no-imm8 +16527 0/imm32/no-disp32 +16528 0/imm32/output-is-write-only 16529 0x11/imm32/alloc-id:fake -16530 Single-int-var-in-esi/imm32/outputs -16531 0x11/imm32/alloc-id:fake -16532 _string_be_copy_to_esi/imm32/subx-name -16533 0/imm32/no-rm32 -16534 0/imm32/no-r32 -16535 1/imm32/imm32-is-first-inout -16536 0/imm32/no-imm8 -16537 0/imm32/no-disp32 -16538 1/imm32/output-is-write-only -16539 0x11/imm32/alloc-id:fake -16540 _Primitive-copy-to-edi/imm32/next -16541 _Primitive-copy-to-edi: # (payload primitive) -16542 0x11/imm32/alloc-id:fake:payload -16543 # var/edi <- copy lit => bf/copy-to-edi lit/imm32 -16544 0x11/imm32/alloc-id:fake -16545 _string-copy/imm32/name -16546 0x11/imm32/alloc-id:fake -16547 Single-lit-var/imm32/inouts +16530 _Primitive-or-mem-with-reg/imm32/next +16531 _Primitive-or-mem-with-reg: # (payload primitive) +16532 0x11/imm32/alloc-id:fake:payload +16533 # var1/reg <- or var2 => 0b/or var2/rm32 var1/r32 +16534 0x11/imm32/alloc-id:fake +16535 _string-or/imm32/name +16536 0x11/imm32/alloc-id:fake +16537 Single-int-var-in-mem/imm32/inouts +16538 0x11/imm32/alloc-id:fake +16539 Single-int-var-in-some-register/imm32/outputs +16540 0x11/imm32/alloc-id:fake +16541 _string_0b_or/imm32/subx-name +16542 1/imm32/rm32-is-first-inout +16543 3/imm32/r32-is-first-output +16544 0/imm32/no-imm32 +16545 0/imm32/no-imm8 +16546 0/imm32/no-disp32 +16547 0/imm32/output-is-write-only 16548 0x11/imm32/alloc-id:fake -16549 Single-int-var-in-edi/imm32/outputs -16550 0x11/imm32/alloc-id:fake -16551 _string_bf_copy_to_edi/imm32/subx-name -16552 0/imm32/no-rm32 -16553 0/imm32/no-r32 -16554 1/imm32/imm32-is-first-inout -16555 0/imm32/no-imm8 -16556 0/imm32/no-disp32 -16557 1/imm32/output-is-write-only -16558 0x11/imm32/alloc-id:fake -16559 _Primitive-copy-reg-to-reg/imm32/next -16560 _Primitive-copy-reg-to-reg: # (payload primitive) -16561 0x11/imm32/alloc-id:fake:payload -16562 # var1/reg <- copy var2/reg => 89/<- var1/rm32 var2/r32 -16563 0x11/imm32/alloc-id:fake -16564 _string-copy/imm32/name -16565 0x11/imm32/alloc-id:fake -16566 Single-int-var-in-some-register/imm32/inouts +16549 _Primitive-or-lit-with-reg/imm32/next +16550 _Primitive-or-lit-with-reg: # (payload primitive) +16551 0x11/imm32/alloc-id:fake:payload +16552 # var1/reg <- or lit => 81 1/subop/or var1/rm32 lit/imm32 +16553 0x11/imm32/alloc-id:fake +16554 _string-or/imm32/name +16555 0x11/imm32/alloc-id:fake +16556 Single-lit-var/imm32/inouts +16557 0x11/imm32/alloc-id:fake +16558 Single-int-var-in-some-register/imm32/outputs +16559 0x11/imm32/alloc-id:fake +16560 _string_81_subop_or/imm32/subx-name +16561 3/imm32/rm32-is-first-output +16562 0/imm32/no-r32 +16563 1/imm32/imm32-is-first-inout +16564 0/imm32/no-imm8 +16565 0/imm32/no-disp32 +16566 0/imm32/output-is-write-only 16567 0x11/imm32/alloc-id:fake -16568 Single-int-var-in-some-register/imm32/outputs -16569 0x11/imm32/alloc-id:fake -16570 _string_89_<-/imm32/subx-name -16571 3/imm32/rm32-is-first-output -16572 1/imm32/r32-is-first-inout -16573 0/imm32/no-imm32 -16574 0/imm32/no-imm8 -16575 0/imm32/no-disp32 -16576 1/imm32/output-is-write-only -16577 0x11/imm32/alloc-id:fake -16578 _Primitive-copy-reg-to-mem/imm32/next -16579 _Primitive-copy-reg-to-mem: # (payload primitive) -16580 0x11/imm32/alloc-id:fake:payload -16581 # copy-to var1 var2/reg => 89/<- var1 var2/r32 -16582 0x11/imm32/alloc-id:fake -16583 _string-copy-to/imm32/name -16584 0x11/imm32/alloc-id:fake -16585 Two-args-int-stack-int-reg/imm32/inouts -16586 0/imm32/no-outputs -16587 0/imm32/no-outputs -16588 0x11/imm32/alloc-id:fake -16589 _string_89_<-/imm32/subx-name -16590 1/imm32/rm32-is-first-inout -16591 2/imm32/r32-is-second-inout -16592 0/imm32/no-imm32 -16593 0/imm32/no-imm8 -16594 0/imm32/no-disp32 -16595 1/imm32/output-is-write-only +16568 _Primitive-or-lit-with-mem/imm32/next +16569 _Primitive-or-lit-with-mem: # (payload primitive) +16570 0x11/imm32/alloc-id:fake:payload +16571 # or-with var1, lit => 81 1/subop/or var1/rm32 lit/imm32 +16572 0x11/imm32/alloc-id:fake +16573 _string-or-with/imm32/name +16574 0x11/imm32/alloc-id:fake +16575 Int-var-and-literal/imm32/inouts +16576 0/imm32/no-outputs +16577 0/imm32/no-outputs +16578 0x11/imm32/alloc-id:fake +16579 _string_81_subop_or/imm32/subx-name +16580 1/imm32/rm32-is-first-inout +16581 0/imm32/no-r32 +16582 2/imm32/imm32-is-second-inout +16583 0/imm32/no-imm8 +16584 0/imm32/no-disp32 +16585 0/imm32/output-is-write-only +16586 0x11/imm32/alloc-id:fake +16587 _Primitive-xor-with-eax/imm32/next +16588 # - xor +16589 _Primitive-xor-with-eax: # (payload primitive) +16590 0x11/imm32/alloc-id:fake:payload +16591 # var/eax <- xor lit => 35/xor-with-eax lit/imm32 +16592 0x11/imm32/alloc-id:fake +16593 _string-xor/imm32/name +16594 0x11/imm32/alloc-id:fake +16595 Single-lit-var/imm32/inouts 16596 0x11/imm32/alloc-id:fake -16597 _Primitive-copy-mem-to-reg/imm32/next -16598 _Primitive-copy-mem-to-reg: # (payload primitive) -16599 0x11/imm32/alloc-id:fake:payload -16600 # var1/reg <- copy var2 => 8b/-> var2/rm32 var1/r32 -16601 0x11/imm32/alloc-id:fake -16602 _string-copy/imm32/name -16603 0x11/imm32/alloc-id:fake -16604 Single-int-var-in-mem/imm32/inouts -16605 0x11/imm32/alloc-id:fake -16606 Single-int-var-in-some-register/imm32/outputs -16607 0x11/imm32/alloc-id:fake -16608 _string_8b_->/imm32/subx-name -16609 1/imm32/rm32-is-first-inout -16610 3/imm32/r32-is-first-output -16611 0/imm32/no-imm32 -16612 0/imm32/no-imm8 -16613 0/imm32/no-disp32 -16614 1/imm32/output-is-write-only +16597 Single-int-var-in-eax/imm32/outputs +16598 0x11/imm32/alloc-id:fake +16599 _string_35_xor_with_eax/imm32/subx-name +16600 0/imm32/no-rm32 +16601 0/imm32/no-r32 +16602 1/imm32/imm32-is-first-inout +16603 0/imm32/no-imm8 +16604 0/imm32/no-disp32 +16605 0/imm32/output-is-write-only +16606 0x11/imm32/alloc-id:fake +16607 _Primitive-xor-reg-with-reg/imm32/next +16608 _Primitive-xor-reg-with-reg: # (payload primitive) +16609 0x11/imm32/alloc-id:fake:payload +16610 # var1/reg <- xor var2/reg => 31/xor-with var1/rm32 var2/r32 +16611 0x11/imm32/alloc-id:fake +16612 _string-xor/imm32/name +16613 0x11/imm32/alloc-id:fake +16614 Single-int-var-in-some-register/imm32/inouts 16615 0x11/imm32/alloc-id:fake -16616 _Primitive-copy-lit-to-reg/imm32/next -16617 _Primitive-copy-lit-to-reg: # (payload primitive) -16618 0x11/imm32/alloc-id:fake:payload -16619 # var1/reg <- copy lit => c7 0/subop/copy var1/rm32 lit/imm32 -16620 0x11/imm32/alloc-id:fake -16621 _string-copy/imm32/name -16622 0x11/imm32/alloc-id:fake -16623 Single-lit-var/imm32/inouts -16624 0x11/imm32/alloc-id:fake -16625 Single-int-var-in-some-register/imm32/outputs -16626 0x11/imm32/alloc-id:fake -16627 _string_c7_subop_copy/imm32/subx-name -16628 3/imm32/rm32-is-first-output -16629 0/imm32/no-r32 -16630 1/imm32/imm32-is-first-inout -16631 0/imm32/no-imm8 -16632 0/imm32/no-disp32 -16633 1/imm32/output-is-write-only -16634 0x11/imm32/alloc-id:fake -16635 _Primitive-copy-lit-to-mem/imm32/next -16636 _Primitive-copy-lit-to-mem: # (payload primitive) -16637 0x11/imm32/alloc-id:fake:payload -16638 # copy-to var1, lit => c7 0/subop/copy var1/rm32 lit/imm32 -16639 0x11/imm32/alloc-id:fake -16640 _string-copy-to/imm32/name -16641 0x11/imm32/alloc-id:fake -16642 Int-var-and-literal/imm32/inouts -16643 0/imm32/no-outputs -16644 0/imm32/no-outputs -16645 0x11/imm32/alloc-id:fake -16646 _string_c7_subop_copy/imm32/subx-name -16647 1/imm32/rm32-is-first-inout -16648 0/imm32/no-r32 -16649 2/imm32/imm32-is-second-inout -16650 0/imm32/no-imm8 -16651 0/imm32/no-disp32 -16652 1/imm32/output-is-write-only +16616 Single-int-var-in-some-register/imm32/outputs +16617 0x11/imm32/alloc-id:fake +16618 _string_31_xor_with/imm32/subx-name +16619 3/imm32/rm32-is-first-output +16620 1/imm32/r32-is-first-inout +16621 0/imm32/no-imm32 +16622 0/imm32/no-imm8 +16623 0/imm32/no-disp32 +16624 0/imm32/output-is-write-only +16625 0x11/imm32/alloc-id:fake +16626 _Primitive-xor-reg-with-mem/imm32/next +16627 _Primitive-xor-reg-with-mem: # (payload primitive) +16628 0x11/imm32/alloc-id:fake:payload +16629 # xor-with var1 var2/reg => 31/xor-with var1 var2/r32 +16630 0x11/imm32/alloc-id:fake +16631 _string-xor-with/imm32/name +16632 0x11/imm32/alloc-id:fake +16633 Two-args-int-stack-int-reg/imm32/inouts +16634 0/imm32/no-outputs +16635 0/imm32/no-outputs +16636 0x11/imm32/alloc-id:fake +16637 _string_31_xor_with/imm32/subx-name +16638 1/imm32/rm32-is-first-inout +16639 2/imm32/r32-is-second-inout +16640 0/imm32/no-imm32 +16641 0/imm32/no-imm8 +16642 0/imm32/no-disp32 +16643 0/imm32/output-is-write-only +16644 0x11/imm32/alloc-id:fake +16645 _Primitive-xor-mem-with-reg/imm32/next +16646 _Primitive-xor-mem-with-reg: # (payload primitive) +16647 0x11/imm32/alloc-id:fake:payload +16648 # var1/reg <- xor var2 => 33/xor var2/rm32 var1/r32 +16649 0x11/imm32/alloc-id:fake +16650 _string-xor/imm32/name +16651 0x11/imm32/alloc-id:fake +16652 Single-int-var-in-mem/imm32/inouts 16653 0x11/imm32/alloc-id:fake -16654 _Primitive-copy-byte-from-reg/imm32/next -16655 # - copy byte -16656 _Primitive-copy-byte-from-reg: -16657 0x11/imm32/alloc-id:fake:payload -16658 # var/reg <- copy-byte var2/reg2 => 8a/byte-> %var2 var/r32 -16659 0x11/imm32/alloc-id:fake -16660 _string-copy-byte/imm32/name -16661 0x11/imm32/alloc-id:fake -16662 Single-byte-var-in-some-register/imm32/inouts +16654 Single-int-var-in-some-register/imm32/outputs +16655 0x11/imm32/alloc-id:fake +16656 _string_33_xor/imm32/subx-name +16657 1/imm32/rm32-is-first-inout +16658 3/imm32/r32-is-first-output +16659 0/imm32/no-imm32 +16660 0/imm32/no-imm8 +16661 0/imm32/no-disp32 +16662 0/imm32/output-is-write-only 16663 0x11/imm32/alloc-id:fake -16664 Single-byte-var-in-some-register/imm32/outputs -16665 0x11/imm32/alloc-id:fake -16666 _string_8a_copy_byte/imm32/subx-name -16667 1/imm32/rm32-is-first-inout -16668 3/imm32/r32-is-first-output -16669 0/imm32/no-imm32 -16670 0/imm32/no-imm8 -16671 0/imm32/no-disp32 -16672 1/imm32/output-is-write-only -16673 0x11/imm32/alloc-id:fake -16674 _Primitive-copy-byte-from-mem/imm32/next -16675 _Primitive-copy-byte-from-mem: -16676 0x11/imm32/alloc-id:fake:payload -16677 # var/reg <- copy-byte *var2/reg2 => 8a/byte-> *var2 var/r32 -16678 0x11/imm32/alloc-id:fake -16679 _string-copy-byte/imm32/name -16680 0x11/imm32/alloc-id:fake -16681 Single-byte-var-in-mem/imm32/inouts +16664 _Primitive-xor-lit-with-reg/imm32/next +16665 _Primitive-xor-lit-with-reg: # (payload primitive) +16666 0x11/imm32/alloc-id:fake:payload +16667 # var1/reg <- xor lit => 81 6/subop/xor var1/rm32 lit/imm32 +16668 0x11/imm32/alloc-id:fake +16669 _string-xor/imm32/name +16670 0x11/imm32/alloc-id:fake +16671 Single-lit-var/imm32/inouts +16672 0x11/imm32/alloc-id:fake +16673 Single-int-var-in-some-register/imm32/outputs +16674 0x11/imm32/alloc-id:fake +16675 _string_81_subop_xor/imm32/subx-name +16676 3/imm32/rm32-is-first-output +16677 0/imm32/no-r32 +16678 1/imm32/imm32-is-first-inout +16679 0/imm32/no-imm8 +16680 0/imm32/no-disp32 +16681 0/imm32/output-is-write-only 16682 0x11/imm32/alloc-id:fake -16683 Single-byte-var-in-some-register/imm32/outputs -16684 0x11/imm32/alloc-id:fake -16685 _string_8a_copy_byte/imm32/subx-name -16686 1/imm32/rm32-is-first-inout -16687 3/imm32/r32-is-first-output -16688 0/imm32/no-imm32 -16689 0/imm32/no-imm8 -16690 0/imm32/no-disp32 -16691 1/imm32/output-is-write-only -16692 0x11/imm32/alloc-id:fake -16693 _Primitive-copy-byte-to-mem/imm32/next -16694 _Primitive-copy-byte-to-mem: -16695 0x11/imm32/alloc-id:fake:payload -16696 # copy-byte-to *var1/reg1, var2/reg2 => 88/byte<- *reg1 reg2/r32 -16697 0x11/imm32/alloc-id:fake -16698 _string-copy-byte-to/imm32/name -16699 0x11/imm32/alloc-id:fake -16700 Two-args-byte-stack-byte-reg/imm32/inouts -16701 0/imm32/no-outputs -16702 0/imm32/no-outputs -16703 0x11/imm32/alloc-id:fake -16704 _string_88_copy_byte/imm32/subx-name -16705 1/imm32/rm32-is-first-inout -16706 2/imm32/r32-is-second-inout -16707 0/imm32/no-imm32 -16708 0/imm32/no-imm8 -16709 0/imm32/no-disp32 -16710 0/imm32/output-is-write-only -16711 0x11/imm32/alloc-id:fake -16712 _Primitive-address/imm32/next -16713 # - address -16714 _Primitive-address: # (payload primitive) -16715 0x11/imm32/alloc-id:fake:payload -16716 # var1/reg <- address var2 => 8d/copy-address var2/rm32 var1/r32 -16717 0x11/imm32/alloc-id:fake -16718 _string-address/imm32/name -16719 0x11/imm32/alloc-id:fake -16720 Single-int-var-in-mem/imm32/inouts -16721 0x11/imm32/alloc-id:fake -16722 Single-addr-var-in-some-register/imm32/outputs -16723 0x11/imm32/alloc-id:fake -16724 _string_8d_copy_address/imm32/subx-name -16725 1/imm32/rm32-is-first-inout -16726 3/imm32/r32-is-first-output -16727 0/imm32/no-imm32 -16728 0/imm32/no-imm8 -16729 0/imm32/no-disp32 -16730 1/imm32/output-is-write-only +16683 _Primitive-xor-lit-with-mem/imm32/next +16684 _Primitive-xor-lit-with-mem: # (payload primitive) +16685 0x11/imm32/alloc-id:fake:payload +16686 # xor-with var1, lit => 81 6/subop/xor var1/rm32 lit/imm32 +16687 0x11/imm32/alloc-id:fake +16688 _string-xor-with/imm32/name +16689 0x11/imm32/alloc-id:fake +16690 Int-var-and-literal/imm32/inouts +16691 0/imm32/no-outputs +16692 0/imm32/no-outputs +16693 0x11/imm32/alloc-id:fake +16694 _string_81_subop_xor/imm32/subx-name +16695 1/imm32/rm32-is-first-inout +16696 0/imm32/no-r32 +16697 2/imm32/imm32-is-second-inout +16698 0/imm32/no-imm8 +16699 0/imm32/no-disp32 +16700 0/imm32/output-is-write-only +16701 0x11/imm32/alloc-id:fake +16702 _Primitive-shift-reg-left-by-lit/imm32/next +16703 _Primitive-shift-reg-left-by-lit: # (payload primitive) +16704 0x11/imm32/alloc-id:fake:payload +16705 # var1/reg <- shift-left lit => c1/shift 4/subop/left var1/rm32 lit/imm32 +16706 0x11/imm32/alloc-id:fake +16707 _string-shift-left/imm32/name +16708 0x11/imm32/alloc-id:fake +16709 Single-lit-var/imm32/inouts +16710 0x11/imm32/alloc-id:fake +16711 Single-int-var-in-some-register/imm32/outputs +16712 0x11/imm32/alloc-id:fake +16713 _string_c1_subop_shift_left/imm32/subx-name +16714 3/imm32/rm32-is-first-output +16715 0/imm32/no-r32 +16716 0/imm32/no-imm32 +16717 1/imm32/imm8-is-first-inout +16718 0/imm32/no-disp32 +16719 0/imm32/output-is-write-only +16720 0x11/imm32/alloc-id:fake +16721 _Primitive-shift-reg-right-by-lit/imm32/next +16722 _Primitive-shift-reg-right-by-lit: # (payload primitive) +16723 0x11/imm32/alloc-id:fake:payload +16724 # var1/reg <- shift-right lit => c1/shift 5/subop/right var1/rm32 lit/imm32 +16725 0x11/imm32/alloc-id:fake +16726 _string-shift-right/imm32/name +16727 0x11/imm32/alloc-id:fake +16728 Single-lit-var/imm32/inouts +16729 0x11/imm32/alloc-id:fake +16730 Single-int-var-in-some-register/imm32/outputs 16731 0x11/imm32/alloc-id:fake -16732 _Primitive-compare-reg-with-reg/imm32/next -16733 # - compare -16734 _Primitive-compare-reg-with-reg: # (payload primitive) -16735 0x11/imm32/alloc-id:fake:payload -16736 # compare var1/reg1 var2/reg2 => 39/compare var1/rm32 var2/r32 -16737 0x11/imm32/alloc-id:fake -16738 _string-compare/imm32/name +16732 _string_c1_subop_shift_right_padding_zeroes/imm32/subx-name +16733 3/imm32/rm32-is-first-output +16734 0/imm32/no-r32 +16735 0/imm32/no-imm32 +16736 1/imm32/imm8-is-first-inout +16737 0/imm32/no-disp32 +16738 0/imm32/output-is-write-only 16739 0x11/imm32/alloc-id:fake -16740 Two-int-args-in-regs/imm32/inouts -16741 0/imm32/no-outputs -16742 0/imm32/no-outputs -16743 0x11/imm32/alloc-id:fake -16744 _string_39_compare->/imm32/subx-name -16745 1/imm32/rm32-is-first-inout -16746 2/imm32/r32-is-second-inout -16747 0/imm32/no-imm32 -16748 0/imm32/no-imm8 -16749 0/imm32/no-disp32 -16750 0/imm32/output-is-write-only -16751 0x11/imm32/alloc-id:fake -16752 _Primitive-compare-mem-with-reg/imm32/next -16753 _Primitive-compare-mem-with-reg: # (payload primitive) -16754 0x11/imm32/alloc-id:fake:payload -16755 # compare var1 var2/reg => 39/compare var1/rm32 var2/r32 -16756 0x11/imm32/alloc-id:fake -16757 _string-compare/imm32/name +16740 _Primitive-shift-reg-right-signed-by-lit/imm32/next +16741 _Primitive-shift-reg-right-signed-by-lit: # (payload primitive) +16742 0x11/imm32/alloc-id:fake:payload +16743 # var1/reg <- shift-right-signed lit => c1/shift 7/subop/right-preserving-sign var1/rm32 lit/imm32 +16744 0x11/imm32/alloc-id:fake +16745 _string-shift-right-signed/imm32/name +16746 0x11/imm32/alloc-id:fake +16747 Single-lit-var/imm32/inouts +16748 0x11/imm32/alloc-id:fake +16749 Single-int-var-in-some-register/imm32/outputs +16750 0x11/imm32/alloc-id:fake +16751 _string_c1_subop_shift_right_preserving_sign/imm32/subx-name +16752 3/imm32/rm32-is-first-output +16753 0/imm32/no-r32 +16754 0/imm32/no-imm32 +16755 1/imm32/imm8-is-first-inout +16756 0/imm32/no-disp32 +16757 0/imm32/output-is-write-only 16758 0x11/imm32/alloc-id:fake -16759 Two-args-int-stack-int-reg/imm32/inouts -16760 0/imm32/no-outputs -16761 0/imm32/no-outputs -16762 0x11/imm32/alloc-id:fake -16763 _string_39_compare->/imm32/subx-name -16764 1/imm32/rm32-is-first-inout -16765 2/imm32/r32-is-second-inout -16766 0/imm32/no-imm32 -16767 0/imm32/no-imm8 -16768 0/imm32/no-disp32 -16769 0/imm32/output-is-write-only -16770 0x11/imm32/alloc-id:fake -16771 _Primitive-compare-reg-with-mem/imm32/next -16772 _Primitive-compare-reg-with-mem: # (payload primitive) -16773 0x11/imm32/alloc-id:fake:payload -16774 # compare var1/reg var2 => 3b/compare<- var2/rm32 var1/r32 -16775 0x11/imm32/alloc-id:fake -16776 _string-compare/imm32/name +16759 _Primitive-shift-mem-left-by-lit/imm32/next +16760 _Primitive-shift-mem-left-by-lit: # (payload primitive) +16761 0x11/imm32/alloc-id:fake:payload +16762 # shift-left var1, lit => c1/shift 4/subop/left var1/rm32 lit/imm32 +16763 0x11/imm32/alloc-id:fake +16764 _string-shift-left/imm32/name +16765 0x11/imm32/alloc-id:fake +16766 Int-var-and-literal/imm32/inouts +16767 0/imm32/no-outputs +16768 0/imm32/no-outputs +16769 0x11/imm32/alloc-id:fake +16770 _string_c1_subop_shift_left/imm32/subx-name +16771 1/imm32/rm32-is-first-inout +16772 0/imm32/no-r32 +16773 0/imm32/no-imm32 +16774 2/imm32/imm8-is-second-inout +16775 0/imm32/no-disp32 +16776 0/imm32/output-is-write-only 16777 0x11/imm32/alloc-id:fake -16778 Two-args-int-reg-int-stack/imm32/inouts -16779 0/imm32/no-outputs -16780 0/imm32/no-outputs -16781 0x11/imm32/alloc-id:fake -16782 _string_3b_compare<-/imm32/subx-name -16783 2/imm32/rm32-is-second-inout -16784 1/imm32/r32-is-first-inout -16785 0/imm32/no-imm32 -16786 0/imm32/no-imm8 -16787 0/imm32/no-disp32 -16788 0/imm32/output-is-write-only -16789 0x11/imm32/alloc-id:fake -16790 _Primitive-compare-eax-with-literal/imm32/next -16791 _Primitive-compare-eax-with-literal: # (payload primitive) -16792 0x11/imm32/alloc-id:fake:payload -16793 # compare var1/eax n => 3d/compare-eax-with n/imm32 -16794 0x11/imm32/alloc-id:fake -16795 _string-compare/imm32/name +16778 _Primitive-shift-mem-right-by-lit/imm32/next +16779 _Primitive-shift-mem-right-by-lit: # (payload primitive) +16780 0x11/imm32/alloc-id:fake:payload +16781 # shift-right var1, lit => c1/shift 5/subop/right var1/rm32 lit/imm32 +16782 0x11/imm32/alloc-id:fake +16783 _string-shift-right/imm32/name +16784 0x11/imm32/alloc-id:fake +16785 Int-var-and-literal/imm32/inouts +16786 0/imm32/no-outputs +16787 0/imm32/no-outputs +16788 0x11/imm32/alloc-id:fake +16789 _string_c1_subop_shift_right_padding_zeroes/imm32/subx-name +16790 1/imm32/rm32-is-first-inout +16791 0/imm32/no-r32 +16792 0/imm32/no-imm32 +16793 2/imm32/imm8-is-second-inout +16794 0/imm32/no-disp32 +16795 0/imm32/output-is-write-only 16796 0x11/imm32/alloc-id:fake -16797 Two-args-int-eax-int-literal/imm32/inouts -16798 0/imm32/no-outputs -16799 0/imm32/no-outputs -16800 0x11/imm32/alloc-id:fake -16801 _string_3d_compare_eax_with/imm32/subx-name -16802 0/imm32/no-rm32 -16803 0/imm32/no-r32 -16804 2/imm32/imm32-is-second-inout -16805 0/imm32/no-imm8 -16806 0/imm32/no-disp32 -16807 0/imm32/output-is-write-only -16808 0x11/imm32/alloc-id:fake -16809 _Primitive-compare-reg-with-literal/imm32/next -16810 _Primitive-compare-reg-with-literal: # (payload primitive) -16811 0x11/imm32/alloc-id:fake:payload -16812 # compare var1/reg n => 81 7/subop/compare %reg n/imm32 -16813 0x11/imm32/alloc-id:fake -16814 _string-compare/imm32/name +16797 _Primitive-shift-mem-right-signed-by-lit/imm32/next +16798 _Primitive-shift-mem-right-signed-by-lit: # (payload primitive) +16799 0x11/imm32/alloc-id:fake:payload +16800 # shift-right-signed var1, lit => c1/shift 7/subop/right-preserving-sign var1/rm32 lit/imm32 +16801 0x11/imm32/alloc-id:fake +16802 _string-shift-right-signed/imm32/name +16803 0x11/imm32/alloc-id:fake +16804 Int-var-and-literal/imm32/inouts +16805 0/imm32/no-outputs +16806 0/imm32/no-outputs +16807 0x11/imm32/alloc-id:fake +16808 _string_c1_subop_shift_right_preserving_sign/imm32/subx-name +16809 1/imm32/rm32-is-first-inout +16810 0/imm32/no-r32 +16811 0/imm32/no-imm32 +16812 2/imm32/imm8-is-second-inout +16813 0/imm32/no-disp32 +16814 0/imm32/output-is-write-only 16815 0x11/imm32/alloc-id:fake -16816 Int-var-in-register-and-literal/imm32/inouts -16817 0/imm32/no-outputs -16818 0/imm32/no-outputs -16819 0x11/imm32/alloc-id:fake -16820 _string_81_subop_compare/imm32/subx-name -16821 1/imm32/rm32-is-first-inout -16822 0/imm32/no-r32 -16823 2/imm32/imm32-is-second-inout -16824 0/imm32/no-imm8 -16825 0/imm32/no-disp32 -16826 0/imm32/output-is-write-only +16816 _Primitive-copy-to-eax/imm32/next +16817 # - copy +16818 _Primitive-copy-to-eax: # (payload primitive) +16819 0x11/imm32/alloc-id:fake:payload +16820 # var/eax <- copy lit => b8/copy-to-eax lit/imm32 +16821 0x11/imm32/alloc-id:fake +16822 _string-copy/imm32/name +16823 0x11/imm32/alloc-id:fake +16824 Single-lit-var/imm32/inouts +16825 0x11/imm32/alloc-id:fake +16826 Single-int-var-in-eax/imm32/outputs 16827 0x11/imm32/alloc-id:fake -16828 _Primitive-compare-mem-with-literal/imm32/next -16829 _Primitive-compare-mem-with-literal: # (payload primitive) -16830 0x11/imm32/alloc-id:fake:payload -16831 # compare var1 n => 81 7/subop/compare *(ebp+___) n/imm32 -16832 0x11/imm32/alloc-id:fake -16833 _string-compare/imm32/name -16834 0x11/imm32/alloc-id:fake -16835 Int-var-and-literal/imm32/inouts -16836 0/imm32/no-outputs -16837 0/imm32/no-outputs -16838 0x11/imm32/alloc-id:fake -16839 _string_81_subop_compare/imm32/subx-name -16840 1/imm32/rm32-is-first-inout -16841 0/imm32/no-r32 -16842 2/imm32/imm32-is-second-inout -16843 0/imm32/no-imm8 -16844 0/imm32/no-disp32 -16845 0/imm32/output-is-write-only +16828 _string_b8_copy_to_eax/imm32/subx-name +16829 0/imm32/no-rm32 +16830 0/imm32/no-r32 +16831 1/imm32/imm32-is-first-inout +16832 0/imm32/no-imm8 +16833 0/imm32/no-disp32 +16834 1/imm32/output-is-write-only +16835 0x11/imm32/alloc-id:fake +16836 _Primitive-copy-to-ecx/imm32/next +16837 _Primitive-copy-to-ecx: # (payload primitive) +16838 0x11/imm32/alloc-id:fake:payload +16839 # var/ecx <- copy lit => b9/copy-to-ecx lit/imm32 +16840 0x11/imm32/alloc-id:fake +16841 _string-copy/imm32/name +16842 0x11/imm32/alloc-id:fake +16843 Single-lit-var/imm32/inouts +16844 0x11/imm32/alloc-id:fake +16845 Single-int-var-in-ecx/imm32/outputs 16846 0x11/imm32/alloc-id:fake -16847 _Primitive-multiply-reg-by-reg/imm32/next -16848 # - multiply -16849 _Primitive-multiply-reg-by-reg: # (payload primitive) -16850 0x11/imm32/alloc-id:fake:payload -16851 # var1/reg <- multiply var2 => 0f af/multiply var2/rm32 var1/r32 -16852 0x11/imm32/alloc-id:fake -16853 _string-multiply/imm32/name +16847 _string_b9_copy_to_ecx/imm32/subx-name +16848 0/imm32/no-rm32 +16849 0/imm32/no-r32 +16850 1/imm32/imm32-is-first-inout +16851 0/imm32/no-imm8 +16852 0/imm32/no-disp32 +16853 1/imm32/output-is-write-only 16854 0x11/imm32/alloc-id:fake -16855 Single-int-var-in-some-register/imm32/inouts -16856 0x11/imm32/alloc-id:fake -16857 Single-int-var-in-some-register/imm32/outputs -16858 0x11/imm32/alloc-id:fake -16859 _string_0f_af_multiply/imm32/subx-name -16860 1/imm32/rm32-is-first-inout -16861 3/imm32/r32-is-first-output -16862 0/imm32/no-imm32 -16863 0/imm32/no-imm8 -16864 0/imm32/no-disp32 -16865 0/imm32/output-is-write-only -16866 0x11/imm32/alloc-id:fake -16867 _Primitive-multiply-reg-by-mem/imm32/next -16868 _Primitive-multiply-reg-by-mem: # (payload primitive) -16869 0x11/imm32/alloc-id:fake:payload -16870 # var1/reg <- multiply var2 => 0f af/multiply var2/rm32 var1/r32 -16871 0x11/imm32/alloc-id:fake -16872 _string-multiply/imm32/name +16855 _Primitive-copy-to-edx/imm32/next +16856 _Primitive-copy-to-edx: # (payload primitive) +16857 0x11/imm32/alloc-id:fake:payload +16858 # var/edx <- copy lit => ba/copy-to-edx lit/imm32 +16859 0x11/imm32/alloc-id:fake +16860 _string-copy/imm32/name +16861 0x11/imm32/alloc-id:fake +16862 Single-lit-var/imm32/inouts +16863 0x11/imm32/alloc-id:fake +16864 Single-int-var-in-edx/imm32/outputs +16865 0x11/imm32/alloc-id:fake +16866 _string_ba_copy_to_edx/imm32/subx-name +16867 0/imm32/no-rm32 +16868 0/imm32/no-r32 +16869 1/imm32/imm32-is-first-inout +16870 0/imm32/no-imm8 +16871 0/imm32/no-disp32 +16872 1/imm32/output-is-write-only 16873 0x11/imm32/alloc-id:fake -16874 Single-int-var-in-mem/imm32/inouts -16875 0x11/imm32/alloc-id:fake -16876 Single-int-var-in-some-register/imm32/outputs -16877 0x11/imm32/alloc-id:fake -16878 _string_0f_af_multiply/imm32/subx-name -16879 1/imm32/rm32-is-first-inout -16880 3/imm32/r32-is-first-output -16881 0/imm32/no-imm32 -16882 0/imm32/no-imm8 -16883 0/imm32/no-disp32 -16884 0/imm32/output-is-write-only -16885 0x11/imm32/alloc-id:fake -16886 _Primitive-break-if-addr</imm32/next -16887 # - branches -16888 _Primitive-break-if-addr<: # (payload primitive) -16889 0x11/imm32/alloc-id:fake:payload -16890 0x11/imm32/alloc-id:fake -16891 _string-break-if-addr</imm32/name -16892 0/imm32/no-inouts -16893 0/imm32/no-inouts -16894 0/imm32/no-outputs -16895 0/imm32/no-outputs -16896 0x11/imm32/alloc-id:fake -16897 _string_0f_82_jump_break/imm32/subx-name -16898 0/imm32/no-rm32 -16899 0/imm32/no-r32 -16900 0/imm32/no-imm32 -16901 0/imm32/no-imm8 -16902 0/imm32/no-disp32 -16903 0/imm32/no-output -16904 0x11/imm32/alloc-id:fake -16905 _Primitive-break-if-addr>=/imm32/next -16906 _Primitive-break-if-addr>=: # (payload primitive) -16907 0x11/imm32/alloc-id:fake:payload -16908 0x11/imm32/alloc-id:fake -16909 _string-break-if-addr>=/imm32/name -16910 0/imm32/no-inouts -16911 0/imm32/no-inouts -16912 0/imm32/no-outputs -16913 0/imm32/no-outputs -16914 0x11/imm32/alloc-id:fake -16915 _string_0f_83_jump_break/imm32/subx-name -16916 0/imm32/no-rm32 -16917 0/imm32/no-r32 -16918 0/imm32/no-imm32 -16919 0/imm32/no-imm8 -16920 0/imm32/no-disp32 -16921 0/imm32/no-output +16874 _Primitive-copy-to-ebx/imm32/next +16875 _Primitive-copy-to-ebx: # (payload primitive) +16876 0x11/imm32/alloc-id:fake:payload +16877 # var/ebx <- copy lit => bb/copy-to-ebx lit/imm32 +16878 0x11/imm32/alloc-id:fake +16879 _string-copy/imm32/name +16880 0x11/imm32/alloc-id:fake +16881 Single-lit-var/imm32/inouts +16882 0x11/imm32/alloc-id:fake +16883 Single-int-var-in-ebx/imm32/outputs +16884 0x11/imm32/alloc-id:fake +16885 _string_bb_copy_to_ebx/imm32/subx-name +16886 0/imm32/no-rm32 +16887 0/imm32/no-r32 +16888 1/imm32/imm32-is-first-inout +16889 0/imm32/no-imm8 +16890 0/imm32/no-disp32 +16891 1/imm32/output-is-write-only +16892 0x11/imm32/alloc-id:fake +16893 _Primitive-copy-to-esi/imm32/next +16894 _Primitive-copy-to-esi: # (payload primitive) +16895 0x11/imm32/alloc-id:fake:payload +16896 # var/esi <- copy lit => be/copy-to-esi lit/imm32 +16897 0x11/imm32/alloc-id:fake +16898 _string-copy/imm32/name +16899 0x11/imm32/alloc-id:fake +16900 Single-lit-var/imm32/inouts +16901 0x11/imm32/alloc-id:fake +16902 Single-int-var-in-esi/imm32/outputs +16903 0x11/imm32/alloc-id:fake +16904 _string_be_copy_to_esi/imm32/subx-name +16905 0/imm32/no-rm32 +16906 0/imm32/no-r32 +16907 1/imm32/imm32-is-first-inout +16908 0/imm32/no-imm8 +16909 0/imm32/no-disp32 +16910 1/imm32/output-is-write-only +16911 0x11/imm32/alloc-id:fake +16912 _Primitive-copy-to-edi/imm32/next +16913 _Primitive-copy-to-edi: # (payload primitive) +16914 0x11/imm32/alloc-id:fake:payload +16915 # var/edi <- copy lit => bf/copy-to-edi lit/imm32 +16916 0x11/imm32/alloc-id:fake +16917 _string-copy/imm32/name +16918 0x11/imm32/alloc-id:fake +16919 Single-lit-var/imm32/inouts +16920 0x11/imm32/alloc-id:fake +16921 Single-int-var-in-edi/imm32/outputs 16922 0x11/imm32/alloc-id:fake -16923 _Primitive-break-if-=/imm32/next -16924 _Primitive-break-if-=: # (payload primitive) -16925 0x11/imm32/alloc-id:fake:payload -16926 0x11/imm32/alloc-id:fake -16927 _string-break-if-=/imm32/name -16928 0/imm32/no-inouts -16929 0/imm32/no-inouts -16930 0/imm32/no-outputs -16931 0/imm32/no-outputs -16932 0x11/imm32/alloc-id:fake -16933 _string_0f_84_jump_break/imm32/subx-name -16934 0/imm32/no-rm32 -16935 0/imm32/no-r32 -16936 0/imm32/no-imm32 -16937 0/imm32/no-imm8 -16938 0/imm32/no-disp32 -16939 0/imm32/no-output -16940 0x11/imm32/alloc-id:fake -16941 _Primitive-break-if-!=/imm32/next -16942 _Primitive-break-if-!=: # (payload primitive) -16943 0x11/imm32/alloc-id:fake:payload -16944 0x11/imm32/alloc-id:fake -16945 _string-break-if-!=/imm32/name -16946 0/imm32/no-inouts -16947 0/imm32/no-inouts -16948 0/imm32/no-outputs -16949 0/imm32/no-outputs -16950 0x11/imm32/alloc-id:fake -16951 _string_0f_85_jump_break/imm32/subx-name -16952 0/imm32/no-rm32 -16953 0/imm32/no-r32 -16954 0/imm32/no-imm32 -16955 0/imm32/no-imm8 -16956 0/imm32/no-disp32 -16957 0/imm32/no-output -16958 0x11/imm32/alloc-id:fake -16959 _Primitive-break-if-addr<=/imm32/next -16960 _Primitive-break-if-addr<=: # (payload primitive) -16961 0x11/imm32/alloc-id:fake:payload -16962 0x11/imm32/alloc-id:fake -16963 _string-break-if-addr<=/imm32/name -16964 0/imm32/no-inouts -16965 0/imm32/no-inouts -16966 0/imm32/no-outputs -16967 0/imm32/no-outputs +16923 _string_bf_copy_to_edi/imm32/subx-name +16924 0/imm32/no-rm32 +16925 0/imm32/no-r32 +16926 1/imm32/imm32-is-first-inout +16927 0/imm32/no-imm8 +16928 0/imm32/no-disp32 +16929 1/imm32/output-is-write-only +16930 0x11/imm32/alloc-id:fake +16931 _Primitive-copy-reg-to-reg/imm32/next +16932 _Primitive-copy-reg-to-reg: # (payload primitive) +16933 0x11/imm32/alloc-id:fake:payload +16934 # var1/reg <- copy var2/reg => 89/<- var1/rm32 var2/r32 +16935 0x11/imm32/alloc-id:fake +16936 _string-copy/imm32/name +16937 0x11/imm32/alloc-id:fake +16938 Single-int-var-in-some-register/imm32/inouts +16939 0x11/imm32/alloc-id:fake +16940 Single-int-var-in-some-register/imm32/outputs +16941 0x11/imm32/alloc-id:fake +16942 _string_89_<-/imm32/subx-name +16943 3/imm32/rm32-is-first-output +16944 1/imm32/r32-is-first-inout +16945 0/imm32/no-imm32 +16946 0/imm32/no-imm8 +16947 0/imm32/no-disp32 +16948 1/imm32/output-is-write-only +16949 0x11/imm32/alloc-id:fake +16950 _Primitive-copy-reg-to-mem/imm32/next +16951 _Primitive-copy-reg-to-mem: # (payload primitive) +16952 0x11/imm32/alloc-id:fake:payload +16953 # copy-to var1 var2/reg => 89/<- var1 var2/r32 +16954 0x11/imm32/alloc-id:fake +16955 _string-copy-to/imm32/name +16956 0x11/imm32/alloc-id:fake +16957 Two-args-int-stack-int-reg/imm32/inouts +16958 0/imm32/no-outputs +16959 0/imm32/no-outputs +16960 0x11/imm32/alloc-id:fake +16961 _string_89_<-/imm32/subx-name +16962 1/imm32/rm32-is-first-inout +16963 2/imm32/r32-is-second-inout +16964 0/imm32/no-imm32 +16965 0/imm32/no-imm8 +16966 0/imm32/no-disp32 +16967 1/imm32/output-is-write-only 16968 0x11/imm32/alloc-id:fake -16969 _string_0f_86_jump_break/imm32/subx-name -16970 0/imm32/no-rm32 -16971 0/imm32/no-r32 -16972 0/imm32/no-imm32 -16973 0/imm32/no-imm8 -16974 0/imm32/no-disp32 -16975 0/imm32/no-output -16976 0x11/imm32/alloc-id:fake -16977 _Primitive-break-if-addr>/imm32/next -16978 _Primitive-break-if-addr>: # (payload primitive) -16979 0x11/imm32/alloc-id:fake:payload -16980 0x11/imm32/alloc-id:fake -16981 _string-break-if-addr>/imm32/name -16982 0/imm32/no-inouts -16983 0/imm32/no-inouts -16984 0/imm32/no-outputs -16985 0/imm32/no-outputs -16986 0x11/imm32/alloc-id:fake -16987 _string_0f_87_jump_break/imm32/subx-name -16988 0/imm32/no-rm32 -16989 0/imm32/no-r32 -16990 0/imm32/no-imm32 -16991 0/imm32/no-imm8 -16992 0/imm32/no-disp32 -16993 0/imm32/no-output +16969 _Primitive-copy-mem-to-reg/imm32/next +16970 _Primitive-copy-mem-to-reg: # (payload primitive) +16971 0x11/imm32/alloc-id:fake:payload +16972 # var1/reg <- copy var2 => 8b/-> var2/rm32 var1/r32 +16973 0x11/imm32/alloc-id:fake +16974 _string-copy/imm32/name +16975 0x11/imm32/alloc-id:fake +16976 Single-int-var-in-mem/imm32/inouts +16977 0x11/imm32/alloc-id:fake +16978 Single-int-var-in-some-register/imm32/outputs +16979 0x11/imm32/alloc-id:fake +16980 _string_8b_->/imm32/subx-name +16981 1/imm32/rm32-is-first-inout +16982 3/imm32/r32-is-first-output +16983 0/imm32/no-imm32 +16984 0/imm32/no-imm8 +16985 0/imm32/no-disp32 +16986 1/imm32/output-is-write-only +16987 0x11/imm32/alloc-id:fake +16988 _Primitive-copy-lit-to-reg/imm32/next +16989 _Primitive-copy-lit-to-reg: # (payload primitive) +16990 0x11/imm32/alloc-id:fake:payload +16991 # var1/reg <- copy lit => c7 0/subop/copy var1/rm32 lit/imm32 +16992 0x11/imm32/alloc-id:fake +16993 _string-copy/imm32/name 16994 0x11/imm32/alloc-id:fake -16995 _Primitive-break-if-</imm32/next -16996 _Primitive-break-if-<: # (payload primitive) -16997 0x11/imm32/alloc-id:fake:payload +16995 Single-lit-var/imm32/inouts +16996 0x11/imm32/alloc-id:fake +16997 Single-int-var-in-some-register/imm32/outputs 16998 0x11/imm32/alloc-id:fake -16999 _string-break-if-</imm32/name -17000 0/imm32/no-inouts -17001 0/imm32/no-inouts -17002 0/imm32/no-outputs -17003 0/imm32/no-outputs -17004 0x11/imm32/alloc-id:fake -17005 _string_0f_8c_jump_break/imm32/subx-name -17006 0/imm32/no-rm32 -17007 0/imm32/no-r32 -17008 0/imm32/no-imm32 -17009 0/imm32/no-imm8 -17010 0/imm32/no-disp32 -17011 0/imm32/no-output -17012 0x11/imm32/alloc-id:fake -17013 _Primitive-break-if->=/imm32/next -17014 _Primitive-break-if->=: # (payload primitive) -17015 0x11/imm32/alloc-id:fake:payload -17016 0x11/imm32/alloc-id:fake -17017 _string-break-if->=/imm32/name -17018 0/imm32/no-inouts -17019 0/imm32/no-inouts -17020 0/imm32/no-outputs -17021 0/imm32/no-outputs -17022 0x11/imm32/alloc-id:fake -17023 _string_0f_8d_jump_break/imm32/subx-name -17024 0/imm32/no-rm32 -17025 0/imm32/no-r32 -17026 0/imm32/no-imm32 -17027 0/imm32/no-imm8 -17028 0/imm32/no-disp32 -17029 0/imm32/no-output -17030 0x11/imm32/alloc-id:fake -17031 _Primitive-break-if-<=/imm32/next -17032 _Primitive-break-if-<=: # (payload primitive) -17033 0x11/imm32/alloc-id:fake:payload -17034 0x11/imm32/alloc-id:fake -17035 _string-break-if-<=/imm32/name -17036 0/imm32/no-inouts -17037 0/imm32/no-inouts -17038 0/imm32/no-outputs -17039 0/imm32/no-outputs -17040 0x11/imm32/alloc-id:fake -17041 _string_0f_8e_jump_break/imm32/subx-name -17042 0/imm32/no-rm32 -17043 0/imm32/no-r32 -17044 0/imm32/no-imm32 -17045 0/imm32/no-imm8 -17046 0/imm32/no-disp32 -17047 0/imm32/no-output -17048 0x11/imm32/alloc-id:fake -17049 _Primitive-break-if->/imm32/next -17050 _Primitive-break-if->: # (payload primitive) -17051 0x11/imm32/alloc-id:fake:payload +16999 _string_c7_subop_copy/imm32/subx-name +17000 3/imm32/rm32-is-first-output +17001 0/imm32/no-r32 +17002 1/imm32/imm32-is-first-inout +17003 0/imm32/no-imm8 +17004 0/imm32/no-disp32 +17005 1/imm32/output-is-write-only +17006 0x11/imm32/alloc-id:fake +17007 _Primitive-copy-lit-to-mem/imm32/next +17008 _Primitive-copy-lit-to-mem: # (payload primitive) +17009 0x11/imm32/alloc-id:fake:payload +17010 # copy-to var1, lit => c7 0/subop/copy var1/rm32 lit/imm32 +17011 0x11/imm32/alloc-id:fake +17012 _string-copy-to/imm32/name +17013 0x11/imm32/alloc-id:fake +17014 Int-var-and-literal/imm32/inouts +17015 0/imm32/no-outputs +17016 0/imm32/no-outputs +17017 0x11/imm32/alloc-id:fake +17018 _string_c7_subop_copy/imm32/subx-name +17019 1/imm32/rm32-is-first-inout +17020 0/imm32/no-r32 +17021 2/imm32/imm32-is-second-inout +17022 0/imm32/no-imm8 +17023 0/imm32/no-disp32 +17024 1/imm32/output-is-write-only +17025 0x11/imm32/alloc-id:fake +17026 _Primitive-copy-byte-from-reg/imm32/next +17027 # - copy byte +17028 _Primitive-copy-byte-from-reg: +17029 0x11/imm32/alloc-id:fake:payload +17030 # var/reg <- copy-byte var2/reg2 => 8a/byte-> %var2 var/r32 +17031 0x11/imm32/alloc-id:fake +17032 _string-copy-byte/imm32/name +17033 0x11/imm32/alloc-id:fake +17034 Single-byte-var-in-some-register/imm32/inouts +17035 0x11/imm32/alloc-id:fake +17036 Single-byte-var-in-some-register/imm32/outputs +17037 0x11/imm32/alloc-id:fake +17038 _string_8a_copy_byte/imm32/subx-name +17039 1/imm32/rm32-is-first-inout +17040 3/imm32/r32-is-first-output +17041 0/imm32/no-imm32 +17042 0/imm32/no-imm8 +17043 0/imm32/no-disp32 +17044 1/imm32/output-is-write-only +17045 0x11/imm32/alloc-id:fake +17046 _Primitive-copy-byte-from-mem/imm32/next +17047 _Primitive-copy-byte-from-mem: +17048 0x11/imm32/alloc-id:fake:payload +17049 # var/reg <- copy-byte *var2/reg2 => 8a/byte-> *var2 var/r32 +17050 0x11/imm32/alloc-id:fake +17051 _string-copy-byte/imm32/name 17052 0x11/imm32/alloc-id:fake -17053 _string-break-if->/imm32/name -17054 0/imm32/no-inouts -17055 0/imm32/no-inouts -17056 0/imm32/no-outputs -17057 0/imm32/no-outputs -17058 0x11/imm32/alloc-id:fake -17059 _string_0f_8f_jump_break/imm32/subx-name -17060 0/imm32/no-rm32 -17061 0/imm32/no-r32 -17062 0/imm32/no-imm32 -17063 0/imm32/no-imm8 -17064 0/imm32/no-disp32 -17065 0/imm32/no-output -17066 0x11/imm32/alloc-id:fake -17067 _Primitive-break/imm32/next -17068 _Primitive-break: # (payload primitive) -17069 0x11/imm32/alloc-id:fake:payload -17070 0x11/imm32/alloc-id:fake -17071 _string-break/imm32/name -17072 0/imm32/no-inouts -17073 0/imm32/no-inouts +17053 Single-byte-var-in-mem/imm32/inouts +17054 0x11/imm32/alloc-id:fake +17055 Single-byte-var-in-some-register/imm32/outputs +17056 0x11/imm32/alloc-id:fake +17057 _string_8a_copy_byte/imm32/subx-name +17058 1/imm32/rm32-is-first-inout +17059 3/imm32/r32-is-first-output +17060 0/imm32/no-imm32 +17061 0/imm32/no-imm8 +17062 0/imm32/no-disp32 +17063 1/imm32/output-is-write-only +17064 0x11/imm32/alloc-id:fake +17065 _Primitive-copy-byte-to-mem/imm32/next +17066 _Primitive-copy-byte-to-mem: +17067 0x11/imm32/alloc-id:fake:payload +17068 # copy-byte-to *var1/reg1, var2/reg2 => 88/byte<- *reg1 reg2/r32 +17069 0x11/imm32/alloc-id:fake +17070 _string-copy-byte-to/imm32/name +17071 0x11/imm32/alloc-id:fake +17072 Two-args-byte-stack-byte-reg/imm32/inouts +17073 0/imm32/no-outputs 17074 0/imm32/no-outputs -17075 0/imm32/no-outputs -17076 0x11/imm32/alloc-id:fake -17077 _string_e9_jump_break/imm32/subx-name -17078 0/imm32/no-rm32 -17079 0/imm32/no-r32 -17080 0/imm32/no-imm32 -17081 0/imm32/no-imm8 -17082 0/imm32/no-disp32 -17083 0/imm32/no-output -17084 0x11/imm32/alloc-id:fake -17085 _Primitive-loop-if-addr</imm32/next -17086 _Primitive-loop-if-addr<: # (payload primitive) +17075 0x11/imm32/alloc-id:fake +17076 _string_88_copy_byte/imm32/subx-name +17077 1/imm32/rm32-is-first-inout +17078 2/imm32/r32-is-second-inout +17079 0/imm32/no-imm32 +17080 0/imm32/no-imm8 +17081 0/imm32/no-disp32 +17082 0/imm32/output-is-write-only +17083 0x11/imm32/alloc-id:fake +17084 _Primitive-address/imm32/next +17085 # - address +17086 _Primitive-address: # (payload primitive) 17087 0x11/imm32/alloc-id:fake:payload -17088 0x11/imm32/alloc-id:fake -17089 _string-loop-if-addr</imm32/name -17090 0/imm32/no-inouts -17091 0/imm32/no-inouts -17092 0/imm32/no-outputs -17093 0/imm32/no-outputs -17094 0x11/imm32/alloc-id:fake -17095 _string_0f_82_jump_loop/imm32/subx-name -17096 0/imm32/no-rm32 -17097 0/imm32/no-r32 -17098 0/imm32/no-imm32 -17099 0/imm32/no-imm8 -17100 0/imm32/no-disp32 -17101 0/imm32/no-output -17102 0x11/imm32/alloc-id:fake -17103 _Primitive-loop-if-addr>=/imm32/next -17104 _Primitive-loop-if-addr>=: # (payload primitive) -17105 0x11/imm32/alloc-id:fake:payload -17106 0x11/imm32/alloc-id:fake -17107 _string-loop-if-addr>=/imm32/name -17108 0/imm32/no-inouts -17109 0/imm32/no-inouts -17110 0/imm32/no-outputs -17111 0/imm32/no-outputs -17112 0x11/imm32/alloc-id:fake -17113 _string_0f_83_jump_loop/imm32/subx-name -17114 0/imm32/no-rm32 -17115 0/imm32/no-r32 -17116 0/imm32/no-imm32 -17117 0/imm32/no-imm8 -17118 0/imm32/no-disp32 -17119 0/imm32/no-output -17120 0x11/imm32/alloc-id:fake -17121 _Primitive-loop-if-=/imm32/next -17122 _Primitive-loop-if-=: # (payload primitive) -17123 0x11/imm32/alloc-id:fake:payload -17124 0x11/imm32/alloc-id:fake -17125 _string-loop-if-=/imm32/name -17126 0/imm32/no-inouts -17127 0/imm32/no-inouts -17128 0/imm32/no-outputs -17129 0/imm32/no-outputs +17088 # var1/reg <- address var2 => 8d/copy-address var2/rm32 var1/r32 +17089 0x11/imm32/alloc-id:fake +17090 _string-address/imm32/name +17091 0x11/imm32/alloc-id:fake +17092 Single-int-var-in-mem/imm32/inouts +17093 0x11/imm32/alloc-id:fake +17094 Single-addr-var-in-some-register/imm32/outputs +17095 0x11/imm32/alloc-id:fake +17096 _string_8d_copy_address/imm32/subx-name +17097 1/imm32/rm32-is-first-inout +17098 3/imm32/r32-is-first-output +17099 0/imm32/no-imm32 +17100 0/imm32/no-imm8 +17101 0/imm32/no-disp32 +17102 1/imm32/output-is-write-only +17103 0x11/imm32/alloc-id:fake +17104 _Primitive-compare-reg-with-reg/imm32/next +17105 # - compare +17106 _Primitive-compare-reg-with-reg: # (payload primitive) +17107 0x11/imm32/alloc-id:fake:payload +17108 # compare var1/reg1 var2/reg2 => 39/compare var1/rm32 var2/r32 +17109 0x11/imm32/alloc-id:fake +17110 _string-compare/imm32/name +17111 0x11/imm32/alloc-id:fake +17112 Two-int-args-in-regs/imm32/inouts +17113 0/imm32/no-outputs +17114 0/imm32/no-outputs +17115 0x11/imm32/alloc-id:fake +17116 _string_39_compare->/imm32/subx-name +17117 1/imm32/rm32-is-first-inout +17118 2/imm32/r32-is-second-inout +17119 0/imm32/no-imm32 +17120 0/imm32/no-imm8 +17121 0/imm32/no-disp32 +17122 0/imm32/output-is-write-only +17123 0x11/imm32/alloc-id:fake +17124 _Primitive-compare-mem-with-reg/imm32/next +17125 _Primitive-compare-mem-with-reg: # (payload primitive) +17126 0x11/imm32/alloc-id:fake:payload +17127 # compare var1 var2/reg => 39/compare var1/rm32 var2/r32 +17128 0x11/imm32/alloc-id:fake +17129 _string-compare/imm32/name 17130 0x11/imm32/alloc-id:fake -17131 _string_0f_84_jump_loop/imm32/subx-name -17132 0/imm32/no-rm32 -17133 0/imm32/no-r32 -17134 0/imm32/no-imm32 -17135 0/imm32/no-imm8 -17136 0/imm32/no-disp32 -17137 0/imm32/no-output -17138 0x11/imm32/alloc-id:fake -17139 _Primitive-loop-if-!=/imm32/next -17140 _Primitive-loop-if-!=: # (payload primitive) -17141 0x11/imm32/alloc-id:fake:payload +17131 Two-args-int-stack-int-reg/imm32/inouts +17132 0/imm32/no-outputs +17133 0/imm32/no-outputs +17134 0x11/imm32/alloc-id:fake +17135 _string_39_compare->/imm32/subx-name +17136 1/imm32/rm32-is-first-inout +17137 2/imm32/r32-is-second-inout +17138 0/imm32/no-imm32 +17139 0/imm32/no-imm8 +17140 0/imm32/no-disp32 +17141 0/imm32/output-is-write-only 17142 0x11/imm32/alloc-id:fake -17143 _string-loop-if-!=/imm32/name -17144 0/imm32/no-inouts -17145 0/imm32/no-inouts -17146 0/imm32/no-outputs -17147 0/imm32/no-outputs -17148 0x11/imm32/alloc-id:fake -17149 _string_0f_85_jump_loop/imm32/subx-name -17150 0/imm32/no-rm32 -17151 0/imm32/no-r32 -17152 0/imm32/no-imm32 -17153 0/imm32/no-imm8 -17154 0/imm32/no-disp32 -17155 0/imm32/no-output -17156 0x11/imm32/alloc-id:fake -17157 _Primitive-loop-if-addr<=/imm32/next -17158 _Primitive-loop-if-addr<=: # (payload primitive) -17159 0x11/imm32/alloc-id:fake:payload -17160 0x11/imm32/alloc-id:fake -17161 _string-loop-if-addr<=/imm32/name -17162 0/imm32/no-inouts -17163 0/imm32/no-inouts -17164 0/imm32/no-outputs -17165 0/imm32/no-outputs +17143 _Primitive-compare-reg-with-mem/imm32/next +17144 _Primitive-compare-reg-with-mem: # (payload primitive) +17145 0x11/imm32/alloc-id:fake:payload +17146 # compare var1/reg var2 => 3b/compare<- var2/rm32 var1/r32 +17147 0x11/imm32/alloc-id:fake +17148 _string-compare/imm32/name +17149 0x11/imm32/alloc-id:fake +17150 Two-args-int-reg-int-stack/imm32/inouts +17151 0/imm32/no-outputs +17152 0/imm32/no-outputs +17153 0x11/imm32/alloc-id:fake +17154 _string_3b_compare<-/imm32/subx-name +17155 2/imm32/rm32-is-second-inout +17156 1/imm32/r32-is-first-inout +17157 0/imm32/no-imm32 +17158 0/imm32/no-imm8 +17159 0/imm32/no-disp32 +17160 0/imm32/output-is-write-only +17161 0x11/imm32/alloc-id:fake +17162 _Primitive-compare-eax-with-literal/imm32/next +17163 _Primitive-compare-eax-with-literal: # (payload primitive) +17164 0x11/imm32/alloc-id:fake:payload +17165 # compare var1/eax n => 3d/compare-eax-with n/imm32 17166 0x11/imm32/alloc-id:fake -17167 _string_0f_86_jump_loop/imm32/subx-name -17168 0/imm32/no-rm32 -17169 0/imm32/no-r32 -17170 0/imm32/no-imm32 -17171 0/imm32/no-imm8 -17172 0/imm32/no-disp32 -17173 0/imm32/no-output -17174 0x11/imm32/alloc-id:fake -17175 _Primitive-loop-if-addr>/imm32/next -17176 _Primitive-loop-if-addr>: # (payload primitive) -17177 0x11/imm32/alloc-id:fake:payload -17178 0x11/imm32/alloc-id:fake -17179 _string-loop-if-addr>/imm32/name -17180 0/imm32/no-inouts -17181 0/imm32/no-inouts -17182 0/imm32/no-outputs -17183 0/imm32/no-outputs -17184 0x11/imm32/alloc-id:fake -17185 _string_0f_87_jump_loop/imm32/subx-name -17186 0/imm32/no-rm32 -17187 0/imm32/no-r32 -17188 0/imm32/no-imm32 -17189 0/imm32/no-imm8 -17190 0/imm32/no-disp32 -17191 0/imm32/no-output -17192 0x11/imm32/alloc-id:fake -17193 _Primitive-loop-if-</imm32/next -17194 _Primitive-loop-if-<: # (payload primitive) -17195 0x11/imm32/alloc-id:fake:payload -17196 0x11/imm32/alloc-id:fake -17197 _string-loop-if-</imm32/name -17198 0/imm32/no-inouts -17199 0/imm32/no-inouts -17200 0/imm32/no-outputs -17201 0/imm32/no-outputs -17202 0x11/imm32/alloc-id:fake -17203 _string_0f_8c_jump_loop/imm32/subx-name -17204 0/imm32/no-rm32 -17205 0/imm32/no-r32 -17206 0/imm32/no-imm32 -17207 0/imm32/no-imm8 -17208 0/imm32/no-disp32 -17209 0/imm32/no-output +17167 _string-compare/imm32/name +17168 0x11/imm32/alloc-id:fake +17169 Two-args-int-eax-int-literal/imm32/inouts +17170 0/imm32/no-outputs +17171 0/imm32/no-outputs +17172 0x11/imm32/alloc-id:fake +17173 _string_3d_compare_eax_with/imm32/subx-name +17174 0/imm32/no-rm32 +17175 0/imm32/no-r32 +17176 2/imm32/imm32-is-second-inout +17177 0/imm32/no-imm8 +17178 0/imm32/no-disp32 +17179 0/imm32/output-is-write-only +17180 0x11/imm32/alloc-id:fake +17181 _Primitive-compare-reg-with-literal/imm32/next +17182 _Primitive-compare-reg-with-literal: # (payload primitive) +17183 0x11/imm32/alloc-id:fake:payload +17184 # compare var1/reg n => 81 7/subop/compare %reg n/imm32 +17185 0x11/imm32/alloc-id:fake +17186 _string-compare/imm32/name +17187 0x11/imm32/alloc-id:fake +17188 Int-var-in-register-and-literal/imm32/inouts +17189 0/imm32/no-outputs +17190 0/imm32/no-outputs +17191 0x11/imm32/alloc-id:fake +17192 _string_81_subop_compare/imm32/subx-name +17193 1/imm32/rm32-is-first-inout +17194 0/imm32/no-r32 +17195 2/imm32/imm32-is-second-inout +17196 0/imm32/no-imm8 +17197 0/imm32/no-disp32 +17198 0/imm32/output-is-write-only +17199 0x11/imm32/alloc-id:fake +17200 _Primitive-compare-mem-with-literal/imm32/next +17201 _Primitive-compare-mem-with-literal: # (payload primitive) +17202 0x11/imm32/alloc-id:fake:payload +17203 # compare var1 n => 81 7/subop/compare *(ebp+___) n/imm32 +17204 0x11/imm32/alloc-id:fake +17205 _string-compare/imm32/name +17206 0x11/imm32/alloc-id:fake +17207 Int-var-and-literal/imm32/inouts +17208 0/imm32/no-outputs +17209 0/imm32/no-outputs 17210 0x11/imm32/alloc-id:fake -17211 _Primitive-loop-if->=/imm32/next -17212 _Primitive-loop-if->=: # (payload primitive) -17213 0x11/imm32/alloc-id:fake:payload -17214 0x11/imm32/alloc-id:fake -17215 _string-loop-if->=/imm32/name -17216 0/imm32/no-inouts -17217 0/imm32/no-inouts -17218 0/imm32/no-outputs -17219 0/imm32/no-outputs -17220 0x11/imm32/alloc-id:fake -17221 _string_0f_8d_jump_loop/imm32/subx-name -17222 0/imm32/no-rm32 -17223 0/imm32/no-r32 -17224 0/imm32/no-imm32 -17225 0/imm32/no-imm8 -17226 0/imm32/no-disp32 -17227 0/imm32/no-output +17211 _string_81_subop_compare/imm32/subx-name +17212 1/imm32/rm32-is-first-inout +17213 0/imm32/no-r32 +17214 2/imm32/imm32-is-second-inout +17215 0/imm32/no-imm8 +17216 0/imm32/no-disp32 +17217 0/imm32/output-is-write-only +17218 0x11/imm32/alloc-id:fake +17219 _Primitive-multiply-reg-by-reg/imm32/next +17220 # - multiply +17221 _Primitive-multiply-reg-by-reg: # (payload primitive) +17222 0x11/imm32/alloc-id:fake:payload +17223 # var1/reg <- multiply var2 => 0f af/multiply var2/rm32 var1/r32 +17224 0x11/imm32/alloc-id:fake +17225 _string-multiply/imm32/name +17226 0x11/imm32/alloc-id:fake +17227 Single-int-var-in-some-register/imm32/inouts 17228 0x11/imm32/alloc-id:fake -17229 _Primitive-loop-if-<=/imm32/next -17230 _Primitive-loop-if-<=: # (payload primitive) -17231 0x11/imm32/alloc-id:fake:payload -17232 0x11/imm32/alloc-id:fake -17233 _string-loop-if-<=/imm32/name -17234 0/imm32/no-inouts -17235 0/imm32/no-inouts -17236 0/imm32/no-outputs -17237 0/imm32/no-outputs +17229 Single-int-var-in-some-register/imm32/outputs +17230 0x11/imm32/alloc-id:fake +17231 _string_0f_af_multiply/imm32/subx-name +17232 1/imm32/rm32-is-first-inout +17233 3/imm32/r32-is-first-output +17234 0/imm32/no-imm32 +17235 0/imm32/no-imm8 +17236 0/imm32/no-disp32 +17237 0/imm32/output-is-write-only 17238 0x11/imm32/alloc-id:fake -17239 _string_0f_8e_jump_loop/imm32/subx-name -17240 0/imm32/no-rm32 -17241 0/imm32/no-r32 -17242 0/imm32/no-imm32 -17243 0/imm32/no-imm8 -17244 0/imm32/no-disp32 -17245 0/imm32/no-output -17246 0x11/imm32/alloc-id:fake -17247 _Primitive-loop-if->/imm32/next -17248 _Primitive-loop-if->: # (payload primitive) -17249 0x11/imm32/alloc-id:fake:payload -17250 0x11/imm32/alloc-id:fake -17251 _string-loop-if->/imm32/name -17252 0/imm32/no-inouts -17253 0/imm32/no-inouts -17254 0/imm32/no-outputs -17255 0/imm32/no-outputs -17256 0x11/imm32/alloc-id:fake -17257 _string_0f_8f_jump_loop/imm32/subx-name -17258 0/imm32/no-rm32 -17259 0/imm32/no-r32 -17260 0/imm32/no-imm32 -17261 0/imm32/no-imm8 -17262 0/imm32/no-disp32 -17263 0/imm32/no-output -17264 0x11/imm32/alloc-id:fake -17265 _Primitive-loop/imm32/next # we probably don't need an unconditional break -17266 _Primitive-loop: # (payload primitive) -17267 0x11/imm32/alloc-id:fake:payload +17239 _Primitive-multiply-reg-by-mem/imm32/next +17240 _Primitive-multiply-reg-by-mem: # (payload primitive) +17241 0x11/imm32/alloc-id:fake:payload +17242 # var1/reg <- multiply var2 => 0f af/multiply var2/rm32 var1/r32 +17243 0x11/imm32/alloc-id:fake +17244 _string-multiply/imm32/name +17245 0x11/imm32/alloc-id:fake +17246 Single-int-var-in-mem/imm32/inouts +17247 0x11/imm32/alloc-id:fake +17248 Single-int-var-in-some-register/imm32/outputs +17249 0x11/imm32/alloc-id:fake +17250 _string_0f_af_multiply/imm32/subx-name +17251 1/imm32/rm32-is-first-inout +17252 3/imm32/r32-is-first-output +17253 0/imm32/no-imm32 +17254 0/imm32/no-imm8 +17255 0/imm32/no-disp32 +17256 0/imm32/output-is-write-only +17257 0x11/imm32/alloc-id:fake +17258 _Primitive-break-if-addr</imm32/next +17259 # - branches +17260 _Primitive-break-if-addr<: # (payload primitive) +17261 0x11/imm32/alloc-id:fake:payload +17262 0x11/imm32/alloc-id:fake +17263 _string-break-if-addr</imm32/name +17264 0/imm32/no-inouts +17265 0/imm32/no-inouts +17266 0/imm32/no-outputs +17267 0/imm32/no-outputs 17268 0x11/imm32/alloc-id:fake -17269 _string-loop/imm32/name -17270 0/imm32/no-inouts -17271 0/imm32/no-inouts -17272 0/imm32/no-outputs -17273 0/imm32/no-outputs -17274 0x11/imm32/alloc-id:fake -17275 _string_e9_jump_loop/imm32/subx-name -17276 0/imm32/no-rm32 -17277 0/imm32/no-r32 -17278 0/imm32/no-imm32 -17279 0/imm32/no-imm8 -17280 0/imm32/no-disp32 -17281 0/imm32/no-output -17282 0x11/imm32/alloc-id:fake -17283 _Primitive-break-if-addr<-named/imm32/next -17284 # - branches to named blocks -17285 _Primitive-break-if-addr<-named: # (payload primitive) -17286 0x11/imm32/alloc-id:fake:payload -17287 0x11/imm32/alloc-id:fake -17288 _string-break-if-addr</imm32/name -17289 0x11/imm32/alloc-id:fake -17290 Single-lit-var/imm32/inouts -17291 0/imm32/no-outputs -17292 0/imm32/no-outputs -17293 0x11/imm32/alloc-id:fake -17294 _string_0f_82_jump_label/imm32/subx-name -17295 0/imm32/no-rm32 -17296 0/imm32/no-r32 -17297 0/imm32/no-imm32 -17298 0/imm32/no-imm8 -17299 1/imm32/disp32-is-first-inout -17300 0/imm32/no-output -17301 0x11/imm32/alloc-id:fake -17302 _Primitive-break-if-addr>=-named/imm32/next -17303 _Primitive-break-if-addr>=-named: # (payload primitive) -17304 0x11/imm32/alloc-id:fake:payload -17305 0x11/imm32/alloc-id:fake -17306 _string-break-if-addr>=/imm32/name -17307 0x11/imm32/alloc-id:fake -17308 Single-lit-var/imm32/inouts -17309 0/imm32/no-outputs -17310 0/imm32/no-outputs -17311 0x11/imm32/alloc-id:fake -17312 _string_0f_83_jump_label/imm32/subx-name -17313 0/imm32/no-rm32 -17314 0/imm32/no-r32 -17315 0/imm32/no-imm32 -17316 0/imm32/no-imm8 -17317 1/imm32/disp32-is-first-inout -17318 0/imm32/no-output -17319 0x11/imm32/alloc-id:fake -17320 _Primitive-break-if-=-named/imm32/next -17321 _Primitive-break-if-=-named: # (payload primitive) -17322 0x11/imm32/alloc-id:fake:payload -17323 0x11/imm32/alloc-id:fake -17324 _string-break-if-=/imm32/name -17325 0x11/imm32/alloc-id:fake -17326 Single-lit-var/imm32/inouts -17327 0/imm32/no-outputs -17328 0/imm32/no-outputs -17329 0x11/imm32/alloc-id:fake -17330 _string_0f_84_jump_label/imm32/subx-name -17331 0/imm32/no-rm32 -17332 0/imm32/no-r32 -17333 0/imm32/no-imm32 -17334 0/imm32/no-imm8 -17335 1/imm32/disp32-is-first-inout -17336 0/imm32/no-output -17337 0x11/imm32/alloc-id:fake -17338 _Primitive-break-if-!=-named/imm32/next -17339 _Primitive-break-if-!=-named: # (payload primitive) -17340 0x11/imm32/alloc-id:fake:payload -17341 0x11/imm32/alloc-id:fake -17342 _string-break-if-!=/imm32/name -17343 0x11/imm32/alloc-id:fake -17344 Single-lit-var/imm32/inouts -17345 0/imm32/no-outputs -17346 0/imm32/no-outputs -17347 0x11/imm32/alloc-id:fake -17348 _string_0f_85_jump_label/imm32/subx-name -17349 0/imm32/no-rm32 -17350 0/imm32/no-r32 -17351 0/imm32/no-imm32 -17352 0/imm32/no-imm8 -17353 1/imm32/disp32-is-first-inout -17354 0/imm32/no-output -17355 0x11/imm32/alloc-id:fake -17356 _Primitive-break-if-addr<=-named/imm32/next -17357 _Primitive-break-if-addr<=-named: # (payload primitive) -17358 0x11/imm32/alloc-id:fake:payload -17359 0x11/imm32/alloc-id:fake -17360 _string-break-if-addr<=/imm32/name -17361 0x11/imm32/alloc-id:fake -17362 Single-lit-var/imm32/inouts -17363 0/imm32/no-outputs -17364 0/imm32/no-outputs -17365 0x11/imm32/alloc-id:fake -17366 _string_0f_86_jump_label/imm32/subx-name -17367 0/imm32/no-rm32 -17368 0/imm32/no-r32 -17369 0/imm32/no-imm32 -17370 0/imm32/no-imm8 -17371 1/imm32/disp32-is-first-inout -17372 0/imm32/no-output -17373 0x11/imm32/alloc-id:fake -17374 _Primitive-break-if-addr>-named/imm32/next -17375 _Primitive-break-if-addr>-named: # (payload primitive) -17376 0x11/imm32/alloc-id:fake:payload -17377 0x11/imm32/alloc-id:fake -17378 _string-break-if-addr>/imm32/name -17379 0x11/imm32/alloc-id:fake -17380 Single-lit-var/imm32/inouts -17381 0/imm32/no-outputs -17382 0/imm32/no-outputs -17383 0x11/imm32/alloc-id:fake -17384 _string_0f_87_jump_label/imm32/subx-name -17385 0/imm32/no-rm32 -17386 0/imm32/no-r32 -17387 0/imm32/no-imm32 -17388 0/imm32/no-imm8 -17389 1/imm32/disp32-is-first-inout -17390 0/imm32/no-output -17391 0x11/imm32/alloc-id:fake -17392 _Primitive-break-if-<-named/imm32/next -17393 _Primitive-break-if-<-named: # (payload primitive) -17394 0x11/imm32/alloc-id:fake:payload -17395 0x11/imm32/alloc-id:fake -17396 _string-break-if-</imm32/name -17397 0x11/imm32/alloc-id:fake -17398 Single-lit-var/imm32/inouts -17399 0/imm32/no-outputs -17400 0/imm32/no-outputs -17401 0x11/imm32/alloc-id:fake -17402 _string_0f_8c_jump_label/imm32/subx-name -17403 0/imm32/no-rm32 -17404 0/imm32/no-r32 -17405 0/imm32/no-imm32 -17406 0/imm32/no-imm8 -17407 1/imm32/disp32-is-first-inout -17408 0/imm32/no-output -17409 0x11/imm32/alloc-id:fake -17410 _Primitive-break-if->=-named/imm32/next -17411 _Primitive-break-if->=-named: # (payload primitive) -17412 0x11/imm32/alloc-id:fake:payload -17413 0x11/imm32/alloc-id:fake -17414 _string-break-if->=/imm32/name -17415 0x11/imm32/alloc-id:fake -17416 Single-lit-var/imm32/inouts -17417 0/imm32/no-outputs -17418 0/imm32/no-outputs -17419 0x11/imm32/alloc-id:fake -17420 _string_0f_8d_jump_label/imm32/subx-name -17421 0/imm32/no-rm32 -17422 0/imm32/no-r32 -17423 0/imm32/no-imm32 -17424 0/imm32/no-imm8 -17425 1/imm32/disp32-is-first-inout -17426 0/imm32/no-output -17427 0x11/imm32/alloc-id:fake -17428 _Primitive-break-if-<=-named/imm32/next -17429 _Primitive-break-if-<=-named: # (payload primitive) -17430 0x11/imm32/alloc-id:fake:payload -17431 0x11/imm32/alloc-id:fake -17432 _string-break-if-<=/imm32/name -17433 0x11/imm32/alloc-id:fake -17434 Single-lit-var/imm32/inouts -17435 0/imm32/no-outputs -17436 0/imm32/no-outputs -17437 0x11/imm32/alloc-id:fake -17438 _string_0f_8e_jump_label/imm32/subx-name -17439 0/imm32/no-rm32 -17440 0/imm32/no-r32 -17441 0/imm32/no-imm32 -17442 0/imm32/no-imm8 -17443 1/imm32/disp32-is-first-inout -17444 0/imm32/no-output -17445 0x11/imm32/alloc-id:fake -17446 _Primitive-break-if->-named/imm32/next -17447 _Primitive-break-if->-named: # (payload primitive) -17448 0x11/imm32/alloc-id:fake:payload -17449 0x11/imm32/alloc-id:fake -17450 _string-break-if->/imm32/name -17451 0x11/imm32/alloc-id:fake -17452 Single-lit-var/imm32/inouts -17453 0/imm32/no-outputs -17454 0/imm32/no-outputs -17455 0x11/imm32/alloc-id:fake -17456 _string_0f_8f_jump_label/imm32/subx-name -17457 0/imm32/no-rm32 -17458 0/imm32/no-r32 -17459 0/imm32/no-imm32 -17460 0/imm32/no-imm8 -17461 1/imm32/disp32-is-first-inout -17462 0/imm32/no-output -17463 0x11/imm32/alloc-id:fake -17464 _Primitive-break-named/imm32/next -17465 _Primitive-break-named: # (payload primitive) -17466 0x11/imm32/alloc-id:fake:payload -17467 0x11/imm32/alloc-id:fake -17468 _string-break/imm32/name -17469 0x11/imm32/alloc-id:fake -17470 Single-lit-var/imm32/inouts -17471 0/imm32/no-outputs -17472 0/imm32/no-outputs -17473 0x11/imm32/alloc-id:fake -17474 _string_e9_jump_label/imm32/subx-name -17475 0/imm32/no-rm32 -17476 0/imm32/no-r32 -17477 0/imm32/no-imm32 -17478 0/imm32/no-imm8 -17479 1/imm32/disp32-is-first-inout -17480 0/imm32/no-output -17481 0x11/imm32/alloc-id:fake -17482 _Primitive-loop-if-addr<-named/imm32/next -17483 _Primitive-loop-if-addr<-named: # (payload primitive) -17484 0x11/imm32/alloc-id:fake:payload -17485 0x11/imm32/alloc-id:fake -17486 _string-loop-if-addr</imm32/name -17487 0x11/imm32/alloc-id:fake -17488 Single-lit-var/imm32/inouts -17489 0/imm32/no-outputs -17490 0/imm32/no-outputs -17491 0x11/imm32/alloc-id:fake -17492 _string_0f_82_jump_label/imm32/subx-name -17493 0/imm32/no-rm32 -17494 0/imm32/no-r32 -17495 0/imm32/no-imm32 -17496 0/imm32/no-imm8 -17497 1/imm32/disp32-is-first-inout -17498 0/imm32/no-output -17499 0x11/imm32/alloc-id:fake -17500 _Primitive-loop-if-addr>=-named/imm32/next -17501 _Primitive-loop-if-addr>=-named: # (payload primitive) -17502 0x11/imm32/alloc-id:fake:payload -17503 0x11/imm32/alloc-id:fake -17504 _string-loop-if-addr>=/imm32/name -17505 0x11/imm32/alloc-id:fake -17506 Single-lit-var/imm32/inouts -17507 0/imm32/no-outputs -17508 0/imm32/no-outputs -17509 0x11/imm32/alloc-id:fake -17510 _string_0f_83_jump_label/imm32/subx-name -17511 0/imm32/no-rm32 -17512 0/imm32/no-r32 -17513 0/imm32/no-imm32 -17514 0/imm32/no-imm8 -17515 1/imm32/disp32-is-first-inout -17516 0/imm32/no-output -17517 0x11/imm32/alloc-id:fake -17518 _Primitive-loop-if-=-named/imm32/next -17519 _Primitive-loop-if-=-named: # (payload primitive) -17520 0x11/imm32/alloc-id:fake:payload -17521 0x11/imm32/alloc-id:fake -17522 _string-loop-if-=/imm32/name -17523 0x11/imm32/alloc-id:fake -17524 Single-lit-var/imm32/inouts -17525 0/imm32/no-outputs -17526 0/imm32/no-outputs -17527 0x11/imm32/alloc-id:fake -17528 _string_0f_84_jump_label/imm32/subx-name -17529 0/imm32/no-rm32 -17530 0/imm32/no-r32 -17531 0/imm32/no-imm32 -17532 0/imm32/no-imm8 -17533 1/imm32/disp32-is-first-inout -17534 0/imm32/no-output -17535 0x11/imm32/alloc-id:fake -17536 _Primitive-loop-if-!=-named/imm32/next -17537 _Primitive-loop-if-!=-named: # (payload primitive) -17538 0x11/imm32/alloc-id:fake:payload -17539 0x11/imm32/alloc-id:fake -17540 _string-loop-if-!=/imm32/name -17541 0x11/imm32/alloc-id:fake -17542 Single-lit-var/imm32/inouts -17543 0/imm32/no-outputs -17544 0/imm32/no-outputs -17545 0x11/imm32/alloc-id:fake -17546 _string_0f_85_jump_label/imm32/subx-name -17547 0/imm32/no-rm32 -17548 0/imm32/no-r32 -17549 0/imm32/no-imm32 -17550 0/imm32/no-imm8 -17551 1/imm32/disp32-is-first-inout -17552 0/imm32/no-output -17553 0x11/imm32/alloc-id:fake -17554 _Primitive-loop-if-addr<=-named/imm32/next -17555 _Primitive-loop-if-addr<=-named: # (payload primitive) -17556 0x11/imm32/alloc-id:fake:payload -17557 0x11/imm32/alloc-id:fake -17558 _string-loop-if-addr<=/imm32/name -17559 0x11/imm32/alloc-id:fake -17560 Single-lit-var/imm32/inouts -17561 0/imm32/no-outputs -17562 0/imm32/no-outputs -17563 0x11/imm32/alloc-id:fake -17564 _string_0f_86_jump_label/imm32/subx-name -17565 0/imm32/no-rm32 -17566 0/imm32/no-r32 -17567 0/imm32/no-imm32 -17568 0/imm32/no-imm8 -17569 1/imm32/disp32-is-first-inout -17570 0/imm32/no-output -17571 0x11/imm32/alloc-id:fake -17572 _Primitive-loop-if-addr>-named/imm32/next -17573 _Primitive-loop-if-addr>-named: # (payload primitive) -17574 0x11/imm32/alloc-id:fake:payload -17575 0x11/imm32/alloc-id:fake -17576 _string-loop-if-addr>/imm32/name -17577 0x11/imm32/alloc-id:fake -17578 Single-lit-var/imm32/inouts -17579 0/imm32/no-outputs -17580 0/imm32/no-outputs -17581 0x11/imm32/alloc-id:fake -17582 _string_0f_87_jump_label/imm32/subx-name -17583 0/imm32/no-rm32 -17584 0/imm32/no-r32 -17585 0/imm32/no-imm32 -17586 0/imm32/no-imm8 -17587 1/imm32/disp32-is-first-inout -17588 0/imm32/no-output -17589 0x11/imm32/alloc-id:fake -17590 _Primitive-loop-if-<-named/imm32/next -17591 _Primitive-loop-if-<-named: # (payload primitive) -17592 0x11/imm32/alloc-id:fake:payload -17593 0x11/imm32/alloc-id:fake -17594 _string-loop-if-</imm32/name -17595 0x11/imm32/alloc-id:fake -17596 Single-lit-var/imm32/inouts -17597 0/imm32/no-outputs -17598 0/imm32/no-outputs -17599 0x11/imm32/alloc-id:fake -17600 _string_0f_8c_jump_label/imm32/subx-name -17601 0/imm32/no-rm32 -17602 0/imm32/no-r32 -17603 0/imm32/no-imm32 -17604 0/imm32/no-imm8 -17605 1/imm32/disp32-is-first-inout -17606 0/imm32/no-output -17607 0x11/imm32/alloc-id:fake -17608 _Primitive-loop-if->=-named/imm32/next -17609 _Primitive-loop-if->=-named: # (payload primitive) -17610 0x11/imm32/alloc-id:fake:payload -17611 0x11/imm32/alloc-id:fake -17612 _string-loop-if->=/imm32/name -17613 0x11/imm32/alloc-id:fake -17614 Single-lit-var/imm32/inouts -17615 0/imm32/no-outputs -17616 0/imm32/no-outputs -17617 0x11/imm32/alloc-id:fake -17618 _string_0f_8d_jump_label/imm32/subx-name -17619 0/imm32/no-rm32 -17620 0/imm32/no-r32 -17621 0/imm32/no-imm32 -17622 0/imm32/no-imm8 -17623 1/imm32/disp32-is-first-inout -17624 0/imm32/no-output -17625 0x11/imm32/alloc-id:fake -17626 _Primitive-loop-if-<=-named/imm32/next -17627 _Primitive-loop-if-<=-named: # (payload primitive) -17628 0x11/imm32/alloc-id:fake:payload -17629 0x11/imm32/alloc-id:fake -17630 _string-loop-if-<=/imm32/name -17631 0x11/imm32/alloc-id:fake -17632 Single-lit-var/imm32/inouts -17633 0/imm32/no-outputs -17634 0/imm32/no-outputs -17635 0x11/imm32/alloc-id:fake -17636 _string_0f_8e_jump_label/imm32/subx-name -17637 0/imm32/no-rm32 -17638 0/imm32/no-r32 -17639 0/imm32/no-imm32 -17640 0/imm32/no-imm8 -17641 1/imm32/disp32-is-first-inout -17642 0/imm32/no-output -17643 0x11/imm32/alloc-id:fake -17644 _Primitive-loop-if->-named/imm32/next -17645 _Primitive-loop-if->-named: # (payload primitive) -17646 0x11/imm32/alloc-id:fake:payload -17647 0x11/imm32/alloc-id:fake -17648 _string-loop-if->/imm32/name -17649 0x11/imm32/alloc-id:fake -17650 Single-lit-var/imm32/inouts -17651 0/imm32/no-outputs -17652 0/imm32/no-outputs -17653 0x11/imm32/alloc-id:fake -17654 _string_0f_8f_jump_label/imm32/subx-name -17655 0/imm32/no-rm32 -17656 0/imm32/no-r32 -17657 0/imm32/no-imm32 -17658 0/imm32/no-imm8 -17659 1/imm32/disp32-is-first-inout -17660 0/imm32/no-output +17269 _string_0f_82_jump_break/imm32/subx-name +17270 0/imm32/no-rm32 +17271 0/imm32/no-r32 +17272 0/imm32/no-imm32 +17273 0/imm32/no-imm8 +17274 0/imm32/no-disp32 +17275 0/imm32/no-output +17276 0x11/imm32/alloc-id:fake +17277 _Primitive-break-if-addr>=/imm32/next +17278 _Primitive-break-if-addr>=: # (payload primitive) +17279 0x11/imm32/alloc-id:fake:payload +17280 0x11/imm32/alloc-id:fake +17281 _string-break-if-addr>=/imm32/name +17282 0/imm32/no-inouts +17283 0/imm32/no-inouts +17284 0/imm32/no-outputs +17285 0/imm32/no-outputs +17286 0x11/imm32/alloc-id:fake +17287 _string_0f_83_jump_break/imm32/subx-name +17288 0/imm32/no-rm32 +17289 0/imm32/no-r32 +17290 0/imm32/no-imm32 +17291 0/imm32/no-imm8 +17292 0/imm32/no-disp32 +17293 0/imm32/no-output +17294 0x11/imm32/alloc-id:fake +17295 _Primitive-break-if-=/imm32/next +17296 _Primitive-break-if-=: # (payload primitive) +17297 0x11/imm32/alloc-id:fake:payload +17298 0x11/imm32/alloc-id:fake +17299 _string-break-if-=/imm32/name +17300 0/imm32/no-inouts +17301 0/imm32/no-inouts +17302 0/imm32/no-outputs +17303 0/imm32/no-outputs +17304 0x11/imm32/alloc-id:fake +17305 _string_0f_84_jump_break/imm32/subx-name +17306 0/imm32/no-rm32 +17307 0/imm32/no-r32 +17308 0/imm32/no-imm32 +17309 0/imm32/no-imm8 +17310 0/imm32/no-disp32 +17311 0/imm32/no-output +17312 0x11/imm32/alloc-id:fake +17313 _Primitive-break-if-!=/imm32/next +17314 _Primitive-break-if-!=: # (payload primitive) +17315 0x11/imm32/alloc-id:fake:payload +17316 0x11/imm32/alloc-id:fake +17317 _string-break-if-!=/imm32/name +17318 0/imm32/no-inouts +17319 0/imm32/no-inouts +17320 0/imm32/no-outputs +17321 0/imm32/no-outputs +17322 0x11/imm32/alloc-id:fake +17323 _string_0f_85_jump_break/imm32/subx-name +17324 0/imm32/no-rm32 +17325 0/imm32/no-r32 +17326 0/imm32/no-imm32 +17327 0/imm32/no-imm8 +17328 0/imm32/no-disp32 +17329 0/imm32/no-output +17330 0x11/imm32/alloc-id:fake +17331 _Primitive-break-if-addr<=/imm32/next +17332 _Primitive-break-if-addr<=: # (payload primitive) +17333 0x11/imm32/alloc-id:fake:payload +17334 0x11/imm32/alloc-id:fake +17335 _string-break-if-addr<=/imm32/name +17336 0/imm32/no-inouts +17337 0/imm32/no-inouts +17338 0/imm32/no-outputs +17339 0/imm32/no-outputs +17340 0x11/imm32/alloc-id:fake +17341 _string_0f_86_jump_break/imm32/subx-name +17342 0/imm32/no-rm32 +17343 0/imm32/no-r32 +17344 0/imm32/no-imm32 +17345 0/imm32/no-imm8 +17346 0/imm32/no-disp32 +17347 0/imm32/no-output +17348 0x11/imm32/alloc-id:fake +17349 _Primitive-break-if-addr>/imm32/next +17350 _Primitive-break-if-addr>: # (payload primitive) +17351 0x11/imm32/alloc-id:fake:payload +17352 0x11/imm32/alloc-id:fake +17353 _string-break-if-addr>/imm32/name +17354 0/imm32/no-inouts +17355 0/imm32/no-inouts +17356 0/imm32/no-outputs +17357 0/imm32/no-outputs +17358 0x11/imm32/alloc-id:fake +17359 _string_0f_87_jump_break/imm32/subx-name +17360 0/imm32/no-rm32 +17361 0/imm32/no-r32 +17362 0/imm32/no-imm32 +17363 0/imm32/no-imm8 +17364 0/imm32/no-disp32 +17365 0/imm32/no-output +17366 0x11/imm32/alloc-id:fake +17367 _Primitive-break-if-</imm32/next +17368 _Primitive-break-if-<: # (payload primitive) +17369 0x11/imm32/alloc-id:fake:payload +17370 0x11/imm32/alloc-id:fake +17371 _string-break-if-</imm32/name +17372 0/imm32/no-inouts +17373 0/imm32/no-inouts +17374 0/imm32/no-outputs +17375 0/imm32/no-outputs +17376 0x11/imm32/alloc-id:fake +17377 _string_0f_8c_jump_break/imm32/subx-name +17378 0/imm32/no-rm32 +17379 0/imm32/no-r32 +17380 0/imm32/no-imm32 +17381 0/imm32/no-imm8 +17382 0/imm32/no-disp32 +17383 0/imm32/no-output +17384 0x11/imm32/alloc-id:fake +17385 _Primitive-break-if->=/imm32/next +17386 _Primitive-break-if->=: # (payload primitive) +17387 0x11/imm32/alloc-id:fake:payload +17388 0x11/imm32/alloc-id:fake +17389 _string-break-if->=/imm32/name +17390 0/imm32/no-inouts +17391 0/imm32/no-inouts +17392 0/imm32/no-outputs +17393 0/imm32/no-outputs +17394 0x11/imm32/alloc-id:fake +17395 _string_0f_8d_jump_break/imm32/subx-name +17396 0/imm32/no-rm32 +17397 0/imm32/no-r32 +17398 0/imm32/no-imm32 +17399 0/imm32/no-imm8 +17400 0/imm32/no-disp32 +17401 0/imm32/no-output +17402 0x11/imm32/alloc-id:fake +17403 _Primitive-break-if-<=/imm32/next +17404 _Primitive-break-if-<=: # (payload primitive) +17405 0x11/imm32/alloc-id:fake:payload +17406 0x11/imm32/alloc-id:fake +17407 _string-break-if-<=/imm32/name +17408 0/imm32/no-inouts +17409 0/imm32/no-inouts +17410 0/imm32/no-outputs +17411 0/imm32/no-outputs +17412 0x11/imm32/alloc-id:fake +17413 _string_0f_8e_jump_break/imm32/subx-name +17414 0/imm32/no-rm32 +17415 0/imm32/no-r32 +17416 0/imm32/no-imm32 +17417 0/imm32/no-imm8 +17418 0/imm32/no-disp32 +17419 0/imm32/no-output +17420 0x11/imm32/alloc-id:fake +17421 _Primitive-break-if->/imm32/next +17422 _Primitive-break-if->: # (payload primitive) +17423 0x11/imm32/alloc-id:fake:payload +17424 0x11/imm32/alloc-id:fake +17425 _string-break-if->/imm32/name +17426 0/imm32/no-inouts +17427 0/imm32/no-inouts +17428 0/imm32/no-outputs +17429 0/imm32/no-outputs +17430 0x11/imm32/alloc-id:fake +17431 _string_0f_8f_jump_break/imm32/subx-name +17432 0/imm32/no-rm32 +17433 0/imm32/no-r32 +17434 0/imm32/no-imm32 +17435 0/imm32/no-imm8 +17436 0/imm32/no-disp32 +17437 0/imm32/no-output +17438 0x11/imm32/alloc-id:fake +17439 _Primitive-break/imm32/next +17440 _Primitive-break: # (payload primitive) +17441 0x11/imm32/alloc-id:fake:payload +17442 0x11/imm32/alloc-id:fake +17443 _string-break/imm32/name +17444 0/imm32/no-inouts +17445 0/imm32/no-inouts +17446 0/imm32/no-outputs +17447 0/imm32/no-outputs +17448 0x11/imm32/alloc-id:fake +17449 _string_e9_jump_break/imm32/subx-name +17450 0/imm32/no-rm32 +17451 0/imm32/no-r32 +17452 0/imm32/no-imm32 +17453 0/imm32/no-imm8 +17454 0/imm32/no-disp32 +17455 0/imm32/no-output +17456 0x11/imm32/alloc-id:fake +17457 _Primitive-loop-if-addr</imm32/next +17458 _Primitive-loop-if-addr<: # (payload primitive) +17459 0x11/imm32/alloc-id:fake:payload +17460 0x11/imm32/alloc-id:fake +17461 _string-loop-if-addr</imm32/name +17462 0/imm32/no-inouts +17463 0/imm32/no-inouts +17464 0/imm32/no-outputs +17465 0/imm32/no-outputs +17466 0x11/imm32/alloc-id:fake +17467 _string_0f_82_jump_loop/imm32/subx-name +17468 0/imm32/no-rm32 +17469 0/imm32/no-r32 +17470 0/imm32/no-imm32 +17471 0/imm32/no-imm8 +17472 0/imm32/no-disp32 +17473 0/imm32/no-output +17474 0x11/imm32/alloc-id:fake +17475 _Primitive-loop-if-addr>=/imm32/next +17476 _Primitive-loop-if-addr>=: # (payload primitive) +17477 0x11/imm32/alloc-id:fake:payload +17478 0x11/imm32/alloc-id:fake +17479 _string-loop-if-addr>=/imm32/name +17480 0/imm32/no-inouts +17481 0/imm32/no-inouts +17482 0/imm32/no-outputs +17483 0/imm32/no-outputs +17484 0x11/imm32/alloc-id:fake +17485 _string_0f_83_jump_loop/imm32/subx-name +17486 0/imm32/no-rm32 +17487 0/imm32/no-r32 +17488 0/imm32/no-imm32 +17489 0/imm32/no-imm8 +17490 0/imm32/no-disp32 +17491 0/imm32/no-output +17492 0x11/imm32/alloc-id:fake +17493 _Primitive-loop-if-=/imm32/next +17494 _Primitive-loop-if-=: # (payload primitive) +17495 0x11/imm32/alloc-id:fake:payload +17496 0x11/imm32/alloc-id:fake +17497 _string-loop-if-=/imm32/name +17498 0/imm32/no-inouts +17499 0/imm32/no-inouts +17500 0/imm32/no-outputs +17501 0/imm32/no-outputs +17502 0x11/imm32/alloc-id:fake +17503 _string_0f_84_jump_loop/imm32/subx-name +17504 0/imm32/no-rm32 +17505 0/imm32/no-r32 +17506 0/imm32/no-imm32 +17507 0/imm32/no-imm8 +17508 0/imm32/no-disp32 +17509 0/imm32/no-output +17510 0x11/imm32/alloc-id:fake +17511 _Primitive-loop-if-!=/imm32/next +17512 _Primitive-loop-if-!=: # (payload primitive) +17513 0x11/imm32/alloc-id:fake:payload +17514 0x11/imm32/alloc-id:fake +17515 _string-loop-if-!=/imm32/name +17516 0/imm32/no-inouts +17517 0/imm32/no-inouts +17518 0/imm32/no-outputs +17519 0/imm32/no-outputs +17520 0x11/imm32/alloc-id:fake +17521 _string_0f_85_jump_loop/imm32/subx-name +17522 0/imm32/no-rm32 +17523 0/imm32/no-r32 +17524 0/imm32/no-imm32 +17525 0/imm32/no-imm8 +17526 0/imm32/no-disp32 +17527 0/imm32/no-output +17528 0x11/imm32/alloc-id:fake +17529 _Primitive-loop-if-addr<=/imm32/next +17530 _Primitive-loop-if-addr<=: # (payload primitive) +17531 0x11/imm32/alloc-id:fake:payload +17532 0x11/imm32/alloc-id:fake +17533 _string-loop-if-addr<=/imm32/name +17534 0/imm32/no-inouts +17535 0/imm32/no-inouts +17536 0/imm32/no-outputs +17537 0/imm32/no-outputs +17538 0x11/imm32/alloc-id:fake +17539 _string_0f_86_jump_loop/imm32/subx-name +17540 0/imm32/no-rm32 +17541 0/imm32/no-r32 +17542 0/imm32/no-imm32 +17543 0/imm32/no-imm8 +17544 0/imm32/no-disp32 +17545 0/imm32/no-output +17546 0x11/imm32/alloc-id:fake +17547 _Primitive-loop-if-addr>/imm32/next +17548 _Primitive-loop-if-addr>: # (payload primitive) +17549 0x11/imm32/alloc-id:fake:payload +17550 0x11/imm32/alloc-id:fake +17551 _string-loop-if-addr>/imm32/name +17552 0/imm32/no-inouts +17553 0/imm32/no-inouts +17554 0/imm32/no-outputs +17555 0/imm32/no-outputs +17556 0x11/imm32/alloc-id:fake +17557 _string_0f_87_jump_loop/imm32/subx-name +17558 0/imm32/no-rm32 +17559 0/imm32/no-r32 +17560 0/imm32/no-imm32 +17561 0/imm32/no-imm8 +17562 0/imm32/no-disp32 +17563 0/imm32/no-output +17564 0x11/imm32/alloc-id:fake +17565 _Primitive-loop-if-</imm32/next +17566 _Primitive-loop-if-<: # (payload primitive) +17567 0x11/imm32/alloc-id:fake:payload +17568 0x11/imm32/alloc-id:fake +17569 _string-loop-if-</imm32/name +17570 0/imm32/no-inouts +17571 0/imm32/no-inouts +17572 0/imm32/no-outputs +17573 0/imm32/no-outputs +17574 0x11/imm32/alloc-id:fake +17575 _string_0f_8c_jump_loop/imm32/subx-name +17576 0/imm32/no-rm32 +17577 0/imm32/no-r32 +17578 0/imm32/no-imm32 +17579 0/imm32/no-imm8 +17580 0/imm32/no-disp32 +17581 0/imm32/no-output +17582 0x11/imm32/alloc-id:fake +17583 _Primitive-loop-if->=/imm32/next +17584 _Primitive-loop-if->=: # (payload primitive) +17585 0x11/imm32/alloc-id:fake:payload +17586 0x11/imm32/alloc-id:fake +17587 _string-loop-if->=/imm32/name +17588 0/imm32/no-inouts +17589 0/imm32/no-inouts +17590 0/imm32/no-outputs +17591 0/imm32/no-outputs +17592 0x11/imm32/alloc-id:fake +17593 _string_0f_8d_jump_loop/imm32/subx-name +17594 0/imm32/no-rm32 +17595 0/imm32/no-r32 +17596 0/imm32/no-imm32 +17597 0/imm32/no-imm8 +17598 0/imm32/no-disp32 +17599 0/imm32/no-output +17600 0x11/imm32/alloc-id:fake +17601 _Primitive-loop-if-<=/imm32/next +17602 _Primitive-loop-if-<=: # (payload primitive) +17603 0x11/imm32/alloc-id:fake:payload +17604 0x11/imm32/alloc-id:fake +17605 _string-loop-if-<=/imm32/name +17606 0/imm32/no-inouts +17607 0/imm32/no-inouts +17608 0/imm32/no-outputs +17609 0/imm32/no-outputs +17610 0x11/imm32/alloc-id:fake +17611 _string_0f_8e_jump_loop/imm32/subx-name +17612 0/imm32/no-rm32 +17613 0/imm32/no-r32 +17614 0/imm32/no-imm32 +17615 0/imm32/no-imm8 +17616 0/imm32/no-disp32 +17617 0/imm32/no-output +17618 0x11/imm32/alloc-id:fake +17619 _Primitive-loop-if->/imm32/next +17620 _Primitive-loop-if->: # (payload primitive) +17621 0x11/imm32/alloc-id:fake:payload +17622 0x11/imm32/alloc-id:fake +17623 _string-loop-if->/imm32/name +17624 0/imm32/no-inouts +17625 0/imm32/no-inouts +17626 0/imm32/no-outputs +17627 0/imm32/no-outputs +17628 0x11/imm32/alloc-id:fake +17629 _string_0f_8f_jump_loop/imm32/subx-name +17630 0/imm32/no-rm32 +17631 0/imm32/no-r32 +17632 0/imm32/no-imm32 +17633 0/imm32/no-imm8 +17634 0/imm32/no-disp32 +17635 0/imm32/no-output +17636 0x11/imm32/alloc-id:fake +17637 _Primitive-loop/imm32/next # we probably don't need an unconditional break +17638 _Primitive-loop: # (payload primitive) +17639 0x11/imm32/alloc-id:fake:payload +17640 0x11/imm32/alloc-id:fake +17641 _string-loop/imm32/name +17642 0/imm32/no-inouts +17643 0/imm32/no-inouts +17644 0/imm32/no-outputs +17645 0/imm32/no-outputs +17646 0x11/imm32/alloc-id:fake +17647 _string_e9_jump_loop/imm32/subx-name +17648 0/imm32/no-rm32 +17649 0/imm32/no-r32 +17650 0/imm32/no-imm32 +17651 0/imm32/no-imm8 +17652 0/imm32/no-disp32 +17653 0/imm32/no-output +17654 0x11/imm32/alloc-id:fake +17655 _Primitive-break-if-addr<-named/imm32/next +17656 # - branches to named blocks +17657 _Primitive-break-if-addr<-named: # (payload primitive) +17658 0x11/imm32/alloc-id:fake:payload +17659 0x11/imm32/alloc-id:fake +17660 _string-break-if-addr</imm32/name 17661 0x11/imm32/alloc-id:fake -17662 _Primitive-loop-named/imm32/next # we probably don't need an unconditional break -17663 _Primitive-loop-named: # (payload primitive) -17664 0x11/imm32/alloc-id:fake:payload +17662 Single-lit-var/imm32/inouts +17663 0/imm32/no-outputs +17664 0/imm32/no-outputs 17665 0x11/imm32/alloc-id:fake -17666 _string-loop/imm32/name -17667 0x11/imm32/alloc-id:fake -17668 Single-lit-var/imm32/inouts -17669 0/imm32/no-outputs -17670 0/imm32/no-outputs -17671 0x11/imm32/alloc-id:fake -17672 _string_e9_jump_label/imm32/subx-name -17673 0/imm32/no-rm32 -17674 0/imm32/no-r32 -17675 0/imm32/no-imm32 -17676 0/imm32/no-imm8 -17677 1/imm32/disp32-is-first-inout -17678 0/imm32/no-output -17679 0/imm32/next -17680 0/imm32/next -17681 -17682 # string literals for Mu instructions -17683 _string-add: # (payload array byte) -17684 0x11/imm32/alloc-id:fake:payload -17685 # "add" -17686 0x3/imm32/size -17687 0x61/a 0x64/d 0x64/d -17688 _string-address: # (payload array byte) -17689 0x11/imm32/alloc-id:fake:payload -17690 # "address" -17691 0x7/imm32/size -17692 0x61/a 0x64/d 0x64/d 0x72/r 0x65/e 0x73/s 0x73/s -17693 _string-add-to: # (payload array byte) +17666 _string_0f_82_jump_label/imm32/subx-name +17667 0/imm32/no-rm32 +17668 0/imm32/no-r32 +17669 0/imm32/no-imm32 +17670 0/imm32/no-imm8 +17671 1/imm32/disp32-is-first-inout +17672 0/imm32/no-output +17673 0x11/imm32/alloc-id:fake +17674 _Primitive-break-if-addr>=-named/imm32/next +17675 _Primitive-break-if-addr>=-named: # (payload primitive) +17676 0x11/imm32/alloc-id:fake:payload +17677 0x11/imm32/alloc-id:fake +17678 _string-break-if-addr>=/imm32/name +17679 0x11/imm32/alloc-id:fake +17680 Single-lit-var/imm32/inouts +17681 0/imm32/no-outputs +17682 0/imm32/no-outputs +17683 0x11/imm32/alloc-id:fake +17684 _string_0f_83_jump_label/imm32/subx-name +17685 0/imm32/no-rm32 +17686 0/imm32/no-r32 +17687 0/imm32/no-imm32 +17688 0/imm32/no-imm8 +17689 1/imm32/disp32-is-first-inout +17690 0/imm32/no-output +17691 0x11/imm32/alloc-id:fake +17692 _Primitive-break-if-=-named/imm32/next +17693 _Primitive-break-if-=-named: # (payload primitive) 17694 0x11/imm32/alloc-id:fake:payload -17695 # "add-to" -17696 0x6/imm32/size -17697 0x61/a 0x64/d 0x64/d 0x2d/dash 0x74/t 0x6f/o -17698 _string-and: # (payload array byte) -17699 0x11/imm32/alloc-id:fake:payload -17700 # "and" -17701 0x3/imm32/size -17702 0x61/a 0x6e/n 0x64/d -17703 _string-and-with: # (payload array byte) -17704 0x11/imm32/alloc-id:fake:payload -17705 # "and-with" -17706 0x8/imm32/size -17707 0x61/a 0x6e/n 0x64/d 0x2d/dash 0x77/w 0x69/i 0x74/t 0x68/h -17708 _string-break: # (payload array byte) -17709 0x11/imm32/alloc-id:fake:payload -17710 # "break" -17711 0x5/imm32/size -17712 0x62/b 0x72/r 0x65/e 0x61/a 0x6b/k -17713 _string-break-if-<: # (payload array byte) -17714 0x11/imm32/alloc-id:fake:payload -17715 # "break-if-<" -17716 0xa/imm32/size -17717 0x62/b 0x72/r 0x65/e 0x61/a 0x6b/k 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x3c/< -17718 _string-break-if-<=: # (payload array byte) -17719 0x11/imm32/alloc-id:fake:payload -17720 # "break-if-<=" -17721 0xb/imm32/size -17722 0x62/b 0x72/r 0x65/e 0x61/a 0x6b/k 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x3c/< 0x3d/= -17723 _string-break-if-=: # (payload array byte) -17724 0x11/imm32/alloc-id:fake:payload -17725 # "break-if-=" -17726 0xa/imm32/size -17727 0x62/b 0x72/r 0x65/e 0x61/a 0x6b/k 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x3d/= -17728 _string-break-if->: # (payload array byte) -17729 0x11/imm32/alloc-id:fake:payload -17730 # "break-if->" -17731 0xa/imm32/size -17732 0x62/b 0x72/r 0x65/e 0x61/a 0x6b/k 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x3e/> -17733 _string-break-if->=: # (payload array byte) -17734 0x11/imm32/alloc-id:fake:payload -17735 # "break-if->=" -17736 0xb/imm32/size -17737 0x62/b 0x72/r 0x65/e 0x61/a 0x6b/k 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x3e/> 0x3d/= -17738 _string-break-if-!=: # (payload array byte) -17739 0x11/imm32/alloc-id:fake:payload -17740 # "break-if-!=" -17741 0xb/imm32/size -17742 0x62/b 0x72/r 0x65/e 0x61/a 0x6b/k 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x21/! 0x3d/= -17743 _string-break-if-addr<: # (payload array byte) -17744 0x11/imm32/alloc-id:fake:payload -17745 # "break-if-addr<" -17746 0xe/imm32/size -17747 0x62/b 0x72/r 0x65/e 0x61/a 0x6b/k 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x61/a 0x64/d 0x64/d 0x72/r 0x3c/< -17748 _string-break-if-addr<=: # (payload array byte) -17749 0x11/imm32/alloc-id:fake:payload -17750 # "break-if-addr<=" -17751 0xf/imm32/size -17752 0x62/b 0x72/r 0x65/e 0x61/a 0x6b/k 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x61/a 0x64/d 0x64/d 0x72/r 0x3c/< 0x3d/= -17753 _string-break-if-addr>: # (payload array byte) -17754 0x11/imm32/alloc-id:fake:payload -17755 # "break-if-addr>" -17756 0xe/imm32/size -17757 0x62/b 0x72/r 0x65/e 0x61/a 0x6b/k 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x61/a 0x64/d 0x64/d 0x72/r 0x3e/> -17758 _string-break-if-addr>=: # (payload array byte) -17759 0x11/imm32/alloc-id:fake:payload -17760 # "break-if-addr>=" -17761 0xf/imm32/size -17762 0x62/b 0x72/r 0x65/e 0x61/a 0x6b/k 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x61/a 0x64/d 0x64/d 0x72/r 0x3e/> 0x3d/= -17763 _string-compare: # (payload array byte) -17764 0x11/imm32/alloc-id:fake:payload -17765 # "compare" -17766 0x7/imm32/size -17767 0x63/c 0x6f/o 0x6d/m 0x70/p 0x61/a 0x72/r 0x65/e -17768 _string-copy: # (payload array byte) -17769 0x11/imm32/alloc-id:fake:payload -17770 # "copy" -17771 0x4/imm32/size -17772 0x63/c 0x6f/o 0x70/p 0x79/y -17773 _string-copy-to: # (payload array byte) -17774 0x11/imm32/alloc-id:fake:payload -17775 # "copy-to" -17776 0x7/imm32/size -17777 0x63/c 0x6f/o 0x70/p 0x79/y 0x2d/dash 0x74/t 0x6f/o -17778 _string-copy-byte: -17779 0x11/imm32/alloc-id:fake:payload -17780 # "copy-byte" -17781 0x9/imm32/size -17782 0x63/c 0x6f/o 0x70/p 0x79/y 0x2d/- 0x62/b 0x79/y 0x74/t 0x65/e -17783 _string-copy-byte-to: +17695 0x11/imm32/alloc-id:fake +17696 _string-break-if-=/imm32/name +17697 0x11/imm32/alloc-id:fake +17698 Single-lit-var/imm32/inouts +17699 0/imm32/no-outputs +17700 0/imm32/no-outputs +17701 0x11/imm32/alloc-id:fake +17702 _string_0f_84_jump_label/imm32/subx-name +17703 0/imm32/no-rm32 +17704 0/imm32/no-r32 +17705 0/imm32/no-imm32 +17706 0/imm32/no-imm8 +17707 1/imm32/disp32-is-first-inout +17708 0/imm32/no-output +17709 0x11/imm32/alloc-id:fake +17710 _Primitive-break-if-!=-named/imm32/next +17711 _Primitive-break-if-!=-named: # (payload primitive) +17712 0x11/imm32/alloc-id:fake:payload +17713 0x11/imm32/alloc-id:fake +17714 _string-break-if-!=/imm32/name +17715 0x11/imm32/alloc-id:fake +17716 Single-lit-var/imm32/inouts +17717 0/imm32/no-outputs +17718 0/imm32/no-outputs +17719 0x11/imm32/alloc-id:fake +17720 _string_0f_85_jump_label/imm32/subx-name +17721 0/imm32/no-rm32 +17722 0/imm32/no-r32 +17723 0/imm32/no-imm32 +17724 0/imm32/no-imm8 +17725 1/imm32/disp32-is-first-inout +17726 0/imm32/no-output +17727 0x11/imm32/alloc-id:fake +17728 _Primitive-break-if-addr<=-named/imm32/next +17729 _Primitive-break-if-addr<=-named: # (payload primitive) +17730 0x11/imm32/alloc-id:fake:payload +17731 0x11/imm32/alloc-id:fake +17732 _string-break-if-addr<=/imm32/name +17733 0x11/imm32/alloc-id:fake +17734 Single-lit-var/imm32/inouts +17735 0/imm32/no-outputs +17736 0/imm32/no-outputs +17737 0x11/imm32/alloc-id:fake +17738 _string_0f_86_jump_label/imm32/subx-name +17739 0/imm32/no-rm32 +17740 0/imm32/no-r32 +17741 0/imm32/no-imm32 +17742 0/imm32/no-imm8 +17743 1/imm32/disp32-is-first-inout +17744 0/imm32/no-output +17745 0x11/imm32/alloc-id:fake +17746 _Primitive-break-if-addr>-named/imm32/next +17747 _Primitive-break-if-addr>-named: # (payload primitive) +17748 0x11/imm32/alloc-id:fake:payload +17749 0x11/imm32/alloc-id:fake +17750 _string-break-if-addr>/imm32/name +17751 0x11/imm32/alloc-id:fake +17752 Single-lit-var/imm32/inouts +17753 0/imm32/no-outputs +17754 0/imm32/no-outputs +17755 0x11/imm32/alloc-id:fake +17756 _string_0f_87_jump_label/imm32/subx-name +17757 0/imm32/no-rm32 +17758 0/imm32/no-r32 +17759 0/imm32/no-imm32 +17760 0/imm32/no-imm8 +17761 1/imm32/disp32-is-first-inout +17762 0/imm32/no-output +17763 0x11/imm32/alloc-id:fake +17764 _Primitive-break-if-<-named/imm32/next +17765 _Primitive-break-if-<-named: # (payload primitive) +17766 0x11/imm32/alloc-id:fake:payload +17767 0x11/imm32/alloc-id:fake +17768 _string-break-if-</imm32/name +17769 0x11/imm32/alloc-id:fake +17770 Single-lit-var/imm32/inouts +17771 0/imm32/no-outputs +17772 0/imm32/no-outputs +17773 0x11/imm32/alloc-id:fake +17774 _string_0f_8c_jump_label/imm32/subx-name +17775 0/imm32/no-rm32 +17776 0/imm32/no-r32 +17777 0/imm32/no-imm32 +17778 0/imm32/no-imm8 +17779 1/imm32/disp32-is-first-inout +17780 0/imm32/no-output +17781 0x11/imm32/alloc-id:fake +17782 _Primitive-break-if->=-named/imm32/next +17783 _Primitive-break-if->=-named: # (payload primitive) 17784 0x11/imm32/alloc-id:fake:payload -17785 # "copy-byte-to" -17786 0xc/imm32/size -17787 0x63/c 0x6f/o 0x70/p 0x79/y 0x2d/- 0x62/b 0x79/y 0x74/t 0x65/e 0x2d/- 0x74/t 0x6f/o -17788 _string-decrement: # (payload array byte) -17789 0x11/imm32/alloc-id:fake:payload -17790 # "decrement" -17791 0x9/imm32/size -17792 0x64/d 0x65/e 0x63/c 0x72/r 0x65/e 0x6d/m 0x65/e 0x6e/n 0x74/t -17793 _string-increment: # (payload array byte) -17794 0x11/imm32/alloc-id:fake:payload -17795 # "increment" -17796 0x9/imm32/size -17797 0x69/i 0x6e/n 0x63/c 0x72/r 0x65/e 0x6d/m 0x65/e 0x6e/n 0x74/t -17798 _string-loop: # (payload array byte) -17799 0x11/imm32/alloc-id:fake:payload -17800 # "loop" -17801 0x4/imm32/size -17802 0x6c/l 0x6f/o 0x6f/o 0x70/p -17803 _string-loop-if-<: # (payload array byte) -17804 0x11/imm32/alloc-id:fake:payload -17805 # "loop-if-<" -17806 0x9/imm32/size -17807 0x6c/l 0x6f/o 0x6f/o 0x70/p 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x3c/< -17808 _string-loop-if-<=: # (payload array byte) -17809 0x11/imm32/alloc-id:fake:payload -17810 # "loop-if-<=" -17811 0xa/imm32/size -17812 0x6c/l 0x6f/o 0x6f/o 0x70/p 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x3c/< 0x3d/= -17813 _string-loop-if-=: # (payload array byte) -17814 0x11/imm32/alloc-id:fake:payload -17815 # "loop-if-=" -17816 0x9/imm32/size -17817 0x6c/l 0x6f/o 0x6f/o 0x70/p 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x3d/= -17818 _string-loop-if->: # (payload array byte) -17819 0x11/imm32/alloc-id:fake:payload -17820 # "loop-if->" -17821 0x9/imm32/size -17822 0x6c/l 0x6f/o 0x6f/o 0x70/p 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x3e/> -17823 _string-loop-if->=: # (payload array byte) -17824 0x11/imm32/alloc-id:fake:payload -17825 # "loop-if->=" -17826 0xa/imm32/size -17827 0x6c/l 0x6f/o 0x6f/o 0x70/p 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x3e/> 0x3d/= -17828 _string-loop-if-!=: # (payload array byte) -17829 0x11/imm32/alloc-id:fake:payload -17830 # "loop-if-!=" -17831 0xa/imm32/size -17832 0x6c/l 0x6f/o 0x6f/o 0x70/p 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x21/! 0x3d/= -17833 _string-loop-if-addr<: # (payload array byte) -17834 0x11/imm32/alloc-id:fake:payload -17835 # "loop-if-addr<" -17836 0xd/imm32/size -17837 0x6c/l 0x6f/o 0x6f/o 0x70/p 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x61/a 0x64/d 0x64/d 0x72/r 0x3c/< -17838 _string-loop-if-addr<=: # (payload array byte) -17839 0x11/imm32/alloc-id:fake:payload -17840 # "loop-if-addr<=" -17841 0xe/imm32/size -17842 0x6c/l 0x6f/o 0x6f/o 0x70/p 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x61/a 0x64/d 0x64/d 0x72/r 0x3c/< 0x3d/= -17843 _string-loop-if-addr>: # (payload array byte) -17844 0x11/imm32/alloc-id:fake:payload -17845 # "loop-if-addr>" -17846 0xd/imm32/size -17847 0x6c/l 0x6f/o 0x6f/o 0x70/p 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x61/a 0x64/d 0x64/d 0x72/r 0x3e/> -17848 _string-loop-if-addr>=: # (payload array byte) -17849 0x11/imm32/alloc-id:fake:payload -17850 # "loop-if-addr>=" -17851 0xe/imm32/size -17852 0x6c/l 0x6f/o 0x6f/o 0x70/p 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x61/a 0x64/d 0x64/d 0x72/r 0x3e/> 0x3d/= -17853 _string-multiply: # (payload array byte) -17854 0x11/imm32/alloc-id:fake:payload -17855 # "multiply" -17856 0x8/imm32/size -17857 0x6d/m 0x75/u 0x6c/l 0x74/t 0x69/i 0x70/p 0x6c/l 0x79/y -17858 _string-or: # (payload array byte) -17859 0x11/imm32/alloc-id:fake:payload -17860 # "or" -17861 0x2/imm32/size -17862 0x6f/o 0x72/r -17863 _string-or-with: # (payload array byte) -17864 0x11/imm32/alloc-id:fake:payload -17865 # "or-with" -17866 0x7/imm32/size -17867 0x6f/o 0x72/r 0x2d/dash 0x77/w 0x69/i 0x74/t 0x68/h -17868 _string-subtract: # (payload array byte) -17869 0x11/imm32/alloc-id:fake:payload -17870 # "subtract" -17871 0x8/imm32/size -17872 0x73/s 0x75/u 0x62/b 0x74/t 0x72/r 0x61/a 0x63/c 0x74/t -17873 _string-subtract-from: # (payload array byte) +17785 0x11/imm32/alloc-id:fake +17786 _string-break-if->=/imm32/name +17787 0x11/imm32/alloc-id:fake +17788 Single-lit-var/imm32/inouts +17789 0/imm32/no-outputs +17790 0/imm32/no-outputs +17791 0x11/imm32/alloc-id:fake +17792 _string_0f_8d_jump_label/imm32/subx-name +17793 0/imm32/no-rm32 +17794 0/imm32/no-r32 +17795 0/imm32/no-imm32 +17796 0/imm32/no-imm8 +17797 1/imm32/disp32-is-first-inout +17798 0/imm32/no-output +17799 0x11/imm32/alloc-id:fake +17800 _Primitive-break-if-<=-named/imm32/next +17801 _Primitive-break-if-<=-named: # (payload primitive) +17802 0x11/imm32/alloc-id:fake:payload +17803 0x11/imm32/alloc-id:fake +17804 _string-break-if-<=/imm32/name +17805 0x11/imm32/alloc-id:fake +17806 Single-lit-var/imm32/inouts +17807 0/imm32/no-outputs +17808 0/imm32/no-outputs +17809 0x11/imm32/alloc-id:fake +17810 _string_0f_8e_jump_label/imm32/subx-name +17811 0/imm32/no-rm32 +17812 0/imm32/no-r32 +17813 0/imm32/no-imm32 +17814 0/imm32/no-imm8 +17815 1/imm32/disp32-is-first-inout +17816 0/imm32/no-output +17817 0x11/imm32/alloc-id:fake +17818 _Primitive-break-if->-named/imm32/next +17819 _Primitive-break-if->-named: # (payload primitive) +17820 0x11/imm32/alloc-id:fake:payload +17821 0x11/imm32/alloc-id:fake +17822 _string-break-if->/imm32/name +17823 0x11/imm32/alloc-id:fake +17824 Single-lit-var/imm32/inouts +17825 0/imm32/no-outputs +17826 0/imm32/no-outputs +17827 0x11/imm32/alloc-id:fake +17828 _string_0f_8f_jump_label/imm32/subx-name +17829 0/imm32/no-rm32 +17830 0/imm32/no-r32 +17831 0/imm32/no-imm32 +17832 0/imm32/no-imm8 +17833 1/imm32/disp32-is-first-inout +17834 0/imm32/no-output +17835 0x11/imm32/alloc-id:fake +17836 _Primitive-break-named/imm32/next +17837 _Primitive-break-named: # (payload primitive) +17838 0x11/imm32/alloc-id:fake:payload +17839 0x11/imm32/alloc-id:fake +17840 _string-break/imm32/name +17841 0x11/imm32/alloc-id:fake +17842 Single-lit-var/imm32/inouts +17843 0/imm32/no-outputs +17844 0/imm32/no-outputs +17845 0x11/imm32/alloc-id:fake +17846 _string_e9_jump_label/imm32/subx-name +17847 0/imm32/no-rm32 +17848 0/imm32/no-r32 +17849 0/imm32/no-imm32 +17850 0/imm32/no-imm8 +17851 1/imm32/disp32-is-first-inout +17852 0/imm32/no-output +17853 0x11/imm32/alloc-id:fake +17854 _Primitive-loop-if-addr<-named/imm32/next +17855 _Primitive-loop-if-addr<-named: # (payload primitive) +17856 0x11/imm32/alloc-id:fake:payload +17857 0x11/imm32/alloc-id:fake +17858 _string-loop-if-addr</imm32/name +17859 0x11/imm32/alloc-id:fake +17860 Single-lit-var/imm32/inouts +17861 0/imm32/no-outputs +17862 0/imm32/no-outputs +17863 0x11/imm32/alloc-id:fake +17864 _string_0f_82_jump_label/imm32/subx-name +17865 0/imm32/no-rm32 +17866 0/imm32/no-r32 +17867 0/imm32/no-imm32 +17868 0/imm32/no-imm8 +17869 1/imm32/disp32-is-first-inout +17870 0/imm32/no-output +17871 0x11/imm32/alloc-id:fake +17872 _Primitive-loop-if-addr>=-named/imm32/next +17873 _Primitive-loop-if-addr>=-named: # (payload primitive) 17874 0x11/imm32/alloc-id:fake:payload -17875 # "subtract-from" -17876 0xd/imm32/size -17877 0x73/s 0x75/u 0x62/b 0x74/t 0x72/r 0x61/a 0x63/c 0x74/t 0x2d/dash 0x66/f 0x72/r 0x6f/o 0x6d/m -17878 _string-xor: # (payload array byte) -17879 0x11/imm32/alloc-id:fake:payload -17880 # "xor" -17881 0x3/imm32/size -17882 0x78/x 0x6f/o 0x72/r -17883 _string-xor-with: # (payload array byte) -17884 0x11/imm32/alloc-id:fake:payload -17885 # "xor-with" -17886 0x8/imm32/size -17887 0x78/x 0x6f/o 0x72/r 0x2d/dash 0x77/w 0x69/i 0x74/t 0x68/h -17888 _string-shift-left: # (payload array byte) -17889 0x11/imm32/alloc-id:fake:payload -17890 # "shift-left" -17891 0xa/imm32/size -17892 0x73/s 0x68/h 0x69/i 0x66/f 0x74/t 0x2d/dash 0x6c/l 0x65/e 0x66/f 0x74/t -17893 _string-shift-right: # (payload array byte) -17894 0x11/imm32/alloc-id:fake:payload -17895 # "shift-right" -17896 0xb/imm32/size -17897 0x73/s 0x68/h 0x69/i 0x66/f 0x74/t 0x2d/dash 0x72/r 0x69/i 0x67/g 0x68/h 0x74/t -17898 _string-shift-right-signed: # (payload array byte) -17899 0x11/imm32/alloc-id:fake:payload -17900 # "shift-right-signed" -17901 0x12/imm32/size -17902 0x73/s 0x68/h 0x69/i 0x66/f 0x74/t 0x2d/dash 0x72/r 0x69/i 0x67/g 0x68/h 0x74/t 0x2d/dash 0x73/s 0x69/i 0x67/g 0x6e/n 0x65/e 0x64/d -17903 -17904 # string literals for SubX instructions -17905 _string_01_add_to: # (payload array byte) -17906 0x11/imm32/alloc-id:fake:payload -17907 # "01/add-to" -17908 0x9/imm32/size -17909 0x30/0 0x31/1 0x2f/slash 0x61/a 0x64/d 0x64/d 0x2d/dash 0x74/t 0x6f/o -17910 _string_03_add: # (payload array byte) -17911 0x11/imm32/alloc-id:fake:payload -17912 # "03/add" -17913 0x6/imm32/size -17914 0x30/0 0x33/3 0x2f/slash 0x61/a 0x64/d 0x64/d -17915 _string_05_add_to_eax: # (payload array byte) -17916 0x11/imm32/alloc-id:fake:payload -17917 # "05/add-to-eax" -17918 0xd/imm32/size -17919 0x30/0 0x35/5 0x2f/slash 0x61/a 0x64/d 0x64/d 0x2d/dash 0x74/t 0x6f/o 0x2d/dash 0x65/e 0x61/a 0x78/x -17920 _string_09_or_with: # (payload array byte) -17921 0x11/imm32/alloc-id:fake:payload -17922 # "09/or-with" -17923 0xa/imm32/size -17924 0x30/0 0x39/9 0x2f/slash 0x6f/o 0x72/r 0x2d/dash 0x77/w 0x69/i 0x74/t 0x68/h -17925 _string_0b_or: # (payload array byte) -17926 0x11/imm32/alloc-id:fake:payload -17927 # "0b/or" -17928 0x5/imm32/size -17929 0x30/0 0x62/b 0x2f/slash 0x6f/o 0x72/r -17930 _string_0d_or_with_eax: # (payload array byte) -17931 0x11/imm32/alloc-id:fake:payload -17932 # "0d/or-with-eax" -17933 0xe/imm32/size -17934 0x30/0 0x64/d 0x2f/slash 0x6f/o 0x72/r 0x2d/dash 0x77/w 0x69/i 0x74/t 0x68/h 0x2d/dash 0x65/e 0x61/a 0x78/x -17935 _string_0f_82_jump_label: # (payload array byte) -17936 0x11/imm32/alloc-id:fake:payload -17937 # "0f 82/jump-if-addr<" -17938 0x13/imm32/size -17939 0x30/0 0x66/f 0x20/space 0x38/8 0x32/2 0x2f/slash 0x6a/j 0x75/u 0x6d/m 0x70/p 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x61/a 0x64/d 0x64/d 0x72/r 0x3c/< -17940 _string_0f_82_jump_break: # (payload array byte) -17941 0x11/imm32/alloc-id:fake:payload -17942 # "0f 82/jump-if-addr< break/disp32" -17943 0x20/imm32/size -17944 0x30/0 0x66/f 0x20/space 0x38/8 0x32/2 0x2f/slash 0x6a/j 0x75/u 0x6d/m 0x70/p 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x61/a 0x64/d 0x64/d 0x72/r 0x3c/< 0x20/space 0x62/b 0x72/r 0x65/e 0x61/a 0x6b/k 0x2f/slash 0x64/d 0x69/i 0x73/s 0x70/p 0x33/3 0x32/2 -17945 _string_0f_82_jump_loop: # (payload array byte) +17875 0x11/imm32/alloc-id:fake +17876 _string-loop-if-addr>=/imm32/name +17877 0x11/imm32/alloc-id:fake +17878 Single-lit-var/imm32/inouts +17879 0/imm32/no-outputs +17880 0/imm32/no-outputs +17881 0x11/imm32/alloc-id:fake +17882 _string_0f_83_jump_label/imm32/subx-name +17883 0/imm32/no-rm32 +17884 0/imm32/no-r32 +17885 0/imm32/no-imm32 +17886 0/imm32/no-imm8 +17887 1/imm32/disp32-is-first-inout +17888 0/imm32/no-output +17889 0x11/imm32/alloc-id:fake +17890 _Primitive-loop-if-=-named/imm32/next +17891 _Primitive-loop-if-=-named: # (payload primitive) +17892 0x11/imm32/alloc-id:fake:payload +17893 0x11/imm32/alloc-id:fake +17894 _string-loop-if-=/imm32/name +17895 0x11/imm32/alloc-id:fake +17896 Single-lit-var/imm32/inouts +17897 0/imm32/no-outputs +17898 0/imm32/no-outputs +17899 0x11/imm32/alloc-id:fake +17900 _string_0f_84_jump_label/imm32/subx-name +17901 0/imm32/no-rm32 +17902 0/imm32/no-r32 +17903 0/imm32/no-imm32 +17904 0/imm32/no-imm8 +17905 1/imm32/disp32-is-first-inout +17906 0/imm32/no-output +17907 0x11/imm32/alloc-id:fake +17908 _Primitive-loop-if-!=-named/imm32/next +17909 _Primitive-loop-if-!=-named: # (payload primitive) +17910 0x11/imm32/alloc-id:fake:payload +17911 0x11/imm32/alloc-id:fake +17912 _string-loop-if-!=/imm32/name +17913 0x11/imm32/alloc-id:fake +17914 Single-lit-var/imm32/inouts +17915 0/imm32/no-outputs +17916 0/imm32/no-outputs +17917 0x11/imm32/alloc-id:fake +17918 _string_0f_85_jump_label/imm32/subx-name +17919 0/imm32/no-rm32 +17920 0/imm32/no-r32 +17921 0/imm32/no-imm32 +17922 0/imm32/no-imm8 +17923 1/imm32/disp32-is-first-inout +17924 0/imm32/no-output +17925 0x11/imm32/alloc-id:fake +17926 _Primitive-loop-if-addr<=-named/imm32/next +17927 _Primitive-loop-if-addr<=-named: # (payload primitive) +17928 0x11/imm32/alloc-id:fake:payload +17929 0x11/imm32/alloc-id:fake +17930 _string-loop-if-addr<=/imm32/name +17931 0x11/imm32/alloc-id:fake +17932 Single-lit-var/imm32/inouts +17933 0/imm32/no-outputs +17934 0/imm32/no-outputs +17935 0x11/imm32/alloc-id:fake +17936 _string_0f_86_jump_label/imm32/subx-name +17937 0/imm32/no-rm32 +17938 0/imm32/no-r32 +17939 0/imm32/no-imm32 +17940 0/imm32/no-imm8 +17941 1/imm32/disp32-is-first-inout +17942 0/imm32/no-output +17943 0x11/imm32/alloc-id:fake +17944 _Primitive-loop-if-addr>-named/imm32/next +17945 _Primitive-loop-if-addr>-named: # (payload primitive) 17946 0x11/imm32/alloc-id:fake:payload -17947 # "0f 82/jump-if-addr< loop/disp32" -17948 0x1f/imm32/size -17949 0x30/0 0x66/f 0x20/space 0x38/8 0x32/2 0x2f/slash 0x6a/j 0x75/u 0x6d/m 0x70/p 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x61/a 0x64/d 0x64/d 0x72/r 0x3c/< 0x20/space 0x6c/l 0x6f/o 0x6f/o 0x70/p 0x2f/slash 0x64/d 0x69/i 0x73/s 0x70/p 0x33/3 0x32/2 -17950 _string_0f_83_jump_label: # (payload array byte) -17951 0x11/imm32/alloc-id:fake:payload -17952 # "0f 83/jump-if-addr>=" -17953 0x14/imm32/size -17954 0x30/0 0x66/f 0x20/space 0x38/8 0x33/3 0x2f/slash 0x6a/j 0x75/u 0x6d/m 0x70/p 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x61/a 0x64/d 0x64/d 0x72/r 0x3e/> 0x3d/= -17955 _string_0f_83_jump_break: # (payload array byte) -17956 0x11/imm32/alloc-id:fake:payload -17957 # "0f 83/jump-if-addr>= break/disp32" -17958 0x21/imm32/size -17959 0x30/0 0x66/f 0x20/space 0x38/8 0x33/3 0x2f/slash 0x6a/j 0x75/u 0x6d/m 0x70/p 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x61/a 0x64/d 0x64/d 0x72/r 0x3e/> 0x3d/= 0x20/space 0x62/b 0x72/r 0x65/e 0x61/a 0x6b/k 0x2f/slash 0x64/d 0x69/i 0x73/s 0x70/p 0x33/3 0x32/2 -17960 _string_0f_83_jump_loop: # (payload array byte) -17961 0x11/imm32/alloc-id:fake:payload -17962 # "0f 83/jump-if-addr>= loop/disp32" -17963 0x20/imm32/size -17964 0x30/0 0x66/f 0x20/space 0x38/8 0x33/3 0x2f/slash 0x6a/j 0x75/u 0x6d/m 0x70/p 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x61/a 0x64/d 0x64/d 0x72/r 0x3e/> 0x3d/= 0x20/space 0x6c/l 0x6f/o 0x6f/o 0x70/p 0x2f/slash 0x64/d 0x69/i 0x73/s 0x70/p 0x33/3 0x32/2 -17965 _string_0f_84_jump_label: # (payload array byte) -17966 0x11/imm32/alloc-id:fake:payload -17967 # "0f 84/jump-if-=" -17968 0xf/imm32/size -17969 0x30/0 0x66/f 0x20/space 0x38/8 0x34/4 0x2f/slash 0x6a/j 0x75/u 0x6d/m 0x70/p 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x3d/= -17970 _string_0f_84_jump_break: # (payload array byte) -17971 0x11/imm32/alloc-id:fake:payload -17972 # "0f 84/jump-if-= break/disp32" -17973 0x1c/imm32/size -17974 0x30/0 0x66/f 0x20/space 0x38/8 0x34/4 0x2f/slash 0x6a/j 0x75/u 0x6d/m 0x70/p 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x3d/= 0x20/space 0x62/b 0x72/r 0x65/e 0x61/a 0x6b/k 0x2f/slash 0x64/d 0x69/i 0x73/s 0x70/p 0x33/3 0x32/2 -17975 _string_0f_84_jump_loop: # (payload array byte) -17976 0x11/imm32/alloc-id:fake:payload -17977 # "0f 84/jump-if-= loop/disp32" -17978 0x1b/imm32/size -17979 0x30/0 0x66/f 0x20/space 0x38/8 0x34/4 0x2f/slash 0x6a/j 0x75/u 0x6d/m 0x70/p 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x3d/= 0x6c/l 0x6f/o 0x6f/o 0x70/p 0x2f/slash 0x64/d 0x69/i 0x73/s 0x70/p 0x33/3 0x32/2 -17980 _string_0f_85_jump_label: # (payload array byte) -17981 0x11/imm32/alloc-id:fake:payload -17982 # "0f 85/jump-if-!=" -17983 0x10/imm32/size -17984 0x30/0 0x66/f 0x20/space 0x38/8 0x35/5 0x2f/slash 0x6a/j 0x75/u 0x6d/m 0x70/p 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x21/! 0x3d/= -17985 _string_0f_85_jump_break: # (payload array byte) -17986 0x11/imm32/alloc-id:fake:payload -17987 # "0f 85/jump-if-!= break/disp32" -17988 0x1d/imm32/size -17989 0x30/0 0x66/f 0x20/space 0x38/8 0x35/5 0x2f/slash 0x6a/j 0x75/u 0x6d/m 0x70/p 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x21/! 0x3d/= 0x20/space 0x62/b 0x72/r 0x65/e 0x61/a 0x6b/k 0x2f/slash 0x64/d 0x69/i 0x73/s 0x70/p 0x33/3 0x32/2 -17990 _string_0f_85_jump_loop: # (payload array byte) -17991 0x11/imm32/alloc-id:fake:payload -17992 # "0f 85/jump-if-!= loop/disp32" -17993 0x1c/imm32/size -17994 0x30/0 0x66/f 0x20/space 0x38/8 0x35/5 0x2f/slash 0x6a/j 0x75/u 0x6d/m 0x70/p 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x21/! 0x3d/= 0x20/space 0x6c/l 0x6f/o 0x6f/o 0x70/p 0x2f/slash 0x64/d 0x69/i 0x73/s 0x70/p 0x33/3 0x32/2 -17995 _string_0f_86_jump_label: # (payload array byte) -17996 0x11/imm32/alloc-id:fake:payload -17997 # "0f 86/jump-if-addr<=" -17998 0x14/imm32/size -17999 0x30/0 0x66/f 0x20/space 0x38/8 0x36/6 0x2f/slash 0x6a/j 0x75/u 0x6d/m 0x70/p 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x61/a 0x64/d 0x64/d 0x72/r 0x3c/< 0x3d/= -18000 _string_0f_86_jump_break: # (payload array byte) -18001 0x11/imm32/alloc-id:fake:payload -18002 # "0f 86/jump-if-addr<= break/disp32" -18003 0x21/imm32/size -18004 0x30/0 0x66/f 0x20/space 0x38/8 0x36/6 0x2f/slash 0x6a/j 0x75/u 0x6d/m 0x70/p 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x61/a 0x64/d 0x64/d 0x72/r 0x3c/< 0x3d/= 0x20/space 0x62/b 0x72/r 0x65/e 0x61/a 0x6b/k 0x2f/slash 0x64/d 0x69/i 0x73/s 0x70/p 0x33/3 0x32/2 -18005 _string_0f_86_jump_loop: # (payload array byte) -18006 0x11/imm32/alloc-id:fake:payload -18007 # "0f 86/jump-if-addr<= loop/disp32" -18008 0x20/imm32/size -18009 0x30/0 0x66/f 0x20/space 0x38/8 0x36/6 0x2f/slash 0x6a/j 0x75/u 0x6d/m 0x70/p 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x61/a 0x64/d 0x64/d 0x72/r 0x3c/< 0x3d/= 0x20/space 0x6c/l 0x6f/o 0x6f/o 0x70/p 0x2f/slash 0x64/d 0x69/i 0x73/s 0x70/p 0x33/3 0x32/2 -18010 _string_0f_87_jump_label: # (payload array byte) -18011 0x11/imm32/alloc-id:fake:payload -18012 # "0f 87/jump-if-addr>" -18013 0x13/imm32/size -18014 0x30/0 0x66/f 0x20/space 0x38/8 0x37/7 0x2f/slash 0x6a/j 0x75/u 0x6d/m 0x70/p 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x61/a 0x64/d 0x64/d 0x72/r 0x3e/> -18015 _string_0f_87_jump_break: # (payload array byte) -18016 0x11/imm32/alloc-id:fake:payload -18017 # "0f 87/jump-if-addr> break/disp32" -18018 0x20/imm32/size -18019 0x30/0 0x66/f 0x20/space 0x38/8 0x37/7 0x2f/slash 0x6a/j 0x75/u 0x6d/m 0x70/p 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x61/a 0x64/d 0x64/d 0x72/r 0x3e/> 0x20/space 0x62/b 0x72/r 0x65/e 0x61/a 0x6b/k 0x2f/slash 0x64/d 0x69/i 0x73/s 0x70/p 0x33/3 0x32/2 -18020 _string_0f_87_jump_loop: # (payload array byte) -18021 0x11/imm32/alloc-id:fake:payload -18022 # "0f 87/jump-if-addr> loop/disp32" -18023 0x1f/imm32/size -18024 0x30/0 0x66/f 0x20/space 0x38/8 0x37/7 0x2f/slash 0x6a/j 0x75/u 0x6d/m 0x70/p 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x61/a 0x64/d 0x64/d 0x72/r 0x3e/> 0x20/space 0x6c/l 0x6f/o 0x6f/o 0x70/p 0x2f/slash 0x64/d 0x69/i 0x73/s 0x70/p 0x33/3 0x32/2 -18025 _string_0f_8c_jump_label: # (payload array byte) -18026 0x11/imm32/alloc-id:fake:payload -18027 # "0f 8c/jump-if-<" -18028 0xf/imm32/size -18029 0x30/0 0x66/f 0x20/space 0x38/8 0x63/c 0x2f/slash 0x6a/j 0x75/u 0x6d/m 0x70/p 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x3c/< -18030 _string_0f_8c_jump_break: # (payload array byte) -18031 0x11/imm32/alloc-id:fake:payload -18032 # "0f 8c/jump-if-< break/disp32" -18033 0x1c/imm32/size -18034 0x30/0 0x66/f 0x20/space 0x38/8 0x63/c 0x2f/slash 0x6a/j 0x75/u 0x6d/m 0x70/p 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x3c/< 0x20/space 0x62/b 0x72/r 0x65/e 0x61/a 0x6b/k 0x2f/slash 0x64/d 0x69/i 0x73/s 0x70/p 0x33/3 0x32/2 -18035 _string_0f_8c_jump_loop: # (payload array byte) +17947 0x11/imm32/alloc-id:fake +17948 _string-loop-if-addr>/imm32/name +17949 0x11/imm32/alloc-id:fake +17950 Single-lit-var/imm32/inouts +17951 0/imm32/no-outputs +17952 0/imm32/no-outputs +17953 0x11/imm32/alloc-id:fake +17954 _string_0f_87_jump_label/imm32/subx-name +17955 0/imm32/no-rm32 +17956 0/imm32/no-r32 +17957 0/imm32/no-imm32 +17958 0/imm32/no-imm8 +17959 1/imm32/disp32-is-first-inout +17960 0/imm32/no-output +17961 0x11/imm32/alloc-id:fake +17962 _Primitive-loop-if-<-named/imm32/next +17963 _Primitive-loop-if-<-named: # (payload primitive) +17964 0x11/imm32/alloc-id:fake:payload +17965 0x11/imm32/alloc-id:fake +17966 _string-loop-if-</imm32/name +17967 0x11/imm32/alloc-id:fake +17968 Single-lit-var/imm32/inouts +17969 0/imm32/no-outputs +17970 0/imm32/no-outputs +17971 0x11/imm32/alloc-id:fake +17972 _string_0f_8c_jump_label/imm32/subx-name +17973 0/imm32/no-rm32 +17974 0/imm32/no-r32 +17975 0/imm32/no-imm32 +17976 0/imm32/no-imm8 +17977 1/imm32/disp32-is-first-inout +17978 0/imm32/no-output +17979 0x11/imm32/alloc-id:fake +17980 _Primitive-loop-if->=-named/imm32/next +17981 _Primitive-loop-if->=-named: # (payload primitive) +17982 0x11/imm32/alloc-id:fake:payload +17983 0x11/imm32/alloc-id:fake +17984 _string-loop-if->=/imm32/name +17985 0x11/imm32/alloc-id:fake +17986 Single-lit-var/imm32/inouts +17987 0/imm32/no-outputs +17988 0/imm32/no-outputs +17989 0x11/imm32/alloc-id:fake +17990 _string_0f_8d_jump_label/imm32/subx-name +17991 0/imm32/no-rm32 +17992 0/imm32/no-r32 +17993 0/imm32/no-imm32 +17994 0/imm32/no-imm8 +17995 1/imm32/disp32-is-first-inout +17996 0/imm32/no-output +17997 0x11/imm32/alloc-id:fake +17998 _Primitive-loop-if-<=-named/imm32/next +17999 _Primitive-loop-if-<=-named: # (payload primitive) +18000 0x11/imm32/alloc-id:fake:payload +18001 0x11/imm32/alloc-id:fake +18002 _string-loop-if-<=/imm32/name +18003 0x11/imm32/alloc-id:fake +18004 Single-lit-var/imm32/inouts +18005 0/imm32/no-outputs +18006 0/imm32/no-outputs +18007 0x11/imm32/alloc-id:fake +18008 _string_0f_8e_jump_label/imm32/subx-name +18009 0/imm32/no-rm32 +18010 0/imm32/no-r32 +18011 0/imm32/no-imm32 +18012 0/imm32/no-imm8 +18013 1/imm32/disp32-is-first-inout +18014 0/imm32/no-output +18015 0x11/imm32/alloc-id:fake +18016 _Primitive-loop-if->-named/imm32/next +18017 _Primitive-loop-if->-named: # (payload primitive) +18018 0x11/imm32/alloc-id:fake:payload +18019 0x11/imm32/alloc-id:fake +18020 _string-loop-if->/imm32/name +18021 0x11/imm32/alloc-id:fake +18022 Single-lit-var/imm32/inouts +18023 0/imm32/no-outputs +18024 0/imm32/no-outputs +18025 0x11/imm32/alloc-id:fake +18026 _string_0f_8f_jump_label/imm32/subx-name +18027 0/imm32/no-rm32 +18028 0/imm32/no-r32 +18029 0/imm32/no-imm32 +18030 0/imm32/no-imm8 +18031 1/imm32/disp32-is-first-inout +18032 0/imm32/no-output +18033 0x11/imm32/alloc-id:fake +18034 _Primitive-loop-named/imm32/next # we probably don't need an unconditional break +18035 _Primitive-loop-named: # (payload primitive) 18036 0x11/imm32/alloc-id:fake:payload -18037 # "0f 8c/jump-if-< loop/disp32" -18038 0x1b/imm32/size -18039 0x30/0 0x66/f 0x20/space 0x38/8 0x63/c 0x2f/slash 0x6a/j 0x75/u 0x6d/m 0x70/p 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x3c/< 0x20/space 0x6c/l 0x6f/o 0x6f/o 0x70/p 0x2f/slash 0x64/d 0x69/i 0x73/s 0x70/p 0x33/3 0x32/2 -18040 _string_0f_8d_jump_label: # (payload array byte) -18041 0x11/imm32/alloc-id:fake:payload -18042 # "0f 8d/jump-if->=" -18043 0x10/imm32/size -18044 0x30/0 0x66/f 0x20/space 0x38/8 0x64/d 0x2f/slash 0x6a/j 0x75/u 0x6d/m 0x70/p 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x3e/> 0x3d/= -18045 _string_0f_8d_jump_break: # (payload array byte) -18046 0x11/imm32/alloc-id:fake:payload -18047 # "0f 8d/jump-if->= break/disp32" -18048 0x1d/imm32/size -18049 0x30/0 0x66/f 0x20/space 0x38/8 0x64/d 0x2f/slash 0x6a/j 0x75/u 0x6d/m 0x70/p 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x3e/> 0x3d/= 0x20/space 0x62/b 0x72/r 0x65/e 0x61/a 0x6b/k 0x2f/slash 0x64/d 0x69/i 0x73/s 0x70/p 0x33/3 0x32/2 -18050 _string_0f_8d_jump_loop: # (payload array byte) -18051 0x11/imm32/alloc-id:fake:payload -18052 # "0f 8d/jump-if->= loop/disp32" -18053 0x1c/imm32/size -18054 0x30/0 0x66/f 0x20/space 0x38/8 0x64/d 0x2f/slash 0x6a/j 0x75/u 0x6d/m 0x70/p 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x3e/> 0x3d/= 0x20/space 0x6c/l 0x6f/o 0x6f/o 0x70/p 0x2f/slash 0x64/d 0x69/i 0x73/s 0x70/p 0x33/3 0x32/2 -18055 _string_0f_8e_jump_label: # (payload array byte) +18037 0x11/imm32/alloc-id:fake +18038 _string-loop/imm32/name +18039 0x11/imm32/alloc-id:fake +18040 Single-lit-var/imm32/inouts +18041 0/imm32/no-outputs +18042 0/imm32/no-outputs +18043 0x11/imm32/alloc-id:fake +18044 _string_e9_jump_label/imm32/subx-name +18045 0/imm32/no-rm32 +18046 0/imm32/no-r32 +18047 0/imm32/no-imm32 +18048 0/imm32/no-imm8 +18049 1/imm32/disp32-is-first-inout +18050 0/imm32/no-output +18051 0/imm32/next +18052 0/imm32/next +18053 +18054 # string literals for Mu instructions +18055 _string-add: # (payload array byte) 18056 0x11/imm32/alloc-id:fake:payload -18057 # "0f 8e/jump-if-<=" -18058 0x10/imm32/size -18059 0x30/0 0x66/f 0x20/space 0x38/8 0x65/e 0x2f/slash 0x6a/j 0x75/u 0x6d/m 0x70/p 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x3c/< 0x3d/= -18060 _string_0f_8e_jump_break: # (payload array byte) +18057 # "add" +18058 0x3/imm32/size +18059 0x61/a 0x64/d 0x64/d +18060 _string-address: # (payload array byte) 18061 0x11/imm32/alloc-id:fake:payload -18062 # "0f 8e/jump-if-<= break/disp32" -18063 0x1d/imm32/size -18064 0x30/0 0x66/f 0x20/space 0x38/8 0x65/e 0x2f/slash 0x6a/j 0x75/u 0x6d/m 0x70/p 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x3c/< 0x3d/= 0x20/space 0x62/b 0x72/r 0x65/e 0x61/a 0x6b/k 0x2f/slash 0x64/d 0x69/i 0x73/s 0x70/p 0x33/3 0x32/2 -18065 _string_0f_8e_jump_loop: # (payload array byte) +18062 # "address" +18063 0x7/imm32/size +18064 0x61/a 0x64/d 0x64/d 0x72/r 0x65/e 0x73/s 0x73/s +18065 _string-add-to: # (payload array byte) 18066 0x11/imm32/alloc-id:fake:payload -18067 # "0f 8e/jump-if-<= loop/disp32" -18068 0x1c/imm32/size -18069 0x30/0 0x66/f 0x20/space 0x38/8 0x65/e 0x2f/slash 0x6a/j 0x75/u 0x6d/m 0x70/p 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x3c/< 0x3d/= 0x20/space 0x6c/l 0x6f/o 0x6f/o 0x70/p 0x2f/slash 0x64/d 0x69/i 0x73/s 0x70/p 0x33/3 0x32/2 -18070 _string_0f_8f_jump_label: # (payload array byte) +18067 # "add-to" +18068 0x6/imm32/size +18069 0x61/a 0x64/d 0x64/d 0x2d/dash 0x74/t 0x6f/o +18070 _string-and: # (payload array byte) 18071 0x11/imm32/alloc-id:fake:payload -18072 # "0f 8f/jump-if->" -18073 0xf/imm32/size -18074 0x30/0 0x66/f 0x20/space 0x38/8 0x66/f 0x2f/slash 0x6a/j 0x75/u 0x6d/m 0x70/p 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x3e/> -18075 _string_0f_8f_jump_break: # (payload array byte) +18072 # "and" +18073 0x3/imm32/size +18074 0x61/a 0x6e/n 0x64/d +18075 _string-and-with: # (payload array byte) 18076 0x11/imm32/alloc-id:fake:payload -18077 # "0f 8f/jump-if-> break/disp32" -18078 0x1c/imm32/size -18079 0x30/0 0x66/f 0x20/space 0x38/8 0x66/f 0x2f/slash 0x6a/j 0x75/u 0x6d/m 0x70/p 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x3e/> 0x20/space 0x62/b 0x72/r 0x65/e 0x61/a 0x6b/k 0x2f/slash 0x64/d 0x69/i 0x73/s 0x70/p 0x33/3 0x32/2 -18080 _string_0f_8f_jump_loop: # (payload array byte) +18077 # "and-with" +18078 0x8/imm32/size +18079 0x61/a 0x6e/n 0x64/d 0x2d/dash 0x77/w 0x69/i 0x74/t 0x68/h +18080 _string-break: # (payload array byte) 18081 0x11/imm32/alloc-id:fake:payload -18082 # "0f 8f/jump-if-> loop/disp32" -18083 0x1b/imm32/size -18084 0x30/0 0x66/f 0x20/space 0x38/8 0x66/f 0x2f/slash 0x6a/j 0x75/u 0x6d/m 0x70/p 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x3e/> 0x20/space 0x6c/l 0x6f/o 0x6f/o 0x70/p 0x2f/slash 0x64/d 0x69/i 0x73/s 0x70/p 0x33/3 0x32/2 -18085 _string_0f_af_multiply: # (payload array byte) +18082 # "break" +18083 0x5/imm32/size +18084 0x62/b 0x72/r 0x65/e 0x61/a 0x6b/k +18085 _string-break-if-<: # (payload array byte) 18086 0x11/imm32/alloc-id:fake:payload -18087 # "0f af/multiply" -18088 0xe/imm32/size -18089 0x30/0 0x66/f 0x20/space 0x61/a 0x66/f 0x2f/slash 0x6d/m 0x75/u 0x6c/l 0x74/t 0x69/i 0x70/p 0x6c/l 0x79/y -18090 _string_21_and_with: # (payload array byte) +18087 # "break-if-<" +18088 0xa/imm32/size +18089 0x62/b 0x72/r 0x65/e 0x61/a 0x6b/k 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x3c/< +18090 _string-break-if-<=: # (payload array byte) 18091 0x11/imm32/alloc-id:fake:payload -18092 # "21/and-with" +18092 # "break-if-<=" 18093 0xb/imm32/size -18094 0x32/2 0x31/1 0x2f/slash 0x61/a 0x6e/n 0x64/d 0x2d/dash 0x77/w 0x69/i 0x74/t 0x68/h -18095 _string_23_and: # (payload array byte) +18094 0x62/b 0x72/r 0x65/e 0x61/a 0x6b/k 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x3c/< 0x3d/= +18095 _string-break-if-=: # (payload array byte) 18096 0x11/imm32/alloc-id:fake:payload -18097 # "23/and" -18098 0x6/imm32/size -18099 0x32/2 0x33/3 0x2f/slash 0x61/a 0x6e/n 0x64/d -18100 _string_25_and_with_eax: # (payload array byte) +18097 # "break-if-=" +18098 0xa/imm32/size +18099 0x62/b 0x72/r 0x65/e 0x61/a 0x6b/k 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x3d/= +18100 _string-break-if->: # (payload array byte) 18101 0x11/imm32/alloc-id:fake:payload -18102 # "25/and-with-eax" -18103 0xf/imm32/size -18104 0x32/2 0x35/5 0x2f/slash 0x61/a 0x6e/n 0x64/d 0x2d/dash 0x77/w 0x69/i 0x74/t 0x68/h 0x2d/dash 0x65/e 0x61/a 0x78/x -18105 _string_29_subtract_from: # (payload array byte) +18102 # "break-if->" +18103 0xa/imm32/size +18104 0x62/b 0x72/r 0x65/e 0x61/a 0x6b/k 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x3e/> +18105 _string-break-if->=: # (payload array byte) 18106 0x11/imm32/alloc-id:fake:payload -18107 # "29/subtract-from" -18108 0x10/imm32/size -18109 0x32/2 0x39/9 0x2f/slash 0x73/s 0x75/u 0x62/b 0x74/t 0x72/r 0x61/a 0x63/c 0x74/t 0x2d/dash 0x66/f 0x72/r 0x6f/o 0x6d/m -18110 _string_2b_subtract: # (payload array byte) +18107 # "break-if->=" +18108 0xb/imm32/size +18109 0x62/b 0x72/r 0x65/e 0x61/a 0x6b/k 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x3e/> 0x3d/= +18110 _string-break-if-!=: # (payload array byte) 18111 0x11/imm32/alloc-id:fake:payload -18112 # "2b/subtract" +18112 # "break-if-!=" 18113 0xb/imm32/size -18114 0x32/2 0x62/b 0x2f/slash 0x73/s 0x75/u 0x62/b 0x74/t 0x72/r 0x61/a 0x63/c 0x74/t -18115 _string_2d_subtract_from_eax: # (payload array byte) +18114 0x62/b 0x72/r 0x65/e 0x61/a 0x6b/k 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x21/! 0x3d/= +18115 _string-break-if-addr<: # (payload array byte) 18116 0x11/imm32/alloc-id:fake:payload -18117 # "2d/subtract-from-eax" -18118 0x14/imm32/size -18119 0x32/2 0x64/d 0x2f/slash 0x73/s 0x75/u 0x62/b 0x74/t 0x72/r 0x61/a 0x63/c 0x74/t 0x2d/dash 0x66/f 0x72/r 0x6f/o 0x6d/m 0x2d/dash 0x65/e 0x61/a 0x78/x -18120 _string_31_xor_with: # (payload array byte) +18117 # "break-if-addr<" +18118 0xe/imm32/size +18119 0x62/b 0x72/r 0x65/e 0x61/a 0x6b/k 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x61/a 0x64/d 0x64/d 0x72/r 0x3c/< +18120 _string-break-if-addr<=: # (payload array byte) 18121 0x11/imm32/alloc-id:fake:payload -18122 # "31/xor-with" -18123 0xb/imm32/size -18124 0x33/3 0x31/1 0x2f/slash 0x78/x 0x6f/o 0x72/r 0x2d/dash 0x77/w 0x69/i 0x74/t 0x68/h -18125 _string_33_xor: # (payload array byte) +18122 # "break-if-addr<=" +18123 0xf/imm32/size +18124 0x62/b 0x72/r 0x65/e 0x61/a 0x6b/k 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x61/a 0x64/d 0x64/d 0x72/r 0x3c/< 0x3d/= +18125 _string-break-if-addr>: # (payload array byte) 18126 0x11/imm32/alloc-id:fake:payload -18127 # "33/xor" -18128 0x6/imm32/size -18129 0x33/3 0x33/3 0x2f/slash 0x78/x 0x6f/o 0x72/r -18130 _string_35_xor_with_eax: # (payload array byte) +18127 # "break-if-addr>" +18128 0xe/imm32/size +18129 0x62/b 0x72/r 0x65/e 0x61/a 0x6b/k 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x61/a 0x64/d 0x64/d 0x72/r 0x3e/> +18130 _string-break-if-addr>=: # (payload array byte) 18131 0x11/imm32/alloc-id:fake:payload -18132 # "35/xor-with-eax" +18132 # "break-if-addr>=" 18133 0xf/imm32/size -18134 0x33/3 0x35/5 0x2f/slash 0x78/x 0x6f/o 0x72/r 0x2d/dash 0x77/w 0x69/i 0x74/t 0x68/h 0x2d/dash 0x65/e 0x61/a 0x78/x -18135 _string_39_compare->: # (payload array byte) +18134 0x62/b 0x72/r 0x65/e 0x61/a 0x6b/k 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x61/a 0x64/d 0x64/d 0x72/r 0x3e/> 0x3d/= +18135 _string-compare: # (payload array byte) 18136 0x11/imm32/alloc-id:fake:payload -18137 # "39/compare->" -18138 0xc/imm32/size -18139 0x33/3 0x39/9 0x2f/slash 0x63/c 0x6f/o 0x6d/m 0x70/p 0x61/a 0x72/r 0x65/e 0x2d/dash 0x3e/> -18140 _string_3b_compare<-: # (payload array byte) +18137 # "compare" +18138 0x7/imm32/size +18139 0x63/c 0x6f/o 0x6d/m 0x70/p 0x61/a 0x72/r 0x65/e +18140 _string-copy: # (payload array byte) 18141 0x11/imm32/alloc-id:fake:payload -18142 # "3b/compare<-" -18143 0xc/imm32/size -18144 0x33/3 0x62/b 0x2f/slash 0x63/c 0x6f/o 0x6d/m 0x70/p 0x61/a 0x72/r 0x65/e 0x3c/< 0x2d/dash -18145 _string_3d_compare_eax_with: # (payload array byte) +18142 # "copy" +18143 0x4/imm32/size +18144 0x63/c 0x6f/o 0x70/p 0x79/y +18145 _string-copy-to: # (payload array byte) 18146 0x11/imm32/alloc-id:fake:payload -18147 # "3d/compare-eax-with" -18148 0x13/imm32/size -18149 0x33/3 0x64/d 0x2f/slash 0x63/c 0x6f/o 0x6d/m 0x70/p 0x61/a 0x72/r 0x65/e 0x2d/dash 0x65/e 0x61/a 0x78/x 0x2d/dash 0x77/w 0x69/i 0x74/t 0x68/h -18150 _string_40_increment_eax: # (payload array byte) +18147 # "copy-to" +18148 0x7/imm32/size +18149 0x63/c 0x6f/o 0x70/p 0x79/y 0x2d/dash 0x74/t 0x6f/o +18150 _string-copy-byte: 18151 0x11/imm32/alloc-id:fake:payload -18152 # "40/increment-eax" -18153 0x10/imm32/size -18154 0x34/4 0x30/0 0x2f/slash 0x69/i 0x6e/n 0x63/c 0x72/r 0x65/e 0x6d/m 0x65/e 0x6e/n 0x74/t 0x2d/dash 0x65/e 0x61/a 0x78/x -18155 _string_41_increment_ecx: # (payload array byte) +18152 # "copy-byte" +18153 0x9/imm32/size +18154 0x63/c 0x6f/o 0x70/p 0x79/y 0x2d/- 0x62/b 0x79/y 0x74/t 0x65/e +18155 _string-copy-byte-to: 18156 0x11/imm32/alloc-id:fake:payload -18157 # "41/increment-ecx" -18158 0x10/imm32/size -18159 0x34/4 0x31/1 0x2f/slash 0x69/i 0x6e/n 0x63/c 0x72/r 0x65/e 0x6d/m 0x65/e 0x6e/n 0x74/t 0x2d/dash 0x65/e 0x63/c 0x78/x -18160 _string_42_increment_edx: # (payload array byte) +18157 # "copy-byte-to" +18158 0xc/imm32/size +18159 0x63/c 0x6f/o 0x70/p 0x79/y 0x2d/- 0x62/b 0x79/y 0x74/t 0x65/e 0x2d/- 0x74/t 0x6f/o +18160 _string-decrement: # (payload array byte) 18161 0x11/imm32/alloc-id:fake:payload -18162 # "42/increment-edx" -18163 0x10/imm32/size -18164 0x34/4 0x32/2 0x2f/slash 0x69/i 0x6e/n 0x63/c 0x72/r 0x65/e 0x6d/m 0x65/e 0x6e/n 0x74/t 0x2d/dash 0x65/e 0x64/d 0x78/x -18165 _string_43_increment_ebx: # (payload array byte) +18162 # "decrement" +18163 0x9/imm32/size +18164 0x64/d 0x65/e 0x63/c 0x72/r 0x65/e 0x6d/m 0x65/e 0x6e/n 0x74/t +18165 _string-increment: # (payload array byte) 18166 0x11/imm32/alloc-id:fake:payload -18167 # "43/increment-ebx" -18168 0x10/imm32/size -18169 0x34/4 0x33/3 0x2f/slash 0x69/i 0x6e/n 0x63/c 0x72/r 0x65/e 0x6d/m 0x65/e 0x6e/n 0x74/t 0x2d/dash 0x65/e 0x62/b 0x78/x -18170 _string_46_increment_esi: # (payload array byte) +18167 # "increment" +18168 0x9/imm32/size +18169 0x69/i 0x6e/n 0x63/c 0x72/r 0x65/e 0x6d/m 0x65/e 0x6e/n 0x74/t +18170 _string-loop: # (payload array byte) 18171 0x11/imm32/alloc-id:fake:payload -18172 # "46/increment-esi" -18173 0x10/imm32/size -18174 0x34/4 0x36/6 0x2f/slash 0x69/i 0x6e/n 0x63/c 0x72/r 0x65/e 0x6d/m 0x65/e 0x6e/n 0x74/t 0x2d/dash 0x65/e 0x73/s 0x69/i -18175 _string_47_increment_edi: # (payload array byte) +18172 # "loop" +18173 0x4/imm32/size +18174 0x6c/l 0x6f/o 0x6f/o 0x70/p +18175 _string-loop-if-<: # (payload array byte) 18176 0x11/imm32/alloc-id:fake:payload -18177 # "47/increment-edi" -18178 0x10/imm32/size -18179 0x34/4 0x37/7 0x2f/slash 0x69/i 0x6e/n 0x63/c 0x72/r 0x65/e 0x6d/m 0x65/e 0x6e/n 0x74/t 0x2d/dash 0x65/e 0x64/d 0x69/i -18180 _string_48_decrement_eax: # (payload array byte) +18177 # "loop-if-<" +18178 0x9/imm32/size +18179 0x6c/l 0x6f/o 0x6f/o 0x70/p 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x3c/< +18180 _string-loop-if-<=: # (payload array byte) 18181 0x11/imm32/alloc-id:fake:payload -18182 # "48/decrement-eax" -18183 0x10/imm32/size -18184 0x34/4 0x38/8 0x2f/slash 0x64/d 0x65/e 0x63/c 0x72/r 0x65/e 0x6d/m 0x65/e 0x6e/n 0x74/t 0x2d/dash 0x65/e 0x61/a 0x78/x -18185 _string_49_decrement_ecx: # (payload array byte) +18182 # "loop-if-<=" +18183 0xa/imm32/size +18184 0x6c/l 0x6f/o 0x6f/o 0x70/p 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x3c/< 0x3d/= +18185 _string-loop-if-=: # (payload array byte) 18186 0x11/imm32/alloc-id:fake:payload -18187 # "49/decrement-ecx" -18188 0x10/imm32/size -18189 0x34/4 0x39/9 0x2f/slash 0x64/d 0x65/e 0x63/c 0x72/r 0x65/e 0x6d/m 0x65/e 0x6e/n 0x74/t 0x2d/dash 0x65/e 0x63/c 0x78/x -18190 _string_4a_decrement_edx: # (payload array byte) +18187 # "loop-if-=" +18188 0x9/imm32/size +18189 0x6c/l 0x6f/o 0x6f/o 0x70/p 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x3d/= +18190 _string-loop-if->: # (payload array byte) 18191 0x11/imm32/alloc-id:fake:payload -18192 # "4a/decrement-edx" -18193 0x10/imm32/size -18194 0x34/4 0x61/a 0x2f/slash 0x64/d 0x65/e 0x63/c 0x72/r 0x65/e 0x6d/m 0x65/e 0x6e/n 0x74/t 0x2d/dash 0x65/e 0x64/d 0x78/x -18195 _string_4b_decrement_ebx: # (payload array byte) +18192 # "loop-if->" +18193 0x9/imm32/size +18194 0x6c/l 0x6f/o 0x6f/o 0x70/p 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x3e/> +18195 _string-loop-if->=: # (payload array byte) 18196 0x11/imm32/alloc-id:fake:payload -18197 # "4b/decrement-ebx" -18198 0x10/imm32/size -18199 0x34/4 0x62/b 0x2f/slash 0x64/d 0x65/e 0x63/c 0x72/r 0x65/e 0x6d/m 0x65/e 0x6e/n 0x74/t 0x2d/dash 0x65/e 0x62/b 0x78/x -18200 _string_4e_decrement_esi: # (payload array byte) +18197 # "loop-if->=" +18198 0xa/imm32/size +18199 0x6c/l 0x6f/o 0x6f/o 0x70/p 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x3e/> 0x3d/= +18200 _string-loop-if-!=: # (payload array byte) 18201 0x11/imm32/alloc-id:fake:payload -18202 # "4e/decrement-esi" -18203 0x10/imm32/size -18204 0x34/4 0x65/e 0x2f/slash 0x64/d 0x65/e 0x63/c 0x72/r 0x65/e 0x6d/m 0x65/e 0x6e/n 0x74/t 0x2d/dash 0x65/e 0x73/s 0x69/i -18205 _string_4f_decrement_edi: # (payload array byte) +18202 # "loop-if-!=" +18203 0xa/imm32/size +18204 0x6c/l 0x6f/o 0x6f/o 0x70/p 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x21/! 0x3d/= +18205 _string-loop-if-addr<: # (payload array byte) 18206 0x11/imm32/alloc-id:fake:payload -18207 # "4f/decrement-edi" -18208 0x10/imm32/size -18209 0x34/4 0x66/f 0x2f/slash 0x64/d 0x65/e 0x63/c 0x72/r 0x65/e 0x6d/m 0x65/e 0x6e/n 0x74/t 0x2d/dash 0x65/e 0x64/d 0x69/i -18210 _string_81_subop_add: # (payload array byte) +18207 # "loop-if-addr<" +18208 0xd/imm32/size +18209 0x6c/l 0x6f/o 0x6f/o 0x70/p 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x61/a 0x64/d 0x64/d 0x72/r 0x3c/< +18210 _string-loop-if-addr<=: # (payload array byte) 18211 0x11/imm32/alloc-id:fake:payload -18212 # "81 0/subop/add" +18212 # "loop-if-addr<=" 18213 0xe/imm32/size -18214 0x38/8 0x31/1 0x20/space 0x30/0 0x2f/slash 0x73/s 0x75/u 0x62/b 0x6f/o 0x70/p 0x2f/slash 0x61/a 0x64/d 0x64/d -18215 _string_81_subop_or: # (payload array byte) +18214 0x6c/l 0x6f/o 0x6f/o 0x70/p 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x61/a 0x64/d 0x64/d 0x72/r 0x3c/< 0x3d/= +18215 _string-loop-if-addr>: # (payload array byte) 18216 0x11/imm32/alloc-id:fake:payload -18217 # "81 1/subop/or" +18217 # "loop-if-addr>" 18218 0xd/imm32/size -18219 0x38/8 0x31/1 0x20/space 0x31/1 0x2f/slash 0x73/s 0x75/u 0x62/b 0x6f/o 0x70/p 0x2f/slash 0x6f/o 0x72/r -18220 _string_81_subop_and: # (payload array byte) +18219 0x6c/l 0x6f/o 0x6f/o 0x70/p 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x61/a 0x64/d 0x64/d 0x72/r 0x3e/> +18220 _string-loop-if-addr>=: # (payload array byte) 18221 0x11/imm32/alloc-id:fake:payload -18222 # "81 4/subop/and" +18222 # "loop-if-addr>=" 18223 0xe/imm32/size -18224 0x38/8 0x31/1 0x20/space 0x34/4 0x2f/slash 0x73/s 0x75/u 0x62/b 0x6f/o 0x70/p 0x2f/slash 0x61/a 0x6e/n 0x64/d -18225 _string_81_subop_subtract: # (payload array byte) +18224 0x6c/l 0x6f/o 0x6f/o 0x70/p 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x61/a 0x64/d 0x64/d 0x72/r 0x3e/> 0x3d/= +18225 _string-multiply: # (payload array byte) 18226 0x11/imm32/alloc-id:fake:payload -18227 # "81 5/subop/subtract" -18228 0x13/imm32/size -18229 0x38/8 0x31/1 0x20/space 0x35/5 0x2f/slash 0x73/s 0x75/u 0x62/b 0x6f/o 0x70/p 0x2f/slash 0x73/s 0x75/u 0x62/b 0x74/t 0x72/r 0x61/a 0x63/c 0x74/t -18230 _string_81_subop_xor: # (payload array byte) +18227 # "multiply" +18228 0x8/imm32/size +18229 0x6d/m 0x75/u 0x6c/l 0x74/t 0x69/i 0x70/p 0x6c/l 0x79/y +18230 _string-or: # (payload array byte) 18231 0x11/imm32/alloc-id:fake:payload -18232 # "81 6/subop/xor" -18233 0xe/imm32/size -18234 0x38/8 0x31/1 0x20/space 0x36/6 0x2f/slash 0x73/s 0x75/u 0x62/b 0x6f/o 0x70/p 0x2f/slash 0x78/x 0x6f/o 0x72/r -18235 _string_81_subop_compare: # (payload array byte) +18232 # "or" +18233 0x2/imm32/size +18234 0x6f/o 0x72/r +18235 _string-or-with: # (payload array byte) 18236 0x11/imm32/alloc-id:fake:payload -18237 # "81 7/subop/compare" -18238 0x12/imm32/size -18239 0x38/8 0x31/1 0x20/space 0x37/7 0x2f/slash 0x73/s 0x75/u 0x62/b 0x6f/o 0x70/p 0x2f/slash 0x63/c 0x6f/o 0x6d/m 0x70/p 0x61/a 0x72/r 0x65/e -18240 _string_89_<-: # (payload array byte) +18237 # "or-with" +18238 0x7/imm32/size +18239 0x6f/o 0x72/r 0x2d/dash 0x77/w 0x69/i 0x74/t 0x68/h +18240 _string-subtract: # (payload array byte) 18241 0x11/imm32/alloc-id:fake:payload -18242 # "89/<-" -18243 0x5/imm32/size -18244 0x38/8 0x39/9 0x2f/slash 0x3c/< 0x2d/dash -18245 _string_8b_->: # (payload array byte) +18242 # "subtract" +18243 0x8/imm32/size +18244 0x73/s 0x75/u 0x62/b 0x74/t 0x72/r 0x61/a 0x63/c 0x74/t +18245 _string-subtract-from: # (payload array byte) 18246 0x11/imm32/alloc-id:fake:payload -18247 # "8b/->" -18248 0x5/imm32/size -18249 0x38/8 0x62/b 0x2f/slash 0x2d/dash 0x3e/> -18250 _string_8a_copy_byte: +18247 # "subtract-from" +18248 0xd/imm32/size +18249 0x73/s 0x75/u 0x62/b 0x74/t 0x72/r 0x61/a 0x63/c 0x74/t 0x2d/dash 0x66/f 0x72/r 0x6f/o 0x6d/m +18250 _string-xor: # (payload array byte) 18251 0x11/imm32/alloc-id:fake:payload -18252 # "8a/byte->" -18253 0x9/imm32/size -18254 0x38/8 0x61/a 0x2f// 0x62/b 0x79/y 0x74/t 0x65/e 0x2d/- 0x3e/> -18255 _string_88_copy_byte: +18252 # "xor" +18253 0x3/imm32/size +18254 0x78/x 0x6f/o 0x72/r +18255 _string-xor-with: # (payload array byte) 18256 0x11/imm32/alloc-id:fake:payload -18257 # "88/byte<-" -18258 0x9/imm32/size -18259 0x38/8 0x38/8 0x2f// 0x62/b 0x79/y 0x74/t 0x65/e 0x3c/< 0x2d/- -18260 _string_8d_copy_address: # (payload array byte) +18257 # "xor-with" +18258 0x8/imm32/size +18259 0x78/x 0x6f/o 0x72/r 0x2d/dash 0x77/w 0x69/i 0x74/t 0x68/h +18260 _string-shift-left: # (payload array byte) 18261 0x11/imm32/alloc-id:fake:payload -18262 # "8d/copy-address" -18263 0xf/imm32/size -18264 0x38/8 0x64/d 0x2f/slash 0x63/c 0x6f/o 0x70/p 0x79/y 0x2d/dash 0x61/a 0x64/d 0x64/d 0x72/r 0x65/e 0x73/s 0x73/s -18265 _string_b8_copy_to_eax: # (payload array byte) +18262 # "shift-left" +18263 0xa/imm32/size +18264 0x73/s 0x68/h 0x69/i 0x66/f 0x74/t 0x2d/dash 0x6c/l 0x65/e 0x66/f 0x74/t +18265 _string-shift-right: # (payload array byte) 18266 0x11/imm32/alloc-id:fake:payload -18267 # "b8/copy-to-eax" -18268 0xe/imm32/size -18269 0x62/b 0x38/8 0x2f/slash 0x63/c 0x6f/o 0x70/p 0x79/y 0x2d/dash 0x74/t 0x6f/o 0x2d/dash 0x65/e 0x61/a 0x78/x -18270 _string_b9_copy_to_ecx: # (payload array byte) +18267 # "shift-right" +18268 0xb/imm32/size +18269 0x73/s 0x68/h 0x69/i 0x66/f 0x74/t 0x2d/dash 0x72/r 0x69/i 0x67/g 0x68/h 0x74/t +18270 _string-shift-right-signed: # (payload array byte) 18271 0x11/imm32/alloc-id:fake:payload -18272 # "b9/copy-to-ecx" -18273 0xe/imm32/size -18274 0x62/b 0x39/9 0x2f/slash 0x63/c 0x6f/o 0x70/p 0x79/y 0x2d/dash 0x74/t 0x6f/o 0x2d/dash 0x65/e 0x63/c 0x78/x -18275 _string_ba_copy_to_edx: # (payload array byte) -18276 0x11/imm32/alloc-id:fake:payload -18277 # "ba/copy-to-edx" -18278 0xe/imm32/size -18279 0x62/b 0x61/a 0x2f/slash 0x63/c 0x6f/o 0x70/p 0x79/y 0x2d/dash 0x74/t 0x6f/o 0x2d/dash 0x65/e 0x64/d 0x78/x -18280 _string_bb_copy_to_ebx: # (payload array byte) -18281 0x11/imm32/alloc-id:fake:payload -18282 # "bb/copy-to-ebx" -18283 0xe/imm32/size -18284 0x62/b 0x62/b 0x2f/slash 0x63/c 0x6f/o 0x70/p 0x79/y 0x2d/dash 0x74/t 0x6f/o 0x2d/dash 0x65/e 0x62/b 0x78/x -18285 _string_be_copy_to_esi: # (payload array byte) -18286 0x11/imm32/alloc-id:fake:payload -18287 # "be/copy-to-esi" -18288 0xe/imm32/size -18289 0x62/b 0x65/e 0x2f/slash 0x63/c 0x6f/o 0x70/p 0x79/y 0x2d/dash 0x74/t 0x6f/o 0x2d/dash 0x65/e 0x73/s 0x69/i -18290 _string_bf_copy_to_edi: # (payload array byte) -18291 0x11/imm32/alloc-id:fake:payload -18292 # "bf/copy-to-edi" -18293 0xe/imm32/size -18294 0x62/b 0x66/f 0x2f/slash 0x63/c 0x6f/o 0x70/p 0x79/y 0x2d/dash 0x74/t 0x6f/o 0x2d/dash 0x65/e 0x64/d 0x69/i -18295 _string_c7_subop_copy: # (payload array byte) -18296 0x11/imm32/alloc-id:fake:payload -18297 # "c7 0/subop/copy" -18298 0xf/imm32/size -18299 0x63/c 0x37/7 0x20/space 0x30/0 0x2f/slash 0x73/s 0x75/u 0x62/b 0x6f/o 0x70/p 0x2f/slash 0x63/c 0x6f/o 0x70/p 0x79/y -18300 _string_e9_jump_label: # (payload array byte) -18301 0x11/imm32/alloc-id:fake:payload -18302 # "e9/jump" -18303 0x7/imm32/size -18304 0x65/e 0x39/9 0x2f/slash 0x6a/j 0x75/u 0x6d/m 0x70/p -18305 _string_e9_jump_break: # (payload array byte) -18306 0x11/imm32/alloc-id:fake:payload -18307 # "e9/jump break/disp32" -18308 0x14/imm32/size -18309 0x65/e 0x39/9 0x2f/slash 0x6a/j 0x75/u 0x6d/m 0x70/p 0x20/space 0x62/b 0x72/r 0x65/e 0x61/a 0x6b/k 0x2f/slash 0x64/d 0x69/i 0x73/s 0x70/p 0x33/3 0x32/2 -18310 _string_e9_jump_loop: # (payload array byte) -18311 0x11/imm32/alloc-id:fake:payload -18312 # "e9/jump loop/disp32" -18313 0x13/imm32/size -18314 0x65/e 0x39/9 0x2f/slash 0x6a/j 0x75/u 0x6d/m 0x70/p 0x20/space 0x6c/l 0x6f/o 0x6f/o 0x70/p 0x2f/slash 0x64/d 0x69/i 0x73/s 0x70/p 0x33/3 0x32/2 -18315 _string_ff_subop_increment: # (payload array byte) -18316 0x11/imm32/alloc-id:fake:payload -18317 # "ff 0/subop/increment" -18318 0x14/imm32/size -18319 0x66/f 0x66/f 0x20/space 0x30/0 0x2f/slash 0x73/s 0x75/u 0x62/b 0x6f/o 0x70/p 0x2f/slash 0x69/i 0x6e/n 0x63/c 0x72/r 0x65/e 0x6d/m 0x65/e 0x6e/n 0x74/t -18320 _string_ff_subop_decrement: # (payload array byte) -18321 0x11/imm32/alloc-id:fake:payload -18322 # "ff 1/subop/decrement" -18323 0x14/imm32/size -18324 0x66/f 0x66/f 0x20/space 0x31/1 0x2f/slash 0x73/s 0x75/u 0x62/b 0x6f/o 0x70/p 0x2f/slash 0x64/d 0x65/e 0x63/c 0x72/r 0x65/e 0x6d/m 0x65/e 0x6e/n 0x74/t -18325 _string_c1_subop_shift_left: # (payload array byte) -18326 0x11/imm32/alloc-id:fake:payload -18327 # "c1/shift 4/subop/left" -18328 0x15/imm32/size -18329 0x63/c 0x31/1 0x2f/slash 0x73/s 0x68/h 0x69/i 0x66/f 0x74/t 0x20/space 0x34/4 0x2f/slash 0x73/s 0x75/u 0x62/b 0x6f/o 0x70/p 0x2f/slash 0x6c/l 0x65/e 0x66/f 0x74/t -18330 _string_c1_subop_shift_right_padding_zeroes: # (payload array byte) -18331 0x11/imm32/alloc-id:fake:payload -18332 # "c1/shift 5/subop/right-padding-zeroes" -18333 0x25/imm32/size -18334 0x63/c 0x31/1 0x2f/slash 0x73/s 0x68/h 0x69/i 0x66/f 0x74/t 0x20/space 0x35/5 0x2f/slash 0x73/s 0x75/u 0x62/b 0x6f/o 0x70/p 0x2f/slash 0x72/r 0x69/i 0x67/g 0x68/h 0x74/t 0x2d/dash 0x70/p 0x61/a 0x64/d 0x64/d 0x69/i 0x6e/n 0x67/g 0x2d/dash 0x7a/z 0x65/e 0x72/r 0x6f/o 0x65/e 0x73/s -18335 _string_c1_subop_shift_right_preserving_sign: # (payload array byte) -18336 0x11/imm32/alloc-id:fake:payload -18337 # "c1/shift 7/subop/right-preserving-sign" -18338 0x26/imm32/size -18339 0x63/c 0x31/1 0x2f/slash 0x73/s 0x68/h 0x69/i 0x66/f 0x74/t 0x20/space 0x37/7 0x2f/slash 0x73/s 0x75/u 0x62/b 0x6f/o 0x70/p 0x2f/slash 0x72/r 0x69/i 0x67/g 0x68/h 0x74/t 0x2d/dash 0x70/p 0x72/r 0x65/e 0x73/s 0x65/e 0x72/r 0x76/v 0x69/i 0x6e/n 0x67/g 0x2d/dash 0x73/s 0x69/i 0x67/g 0x6e/n -18340 -18341 Single-int-var-in-mem: # (payload list var) -18342 0x11/imm32/alloc-id:fake:payload -18343 0x11/imm32/alloc-id:fake -18344 Int-var-in-mem/imm32 -18345 0/imm32/next -18346 0/imm32/next -18347 -18348 Int-var-in-mem: # (payload var) -18349 0x11/imm32/alloc-id:fake:payload -18350 0/imm32/name -18351 0/imm32/name -18352 0x11/imm32/alloc-id:fake -18353 Type-int/imm32 -18354 1/imm32/some-block-depth -18355 1/imm32/some-stack-offset -18356 0/imm32/no-register -18357 0/imm32/no-register -18358 -18359 # Not really legal, but closest we can currently represent a dereference of an (addr byte) -18360 Single-byte-var-in-mem: # (payload list var) -18361 0x11/imm32/alloc-id:fake:payload -18362 0x11/imm32/alloc-id:fake -18363 Byte-var-in-mem/imm32 -18364 0/imm32/next -18365 0/imm32/next -18366 -18367 # Not really legal, but closest we can currently represent a dereference of an (addr byte) -18368 Byte-var-in-mem: # (payload var) -18369 0x11/imm32/alloc-id:fake:payload -18370 0/imm32/name -18371 0/imm32/name -18372 0x11/imm32/alloc-id:fake -18373 Type-byte/imm32 -18374 1/imm32/some-block-depth -18375 1/imm32/some-stack-offset -18376 0/imm32/no-register -18377 0/imm32/no-register -18378 -18379 Two-args-int-stack-int-reg: # (payload list var) -18380 0x11/imm32/alloc-id:fake:payload -18381 0x11/imm32/alloc-id:fake -18382 Int-var-in-mem/imm32 -18383 0x11/imm32/alloc-id:fake -18384 Single-int-var-in-some-register/imm32/next -18385 -18386 Two-int-args-in-regs: # (payload list var) -18387 0x11/imm32/alloc-id:fake:payload -18388 0x11/imm32/alloc-id:fake -18389 Int-var-in-some-register/imm32 -18390 0x11/imm32/alloc-id:fake -18391 Single-int-var-in-some-register/imm32/next -18392 -18393 # Not really legal, but closest we can currently represent a dereference of an (addr byte) -18394 Two-args-byte-stack-byte-reg: # (payload list var) -18395 0x11/imm32/alloc-id:fake:payload -18396 0x11/imm32/alloc-id:fake -18397 Byte-var-in-mem/imm32 -18398 0x11/imm32/alloc-id:fake -18399 Single-byte-var-in-some-register/imm32/next -18400 -18401 Two-args-int-reg-int-stack: # (payload list var) -18402 0x11/imm32/alloc-id:fake:payload -18403 0x11/imm32/alloc-id:fake -18404 Int-var-in-some-register/imm32 -18405 0x11/imm32/alloc-id:fake -18406 Single-int-var-in-mem/imm32/next -18407 -18408 Two-args-int-eax-int-literal: # (payload list var) -18409 0x11/imm32/alloc-id:fake:payload -18410 0x11/imm32/alloc-id:fake -18411 Int-var-in-eax/imm32 -18412 0x11/imm32/alloc-id:fake -18413 Single-lit-var/imm32/next -18414 -18415 Int-var-and-literal: # (payload list var) -18416 0x11/imm32/alloc-id:fake:payload -18417 0x11/imm32/alloc-id:fake -18418 Int-var-in-mem/imm32 -18419 0x11/imm32/alloc-id:fake -18420 Single-lit-var/imm32/next -18421 -18422 Int-var-in-register-and-literal: # (payload list var) +18272 # "shift-right-signed" +18273 0x12/imm32/size +18274 0x73/s 0x68/h 0x69/i 0x66/f 0x74/t 0x2d/dash 0x72/r 0x69/i 0x67/g 0x68/h 0x74/t 0x2d/dash 0x73/s 0x69/i 0x67/g 0x6e/n 0x65/e 0x64/d +18275 +18276 # string literals for SubX instructions +18277 _string_01_add_to: # (payload array byte) +18278 0x11/imm32/alloc-id:fake:payload +18279 # "01/add-to" +18280 0x9/imm32/size +18281 0x30/0 0x31/1 0x2f/slash 0x61/a 0x64/d 0x64/d 0x2d/dash 0x74/t 0x6f/o +18282 _string_03_add: # (payload array byte) +18283 0x11/imm32/alloc-id:fake:payload +18284 # "03/add" +18285 0x6/imm32/size +18286 0x30/0 0x33/3 0x2f/slash 0x61/a 0x64/d 0x64/d +18287 _string_05_add_to_eax: # (payload array byte) +18288 0x11/imm32/alloc-id:fake:payload +18289 # "05/add-to-eax" +18290 0xd/imm32/size +18291 0x30/0 0x35/5 0x2f/slash 0x61/a 0x64/d 0x64/d 0x2d/dash 0x74/t 0x6f/o 0x2d/dash 0x65/e 0x61/a 0x78/x +18292 _string_09_or_with: # (payload array byte) +18293 0x11/imm32/alloc-id:fake:payload +18294 # "09/or-with" +18295 0xa/imm32/size +18296 0x30/0 0x39/9 0x2f/slash 0x6f/o 0x72/r 0x2d/dash 0x77/w 0x69/i 0x74/t 0x68/h +18297 _string_0b_or: # (payload array byte) +18298 0x11/imm32/alloc-id:fake:payload +18299 # "0b/or" +18300 0x5/imm32/size +18301 0x30/0 0x62/b 0x2f/slash 0x6f/o 0x72/r +18302 _string_0d_or_with_eax: # (payload array byte) +18303 0x11/imm32/alloc-id:fake:payload +18304 # "0d/or-with-eax" +18305 0xe/imm32/size +18306 0x30/0 0x64/d 0x2f/slash 0x6f/o 0x72/r 0x2d/dash 0x77/w 0x69/i 0x74/t 0x68/h 0x2d/dash 0x65/e 0x61/a 0x78/x +18307 _string_0f_82_jump_label: # (payload array byte) +18308 0x11/imm32/alloc-id:fake:payload +18309 # "0f 82/jump-if-addr<" +18310 0x13/imm32/size +18311 0x30/0 0x66/f 0x20/space 0x38/8 0x32/2 0x2f/slash 0x6a/j 0x75/u 0x6d/m 0x70/p 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x61/a 0x64/d 0x64/d 0x72/r 0x3c/< +18312 _string_0f_82_jump_break: # (payload array byte) +18313 0x11/imm32/alloc-id:fake:payload +18314 # "0f 82/jump-if-addr< break/disp32" +18315 0x20/imm32/size +18316 0x30/0 0x66/f 0x20/space 0x38/8 0x32/2 0x2f/slash 0x6a/j 0x75/u 0x6d/m 0x70/p 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x61/a 0x64/d 0x64/d 0x72/r 0x3c/< 0x20/space 0x62/b 0x72/r 0x65/e 0x61/a 0x6b/k 0x2f/slash 0x64/d 0x69/i 0x73/s 0x70/p 0x33/3 0x32/2 +18317 _string_0f_82_jump_loop: # (payload array byte) +18318 0x11/imm32/alloc-id:fake:payload +18319 # "0f 82/jump-if-addr< loop/disp32" +18320 0x1f/imm32/size +18321 0x30/0 0x66/f 0x20/space 0x38/8 0x32/2 0x2f/slash 0x6a/j 0x75/u 0x6d/m 0x70/p 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x61/a 0x64/d 0x64/d 0x72/r 0x3c/< 0x20/space 0x6c/l 0x6f/o 0x6f/o 0x70/p 0x2f/slash 0x64/d 0x69/i 0x73/s 0x70/p 0x33/3 0x32/2 +18322 _string_0f_83_jump_label: # (payload array byte) +18323 0x11/imm32/alloc-id:fake:payload +18324 # "0f 83/jump-if-addr>=" +18325 0x14/imm32/size +18326 0x30/0 0x66/f 0x20/space 0x38/8 0x33/3 0x2f/slash 0x6a/j 0x75/u 0x6d/m 0x70/p 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x61/a 0x64/d 0x64/d 0x72/r 0x3e/> 0x3d/= +18327 _string_0f_83_jump_break: # (payload array byte) +18328 0x11/imm32/alloc-id:fake:payload +18329 # "0f 83/jump-if-addr>= break/disp32" +18330 0x21/imm32/size +18331 0x30/0 0x66/f 0x20/space 0x38/8 0x33/3 0x2f/slash 0x6a/j 0x75/u 0x6d/m 0x70/p 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x61/a 0x64/d 0x64/d 0x72/r 0x3e/> 0x3d/= 0x20/space 0x62/b 0x72/r 0x65/e 0x61/a 0x6b/k 0x2f/slash 0x64/d 0x69/i 0x73/s 0x70/p 0x33/3 0x32/2 +18332 _string_0f_83_jump_loop: # (payload array byte) +18333 0x11/imm32/alloc-id:fake:payload +18334 # "0f 83/jump-if-addr>= loop/disp32" +18335 0x20/imm32/size +18336 0x30/0 0x66/f 0x20/space 0x38/8 0x33/3 0x2f/slash 0x6a/j 0x75/u 0x6d/m 0x70/p 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x61/a 0x64/d 0x64/d 0x72/r 0x3e/> 0x3d/= 0x20/space 0x6c/l 0x6f/o 0x6f/o 0x70/p 0x2f/slash 0x64/d 0x69/i 0x73/s 0x70/p 0x33/3 0x32/2 +18337 _string_0f_84_jump_label: # (payload array byte) +18338 0x11/imm32/alloc-id:fake:payload +18339 # "0f 84/jump-if-=" +18340 0xf/imm32/size +18341 0x30/0 0x66/f 0x20/space 0x38/8 0x34/4 0x2f/slash 0x6a/j 0x75/u 0x6d/m 0x70/p 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x3d/= +18342 _string_0f_84_jump_break: # (payload array byte) +18343 0x11/imm32/alloc-id:fake:payload +18344 # "0f 84/jump-if-= break/disp32" +18345 0x1c/imm32/size +18346 0x30/0 0x66/f 0x20/space 0x38/8 0x34/4 0x2f/slash 0x6a/j 0x75/u 0x6d/m 0x70/p 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x3d/= 0x20/space 0x62/b 0x72/r 0x65/e 0x61/a 0x6b/k 0x2f/slash 0x64/d 0x69/i 0x73/s 0x70/p 0x33/3 0x32/2 +18347 _string_0f_84_jump_loop: # (payload array byte) +18348 0x11/imm32/alloc-id:fake:payload +18349 # "0f 84/jump-if-= loop/disp32" +18350 0x1b/imm32/size +18351 0x30/0 0x66/f 0x20/space 0x38/8 0x34/4 0x2f/slash 0x6a/j 0x75/u 0x6d/m 0x70/p 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x3d/= 0x6c/l 0x6f/o 0x6f/o 0x70/p 0x2f/slash 0x64/d 0x69/i 0x73/s 0x70/p 0x33/3 0x32/2 +18352 _string_0f_85_jump_label: # (payload array byte) +18353 0x11/imm32/alloc-id:fake:payload +18354 # "0f 85/jump-if-!=" +18355 0x10/imm32/size +18356 0x30/0 0x66/f 0x20/space 0x38/8 0x35/5 0x2f/slash 0x6a/j 0x75/u 0x6d/m 0x70/p 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x21/! 0x3d/= +18357 _string_0f_85_jump_break: # (payload array byte) +18358 0x11/imm32/alloc-id:fake:payload +18359 # "0f 85/jump-if-!= break/disp32" +18360 0x1d/imm32/size +18361 0x30/0 0x66/f 0x20/space 0x38/8 0x35/5 0x2f/slash 0x6a/j 0x75/u 0x6d/m 0x70/p 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x21/! 0x3d/= 0x20/space 0x62/b 0x72/r 0x65/e 0x61/a 0x6b/k 0x2f/slash 0x64/d 0x69/i 0x73/s 0x70/p 0x33/3 0x32/2 +18362 _string_0f_85_jump_loop: # (payload array byte) +18363 0x11/imm32/alloc-id:fake:payload +18364 # "0f 85/jump-if-!= loop/disp32" +18365 0x1c/imm32/size +18366 0x30/0 0x66/f 0x20/space 0x38/8 0x35/5 0x2f/slash 0x6a/j 0x75/u 0x6d/m 0x70/p 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x21/! 0x3d/= 0x20/space 0x6c/l 0x6f/o 0x6f/o 0x70/p 0x2f/slash 0x64/d 0x69/i 0x73/s 0x70/p 0x33/3 0x32/2 +18367 _string_0f_86_jump_label: # (payload array byte) +18368 0x11/imm32/alloc-id:fake:payload +18369 # "0f 86/jump-if-addr<=" +18370 0x14/imm32/size +18371 0x30/0 0x66/f 0x20/space 0x38/8 0x36/6 0x2f/slash 0x6a/j 0x75/u 0x6d/m 0x70/p 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x61/a 0x64/d 0x64/d 0x72/r 0x3c/< 0x3d/= +18372 _string_0f_86_jump_break: # (payload array byte) +18373 0x11/imm32/alloc-id:fake:payload +18374 # "0f 86/jump-if-addr<= break/disp32" +18375 0x21/imm32/size +18376 0x30/0 0x66/f 0x20/space 0x38/8 0x36/6 0x2f/slash 0x6a/j 0x75/u 0x6d/m 0x70/p 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x61/a 0x64/d 0x64/d 0x72/r 0x3c/< 0x3d/= 0x20/space 0x62/b 0x72/r 0x65/e 0x61/a 0x6b/k 0x2f/slash 0x64/d 0x69/i 0x73/s 0x70/p 0x33/3 0x32/2 +18377 _string_0f_86_jump_loop: # (payload array byte) +18378 0x11/imm32/alloc-id:fake:payload +18379 # "0f 86/jump-if-addr<= loop/disp32" +18380 0x20/imm32/size +18381 0x30/0 0x66/f 0x20/space 0x38/8 0x36/6 0x2f/slash 0x6a/j 0x75/u 0x6d/m 0x70/p 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x61/a 0x64/d 0x64/d 0x72/r 0x3c/< 0x3d/= 0x20/space 0x6c/l 0x6f/o 0x6f/o 0x70/p 0x2f/slash 0x64/d 0x69/i 0x73/s 0x70/p 0x33/3 0x32/2 +18382 _string_0f_87_jump_label: # (payload array byte) +18383 0x11/imm32/alloc-id:fake:payload +18384 # "0f 87/jump-if-addr>" +18385 0x13/imm32/size +18386 0x30/0 0x66/f 0x20/space 0x38/8 0x37/7 0x2f/slash 0x6a/j 0x75/u 0x6d/m 0x70/p 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x61/a 0x64/d 0x64/d 0x72/r 0x3e/> +18387 _string_0f_87_jump_break: # (payload array byte) +18388 0x11/imm32/alloc-id:fake:payload +18389 # "0f 87/jump-if-addr> break/disp32" +18390 0x20/imm32/size +18391 0x30/0 0x66/f 0x20/space 0x38/8 0x37/7 0x2f/slash 0x6a/j 0x75/u 0x6d/m 0x70/p 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x61/a 0x64/d 0x64/d 0x72/r 0x3e/> 0x20/space 0x62/b 0x72/r 0x65/e 0x61/a 0x6b/k 0x2f/slash 0x64/d 0x69/i 0x73/s 0x70/p 0x33/3 0x32/2 +18392 _string_0f_87_jump_loop: # (payload array byte) +18393 0x11/imm32/alloc-id:fake:payload +18394 # "0f 87/jump-if-addr> loop/disp32" +18395 0x1f/imm32/size +18396 0x30/0 0x66/f 0x20/space 0x38/8 0x37/7 0x2f/slash 0x6a/j 0x75/u 0x6d/m 0x70/p 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x61/a 0x64/d 0x64/d 0x72/r 0x3e/> 0x20/space 0x6c/l 0x6f/o 0x6f/o 0x70/p 0x2f/slash 0x64/d 0x69/i 0x73/s 0x70/p 0x33/3 0x32/2 +18397 _string_0f_8c_jump_label: # (payload array byte) +18398 0x11/imm32/alloc-id:fake:payload +18399 # "0f 8c/jump-if-<" +18400 0xf/imm32/size +18401 0x30/0 0x66/f 0x20/space 0x38/8 0x63/c 0x2f/slash 0x6a/j 0x75/u 0x6d/m 0x70/p 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x3c/< +18402 _string_0f_8c_jump_break: # (payload array byte) +18403 0x11/imm32/alloc-id:fake:payload +18404 # "0f 8c/jump-if-< break/disp32" +18405 0x1c/imm32/size +18406 0x30/0 0x66/f 0x20/space 0x38/8 0x63/c 0x2f/slash 0x6a/j 0x75/u 0x6d/m 0x70/p 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x3c/< 0x20/space 0x62/b 0x72/r 0x65/e 0x61/a 0x6b/k 0x2f/slash 0x64/d 0x69/i 0x73/s 0x70/p 0x33/3 0x32/2 +18407 _string_0f_8c_jump_loop: # (payload array byte) +18408 0x11/imm32/alloc-id:fake:payload +18409 # "0f 8c/jump-if-< loop/disp32" +18410 0x1b/imm32/size +18411 0x30/0 0x66/f 0x20/space 0x38/8 0x63/c 0x2f/slash 0x6a/j 0x75/u 0x6d/m 0x70/p 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x3c/< 0x20/space 0x6c/l 0x6f/o 0x6f/o 0x70/p 0x2f/slash 0x64/d 0x69/i 0x73/s 0x70/p 0x33/3 0x32/2 +18412 _string_0f_8d_jump_label: # (payload array byte) +18413 0x11/imm32/alloc-id:fake:payload +18414 # "0f 8d/jump-if->=" +18415 0x10/imm32/size +18416 0x30/0 0x66/f 0x20/space 0x38/8 0x64/d 0x2f/slash 0x6a/j 0x75/u 0x6d/m 0x70/p 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x3e/> 0x3d/= +18417 _string_0f_8d_jump_break: # (payload array byte) +18418 0x11/imm32/alloc-id:fake:payload +18419 # "0f 8d/jump-if->= break/disp32" +18420 0x1d/imm32/size +18421 0x30/0 0x66/f 0x20/space 0x38/8 0x64/d 0x2f/slash 0x6a/j 0x75/u 0x6d/m 0x70/p 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x3e/> 0x3d/= 0x20/space 0x62/b 0x72/r 0x65/e 0x61/a 0x6b/k 0x2f/slash 0x64/d 0x69/i 0x73/s 0x70/p 0x33/3 0x32/2 +18422 _string_0f_8d_jump_loop: # (payload array byte) 18423 0x11/imm32/alloc-id:fake:payload -18424 0x11/imm32/alloc-id:fake -18425 Int-var-in-some-register/imm32 -18426 0x11/imm32/alloc-id:fake -18427 Single-lit-var/imm32/next -18428 -18429 Single-int-var-in-some-register: # (payload list var) -18430 0x11/imm32/alloc-id:fake:payload -18431 0x11/imm32/alloc-id:fake -18432 Int-var-in-some-register/imm32 -18433 0/imm32/next -18434 0/imm32/next -18435 -18436 Single-addr-var-in-some-register: # (payload list var) -18437 0x11/imm32/alloc-id:fake:payload -18438 0x11/imm32/alloc-id:fake -18439 Addr-var-in-some-register/imm32 -18440 0/imm32/next -18441 0/imm32/next -18442 -18443 Single-byte-var-in-some-register: # (payload list var) -18444 0x11/imm32/alloc-id:fake:payload -18445 0x11/imm32/alloc-id:fake -18446 Byte-var-in-some-register/imm32 -18447 0/imm32/next -18448 0/imm32/next -18449 -18450 Int-var-in-some-register: # (payload var) -18451 0x11/imm32/alloc-id:fake:payload -18452 0/imm32/name -18453 0/imm32/name -18454 0x11/imm32/alloc-id:fake -18455 Type-int/imm32 -18456 1/imm32/some-block-depth -18457 0/imm32/no-stack-offset -18458 0x11/imm32/alloc-id:fake -18459 Any-register/imm32 -18460 -18461 Any-register: # (payload array byte) -18462 0x11/imm32/alloc-id:fake:payload -18463 1/imm32/size -18464 # data -18465 2a/asterisk -18466 -18467 Addr-var-in-some-register: # (payload var) +18424 # "0f 8d/jump-if->= loop/disp32" +18425 0x1c/imm32/size +18426 0x30/0 0x66/f 0x20/space 0x38/8 0x64/d 0x2f/slash 0x6a/j 0x75/u 0x6d/m 0x70/p 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x3e/> 0x3d/= 0x20/space 0x6c/l 0x6f/o 0x6f/o 0x70/p 0x2f/slash 0x64/d 0x69/i 0x73/s 0x70/p 0x33/3 0x32/2 +18427 _string_0f_8e_jump_label: # (payload array byte) +18428 0x11/imm32/alloc-id:fake:payload +18429 # "0f 8e/jump-if-<=" +18430 0x10/imm32/size +18431 0x30/0 0x66/f 0x20/space 0x38/8 0x65/e 0x2f/slash 0x6a/j 0x75/u 0x6d/m 0x70/p 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x3c/< 0x3d/= +18432 _string_0f_8e_jump_break: # (payload array byte) +18433 0x11/imm32/alloc-id:fake:payload +18434 # "0f 8e/jump-if-<= break/disp32" +18435 0x1d/imm32/size +18436 0x30/0 0x66/f 0x20/space 0x38/8 0x65/e 0x2f/slash 0x6a/j 0x75/u 0x6d/m 0x70/p 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x3c/< 0x3d/= 0x20/space 0x62/b 0x72/r 0x65/e 0x61/a 0x6b/k 0x2f/slash 0x64/d 0x69/i 0x73/s 0x70/p 0x33/3 0x32/2 +18437 _string_0f_8e_jump_loop: # (payload array byte) +18438 0x11/imm32/alloc-id:fake:payload +18439 # "0f 8e/jump-if-<= loop/disp32" +18440 0x1c/imm32/size +18441 0x30/0 0x66/f 0x20/space 0x38/8 0x65/e 0x2f/slash 0x6a/j 0x75/u 0x6d/m 0x70/p 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x3c/< 0x3d/= 0x20/space 0x6c/l 0x6f/o 0x6f/o 0x70/p 0x2f/slash 0x64/d 0x69/i 0x73/s 0x70/p 0x33/3 0x32/2 +18442 _string_0f_8f_jump_label: # (payload array byte) +18443 0x11/imm32/alloc-id:fake:payload +18444 # "0f 8f/jump-if->" +18445 0xf/imm32/size +18446 0x30/0 0x66/f 0x20/space 0x38/8 0x66/f 0x2f/slash 0x6a/j 0x75/u 0x6d/m 0x70/p 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x3e/> +18447 _string_0f_8f_jump_break: # (payload array byte) +18448 0x11/imm32/alloc-id:fake:payload +18449 # "0f 8f/jump-if-> break/disp32" +18450 0x1c/imm32/size +18451 0x30/0 0x66/f 0x20/space 0x38/8 0x66/f 0x2f/slash 0x6a/j 0x75/u 0x6d/m 0x70/p 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x3e/> 0x20/space 0x62/b 0x72/r 0x65/e 0x61/a 0x6b/k 0x2f/slash 0x64/d 0x69/i 0x73/s 0x70/p 0x33/3 0x32/2 +18452 _string_0f_8f_jump_loop: # (payload array byte) +18453 0x11/imm32/alloc-id:fake:payload +18454 # "0f 8f/jump-if-> loop/disp32" +18455 0x1b/imm32/size +18456 0x30/0 0x66/f 0x20/space 0x38/8 0x66/f 0x2f/slash 0x6a/j 0x75/u 0x6d/m 0x70/p 0x2d/dash 0x69/i 0x66/f 0x2d/dash 0x3e/> 0x20/space 0x6c/l 0x6f/o 0x6f/o 0x70/p 0x2f/slash 0x64/d 0x69/i 0x73/s 0x70/p 0x33/3 0x32/2 +18457 _string_0f_af_multiply: # (payload array byte) +18458 0x11/imm32/alloc-id:fake:payload +18459 # "0f af/multiply" +18460 0xe/imm32/size +18461 0x30/0 0x66/f 0x20/space 0x61/a 0x66/f 0x2f/slash 0x6d/m 0x75/u 0x6c/l 0x74/t 0x69/i 0x70/p 0x6c/l 0x79/y +18462 _string_21_and_with: # (payload array byte) +18463 0x11/imm32/alloc-id:fake:payload +18464 # "21/and-with" +18465 0xb/imm32/size +18466 0x32/2 0x31/1 0x2f/slash 0x61/a 0x6e/n 0x64/d 0x2d/dash 0x77/w 0x69/i 0x74/t 0x68/h +18467 _string_23_and: # (payload array byte) 18468 0x11/imm32/alloc-id:fake:payload -18469 0/imm32/name -18470 0/imm32/name -18471 0x11/imm32/alloc-id:fake -18472 Type-addr/imm32 -18473 1/imm32/some-block-depth -18474 0/imm32/no-stack-offset -18475 0x11/imm32/alloc-id:fake -18476 Any-register/imm32 -18477 -18478 Byte-var-in-some-register: # (payload var) -18479 0x11/imm32/alloc-id:fake:payload -18480 0/imm32/name -18481 0/imm32/name -18482 0x11/imm32/alloc-id:fake -18483 Type-byte/imm32 -18484 1/imm32/some-block-depth -18485 0/imm32/no-stack-offset -18486 0x11/imm32/alloc-id:fake -18487 Any-register/imm32 -18488 -18489 Single-int-var-in-eax: # (payload list var) -18490 0x11/imm32/alloc-id:fake:payload -18491 0x11/imm32/alloc-id:fake -18492 Int-var-in-eax/imm32 -18493 0/imm32/next -18494 0/imm32/next -18495 -18496 Int-var-in-eax: -18497 0x11/imm32/alloc-id:fake:payload -18498 0/imm32/name -18499 0/imm32/name -18500 0x11/imm32/alloc-id:fake -18501 Type-int/imm32 -18502 1/imm32/some-block-depth -18503 0/imm32/no-stack-offset -18504 0x11/imm32/alloc-id:fake -18505 $Register-eax/imm32 -18506 -18507 Single-int-var-in-ecx: # (payload list var) +18469 # "23/and" +18470 0x6/imm32/size +18471 0x32/2 0x33/3 0x2f/slash 0x61/a 0x6e/n 0x64/d +18472 _string_25_and_with_eax: # (payload array byte) +18473 0x11/imm32/alloc-id:fake:payload +18474 # "25/and-with-eax" +18475 0xf/imm32/size +18476 0x32/2 0x35/5 0x2f/slash 0x61/a 0x6e/n 0x64/d 0x2d/dash 0x77/w 0x69/i 0x74/t 0x68/h 0x2d/dash 0x65/e 0x61/a 0x78/x +18477 _string_29_subtract_from: # (payload array byte) +18478 0x11/imm32/alloc-id:fake:payload +18479 # "29/subtract-from" +18480 0x10/imm32/size +18481 0x32/2 0x39/9 0x2f/slash 0x73/s 0x75/u 0x62/b 0x74/t 0x72/r 0x61/a 0x63/c 0x74/t 0x2d/dash 0x66/f 0x72/r 0x6f/o 0x6d/m +18482 _string_2b_subtract: # (payload array byte) +18483 0x11/imm32/alloc-id:fake:payload +18484 # "2b/subtract" +18485 0xb/imm32/size +18486 0x32/2 0x62/b 0x2f/slash 0x73/s 0x75/u 0x62/b 0x74/t 0x72/r 0x61/a 0x63/c 0x74/t +18487 _string_2d_subtract_from_eax: # (payload array byte) +18488 0x11/imm32/alloc-id:fake:payload +18489 # "2d/subtract-from-eax" +18490 0x14/imm32/size +18491 0x32/2 0x64/d 0x2f/slash 0x73/s 0x75/u 0x62/b 0x74/t 0x72/r 0x61/a 0x63/c 0x74/t 0x2d/dash 0x66/f 0x72/r 0x6f/o 0x6d/m 0x2d/dash 0x65/e 0x61/a 0x78/x +18492 _string_31_xor_with: # (payload array byte) +18493 0x11/imm32/alloc-id:fake:payload +18494 # "31/xor-with" +18495 0xb/imm32/size +18496 0x33/3 0x31/1 0x2f/slash 0x78/x 0x6f/o 0x72/r 0x2d/dash 0x77/w 0x69/i 0x74/t 0x68/h +18497 _string_33_xor: # (payload array byte) +18498 0x11/imm32/alloc-id:fake:payload +18499 # "33/xor" +18500 0x6/imm32/size +18501 0x33/3 0x33/3 0x2f/slash 0x78/x 0x6f/o 0x72/r +18502 _string_35_xor_with_eax: # (payload array byte) +18503 0x11/imm32/alloc-id:fake:payload +18504 # "35/xor-with-eax" +18505 0xf/imm32/size +18506 0x33/3 0x35/5 0x2f/slash 0x78/x 0x6f/o 0x72/r 0x2d/dash 0x77/w 0x69/i 0x74/t 0x68/h 0x2d/dash 0x65/e 0x61/a 0x78/x +18507 _string_39_compare->: # (payload array byte) 18508 0x11/imm32/alloc-id:fake:payload -18509 0x11/imm32/alloc-id:fake -18510 Int-var-in-ecx/imm32 -18511 0/imm32/next -18512 0/imm32/next -18513 -18514 Int-var-in-ecx: -18515 0x11/imm32/alloc-id:fake:payload -18516 0/imm32/name -18517 0/imm32/name -18518 0x11/imm32/alloc-id:fake -18519 Type-int/imm32 -18520 1/imm32/some-block-depth -18521 0/imm32/no-stack-offset -18522 0x11/imm32/alloc-id:fake -18523 $Register-ecx/imm32/register -18524 -18525 Single-int-var-in-edx: # (payload list var) -18526 0x11/imm32/alloc-id:fake:payload -18527 0x11/imm32/alloc-id:fake -18528 Int-var-in-edx/imm32 -18529 0/imm32/next -18530 0/imm32/next -18531 -18532 Int-var-in-edx: # (payload list var) +18509 # "39/compare->" +18510 0xc/imm32/size +18511 0x33/3 0x39/9 0x2f/slash 0x63/c 0x6f/o 0x6d/m 0x70/p 0x61/a 0x72/r 0x65/e 0x2d/dash 0x3e/> +18512 _string_3b_compare<-: # (payload array byte) +18513 0x11/imm32/alloc-id:fake:payload +18514 # "3b/compare<-" +18515 0xc/imm32/size +18516 0x33/3 0x62/b 0x2f/slash 0x63/c 0x6f/o 0x6d/m 0x70/p 0x61/a 0x72/r 0x65/e 0x3c/< 0x2d/dash +18517 _string_3d_compare_eax_with: # (payload array byte) +18518 0x11/imm32/alloc-id:fake:payload +18519 # "3d/compare-eax-with" +18520 0x13/imm32/size +18521 0x33/3 0x64/d 0x2f/slash 0x63/c 0x6f/o 0x6d/m 0x70/p 0x61/a 0x72/r 0x65/e 0x2d/dash 0x65/e 0x61/a 0x78/x 0x2d/dash 0x77/w 0x69/i 0x74/t 0x68/h +18522 _string_40_increment_eax: # (payload array byte) +18523 0x11/imm32/alloc-id:fake:payload +18524 # "40/increment-eax" +18525 0x10/imm32/size +18526 0x34/4 0x30/0 0x2f/slash 0x69/i 0x6e/n 0x63/c 0x72/r 0x65/e 0x6d/m 0x65/e 0x6e/n 0x74/t 0x2d/dash 0x65/e 0x61/a 0x78/x +18527 _string_41_increment_ecx: # (payload array byte) +18528 0x11/imm32/alloc-id:fake:payload +18529 # "41/increment-ecx" +18530 0x10/imm32/size +18531 0x34/4 0x31/1 0x2f/slash 0x69/i 0x6e/n 0x63/c 0x72/r 0x65/e 0x6d/m 0x65/e 0x6e/n 0x74/t 0x2d/dash 0x65/e 0x63/c 0x78/x +18532 _string_42_increment_edx: # (payload array byte) 18533 0x11/imm32/alloc-id:fake:payload -18534 0/imm32/name -18535 0/imm32/name -18536 0x11/imm32/alloc-id:fake -18537 Type-int/imm32 -18538 1/imm32/some-block-depth -18539 0/imm32/no-stack-offset -18540 0x11/imm32/alloc-id:fake -18541 $Register-edx/imm32/register -18542 -18543 Single-int-var-in-ebx: # (payload list var) -18544 0x11/imm32/alloc-id:fake:payload -18545 0x11/imm32/alloc-id:fake -18546 Int-var-in-ebx/imm32 -18547 0/imm32/next -18548 0/imm32/next -18549 -18550 Int-var-in-ebx: # (payload list var) -18551 0x11/imm32/alloc-id:fake:payload -18552 0/imm32/name -18553 0/imm32/name -18554 0x11/imm32/alloc-id:fake -18555 Type-int/imm32 -18556 1/imm32/some-block-depth -18557 0/imm32/no-stack-offset -18558 0x11/imm32/alloc-id:fake -18559 $Register-ebx/imm32/register -18560 -18561 Single-int-var-in-esi: # (payload list var) -18562 0x11/imm32/alloc-id:fake:payload -18563 0x11/imm32/alloc-id:fake -18564 Int-var-in-esi/imm32 -18565 0/imm32/next -18566 0/imm32/next -18567 -18568 Int-var-in-esi: # (payload list var) -18569 0x11/imm32/alloc-id:fake:payload -18570 0/imm32/name -18571 0/imm32/name -18572 0x11/imm32/alloc-id:fake -18573 Type-int/imm32 -18574 1/imm32/some-block-depth -18575 0/imm32/no-stack-offset -18576 0x11/imm32/alloc-id:fake -18577 $Register-esi/imm32/register -18578 -18579 Single-int-var-in-edi: # (payload list var) -18580 0x11/imm32/alloc-id:fake:payload -18581 0x11/imm32/alloc-id:fake -18582 Int-var-in-edi/imm32 -18583 0/imm32/next -18584 0/imm32/next -18585 -18586 Int-var-in-edi: # (payload list var) -18587 0x11/imm32/alloc-id:fake:payload -18588 0/imm32/name -18589 0/imm32/name -18590 0x11/imm32/alloc-id:fake -18591 Type-int/imm32 -18592 1/imm32/some-block-depth -18593 0/imm32/no-stack-offset -18594 0x11/imm32/alloc-id:fake -18595 $Register-edi/imm32/register -18596 -18597 Single-lit-var: # (payload list var) +18534 # "42/increment-edx" +18535 0x10/imm32/size +18536 0x34/4 0x32/2 0x2f/slash 0x69/i 0x6e/n 0x63/c 0x72/r 0x65/e 0x6d/m 0x65/e 0x6e/n 0x74/t 0x2d/dash 0x65/e 0x64/d 0x78/x +18537 _string_43_increment_ebx: # (payload array byte) +18538 0x11/imm32/alloc-id:fake:payload +18539 # "43/increment-ebx" +18540 0x10/imm32/size +18541 0x34/4 0x33/3 0x2f/slash 0x69/i 0x6e/n 0x63/c 0x72/r 0x65/e 0x6d/m 0x65/e 0x6e/n 0x74/t 0x2d/dash 0x65/e 0x62/b 0x78/x +18542 _string_46_increment_esi: # (payload array byte) +18543 0x11/imm32/alloc-id:fake:payload +18544 # "46/increment-esi" +18545 0x10/imm32/size +18546 0x34/4 0x36/6 0x2f/slash 0x69/i 0x6e/n 0x63/c 0x72/r 0x65/e 0x6d/m 0x65/e 0x6e/n 0x74/t 0x2d/dash 0x65/e 0x73/s 0x69/i +18547 _string_47_increment_edi: # (payload array byte) +18548 0x11/imm32/alloc-id:fake:payload +18549 # "47/increment-edi" +18550 0x10/imm32/size +18551 0x34/4 0x37/7 0x2f/slash 0x69/i 0x6e/n 0x63/c 0x72/r 0x65/e 0x6d/m 0x65/e 0x6e/n 0x74/t 0x2d/dash 0x65/e 0x64/d 0x69/i +18552 _string_48_decrement_eax: # (payload array byte) +18553 0x11/imm32/alloc-id:fake:payload +18554 # "48/decrement-eax" +18555 0x10/imm32/size +18556 0x34/4 0x38/8 0x2f/slash 0x64/d 0x65/e 0x63/c 0x72/r 0x65/e 0x6d/m 0x65/e 0x6e/n 0x74/t 0x2d/dash 0x65/e 0x61/a 0x78/x +18557 _string_49_decrement_ecx: # (payload array byte) +18558 0x11/imm32/alloc-id:fake:payload +18559 # "49/decrement-ecx" +18560 0x10/imm32/size +18561 0x34/4 0x39/9 0x2f/slash 0x64/d 0x65/e 0x63/c 0x72/r 0x65/e 0x6d/m 0x65/e 0x6e/n 0x74/t 0x2d/dash 0x65/e 0x63/c 0x78/x +18562 _string_4a_decrement_edx: # (payload array byte) +18563 0x11/imm32/alloc-id:fake:payload +18564 # "4a/decrement-edx" +18565 0x10/imm32/size +18566 0x34/4 0x61/a 0x2f/slash 0x64/d 0x65/e 0x63/c 0x72/r 0x65/e 0x6d/m 0x65/e 0x6e/n 0x74/t 0x2d/dash 0x65/e 0x64/d 0x78/x +18567 _string_4b_decrement_ebx: # (payload array byte) +18568 0x11/imm32/alloc-id:fake:payload +18569 # "4b/decrement-ebx" +18570 0x10/imm32/size +18571 0x34/4 0x62/b 0x2f/slash 0x64/d 0x65/e 0x63/c 0x72/r 0x65/e 0x6d/m 0x65/e 0x6e/n 0x74/t 0x2d/dash 0x65/e 0x62/b 0x78/x +18572 _string_4e_decrement_esi: # (payload array byte) +18573 0x11/imm32/alloc-id:fake:payload +18574 # "4e/decrement-esi" +18575 0x10/imm32/size +18576 0x34/4 0x65/e 0x2f/slash 0x64/d 0x65/e 0x63/c 0x72/r 0x65/e 0x6d/m 0x65/e 0x6e/n 0x74/t 0x2d/dash 0x65/e 0x73/s 0x69/i +18577 _string_4f_decrement_edi: # (payload array byte) +18578 0x11/imm32/alloc-id:fake:payload +18579 # "4f/decrement-edi" +18580 0x10/imm32/size +18581 0x34/4 0x66/f 0x2f/slash 0x64/d 0x65/e 0x63/c 0x72/r 0x65/e 0x6d/m 0x65/e 0x6e/n 0x74/t 0x2d/dash 0x65/e 0x64/d 0x69/i +18582 _string_81_subop_add: # (payload array byte) +18583 0x11/imm32/alloc-id:fake:payload +18584 # "81 0/subop/add" +18585 0xe/imm32/size +18586 0x38/8 0x31/1 0x20/space 0x30/0 0x2f/slash 0x73/s 0x75/u 0x62/b 0x6f/o 0x70/p 0x2f/slash 0x61/a 0x64/d 0x64/d +18587 _string_81_subop_or: # (payload array byte) +18588 0x11/imm32/alloc-id:fake:payload +18589 # "81 1/subop/or" +18590 0xd/imm32/size +18591 0x38/8 0x31/1 0x20/space 0x31/1 0x2f/slash 0x73/s 0x75/u 0x62/b 0x6f/o 0x70/p 0x2f/slash 0x6f/o 0x72/r +18592 _string_81_subop_and: # (payload array byte) +18593 0x11/imm32/alloc-id:fake:payload +18594 # "81 4/subop/and" +18595 0xe/imm32/size +18596 0x38/8 0x31/1 0x20/space 0x34/4 0x2f/slash 0x73/s 0x75/u 0x62/b 0x6f/o 0x70/p 0x2f/slash 0x61/a 0x6e/n 0x64/d +18597 _string_81_subop_subtract: # (payload array byte) 18598 0x11/imm32/alloc-id:fake:payload -18599 0x11/imm32/alloc-id:fake -18600 Lit-var/imm32 -18601 0/imm32/next -18602 0/imm32/next -18603 -18604 Lit-var: # (payload var) -18605 0x11/imm32/alloc-id:fake:payload -18606 0/imm32/name -18607 0/imm32/name -18608 0x11/imm32/alloc-id:fake -18609 Type-literal/imm32 -18610 1/imm32/some-block-depth -18611 0/imm32/no-stack-offset -18612 0/imm32/no-register -18613 0/imm32/no-register -18614 -18615 Type-int: # (payload type-tree) -18616 0x11/imm32/alloc-id:fake:payload -18617 1/imm32/is-atom -18618 1/imm32/value:int -18619 0/imm32/left:unused -18620 0/imm32/right:null -18621 0/imm32/right:null -18622 -18623 Type-literal: # (payload type-tree) -18624 0x11/imm32/alloc-id:fake:payload -18625 1/imm32/is-atom -18626 0/imm32/value:literal -18627 0/imm32/left:unused -18628 0/imm32/right:null -18629 0/imm32/right:null -18630 -18631 Type-addr: # (payload type-tree) -18632 0x11/imm32/alloc-id:fake:payload -18633 1/imm32/is-atom -18634 2/imm32/value:addr -18635 0/imm32/left:unused -18636 0/imm32/right:null -18637 0/imm32/right:null -18638 -18639 Type-byte: # (payload type-tree) -18640 0x11/imm32/alloc-id:fake:payload -18641 1/imm32/is-atom -18642 8/imm32/value:byte -18643 0/imm32/left:unused -18644 0/imm32/right:null -18645 0/imm32/right:null -18646 -18647 == code -18648 emit-subx-primitive: # out: (addr buffered-file), stmt: (addr stmt), primitive: (addr primitive), err: (addr buffered-file), ed: (addr exit-descriptor) -18649 # . prologue -18650 55/push-ebp -18651 89/<- %ebp 4/r32/esp -18652 # . save registers -18653 50/push-eax -18654 51/push-ecx -18655 # ecx = primitive -18656 8b/-> *(ebp+0x10) 1/r32/ecx -18657 # emit primitive name -18658 (emit-indent *(ebp+8) *Curr-block-depth) -18659 (lookup *(ecx+0x18) *(ecx+0x1c)) # Primitive-subx-name Primitive-subx-name => eax -18660 (write-buffered *(ebp+8) %eax) -18661 # emit rm32 if necessary -18662 (emit-subx-rm32 *(ebp+8) *(ecx+0x20) *(ebp+0xc) *(ebp+0x14) *(ebp+0x18)) # Primitive-subx-rm32 -18663 # emit r32 if necessary -18664 (emit-subx-r32 *(ebp+8) *(ecx+0x24) *(ebp+0xc)) # Primitive-subx-r32 -18665 # emit imm32 if necessary -18666 (emit-subx-imm32 *(ebp+8) *(ecx+0x28) *(ebp+0xc)) # Primitive-subx-imm32 -18667 # emit imm8 if necessary -18668 (emit-subx-imm8 *(ebp+8) *(ecx+0x2c) *(ebp+0xc)) # Primitive-subx-imm8 -18669 # emit disp32 if necessary -18670 (emit-subx-disp32 *(ebp+8) *(ecx+0x30) *(ebp+0xc) *(ebp+0x14) *(ebp+0x18)) # Primitive-subx-disp32 -18671 (write-buffered *(ebp+8) Newline) -18672 $emit-subx-primitive:end: -18673 # . restore registers -18674 59/pop-to-ecx -18675 58/pop-to-eax -18676 # . epilogue -18677 89/<- %esp 5/r32/ebp -18678 5d/pop-to-ebp -18679 c3/return -18680 -18681 emit-subx-rm32: # out: (addr buffered-file), l: arg-location, stmt: (addr stmt), err: (addr buffered-file), ed: (addr exit-descriptor) -18682 # . prologue -18683 55/push-ebp -18684 89/<- %ebp 4/r32/esp -18685 # . save registers -18686 50/push-eax -18687 # if (l == 0) return -18688 81 7/subop/compare *(ebp+0xc) 0/imm32 -18689 74/jump-if-= $emit-subx-rm32:end/disp8 -18690 # var v/eax: (addr stmt-var) -18691 (get-stmt-operand-from-arg-location *(ebp+0x10) *(ebp+0xc) *(ebp+0x14) *(ebp+0x18)) # => eax -18692 (emit-subx-var-as-rm32 *(ebp+8) %eax) -18693 $emit-subx-rm32:end: -18694 # . restore registers -18695 58/pop-to-eax -18696 # . epilogue -18697 89/<- %esp 5/r32/ebp -18698 5d/pop-to-ebp -18699 c3/return -18700 -18701 get-stmt-operand-from-arg-location: # stmt: (addr stmt), l: arg-location, err: (addr buffered-file), ed: (addr exit-descriptor) -> var/eax: (addr stmt-var) -18702 # . prologue -18703 55/push-ebp -18704 89/<- %ebp 4/r32/esp -18705 # . save registers -18706 51/push-ecx -18707 # eax = l -18708 8b/-> *(ebp+0xc) 0/r32/eax -18709 # ecx = stmt -18710 8b/-> *(ebp+8) 1/r32/ecx -18711 # if (l == 1) return stmt->inouts -18712 { -18713 3d/compare-eax-and 1/imm32 -18714 75/jump-if-!= break/disp8 -18715 $get-stmt-operand-from-arg-location:1: -18716 (lookup *(ecx+0xc) *(ecx+0x10)) # Stmt1-inouts Stmt1-inouts => eax -18717 eb/jump $get-stmt-operand-from-arg-location:end/disp8 -18718 } -18719 # if (l == 2) return stmt->inouts->next -18720 { -18721 3d/compare-eax-and 2/imm32 -18722 75/jump-if-!= break/disp8 -18723 $get-stmt-operand-from-arg-location:2: -18724 (lookup *(ecx+0xc) *(ecx+0x10)) # Stmt1-inouts Stmt1-inouts => eax -18725 (lookup *(eax+8) *(eax+0xc)) # Stmt-var-next Stmt-var-next => eax -18726 eb/jump $get-stmt-operand-from-arg-location:end/disp8 -18727 } -18728 # if (l == 3) return stmt->outputs -18729 { -18730 3d/compare-eax-and 3/imm32 -18731 75/jump-if-!= break/disp8 -18732 $get-stmt-operand-from-arg-location:3: -18733 (lookup *(ecx+0x14) *(ecx+0x18)) # Stmt1-outputs Stmt1-outputs => eax -18734 eb/jump $get-stmt-operand-from-arg-location:end/disp8 -18735 } -18736 # abort -18737 e9/jump $get-stmt-operand-from-arg-location:abort/disp32 -18738 $get-stmt-operand-from-arg-location:end: -18739 # . restore registers -18740 59/pop-to-ecx -18741 # . epilogue -18742 89/<- %esp 5/r32/ebp -18743 5d/pop-to-ebp -18744 c3/return -18745 -18746 $get-stmt-operand-from-arg-location:abort: -18747 # error("invalid arg-location " eax) -18748 (write-buffered *(ebp+0x10) "invalid arg-location ") -18749 (write-int32-hex-buffered *(ebp+0x10) %eax) -18750 (write-buffered *(ebp+0x10) Newline) -18751 (flush *(ebp+0x10)) -18752 (stop *(ebp+0x14) 1) -18753 # never gets here -18754 -18755 emit-subx-r32: # out: (addr buffered-file), l: arg-location, stmt: (addr stmt) -18756 # . prologue -18757 55/push-ebp -18758 89/<- %ebp 4/r32/esp -18759 # . save registers -18760 50/push-eax -18761 51/push-ecx -18762 # if (l == 0) return -18763 81 7/subop/compare *(ebp+0xc) 0/imm32 -18764 0f 84/jump-if-= $emit-subx-r32:end/disp32 -18765 # var v/eax: (addr stmt-var) -18766 (get-stmt-operand-from-arg-location *(ebp+0x10) *(ebp+0xc)) # => eax -18767 (lookup *eax *(eax+4)) # Stmt-var-value Stmt-var-value => eax -18768 (lookup *(eax+0x18) *(eax+0x1c)) # Var-register Var-register => eax -18769 (maybe-get Mu-registers %eax 0xc) # => eax: (addr register-index) -18770 (write-buffered *(ebp+8) Space) -18771 (write-int32-hex-buffered *(ebp+8) *eax) -18772 (write-buffered *(ebp+8) "/r32") -18773 $emit-subx-r32:end: -18774 # . restore registers -18775 59/pop-to-ecx -18776 58/pop-to-eax -18777 # . epilogue -18778 89/<- %esp 5/r32/ebp -18779 5d/pop-to-ebp -18780 c3/return -18781 -18782 emit-subx-imm32: # out: (addr buffered-file), l: arg-location, stmt: (addr stmt) -18783 # . prologue -18784 55/push-ebp -18785 89/<- %ebp 4/r32/esp -18786 # . save registers -18787 50/push-eax -18788 51/push-ecx -18789 # if (l == 0) return -18790 81 7/subop/compare *(ebp+0xc) 0/imm32 -18791 0f 84/jump-if-= $emit-subx-imm32:end/disp32 -18792 # var v/eax: (handle var) -18793 (get-stmt-operand-from-arg-location *(ebp+0x10) *(ebp+0xc)) # => eax -18794 (lookup *eax *(eax+4)) # Stmt-var-value Stmt-var-value => eax -18795 (lookup *eax *(eax+4)) # Var-name Var-name => eax -18796 (write-buffered *(ebp+8) Space) -18797 (write-buffered *(ebp+8) %eax) -18798 (write-buffered *(ebp+8) "/imm32") -18799 $emit-subx-imm32:end: -18800 # . restore registers -18801 59/pop-to-ecx -18802 58/pop-to-eax -18803 # . epilogue -18804 89/<- %esp 5/r32/ebp -18805 5d/pop-to-ebp -18806 c3/return +18599 # "81 5/subop/subtract" +18600 0x13/imm32/size +18601 0x38/8 0x31/1 0x20/space 0x35/5 0x2f/slash 0x73/s 0x75/u 0x62/b 0x6f/o 0x70/p 0x2f/slash 0x73/s 0x75/u 0x62/b 0x74/t 0x72/r 0x61/a 0x63/c 0x74/t +18602 _string_81_subop_xor: # (payload array byte) +18603 0x11/imm32/alloc-id:fake:payload +18604 # "81 6/subop/xor" +18605 0xe/imm32/size +18606 0x38/8 0x31/1 0x20/space 0x36/6 0x2f/slash 0x73/s 0x75/u 0x62/b 0x6f/o 0x70/p 0x2f/slash 0x78/x 0x6f/o 0x72/r +18607 _string_81_subop_compare: # (payload array byte) +18608 0x11/imm32/alloc-id:fake:payload +18609 # "81 7/subop/compare" +18610 0x12/imm32/size +18611 0x38/8 0x31/1 0x20/space 0x37/7 0x2f/slash 0x73/s 0x75/u 0x62/b 0x6f/o 0x70/p 0x2f/slash 0x63/c 0x6f/o 0x6d/m 0x70/p 0x61/a 0x72/r 0x65/e +18612 _string_89_<-: # (payload array byte) +18613 0x11/imm32/alloc-id:fake:payload +18614 # "89/<-" +18615 0x5/imm32/size +18616 0x38/8 0x39/9 0x2f/slash 0x3c/< 0x2d/dash +18617 _string_8b_->: # (payload array byte) +18618 0x11/imm32/alloc-id:fake:payload +18619 # "8b/->" +18620 0x5/imm32/size +18621 0x38/8 0x62/b 0x2f/slash 0x2d/dash 0x3e/> +18622 _string_8a_copy_byte: +18623 0x11/imm32/alloc-id:fake:payload +18624 # "8a/byte->" +18625 0x9/imm32/size +18626 0x38/8 0x61/a 0x2f// 0x62/b 0x79/y 0x74/t 0x65/e 0x2d/- 0x3e/> +18627 _string_88_copy_byte: +18628 0x11/imm32/alloc-id:fake:payload +18629 # "88/byte<-" +18630 0x9/imm32/size +18631 0x38/8 0x38/8 0x2f// 0x62/b 0x79/y 0x74/t 0x65/e 0x3c/< 0x2d/- +18632 _string_8d_copy_address: # (payload array byte) +18633 0x11/imm32/alloc-id:fake:payload +18634 # "8d/copy-address" +18635 0xf/imm32/size +18636 0x38/8 0x64/d 0x2f/slash 0x63/c 0x6f/o 0x70/p 0x79/y 0x2d/dash 0x61/a 0x64/d 0x64/d 0x72/r 0x65/e 0x73/s 0x73/s +18637 _string_b8_copy_to_eax: # (payload array byte) +18638 0x11/imm32/alloc-id:fake:payload +18639 # "b8/copy-to-eax" +18640 0xe/imm32/size +18641 0x62/b 0x38/8 0x2f/slash 0x63/c 0x6f/o 0x70/p 0x79/y 0x2d/dash 0x74/t 0x6f/o 0x2d/dash 0x65/e 0x61/a 0x78/x +18642 _string_b9_copy_to_ecx: # (payload array byte) +18643 0x11/imm32/alloc-id:fake:payload +18644 # "b9/copy-to-ecx" +18645 0xe/imm32/size +18646 0x62/b 0x39/9 0x2f/slash 0x63/c 0x6f/o 0x70/p 0x79/y 0x2d/dash 0x74/t 0x6f/o 0x2d/dash 0x65/e 0x63/c 0x78/x +18647 _string_ba_copy_to_edx: # (payload array byte) +18648 0x11/imm32/alloc-id:fake:payload +18649 # "ba/copy-to-edx" +18650 0xe/imm32/size +18651 0x62/b 0x61/a 0x2f/slash 0x63/c 0x6f/o 0x70/p 0x79/y 0x2d/dash 0x74/t 0x6f/o 0x2d/dash 0x65/e 0x64/d 0x78/x +18652 _string_bb_copy_to_ebx: # (payload array byte) +18653 0x11/imm32/alloc-id:fake:payload +18654 # "bb/copy-to-ebx" +18655 0xe/imm32/size +18656 0x62/b 0x62/b 0x2f/slash 0x63/c 0x6f/o 0x70/p 0x79/y 0x2d/dash 0x74/t 0x6f/o 0x2d/dash 0x65/e 0x62/b 0x78/x +18657 _string_be_copy_to_esi: # (payload array byte) +18658 0x11/imm32/alloc-id:fake:payload +18659 # "be/copy-to-esi" +18660 0xe/imm32/size +18661 0x62/b 0x65/e 0x2f/slash 0x63/c 0x6f/o 0x70/p 0x79/y 0x2d/dash 0x74/t 0x6f/o 0x2d/dash 0x65/e 0x73/s 0x69/i +18662 _string_bf_copy_to_edi: # (payload array byte) +18663 0x11/imm32/alloc-id:fake:payload +18664 # "bf/copy-to-edi" +18665 0xe/imm32/size +18666 0x62/b 0x66/f 0x2f/slash 0x63/c 0x6f/o 0x70/p 0x79/y 0x2d/dash 0x74/t 0x6f/o 0x2d/dash 0x65/e 0x64/d 0x69/i +18667 _string_c7_subop_copy: # (payload array byte) +18668 0x11/imm32/alloc-id:fake:payload +18669 # "c7 0/subop/copy" +18670 0xf/imm32/size +18671 0x63/c 0x37/7 0x20/space 0x30/0 0x2f/slash 0x73/s 0x75/u 0x62/b 0x6f/o 0x70/p 0x2f/slash 0x63/c 0x6f/o 0x70/p 0x79/y +18672 _string_e9_jump_label: # (payload array byte) +18673 0x11/imm32/alloc-id:fake:payload +18674 # "e9/jump" +18675 0x7/imm32/size +18676 0x65/e 0x39/9 0x2f/slash 0x6a/j 0x75/u 0x6d/m 0x70/p +18677 _string_e9_jump_break: # (payload array byte) +18678 0x11/imm32/alloc-id:fake:payload +18679 # "e9/jump break/disp32" +18680 0x14/imm32/size +18681 0x65/e 0x39/9 0x2f/slash 0x6a/j 0x75/u 0x6d/m 0x70/p 0x20/space 0x62/b 0x72/r 0x65/e 0x61/a 0x6b/k 0x2f/slash 0x64/d 0x69/i 0x73/s 0x70/p 0x33/3 0x32/2 +18682 _string_e9_jump_loop: # (payload array byte) +18683 0x11/imm32/alloc-id:fake:payload +18684 # "e9/jump loop/disp32" +18685 0x13/imm32/size +18686 0x65/e 0x39/9 0x2f/slash 0x6a/j 0x75/u 0x6d/m 0x70/p 0x20/space 0x6c/l 0x6f/o 0x6f/o 0x70/p 0x2f/slash 0x64/d 0x69/i 0x73/s 0x70/p 0x33/3 0x32/2 +18687 _string_ff_subop_increment: # (payload array byte) +18688 0x11/imm32/alloc-id:fake:payload +18689 # "ff 0/subop/increment" +18690 0x14/imm32/size +18691 0x66/f 0x66/f 0x20/space 0x30/0 0x2f/slash 0x73/s 0x75/u 0x62/b 0x6f/o 0x70/p 0x2f/slash 0x69/i 0x6e/n 0x63/c 0x72/r 0x65/e 0x6d/m 0x65/e 0x6e/n 0x74/t +18692 _string_ff_subop_decrement: # (payload array byte) +18693 0x11/imm32/alloc-id:fake:payload +18694 # "ff 1/subop/decrement" +18695 0x14/imm32/size +18696 0x66/f 0x66/f 0x20/space 0x31/1 0x2f/slash 0x73/s 0x75/u 0x62/b 0x6f/o 0x70/p 0x2f/slash 0x64/d 0x65/e 0x63/c 0x72/r 0x65/e 0x6d/m 0x65/e 0x6e/n 0x74/t +18697 _string_c1_subop_shift_left: # (payload array byte) +18698 0x11/imm32/alloc-id:fake:payload +18699 # "c1/shift 4/subop/left" +18700 0x15/imm32/size +18701 0x63/c 0x31/1 0x2f/slash 0x73/s 0x68/h 0x69/i 0x66/f 0x74/t 0x20/space 0x34/4 0x2f/slash 0x73/s 0x75/u 0x62/b 0x6f/o 0x70/p 0x2f/slash 0x6c/l 0x65/e 0x66/f 0x74/t +18702 _string_c1_subop_shift_right_padding_zeroes: # (payload array byte) +18703 0x11/imm32/alloc-id:fake:payload +18704 # "c1/shift 5/subop/right-padding-zeroes" +18705 0x25/imm32/size +18706 0x63/c 0x31/1 0x2f/slash 0x73/s 0x68/h 0x69/i 0x66/f 0x74/t 0x20/space 0x35/5 0x2f/slash 0x73/s 0x75/u 0x62/b 0x6f/o 0x70/p 0x2f/slash 0x72/r 0x69/i 0x67/g 0x68/h 0x74/t 0x2d/dash 0x70/p 0x61/a 0x64/d 0x64/d 0x69/i 0x6e/n 0x67/g 0x2d/dash 0x7a/z 0x65/e 0x72/r 0x6f/o 0x65/e 0x73/s +18707 _string_c1_subop_shift_right_preserving_sign: # (payload array byte) +18708 0x11/imm32/alloc-id:fake:payload +18709 # "c1/shift 7/subop/right-preserving-sign" +18710 0x26/imm32/size +18711 0x63/c 0x31/1 0x2f/slash 0x73/s 0x68/h 0x69/i 0x66/f 0x74/t 0x20/space 0x37/7 0x2f/slash 0x73/s 0x75/u 0x62/b 0x6f/o 0x70/p 0x2f/slash 0x72/r 0x69/i 0x67/g 0x68/h 0x74/t 0x2d/dash 0x70/p 0x72/r 0x65/e 0x73/s 0x65/e 0x72/r 0x76/v 0x69/i 0x6e/n 0x67/g 0x2d/dash 0x73/s 0x69/i 0x67/g 0x6e/n +18712 +18713 Single-int-var-in-mem: # (payload list var) +18714 0x11/imm32/alloc-id:fake:payload +18715 0x11/imm32/alloc-id:fake +18716 Int-var-in-mem/imm32 +18717 0/imm32/next +18718 0/imm32/next +18719 +18720 Int-var-in-mem: # (payload var) +18721 0x11/imm32/alloc-id:fake:payload +18722 0/imm32/name +18723 0/imm32/name +18724 0x11/imm32/alloc-id:fake +18725 Type-int/imm32 +18726 1/imm32/some-block-depth +18727 1/imm32/some-stack-offset +18728 0/imm32/no-register +18729 0/imm32/no-register +18730 +18731 # Not really legal, but closest we can currently represent a dereference of an (addr byte) +18732 Single-byte-var-in-mem: # (payload list var) +18733 0x11/imm32/alloc-id:fake:payload +18734 0x11/imm32/alloc-id:fake +18735 Byte-var-in-mem/imm32 +18736 0/imm32/next +18737 0/imm32/next +18738 +18739 # Not really legal, but closest we can currently represent a dereference of an (addr byte) +18740 Byte-var-in-mem: # (payload var) +18741 0x11/imm32/alloc-id:fake:payload +18742 0/imm32/name +18743 0/imm32/name +18744 0x11/imm32/alloc-id:fake +18745 Type-byte/imm32 +18746 1/imm32/some-block-depth +18747 1/imm32/some-stack-offset +18748 0/imm32/no-register +18749 0/imm32/no-register +18750 +18751 Two-args-int-stack-int-reg: # (payload list var) +18752 0x11/imm32/alloc-id:fake:payload +18753 0x11/imm32/alloc-id:fake +18754 Int-var-in-mem/imm32 +18755 0x11/imm32/alloc-id:fake +18756 Single-int-var-in-some-register/imm32/next +18757 +18758 Two-int-args-in-regs: # (payload list var) +18759 0x11/imm32/alloc-id:fake:payload +18760 0x11/imm32/alloc-id:fake +18761 Int-var-in-some-register/imm32 +18762 0x11/imm32/alloc-id:fake +18763 Single-int-var-in-some-register/imm32/next +18764 +18765 # Not really legal, but closest we can currently represent a dereference of an (addr byte) +18766 Two-args-byte-stack-byte-reg: # (payload list var) +18767 0x11/imm32/alloc-id:fake:payload +18768 0x11/imm32/alloc-id:fake +18769 Byte-var-in-mem/imm32 +18770 0x11/imm32/alloc-id:fake +18771 Single-byte-var-in-some-register/imm32/next +18772 +18773 Two-args-int-reg-int-stack: # (payload list var) +18774 0x11/imm32/alloc-id:fake:payload +18775 0x11/imm32/alloc-id:fake +18776 Int-var-in-some-register/imm32 +18777 0x11/imm32/alloc-id:fake +18778 Single-int-var-in-mem/imm32/next +18779 +18780 Two-args-int-eax-int-literal: # (payload list var) +18781 0x11/imm32/alloc-id:fake:payload +18782 0x11/imm32/alloc-id:fake +18783 Int-var-in-eax/imm32 +18784 0x11/imm32/alloc-id:fake +18785 Single-lit-var/imm32/next +18786 +18787 Int-var-and-literal: # (payload list var) +18788 0x11/imm32/alloc-id:fake:payload +18789 0x11/imm32/alloc-id:fake +18790 Int-var-in-mem/imm32 +18791 0x11/imm32/alloc-id:fake +18792 Single-lit-var/imm32/next +18793 +18794 Int-var-in-register-and-literal: # (payload list var) +18795 0x11/imm32/alloc-id:fake:payload +18796 0x11/imm32/alloc-id:fake +18797 Int-var-in-some-register/imm32 +18798 0x11/imm32/alloc-id:fake +18799 Single-lit-var/imm32/next +18800 +18801 Single-int-var-in-some-register: # (payload list var) +18802 0x11/imm32/alloc-id:fake:payload +18803 0x11/imm32/alloc-id:fake +18804 Int-var-in-some-register/imm32 +18805 0/imm32/next +18806 0/imm32/next 18807 -18808 emit-subx-imm8: # out: (addr buffered-file), l: arg-location, stmt: (addr stmt) -18809 # . prologue -18810 55/push-ebp -18811 89/<- %ebp 4/r32/esp -18812 # . save registers -18813 50/push-eax -18814 51/push-ecx -18815 # if (l == 0) return -18816 81 7/subop/compare *(ebp+0xc) 0/imm32 -18817 0f 84/jump-if-= $emit-subx-imm32:end/disp32 -18818 # var v/eax: (handle var) -18819 (get-stmt-operand-from-arg-location *(ebp+0x10) *(ebp+0xc)) # => eax -18820 (lookup *eax *(eax+4)) # Stmt-var-value Stmt-var-value => eax -18821 (lookup *eax *(eax+4)) # Var-name Var-name => eax -18822 (write-buffered *(ebp+8) Space) -18823 (write-buffered *(ebp+8) %eax) -18824 (write-buffered *(ebp+8) "/imm8") -18825 $emit-subx-imm8:end: -18826 # . restore registers -18827 59/pop-to-ecx -18828 58/pop-to-eax -18829 # . epilogue -18830 89/<- %esp 5/r32/ebp -18831 5d/pop-to-ebp -18832 c3/return -18833 -18834 emit-subx-disp32: # out: (addr buffered-file), l: arg-location, stmt: (addr stmt), err: (addr buffered-file), ed: (addr exit-descriptor) -18835 # . prologue -18836 55/push-ebp -18837 89/<- %ebp 4/r32/esp -18838 # . save registers -18839 50/push-eax -18840 51/push-ecx -18841 # if (location == 0) return -18842 81 7/subop/compare *(ebp+0xc) 0/imm32 -18843 0f 84/jump-if-= $emit-subx-disp32:end/disp32 -18844 # var v/eax: (addr stmt-var) -18845 (get-stmt-operand-from-arg-location *(ebp+0x10) *(ebp+0xc) *(ebp+0x14) *(ebp+0x18)) # => eax -18846 (lookup *eax *(eax+4)) # Stmt-var-value Stmt-var-value => eax -18847 (lookup *eax *(eax+4)) # Var-name Var-name => eax -18848 (write-buffered *(ebp+8) Space) -18849 (write-buffered *(ebp+8) %eax) -18850 # hack: if instruction operation starts with "break", emit ":break" -18851 # var name/ecx: (addr array byte) = lookup(stmt->operation) -18852 8b/-> *(ebp+0x10) 0/r32/eax -18853 (lookup *(eax+4) *(eax+8)) # Stmt1-operation Stmt1-operation => eax -18854 89/<- %ecx 0/r32/eax -18855 { -18856 (string-starts-with? %ecx "break") # => eax -18857 3d/compare-eax-and 0/imm32/false -18858 74/jump-if-= break/disp8 -18859 (write-buffered *(ebp+8) ":break") -18860 } -18861 # hack: if instruction operation starts with "loop", emit ":loop" -18862 { -18863 (string-starts-with? %ecx "loop") # => eax -18864 3d/compare-eax-and 0/imm32/false -18865 74/jump-if-= break/disp8 -18866 (write-buffered *(ebp+8) ":loop") -18867 } -18868 (write-buffered *(ebp+8) "/disp32") -18869 $emit-subx-disp32:end: -18870 # . restore registers -18871 59/pop-to-ecx -18872 58/pop-to-eax -18873 # . epilogue -18874 89/<- %esp 5/r32/ebp -18875 5d/pop-to-ebp -18876 c3/return -18877 -18878 emit-call: # out: (addr buffered-file), stmt: (addr stmt) -18879 # . prologue -18880 55/push-ebp -18881 89/<- %ebp 4/r32/esp -18882 # . save registers -18883 50/push-eax -18884 51/push-ecx -18885 # -18886 (emit-indent *(ebp+8) *Curr-block-depth) -18887 (write-buffered *(ebp+8) "(") -18888 # ecx = stmt -18889 8b/-> *(ebp+0xc) 1/r32/ecx -18890 # - emit function name -18891 (lookup *(ecx+4) *(ecx+8)) # Stmt1-operation Stmt1-operation => eax -18892 (write-buffered *(ebp+8) %eax) -18893 # - emit arguments -18894 # var curr/eax: (addr stmt-var) = lookup(stmt->inouts) -18895 (lookup *(ecx+0xc) *(ecx+0x10)) # Stmt1-inouts Stmt1-inouts => eax -18896 { -18897 # if (curr == null) break -18898 3d/compare-eax-and 0/imm32 -18899 74/jump-if-= break/disp8 -18900 # -18901 (emit-subx-call-operand *(ebp+8) %eax) -18902 # curr = lookup(curr->next) -18903 (lookup *(eax+8) *(eax+0xc)) # Stmt-var-next Stmt-var-next => eax -18904 eb/jump loop/disp8 -18905 } -18906 # -18907 (write-buffered *(ebp+8) ")\n") -18908 $emit-call:end: -18909 # . restore registers -18910 59/pop-to-ecx -18911 58/pop-to-eax -18912 # . epilogue -18913 89/<- %esp 5/r32/ebp -18914 5d/pop-to-ebp -18915 c3/return -18916 -18917 emit-subx-call-operand: # out: (addr buffered-file), s: (addr stmt-var) -18918 # shares code with emit-subx-var-as-rm32 -18919 # . prologue -18920 55/push-ebp -18921 89/<- %ebp 4/r32/esp -18922 # . save registers -18923 50/push-eax -18924 51/push-ecx -18925 56/push-esi -18926 # ecx = s -18927 8b/-> *(ebp+0xc) 1/r32/ecx -18928 # var operand/esi: (addr var) = lookup(s->value) -18929 (lookup *ecx *(ecx+4)) # Stmt-var-value Stmt-var-value => eax -18930 89/<- %esi 0/r32/eax -18931 # if (operand->register && !s->is-deref?) emit "%__" -18932 { -18933 $emit-subx-call-operand:check-for-register-direct: -18934 81 7/subop/compare *(esi+0x18) 0/imm32 # Var-register -18935 74/jump-if-= break/disp8 -18936 81 7/subop/compare *(ecx+0x10) 0/imm32/false # Stmt-var-is-deref -18937 75/jump-if-!= break/disp8 -18938 $emit-subx-call-operand:register-direct: -18939 (write-buffered *(ebp+8) " %") -18940 (lookup *(esi+0x18) *(esi+0x1c)) # Var-register Var-register => eax -18941 (write-buffered *(ebp+8) %eax) -18942 e9/jump $emit-subx-call-operand:end/disp32 -18943 } -18944 # else if (operand->register && s->is-deref?) emit "*__" -18945 { -18946 $emit-subx-call-operand:check-for-register-indirect: -18947 81 7/subop/compare *(esi+0x18) 0/imm32 # Var-register -18948 74/jump-if-= break/disp8 -18949 81 7/subop/compare *(ecx+0x10) 0/imm32/false # Stmt-var-is-deref -18950 74/jump-if-= break/disp8 -18951 $emit-subx-call-operand:register-indirect: -18952 (emit-subx-call-operand-register-indirect *(ebp+8) %esi) -18953 e9/jump $emit-subx-call-operand:end/disp32 -18954 } -18955 # else if (operand->stack-offset) emit "*(ebp+__)" -18956 { -18957 81 7/subop/compare *(esi+0x14) 0/imm32 # Var-offset -18958 74/jump-if-= break/disp8 -18959 $emit-subx-call-operand:stack: -18960 (emit-subx-call-operand-stack *(ebp+8) %esi) -18961 e9/jump $emit-subx-call-operand:end/disp32 -18962 } -18963 # else if (operand->type == literal) emit "__" -18964 { -18965 (lookup *(esi+8) *(esi+0xc)) # Var-type Var-type => eax -18966 81 7/subop/compare *(eax+4) 0/imm32 # Type-tree-left -18967 75/jump-if-!= break/disp8 -18968 $emit-subx-call-operand:literal: -18969 (write-buffered *(ebp+8) Space) -18970 (lookup *esi *(esi+4)) # Var-name Var-name => eax -18971 (write-buffered *(ebp+8) %eax) -18972 } -18973 $emit-subx-call-operand:end: -18974 # . restore registers -18975 5e/pop-to-esi -18976 59/pop-to-ecx -18977 58/pop-to-eax -18978 # . epilogue -18979 89/<- %esp 5/r32/ebp -18980 5d/pop-to-ebp -18981 c3/return -18982 -18983 emit-subx-call-operand-register-indirect: # out: (addr buffered-file), v: (addr var) -18984 # . prologue -18985 55/push-ebp -18986 89/<- %ebp 4/r32/esp -18987 # . save registers -18988 50/push-eax -18989 51/push-ecx -18990 56/push-esi -18991 # esi = v -18992 8b/-> *(ebp+0xc) 6/r32/esi -18993 # var size/ecx: int = size-of-deref(v) -18994 (size-of-deref %esi) # => eax -18995 89/<- %ecx 0/r32/eax -18996 # var reg-name/esi: (addr array byte) = lookup(v->register) -18997 (lookup *(esi+0x18) *(esi+0x1c)) # Var-register Var-register => eax -18998 89/<- %esi 0/r32/eax -18999 # TODO: assert size is a multiple of 4 -19000 # var i/eax: int = 0 -19001 b8/copy-to-eax 0/imm32 -19002 { -19003 $emit-subx-call-operand-register-indirect:loop: -19004 # if (i >= size) break -19005 39/compare %eax 1/r32/ecx -19006 7d/jump-if->= break/disp8 -19007 # emit " *(" v->register "+" i ")" -19008 (write-buffered *(ebp+8) " *(") -19009 (write-buffered *(ebp+8) %esi) -19010 (write-buffered *(ebp+8) "+") -19011 (write-int32-hex-buffered *(ebp+8) %eax) -19012 (write-buffered *(ebp+8) ")") -19013 # i += 4 -19014 05/add-to-eax 4/imm32 -19015 # -19016 eb/jump loop/disp8 -19017 } -19018 $emit-subx-call-operand-register-indirect:end: -19019 # . restore registers -19020 5e/pop-to-esi -19021 59/pop-to-ecx -19022 58/pop-to-eax -19023 # . epilogue -19024 89/<- %esp 5/r32/ebp -19025 5d/pop-to-ebp -19026 c3/return -19027 -19028 emit-subx-call-operand-stack: # out: (addr buffered-file), v: (addr var) -19029 # . prologue -19030 55/push-ebp -19031 89/<- %ebp 4/r32/esp -19032 # . save registers -19033 50/push-eax -19034 51/push-ecx -19035 56/push-esi -19036 # esi = v -19037 8b/-> *(ebp+0xc) 6/r32/esi -19038 # var curr/ecx: int = v->offset -19039 8b/-> *(esi+0x14) 1/r32/ecx # Var-offset -19040 # var max/eax: int = v->offset + size-of(v) -19041 (size-of %esi) # => eax -19042 # TODO: assert size is a multiple of 4 -19043 01/add-to %eax 1/r32/ecx -19044 { -19045 $emit-subx-call-operand-stack:loop: -19046 # if (curr >= max) break -19047 39/compare %ecx 0/r32/eax -19048 7d/jump-if->= break/disp8 -19049 # emit " *(ebp+" curr ")" -19050 (write-buffered *(ebp+8) " *(ebp+") -19051 (write-int32-hex-buffered *(ebp+8) %ecx) -19052 (write-buffered *(ebp+8) ")") -19053 # i += 4 -19054 81 0/subop/add %ecx 4/imm32 -19055 # -19056 eb/jump loop/disp8 -19057 } -19058 $emit-subx-call-operand-stack:end: -19059 # . restore registers -19060 5e/pop-to-esi -19061 59/pop-to-ecx -19062 58/pop-to-eax -19063 # . epilogue -19064 89/<- %esp 5/r32/ebp -19065 5d/pop-to-ebp -19066 c3/return -19067 -19068 emit-subx-var-as-rm32: # out: (addr buffered-file), s: (addr stmt-var) -19069 # . prologue -19070 55/push-ebp -19071 89/<- %ebp 4/r32/esp -19072 # . save registers -19073 50/push-eax -19074 51/push-ecx -19075 56/push-esi -19076 # ecx = s -19077 8b/-> *(ebp+0xc) 1/r32/ecx -19078 # var operand/esi: (addr var) = lookup(s->value) -19079 (lookup *ecx *(ecx+4)) # Stmt-var-value Stmt-var-value => eax -19080 89/<- %esi 0/r32/eax -19081 # if (operand->register && s->is-deref?) emit "*__" -19082 { -19083 $emit-subx-var-as-rm32:check-for-register-indirect: -19084 81 7/subop/compare *(esi+0x18) 0/imm32 # Var-register -19085 74/jump-if-= break/disp8 -19086 81 7/subop/compare *(ecx+0x10) 0/imm32/false # Stmt-var-is-deref -19087 74/jump-if-= break/disp8 -19088 $emit-subx-var-as-rm32:register-indirect: -19089 (write-buffered *(ebp+8) " *") -19090 (lookup *(esi+0x18) *(esi+0x1c)) # Var-register Var-register => eax -19091 (write-buffered *(ebp+8) %eax) -19092 e9/jump $emit-subx-var-as-rm32:end/disp32 -19093 } -19094 # if (operand->register && !s->is-deref?) emit "%__" -19095 { -19096 $emit-subx-var-as-rm32:check-for-register-direct: -19097 81 7/subop/compare *(esi+0x18) 0/imm32 # Var-register -19098 74/jump-if-= break/disp8 -19099 81 7/subop/compare *(ecx+0x10) 0/imm32/false # Stmt-var-is-deref -19100 75/jump-if-!= break/disp8 -19101 $emit-subx-var-as-rm32:register-direct: -19102 (write-buffered *(ebp+8) " %") -19103 (lookup *(esi+0x18) *(esi+0x1c)) # Var-register Var-register => eax -19104 (write-buffered *(ebp+8) %eax) -19105 e9/jump $emit-subx-var-as-rm32:end/disp32 -19106 } -19107 # else if (operand->stack-offset) emit "*(ebp+__)" -19108 { -19109 81 7/subop/compare *(esi+0x14) 0/imm32 # Var-offset -19110 74/jump-if-= break/disp8 -19111 $emit-subx-var-as-rm32:stack: -19112 (write-buffered *(ebp+8) Space) -19113 (write-buffered *(ebp+8) "*(ebp+") -19114 (write-int32-hex-buffered *(ebp+8) *(esi+0x14)) # Var-offset -19115 (write-buffered *(ebp+8) ")") -19116 } -19117 $emit-subx-var-as-rm32:end: -19118 # . restore registers -19119 5e/pop-to-esi -19120 59/pop-to-ecx -19121 58/pop-to-eax -19122 # . epilogue -19123 89/<- %esp 5/r32/ebp -19124 5d/pop-to-ebp -19125 c3/return +18808 Single-addr-var-in-some-register: # (payload list var) +18809 0x11/imm32/alloc-id:fake:payload +18810 0x11/imm32/alloc-id:fake +18811 Addr-var-in-some-register/imm32 +18812 0/imm32/next +18813 0/imm32/next +18814 +18815 Single-byte-var-in-some-register: # (payload list var) +18816 0x11/imm32/alloc-id:fake:payload +18817 0x11/imm32/alloc-id:fake +18818 Byte-var-in-some-register/imm32 +18819 0/imm32/next +18820 0/imm32/next +18821 +18822 Int-var-in-some-register: # (payload var) +18823 0x11/imm32/alloc-id:fake:payload +18824 0/imm32/name +18825 0/imm32/name +18826 0x11/imm32/alloc-id:fake +18827 Type-int/imm32 +18828 1/imm32/some-block-depth +18829 0/imm32/no-stack-offset +18830 0x11/imm32/alloc-id:fake +18831 Any-register/imm32 +18832 +18833 Any-register: # (payload array byte) +18834 0x11/imm32/alloc-id:fake:payload +18835 1/imm32/size +18836 # data +18837 2a/asterisk +18838 +18839 Addr-var-in-some-register: # (payload var) +18840 0x11/imm32/alloc-id:fake:payload +18841 0/imm32/name +18842 0/imm32/name +18843 0x11/imm32/alloc-id:fake +18844 Type-addr/imm32 +18845 1/imm32/some-block-depth +18846 0/imm32/no-stack-offset +18847 0x11/imm32/alloc-id:fake +18848 Any-register/imm32 +18849 +18850 Byte-var-in-some-register: # (payload var) +18851 0x11/imm32/alloc-id:fake:payload +18852 0/imm32/name +18853 0/imm32/name +18854 0x11/imm32/alloc-id:fake +18855 Type-byte/imm32 +18856 1/imm32/some-block-depth +18857 0/imm32/no-stack-offset +18858 0x11/imm32/alloc-id:fake +18859 Any-register/imm32 +18860 +18861 Single-int-var-in-eax: # (payload list var) +18862 0x11/imm32/alloc-id:fake:payload +18863 0x11/imm32/alloc-id:fake +18864 Int-var-in-eax/imm32 +18865 0/imm32/next +18866 0/imm32/next +18867 +18868 Int-var-in-eax: +18869 0x11/imm32/alloc-id:fake:payload +18870 0/imm32/name +18871 0/imm32/name +18872 0x11/imm32/alloc-id:fake +18873 Type-int/imm32 +18874 1/imm32/some-block-depth +18875 0/imm32/no-stack-offset +18876 0x11/imm32/alloc-id:fake +18877 $Register-eax/imm32 +18878 +18879 Single-int-var-in-ecx: # (payload list var) +18880 0x11/imm32/alloc-id:fake:payload +18881 0x11/imm32/alloc-id:fake +18882 Int-var-in-ecx/imm32 +18883 0/imm32/next +18884 0/imm32/next +18885 +18886 Int-var-in-ecx: +18887 0x11/imm32/alloc-id:fake:payload +18888 0/imm32/name +18889 0/imm32/name +18890 0x11/imm32/alloc-id:fake +18891 Type-int/imm32 +18892 1/imm32/some-block-depth +18893 0/imm32/no-stack-offset +18894 0x11/imm32/alloc-id:fake +18895 $Register-ecx/imm32/register +18896 +18897 Single-int-var-in-edx: # (payload list var) +18898 0x11/imm32/alloc-id:fake:payload +18899 0x11/imm32/alloc-id:fake +18900 Int-var-in-edx/imm32 +18901 0/imm32/next +18902 0/imm32/next +18903 +18904 Int-var-in-edx: # (payload list var) +18905 0x11/imm32/alloc-id:fake:payload +18906 0/imm32/name +18907 0/imm32/name +18908 0x11/imm32/alloc-id:fake +18909 Type-int/imm32 +18910 1/imm32/some-block-depth +18911 0/imm32/no-stack-offset +18912 0x11/imm32/alloc-id:fake +18913 $Register-edx/imm32/register +18914 +18915 Single-int-var-in-ebx: # (payload list var) +18916 0x11/imm32/alloc-id:fake:payload +18917 0x11/imm32/alloc-id:fake +18918 Int-var-in-ebx/imm32 +18919 0/imm32/next +18920 0/imm32/next +18921 +18922 Int-var-in-ebx: # (payload list var) +18923 0x11/imm32/alloc-id:fake:payload +18924 0/imm32/name +18925 0/imm32/name +18926 0x11/imm32/alloc-id:fake +18927 Type-int/imm32 +18928 1/imm32/some-block-depth +18929 0/imm32/no-stack-offset +18930 0x11/imm32/alloc-id:fake +18931 $Register-ebx/imm32/register +18932 +18933 Single-int-var-in-esi: # (payload list var) +18934 0x11/imm32/alloc-id:fake:payload +18935 0x11/imm32/alloc-id:fake +18936 Int-var-in-esi/imm32 +18937 0/imm32/next +18938 0/imm32/next +18939 +18940 Int-var-in-esi: # (payload list var) +18941 0x11/imm32/alloc-id:fake:payload +18942 0/imm32/name +18943 0/imm32/name +18944 0x11/imm32/alloc-id:fake +18945 Type-int/imm32 +18946 1/imm32/some-block-depth +18947 0/imm32/no-stack-offset +18948 0x11/imm32/alloc-id:fake +18949 $Register-esi/imm32/register +18950 +18951 Single-int-var-in-edi: # (payload list var) +18952 0x11/imm32/alloc-id:fake:payload +18953 0x11/imm32/alloc-id:fake +18954 Int-var-in-edi/imm32 +18955 0/imm32/next +18956 0/imm32/next +18957 +18958 Int-var-in-edi: # (payload list var) +18959 0x11/imm32/alloc-id:fake:payload +18960 0/imm32/name +18961 0/imm32/name +18962 0x11/imm32/alloc-id:fake +18963 Type-int/imm32 +18964 1/imm32/some-block-depth +18965 0/imm32/no-stack-offset +18966 0x11/imm32/alloc-id:fake +18967 $Register-edi/imm32/register +18968 +18969 Single-lit-var: # (payload list var) +18970 0x11/imm32/alloc-id:fake:payload +18971 0x11/imm32/alloc-id:fake +18972 Lit-var/imm32 +18973 0/imm32/next +18974 0/imm32/next +18975 +18976 Lit-var: # (payload var) +18977 0x11/imm32/alloc-id:fake:payload +18978 0/imm32/name +18979 0/imm32/name +18980 0x11/imm32/alloc-id:fake +18981 Type-literal/imm32 +18982 1/imm32/some-block-depth +18983 0/imm32/no-stack-offset +18984 0/imm32/no-register +18985 0/imm32/no-register +18986 +18987 Type-int: # (payload type-tree) +18988 0x11/imm32/alloc-id:fake:payload +18989 1/imm32/is-atom +18990 1/imm32/value:int +18991 0/imm32/left:unused +18992 0/imm32/right:null +18993 0/imm32/right:null +18994 +18995 Type-literal: # (payload type-tree) +18996 0x11/imm32/alloc-id:fake:payload +18997 1/imm32/is-atom +18998 0/imm32/value:literal +18999 0/imm32/left:unused +19000 0/imm32/right:null +19001 0/imm32/right:null +19002 +19003 Type-addr: # (payload type-tree) +19004 0x11/imm32/alloc-id:fake:payload +19005 1/imm32/is-atom +19006 2/imm32/value:addr +19007 0/imm32/left:unused +19008 0/imm32/right:null +19009 0/imm32/right:null +19010 +19011 Type-byte: # (payload type-tree) +19012 0x11/imm32/alloc-id:fake:payload +19013 1/imm32/is-atom +19014 8/imm32/value:byte +19015 0/imm32/left:unused +19016 0/imm32/right:null +19017 0/imm32/right:null +19018 +19019 == code +19020 emit-subx-primitive: # out: (addr buffered-file), stmt: (addr stmt), primitive: (addr primitive), err: (addr buffered-file), ed: (addr exit-descriptor) +19021 # . prologue +19022 55/push-ebp +19023 89/<- %ebp 4/r32/esp +19024 # . save registers +19025 50/push-eax +19026 51/push-ecx +19027 # ecx = primitive +19028 8b/-> *(ebp+0x10) 1/r32/ecx +19029 # emit primitive name +19030 (emit-indent *(ebp+8) *Curr-block-depth) +19031 (lookup *(ecx+0x18) *(ecx+0x1c)) # Primitive-subx-name Primitive-subx-name => eax +19032 (write-buffered *(ebp+8) %eax) +19033 # emit rm32 if necessary +19034 (emit-subx-rm32 *(ebp+8) *(ecx+0x20) *(ebp+0xc) *(ebp+0x14) *(ebp+0x18)) # Primitive-subx-rm32 +19035 # emit r32 if necessary +19036 (emit-subx-r32 *(ebp+8) *(ecx+0x24) *(ebp+0xc)) # Primitive-subx-r32 +19037 # emit imm32 if necessary +19038 (emit-subx-imm32 *(ebp+8) *(ecx+0x28) *(ebp+0xc)) # Primitive-subx-imm32 +19039 # emit imm8 if necessary +19040 (emit-subx-imm8 *(ebp+8) *(ecx+0x2c) *(ebp+0xc)) # Primitive-subx-imm8 +19041 # emit disp32 if necessary +19042 (emit-subx-disp32 *(ebp+8) *(ecx+0x30) *(ebp+0xc) *(ebp+0x14) *(ebp+0x18)) # Primitive-subx-disp32 +19043 (write-buffered *(ebp+8) Newline) +19044 $emit-subx-primitive:end: +19045 # . restore registers +19046 59/pop-to-ecx +19047 58/pop-to-eax +19048 # . epilogue +19049 89/<- %esp 5/r32/ebp +19050 5d/pop-to-ebp +19051 c3/return +19052 +19053 emit-subx-rm32: # out: (addr buffered-file), l: arg-location, stmt: (addr stmt), err: (addr buffered-file), ed: (addr exit-descriptor) +19054 # . prologue +19055 55/push-ebp +19056 89/<- %ebp 4/r32/esp +19057 # . save registers +19058 50/push-eax +19059 # if (l == 0) return +19060 81 7/subop/compare *(ebp+0xc) 0/imm32 +19061 74/jump-if-= $emit-subx-rm32:end/disp8 +19062 # var v/eax: (addr stmt-var) +19063 (get-stmt-operand-from-arg-location *(ebp+0x10) *(ebp+0xc) *(ebp+0x14) *(ebp+0x18)) # => eax +19064 (emit-subx-var-as-rm32 *(ebp+8) %eax) +19065 $emit-subx-rm32:end: +19066 # . restore registers +19067 58/pop-to-eax +19068 # . epilogue +19069 89/<- %esp 5/r32/ebp +19070 5d/pop-to-ebp +19071 c3/return +19072 +19073 get-stmt-operand-from-arg-location: # stmt: (addr stmt), l: arg-location, err: (addr buffered-file), ed: (addr exit-descriptor) -> var/eax: (addr stmt-var) +19074 # . prologue +19075 55/push-ebp +19076 89/<- %ebp 4/r32/esp +19077 # . save registers +19078 51/push-ecx +19079 # eax = l +19080 8b/-> *(ebp+0xc) 0/r32/eax +19081 # ecx = stmt +19082 8b/-> *(ebp+8) 1/r32/ecx +19083 # if (l == 1) return stmt->inouts +19084 { +19085 3d/compare-eax-and 1/imm32 +19086 75/jump-if-!= break/disp8 +19087 $get-stmt-operand-from-arg-location:1: +19088 (lookup *(ecx+0xc) *(ecx+0x10)) # Stmt1-inouts Stmt1-inouts => eax +19089 eb/jump $get-stmt-operand-from-arg-location:end/disp8 +19090 } +19091 # if (l == 2) return stmt->inouts->next +19092 { +19093 3d/compare-eax-and 2/imm32 +19094 75/jump-if-!= break/disp8 +19095 $get-stmt-operand-from-arg-location:2: +19096 (lookup *(ecx+0xc) *(ecx+0x10)) # Stmt1-inouts Stmt1-inouts => eax +19097 (lookup *(eax+8) *(eax+0xc)) # Stmt-var-next Stmt-var-next => eax +19098 eb/jump $get-stmt-operand-from-arg-location:end/disp8 +19099 } +19100 # if (l == 3) return stmt->outputs +19101 { +19102 3d/compare-eax-and 3/imm32 +19103 75/jump-if-!= break/disp8 +19104 $get-stmt-operand-from-arg-location:3: +19105 (lookup *(ecx+0x14) *(ecx+0x18)) # Stmt1-outputs Stmt1-outputs => eax +19106 eb/jump $get-stmt-operand-from-arg-location:end/disp8 +19107 } +19108 # abort +19109 e9/jump $get-stmt-operand-from-arg-location:abort/disp32 +19110 $get-stmt-operand-from-arg-location:end: +19111 # . restore registers +19112 59/pop-to-ecx +19113 # . epilogue +19114 89/<- %esp 5/r32/ebp +19115 5d/pop-to-ebp +19116 c3/return +19117 +19118 $get-stmt-operand-from-arg-location:abort: +19119 # error("invalid arg-location " eax) +19120 (write-buffered *(ebp+0x10) "invalid arg-location ") +19121 (write-int32-hex-buffered *(ebp+0x10) %eax) +19122 (write-buffered *(ebp+0x10) Newline) +19123 (flush *(ebp+0x10)) +19124 (stop *(ebp+0x14) 1) +19125 # never gets here 19126 -19127 find-matching-primitive: # primitives: (addr primitive), stmt: (addr stmt) -> result/eax: (addr primitive) +19127 emit-subx-r32: # out: (addr buffered-file), l: arg-location, stmt: (addr stmt) 19128 # . prologue 19129 55/push-ebp 19130 89/<- %ebp 4/r32/esp 19131 # . save registers -19132 51/push-ecx -19133 # var curr/ecx: (addr primitive) = primitives -19134 8b/-> *(ebp+8) 1/r32/ecx -19135 { -19136 $find-matching-primitive:loop: -19137 # if (curr == null) break -19138 81 7/subop/compare %ecx 0/imm32 -19139 74/jump-if-= break/disp8 -19140 # if match(curr, stmt) return curr -19141 { -19142 (mu-stmt-matches-primitive? *(ebp+0xc) %ecx) # => eax -19143 3d/compare-eax-and 0/imm32/false -19144 74/jump-if-= break/disp8 -19145 89/<- %eax 1/r32/ecx -19146 eb/jump $find-matching-primitive:end/disp8 -19147 } -19148 $find-matching-primitive:next-primitive: -19149 # curr = curr->next -19150 (lookup *(ecx+0x38) *(ecx+0x3c)) # Primitive-next Primitive-next => eax -19151 89/<- %ecx 0/r32/eax -19152 # -19153 e9/jump loop/disp32 -19154 } -19155 # return null -19156 b8/copy-to-eax 0/imm32 -19157 $find-matching-primitive:end: -19158 # . restore registers -19159 59/pop-to-ecx -19160 # . epilogue -19161 89/<- %esp 5/r32/ebp -19162 5d/pop-to-ebp -19163 c3/return -19164 -19165 mu-stmt-matches-primitive?: # stmt: (addr stmt), primitive: (addr primitive) -> result/eax: boolean -19166 # A mu stmt matches a primitive if the name matches, all the inout vars -19167 # match, and all the output vars match. -19168 # Vars match if types match and registers match. -19169 # In addition, a stmt output matches a primitive's output if types match -19170 # and the primitive has a wildcard register. -19171 # . prologue -19172 55/push-ebp -19173 89/<- %ebp 4/r32/esp -19174 # . save registers -19175 51/push-ecx -19176 52/push-edx -19177 53/push-ebx -19178 56/push-esi -19179 57/push-edi -19180 # ecx = stmt -19181 8b/-> *(ebp+8) 1/r32/ecx -19182 # edx = primitive -19183 8b/-> *(ebp+0xc) 2/r32/edx -19184 { -19185 $mu-stmt-matches-primitive?:check-name: -19186 # if (primitive->name != stmt->operation) return false -19187 # . var esi: (addr array byte) = lookup(stmt->operation) -19188 (lookup *(ecx+4) *(ecx+8)) # Stmt1-operation Stmt1-operation => eax -19189 89/<- %esi 0/r32/eax -19190 # . var edi: (addr array byte) = lookup(primitive->name) -19191 (lookup *edx *(edx+4)) # Primitive-name Primitive-name => eax -19192 89/<- %edi 0/r32/eax -19193 (string-equal? %esi %edi) # => eax -19194 3d/compare-eax-and 0/imm32/false -19195 75/jump-if-!= break/disp8 -19196 b8/copy-to-eax 0/imm32 -19197 e9/jump $mu-stmt-matches-primitive?:end/disp32 -19198 } -19199 # var curr/esi: (addr stmt-var) = lookup(stmt->inouts) -19200 (lookup *(ecx+0xc) *(ecx+0x10)) # Stmt1-inouts Stmt1-inouts => eax -19201 89/<- %esi 0/r32/eax -19202 # var curr2/edi: (addr list var) = lookup(primitive->inouts) -19203 (lookup *(edx+8) *(edx+0xc)) # Primitive-inouts Primitive-inouts => eax -19204 89/<- %edi 0/r32/eax -19205 { -19206 $mu-stmt-matches-primitive?:inouts-loop: -19207 # if (curr == 0 && curr2 == 0) move on to check outputs -19208 { -19209 $mu-stmt-matches-primitive?:check-both-inouts-null: -19210 81 7/subop/compare %esi 0/imm32 -19211 75/jump-if-!= break/disp8 -19212 $mu-stmt-matches-primitive?:stmt-inout-null: -19213 81 7/subop/compare %edi 0/imm32 -19214 0f 84/jump-if-= $mu-stmt-matches-primitive?:check-outputs/disp32 -19215 $mu-stmt-matches-primitive?:stmt-inout-null-and-prim-inout-not-null: -19216 # return false -19217 b8/copy-to-eax 0/imm32/false -19218 e9/jump $mu-stmt-matches-primitive?:end/disp32 -19219 } -19220 # if (curr2 == 0) return false -19221 { -19222 $mu-stmt-matches-primitive?:check-prim-inout-null: -19223 81 7/subop/compare %edi 0/imm32 -19224 75/jump-if-!= break/disp8 -19225 $mu-stmt-matches-primitive?:prim-inout-null: -19226 b8/copy-to-eax 0/imm32/false -19227 e9/jump $mu-stmt-matches-primitive?:end/disp32 -19228 } -19229 # if (curr != curr2) return false -19230 { -19231 $mu-stmt-matches-primitive?:check-inouts-match: -19232 (lookup *edi *(edi+4)) # List-value List-value => eax -19233 (operand-matches-primitive? %esi %eax) # => eax -19234 3d/compare-eax-and 0/imm32/false -19235 75/jump-if-!= break/disp8 -19236 $mu-stmt-matches-primitive?:inouts-match: -19237 b8/copy-to-eax 0/imm32/false -19238 e9/jump $mu-stmt-matches-primitive?:end/disp32 -19239 } -19240 $mu-stmt-matches-primitive?:next-inout: -19241 # curr = lookup(curr->next) -19242 (lookup *(esi+8) *(esi+0xc)) # Stmt-var-next Stmt-var-next => eax -19243 89/<- %esi 0/r32/eax -19244 # curr2 = lookup(curr2->next) -19245 (lookup *(edi+8) *(edi+0xc)) # List-next List-next => eax -19246 89/<- %edi 0/r32/eax -19247 # -19248 e9/jump loop/disp32 -19249 } -19250 $mu-stmt-matches-primitive?:check-outputs: -19251 # var curr/esi: (addr stmt-var) = lookup(stmt->outputs) -19252 (lookup *(ecx+0x14) *(ecx+0x18)) # Stmt1-outputs Stmt1-outputs => eax -19253 89/<- %esi 0/r32/eax -19254 # var curr2/edi: (addr list var) = lookup(primitive->outputs) -19255 (lookup *(edx+0x10) *(edx+0x14)) # Primitive-outputs Primitive-outputs => eax -19256 89/<- %edi 0/r32/eax -19257 { -19258 $mu-stmt-matches-primitive?:outputs-loop: -19259 # if (curr == 0) return (curr2 == 0) -19260 { -19261 $mu-stmt-matches-primitive?:check-both-outputs-null: -19262 81 7/subop/compare %esi 0/imm32 -19263 75/jump-if-!= break/disp8 -19264 { -19265 $mu-stmt-matches-primitive?:stmt-output-null: -19266 81 7/subop/compare %edi 0/imm32 -19267 75/jump-if-!= break/disp8 -19268 $mu-stmt-matches-primitive?:both-outputs-null: -19269 # return true -19270 b8/copy-to-eax 1/imm32 -19271 e9/jump $mu-stmt-matches-primitive?:end/disp32 -19272 } -19273 $mu-stmt-matches-primitive?:stmt-output-null-and-prim-output-not-null: -19274 # return false -19275 b8/copy-to-eax 0/imm32 -19276 e9/jump $mu-stmt-matches-primitive?:end/disp32 -19277 } -19278 # if (curr2 == 0) return false -19279 { -19280 $mu-stmt-matches-primitive?:check-prim-output-null: -19281 81 7/subop/compare %edi 0/imm32 -19282 75/jump-if-!= break/disp8 -19283 $mu-stmt-matches-primitive?:prim-output-is-null: -19284 b8/copy-to-eax 0/imm32 -19285 e9/jump $mu-stmt-matches-primitive?:end/disp32 -19286 } -19287 # if (curr != curr2) return false -19288 { -19289 $mu-stmt-matches-primitive?:check-outputs-match: -19290 (lookup *edi *(edi+4)) # List-value List-value => eax -19291 (operand-matches-primitive? %esi %eax) # => eax -19292 3d/compare-eax-and 0/imm32/false -19293 75/jump-if-!= break/disp8 -19294 $mu-stmt-matches-primitive?:outputs-match: -19295 b8/copy-to-eax 0/imm32 -19296 e9/jump $mu-stmt-matches-primitive?:end/disp32 -19297 } -19298 $mu-stmt-matches-primitive?:next-output: -19299 # curr = lookup(curr->next) -19300 (lookup *(esi+8) *(esi+0xc)) # Stmt-var-next Stmt-var-next => eax -19301 89/<- %esi 0/r32/eax -19302 # curr2 = lookup(curr2->next) -19303 (lookup *(edi+8) *(edi+0xc)) # List-next List-next => eax -19304 89/<- %edi 0/r32/eax -19305 # -19306 e9/jump loop/disp32 -19307 } -19308 $mu-stmt-matches-primitive?:return-true: -19309 b8/copy-to-eax 1/imm32 -19310 $mu-stmt-matches-primitive?:end: -19311 # . restore registers -19312 5f/pop-to-edi -19313 5e/pop-to-esi -19314 5b/pop-to-ebx -19315 5a/pop-to-edx -19316 59/pop-to-ecx -19317 # . epilogue -19318 89/<- %esp 5/r32/ebp -19319 5d/pop-to-ebp -19320 c3/return -19321 -19322 operand-matches-primitive?: # s: (addr stmt-var), prim-var: (addr var) -> result/eax: boolean -19323 # . prologue -19324 55/push-ebp -19325 89/<- %ebp 4/r32/esp -19326 # . save registers -19327 51/push-ecx -19328 52/push-edx -19329 53/push-ebx -19330 56/push-esi -19331 57/push-edi -19332 # ecx = s -19333 8b/-> *(ebp+8) 1/r32/ecx -19334 # var var/esi: (addr var) = lookup(s->value) -19335 (lookup *ecx *(ecx+4)) # Stmt-var-value Stmt-var-value => eax -19336 89/<- %esi 0/r32/eax -19337 # edi = prim-var -19338 8b/-> *(ebp+0xc) 7/r32/edi -19339 $operand-matches-primitive?:check-type: -19340 # if !category-match?(var->type, prim-var->type) return false -19341 # . var vtype/ebx: (addr type-tree) = lookup(var->type) -19342 (lookup *(esi+8) *(esi+0xc)) # Var-type Var-type => eax -19343 89/<- %ebx 0/r32/eax -19344 # . var ptype/eax: (addr type-tree) = lookup(prim-var->type) -19345 (lookup *(edi+8) *(edi+0xc)) # Var-type Var-type => eax -19346 (subx-type-category-match? %ebx %eax) # => eax -19347 3d/compare-eax-and 0/imm32/false -19348 0f 84/jump-if-= $operand-matches-primitive?:return-false/disp32 -19349 { -19350 $operand-matches-primitive?:check-register: -19351 # if prim-var is in memory and var is in register but dereference, match -19352 { -19353 81 7/subop/compare *(edi+0x18) 0/imm32 # Var-register -19354 0f 85/jump-if-!= break/disp32 -19355 81 7/subop/compare *(esi+0x18) 0/imm32 # Var-register -19356 74/jump-if-= break/disp8 -19357 81 7/subop/compare *(ecx+0x10) 0/imm32/false # Stmt-var-is-deref -19358 74/jump-if-= break/disp8 -19359 $operand-matches-primitive?:var-deref-match: -19360 e9/jump $operand-matches-primitive?:return-true/disp32 -19361 } -19362 # if prim-var is in register and var is in register but dereference, no match -19363 { -19364 81 7/subop/compare *(edi+0x18) 0/imm32 # Var-register -19365 0f 84/jump-if-= break/disp32 -19366 81 7/subop/compare *(esi+0x18) 0/imm32 # Var-register -19367 0f 84/jump-if-= break/disp32 -19368 81 7/subop/compare *(ecx+0x10) 0/imm32/false # Stmt-var-is-deref -19369 74/jump-if-= break/disp8 -19370 $operand-matches-primitive?:var-deref-no-match: -19371 e9/jump $operand-matches-primitive?:return-false/disp32 -19372 } -19373 # return false if var->register doesn't match prim-var->register -19374 { -19375 # if register addresses are equal, it's a match -19376 # var vreg/ebx: (addr array byte) = lookup(var->register) -19377 (lookup *(esi+0x18) *(esi+0x1c)) # Var-register Var-register => eax -19378 89/<- %ebx 0/r32/eax -19379 # var preg/ecx: (addr array byte) = lookup(prim-var->register) -19380 (lookup *(edi+0x18) *(edi+0x1c)) # Var-register Var-register => eax -19381 89/<- %ecx 0/r32/eax -19382 # if (vreg == preg) break -19383 39/compare %ecx 3/r32/ebx -19384 74/jump-if-= break/disp8 -19385 $operand-matches-primitive?:var-register-no-match: -19386 # if either address is 0, return false -19387 81 7/subop/compare %ebx 0/imm32 -19388 74/jump-if-= $operand-matches-primitive?:return-false/disp8 -19389 81 7/subop/compare %ecx 0/imm32 -19390 74/jump-if-= $operand-matches-primitive?:return-false/disp8 -19391 # if prim-var->register is wildcard, it's a match -19392 (string-equal? %ecx "*") # Any-register => eax -19393 3d/compare-eax-and 0/imm32/false -19394 75/jump-if-!= break/disp8 -19395 $operand-matches-primitive?:wildcard-no-match: -19396 # if string contents aren't equal, return false -19397 (string-equal? %ecx %ebx) # => eax -19398 3d/compare-eax-and 0/imm32/false -19399 74/jump-if-= $operand-matches-primitive?:return-false/disp8 -19400 } -19401 } -19402 $operand-matches-primitive?:return-true: -19403 b8/copy-to-eax 1/imm32/true -19404 eb/jump $operand-matches-primitive?:end/disp8 -19405 $operand-matches-primitive?:return-false: -19406 b8/copy-to-eax 0/imm32/false -19407 $operand-matches-primitive?:end: -19408 # . restore registers -19409 5f/pop-to-edi -19410 5e/pop-to-esi -19411 5b/pop-to-ebx -19412 5a/pop-to-edx -19413 59/pop-to-ecx -19414 # . epilogue -19415 89/<- %esp 5/r32/ebp -19416 5d/pop-to-ebp -19417 c3/return -19418 -19419 find-matching-function: # functions: (addr function), stmt: (addr stmt) -> result/eax: (addr function) -19420 # . prologue -19421 55/push-ebp -19422 89/<- %ebp 4/r32/esp -19423 # . save registers -19424 51/push-ecx -19425 # var curr/ecx: (handle function) = functions -19426 8b/-> *(ebp+8) 1/r32/ecx -19427 { -19428 # if (curr == null) break -19429 81 7/subop/compare %ecx 0/imm32 -19430 74/jump-if-= break/disp8 -19431 #? (write-buffered Stderr "iter\n") -19432 #? (flush Stderr) -19433 # if match(stmt, curr) return curr -19434 { -19435 (mu-stmt-matches-function? *(ebp+0xc) %ecx) # => eax -19436 3d/compare-eax-and 0/imm32/false -19437 74/jump-if-= break/disp8 -19438 89/<- %eax 1/r32/ecx -19439 eb/jump $find-matching-function:end/disp8 -19440 } -19441 # curr = curr->next -19442 (lookup *(ecx+0x20) *(ecx+0x24)) # Function-next Function-next => eax -19443 89/<- %ecx 0/r32/eax -19444 # -19445 eb/jump loop/disp8 -19446 } -19447 # return null -19448 b8/copy-to-eax 0/imm32 -19449 $find-matching-function:end: -19450 # . restore registers -19451 59/pop-to-ecx -19452 # . epilogue -19453 89/<- %esp 5/r32/ebp -19454 5d/pop-to-ebp -19455 c3/return -19456 -19457 # Just compare names; user-defined functions don't support overloading yet. -19458 mu-stmt-matches-function?: # stmt: (addr stmt1), function: (addr function) -> result/eax: boolean -19459 # . prologue -19460 55/push-ebp -19461 89/<- %ebp 4/r32/esp -19462 # . save registers -19463 51/push-ecx -19464 # return function->name == stmt->operation -19465 # ecx = lookup(stmt->operation) -19466 8b/-> *(ebp+8) 0/r32/eax -19467 (lookup *(eax+4) *(eax+8)) # Stmt1-operation Stmt1-operation => eax -19468 89/<- %ecx 0/r32/eax -19469 # eax = lookup(function->name) -19470 8b/-> *(ebp+0xc) 0/r32/eax -19471 (lookup *eax *(eax+4)) # Function-name Function-name => eax -19472 (string-equal? %eax %ecx) # => eax -19473 $mu-stmt-matches-function?:end: -19474 # . restore registers -19475 59/pop-to-ecx -19476 # . epilogue -19477 89/<- %esp 5/r32/ebp -19478 5d/pop-to-ebp -19479 c3/return -19480 -19481 # Type-checking happens elsewhere. This method is for selecting between -19482 # primitives. -19483 subx-type-category-match?: # a: (addr type-tree), b: (addr type-tree) -> result/eax: boolean -19484 # . prologue -19485 55/push-ebp -19486 89/<- %ebp 4/r32/esp -19487 # . save registers -19488 51/push-ecx -19489 # var alit/ecx: boolean = is-literal-type?(a) -19490 (is-simple-mu-type? *(ebp+8) 0) # => eax -19491 89/<- %ecx 0/r32/eax -19492 # var blit/eax: boolean = is-literal-type?(b) -19493 (is-simple-mu-type? *(ebp+0xc) 0) # => eax -19494 # return alit == blit -19495 39/compare %eax 1/r32/ecx -19496 0f 94/set-byte-if-= %al -19497 81 4/subop/and %eax 0xff/imm32 -19498 $subx-type-category-match?:end: -19499 # . restore registers -19500 59/pop-to-ecx -19501 # . epilogue -19502 89/<- %esp 5/r32/ebp -19503 5d/pop-to-ebp -19504 c3/return -19505 -19506 is-simple-mu-type?: # a: (addr type-tree), n: type-id -> result/eax: boolean -19507 # . prologue -19508 55/push-ebp -19509 89/<- %ebp 4/r32/esp -19510 # . save registers -19511 51/push-ecx -19512 # ecx = n -19513 8b/-> *(ebp+0xc) 1/r32/ecx -19514 # return (a->value == n) -19515 8b/-> *(ebp+8) 0/r32/eax -19516 39/compare *(eax+4) 1/r32/ecx # Type-tree-value -19517 0f 94/set-byte-if-= %al -19518 81 4/subop/and %eax 0xff/imm32 -19519 $is-simple-mu-type?:end: -19520 # . restore registers -19521 59/pop-to-ecx -19522 # . epilogue -19523 89/<- %esp 5/r32/ebp -19524 5d/pop-to-ebp -19525 c3/return -19526 -19527 is-mu-addr-type?: # a: (addr type-tree) -> result/eax: boolean -19528 # . prologue -19529 55/push-ebp -19530 89/<- %ebp 4/r32/esp -19531 # eax = a -19532 8b/-> *(ebp+8) 0/r32/eax -19533 # if (!a->is-atom?) a = a->left -19534 81 7/subop/compare *eax 0/imm32/false # Type-tree-is-atom -19535 { -19536 75/jump-if-!= break/disp8 -19537 (lookup *(eax+4) *(eax+8)) # Type-tree-left Type-tree-left => eax -19538 } -19539 # return (a->value == addr) -19540 81 7/subop/compare *(eax+4) 2/imm32/addr # Type-tree-value -19541 0f 94/set-byte-if-= %al -19542 81 4/subop/and %eax 0xff/imm32 -19543 $is-mu-addr-type?:end: -19544 # . epilogue -19545 89/<- %esp 5/r32/ebp -19546 5d/pop-to-ebp -19547 c3/return -19548 -19549 is-mu-array-type?: # a: (addr type-tree) -> result/eax: boolean -19550 # . prologue -19551 55/push-ebp -19552 89/<- %ebp 4/r32/esp -19553 # eax = a -19554 8b/-> *(ebp+8) 0/r32/eax -19555 # if (!a->is-atom?) a = a->left -19556 81 7/subop/compare *eax 0/imm32/false # Type-tree-is-atom -19557 { -19558 75/jump-if-!= break/disp8 -19559 (lookup *(eax+4) *(eax+8)) # Type-tree-left Type-tree-left => eax -19560 } -19561 # return (a->value == array) -19562 81 7/subop/compare *(eax+4) 3/imm32/array # Type-tree-value -19563 0f 94/set-byte-if-= %al -19564 81 4/subop/and %eax 0xff/imm32 -19565 $is-mu-array-type?:end: -19566 # . epilogue -19567 89/<- %esp 5/r32/ebp -19568 5d/pop-to-ebp -19569 c3/return -19570 -19571 test-emit-subx-stmt-primitive: -19572 # Primitive operation on a variable on the stack. -19573 # increment foo -19574 # => -19575 # ff 0/subop/increment *(ebp-8) -19576 # -19577 # There's a variable on the var stack as follows: -19578 # name: 'foo' -19579 # type: int -19580 # stack-offset: -8 -19581 # -19582 # There's a primitive with this info: -19583 # name: 'increment' -19584 # inouts: int/mem -19585 # value: 'ff 0/subop/increment' -19586 # -19587 # . prologue -19588 55/push-ebp -19589 89/<- %ebp 4/r32/esp -19590 # setup -19591 (clear-stream _test-output-stream) -19592 (clear-stream $_test-output-buffered-file->buffer) -19593 # simulate allocated payloads starting with an initial fake alloc-id (0x11) -19594 $test-emit-subx-stmt-primitive:initialize-type: -19595 # var type/ecx: (payload type-tree) = int -19596 68/push 0/imm32/right:null -19597 68/push 0/imm32/right:null -19598 68/push 0/imm32/left:unused -19599 68/push 1/imm32/value:int -19600 68/push 1/imm32/is-atom?:true -19601 68/push 0x11/imm32/alloc-id:fake:payload -19602 89/<- %ecx 4/r32/esp -19603 $test-emit-subx-stmt-primitive:initialize-var: -19604 # var var-foo/ecx: (payload var) = var(type) -19605 68/push 0/imm32/no-register -19606 68/push 0/imm32/no-register -19607 68/push -8/imm32/stack-offset -19608 68/push 1/imm32/block-depth -19609 51/push-ecx/type -19610 68/push 0x11/imm32/alloc-id:fake -19611 68/push 0/imm32/name -19612 68/push 0/imm32/name -19613 68/push 0x11/imm32/alloc-id:fake:payload -19614 89/<- %ecx 4/r32/esp -19615 $test-emit-subx-stmt-primitive:initialize-var-name: -19616 # var-foo->name = "foo" -19617 8d/copy-address *(ecx+4) 0/r32/eax # Var-name + 4 -19618 (copy-array Heap "foo" %eax) -19619 $test-emit-subx-stmt-primitive:initialize-stmt-var: -19620 # var operand/ebx: (payload stmt-var) = stmt-var(var-foo) -19621 68/push 0/imm32/is-deref:false -19622 68/push 0/imm32/next -19623 68/push 0/imm32/next -19624 51/push-ecx/var-foo -19625 68/push 0x11/imm32/alloc-id:fake -19626 68/push 0x11/imm32/alloc-id:fake:payload -19627 89/<- %ebx 4/r32/esp -19628 $test-emit-subx-stmt-primitive:initialize-stmt: -19629 # var stmt/esi: (addr statement) -19630 68/push 0/imm32/no-outputs -19631 68/push 0/imm32/no-outputs -19632 53/push-ebx/inouts -19633 68/push 0x11/imm32/alloc-id:fake -19634 68/push 0/imm32/operation -19635 68/push 0/imm32/operation -19636 68/push 1/imm32/tag -19637 89/<- %esi 4/r32/esp -19638 $test-emit-subx-stmt-primitive:initialize-stmt-operation: -19639 # stmt->operation = "increment" -19640 8d/copy-address *(esi+4) 0/r32/eax # Stmt1-operation -19641 (copy-array Heap "increment" %eax) -19642 $test-emit-subx-stmt-primitive:initialize-primitive: -19643 # var primitives/ebx: (addr primitive) -19644 68/push 0/imm32/next -19645 68/push 0/imm32/next -19646 68/push 0/imm32/output-is-write-only -19647 68/push 0/imm32/no-disp32 -19648 68/push 0/imm32/no-imm8 -19649 68/push 0/imm32/no-imm32 -19650 68/push 0/imm32/no-r32 -19651 68/push 1/imm32/rm32-is-first-inout -19652 68/push 0/imm32/subx-name -19653 68/push 0/imm32/subx-name -19654 68/push 0/imm32/no-outputs -19655 68/push 0/imm32/no-outputs -19656 53/push-ebx/inouts # hack: reuse stmt-var from call stmt as (list var) in function declaration -19657 68/push 0x11/imm32/alloc-id:fake -19658 68/push 0/imm32/name -19659 68/push 0/imm32/name -19660 89/<- %ebx 4/r32/esp -19661 $test-emit-subx-stmt-primitive:initialize-primitive-name: -19662 # primitives->name = "increment" -19663 (copy-array Heap "increment" %ebx) # Primitive-name -19664 $test-emit-subx-stmt-primitive:initialize-primitive-subx-name: -19665 # primitives->subx-name = "ff 0/subop/increment" -19666 8d/copy-address *(ebx+0x18) 0/r32/eax # Primitive-subx-name -19667 (copy-array Heap "ff 0/subop/increment" %eax) -19668 # convert -19669 c7 0/subop/copy *Curr-block-depth 0/imm32 -19670 (emit-subx-stmt _test-output-buffered-file %esi %ebx Stderr 0) -19671 (flush _test-output-buffered-file) -19672 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- -19678 # check output -19679 (check-next-stream-line-equal _test-output-stream "ff 0/subop/increment *(ebp+0xfffffff8)" "F - test-emit-subx-stmt-primitive") -19680 # . epilogue -19681 89/<- %esp 5/r32/ebp -19682 5d/pop-to-ebp -19683 c3/return -19684 -19685 test-emit-subx-stmt-primitive-register: -19686 # Primitive operation on a variable in a register. -19687 # foo <- increment -19688 # => -19689 # ff 0/subop/increment %eax # sub-optimal, but should suffice -19690 # -19691 # There's a variable on the var stack as follows: -19692 # name: 'foo' -19693 # type: int -19694 # register: 'eax' -19695 # -19696 # There's a primitive with this info: -19697 # name: 'increment' -19698 # out: int/reg -19699 # value: 'ff 0/subop/increment' -19700 # -19701 # . prologue -19702 55/push-ebp -19703 89/<- %ebp 4/r32/esp -19704 # setup -19705 (clear-stream _test-output-stream) -19706 (clear-stream $_test-output-buffered-file->buffer) -19707 $test-emit-subx-stmt-primitive-register:initialize-type: -19708 # var type/ecx: (payload type-tree) = int -19709 68/push 0/imm32/right:null -19710 68/push 0/imm32/right:null -19711 68/push 0/imm32/left:unused -19712 68/push 1/imm32/value:int -19713 68/push 1/imm32/is-atom?:true -19714 68/push 0x11/imm32/alloc-id:fake:payload -19715 89/<- %ecx 4/r32/esp -19716 $test-emit-subx-stmt-primitive-register:initialize-var: -19717 # var var-foo/ecx: (payload var) -19718 68/push 0/imm32/register -19719 68/push 0/imm32/register -19720 68/push 0/imm32/no-stack-offset -19721 68/push 1/imm32/block-depth -19722 51/push-ecx -19723 68/push 0x11/imm32/alloc-id:fake -19724 68/push 0/imm32/name -19725 68/push 0/imm32/name -19726 68/push 0x11/imm32/alloc-id:fake:payload -19727 89/<- %ecx 4/r32/esp -19728 $test-emit-subx-stmt-primitive-register:initialize-var-name: -19729 # var-foo->name = "foo" -19730 8d/copy-address *(ecx+4) 0/r32/eax # Var-name + 4 -19731 (copy-array Heap "foo" %eax) -19732 $test-emit-subx-stmt-primitive-register:initialize-var-register: -19733 # var-foo->register = "eax" -19734 8d/copy-address *(ecx+0x1c) 0/r32/eax # Var-register + 4 -19735 (copy-array Heap "eax" %eax) -19736 $test-emit-subx-stmt-primitive-register:initialize-stmt-var: -19737 # var operand/ebx: (payload stmt-var) -19738 68/push 0/imm32/is-deref:false -19739 68/push 0/imm32/next -19740 68/push 0/imm32/next -19741 51/push-ecx/var-foo -19742 68/push 0x11/imm32/alloc-id:fake -19743 68/push 0x11/imm32/alloc-id:fake:payload -19744 89/<- %ebx 4/r32/esp -19745 $test-emit-subx-stmt-primitive-register:initialize-stmt: -19746 # var stmt/esi: (addr statement) -19747 53/push-ebx/outputs -19748 68/push 0x11/imm32/alloc-id:fake -19749 68/push 0/imm32/no-inouts -19750 68/push 0/imm32/no-inouts -19751 68/push 0/imm32/operation -19752 68/push 0/imm32/operation -19753 68/push 1/imm32 -19754 89/<- %esi 4/r32/esp -19755 $test-emit-subx-stmt-primitive-register:initialize-stmt-operation: -19756 # stmt->operation = "increment" -19757 8d/copy-address *(esi+4) 0/r32/eax # Stmt1-operation -19758 (copy-array Heap "increment" %eax) -19759 $test-emit-subx-stmt-primitive-register:initialize-formal-var: -19760 # var formal-var/ebx: (payload var) -19761 68/push 0/imm32/register -19762 68/push 0/imm32/register -19763 68/push 0/imm32/no-stack-offset -19764 68/push 1/imm32/block-depth -19765 ff 6/subop/push *(ecx+0x10) # Var-type + payload alloc id + handle alloc id -19766 68/push 0x11/imm32/alloc-id:fake -19767 68/push 0/imm32/name -19768 68/push 0/imm32/name -19769 68/push 0x11/imm32/alloc-id:fake:payload -19770 89/<- %ebx 4/r32/esp -19771 $test-emit-subx-stmt-primitive-register:initialize-formal-var-name: -19772 # formal-var->name = "dummy" -19773 8d/copy-address *(ebx+4) 0/r32/eax # Var-name + 4 -19774 (copy-array Heap "dummy" %eax) -19775 $test-emit-subx-stmt-primitive-register:initialize-formal-register: -19776 # formal-var->register = "*" -19777 8d/copy-address *(ebx+0x1c) 0/r32/eax # Var-register + 4 -19778 (copy-array Heap "*" %eax) # Any-register -19779 $test-emit-subx-stmt-primitive-register:initialize-var-list: -19780 # var formal-outputs/ebx: (payload list var) -19781 68/push 0/imm32/next -19782 68/push 0/imm32/next -19783 53/push-ebx/formal-var -19784 68/push 0x11/imm32/alloc-id:fake -19785 68/push 0x11/imm32/alloc-id:fake:payload -19786 89/<- %ebx 4/r32/esp -19787 $test-emit-subx-stmt-primitive-register:initialize-primitive: -19788 # var primitives/ebx: (addr primitive) -19789 68/push 0/imm32/next -19790 68/push 0/imm32/next -19791 68/push 0/imm32/output-is-write-only -19792 68/push 0/imm32/no-disp32 -19793 68/push 0/imm32/no-imm8 -19794 68/push 0/imm32/no-imm32 -19795 68/push 0/imm32/no-r32 -19796 68/push 3/imm32/rm32-is-first-output -19797 68/push 0/imm32/subx-name -19798 68/push 0/imm32/subx-name -19799 53/push-ebx/outputs -19800 68/push 0x11/imm32/alloc-id:fake -19801 68/push 0/imm32/no-inouts -19802 68/push 0/imm32/no-inouts -19803 68/push 0/imm32/name -19804 68/push 0/imm32/name -19805 89/<- %ebx 4/r32/esp -19806 $test-emit-subx-stmt-primitive-register:initialize-primitive-name: -19807 # primitives->name = "increment" -19808 (copy-array Heap "increment" %ebx) # Primitive-name -19809 $test-emit-subx-stmt-primitive-register:initialize-primitive-subx-name: -19810 # primitives->subx-name = "ff 0/subop/increment" -19811 8d/copy-address *(ebx+0x18) 0/r32/eax # Primitive-subx-name -19812 (copy-array Heap "ff 0/subop/increment" %eax) -19813 # convert -19814 c7 0/subop/copy *Curr-block-depth 0/imm32 -19815 (emit-subx-stmt _test-output-buffered-file %esi %ebx Stderr 0) -19816 (flush _test-output-buffered-file) -19817 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- -19823 # check output -19824 (check-next-stream-line-equal _test-output-stream "ff 0/subop/increment %eax" "F - test-emit-subx-stmt-primitive-register") -19825 # . epilogue -19826 89/<- %esp 5/r32/ebp -19827 5d/pop-to-ebp -19828 c3/return -19829 -19830 test-emit-subx-stmt-select-primitive: -19831 # Select the right primitive between overloads. -19832 # foo <- increment -19833 # => -19834 # ff 0/subop/increment %eax # sub-optimal, but should suffice -19835 # -19836 # There's a variable on the var stack as follows: -19837 # name: 'foo' -19838 # type: int -19839 # register: 'eax' -19840 # -19841 # There's two primitives, as follows: -19842 # - name: 'increment' -19843 # out: int/reg -19844 # value: 'ff 0/subop/increment' -19845 # - name: 'increment' -19846 # inout: int/mem -19847 # value: 'ff 0/subop/increment' -19848 # -19849 # . prologue -19850 55/push-ebp -19851 89/<- %ebp 4/r32/esp -19852 # setup -19853 (clear-stream _test-output-stream) -19854 (clear-stream $_test-output-buffered-file->buffer) -19855 $test-emit-subx-stmt-select-primitive:initialize-type: -19856 # var type/ecx: (payload type-tree) = int -19857 68/push 0/imm32/right:null -19858 68/push 0/imm32/right:null -19859 68/push 0/imm32/left:unused -19860 68/push 1/imm32/value:int -19861 68/push 1/imm32/is-atom?:true -19862 68/push 0x11/imm32/alloc-id:fake:payload -19863 89/<- %ecx 4/r32/esp -19864 $test-emit-subx-stmt-select-primitive:initialize-var: -19865 # var var-foo/ecx: (payload var) -19866 68/push 0/imm32/register -19867 68/push 0/imm32/register -19868 68/push 0/imm32/no-stack-offset -19869 68/push 1/imm32/block-depth -19870 51/push-ecx -19871 68/push 0x11/imm32/alloc-id:fake -19872 68/push 0/imm32/name -19873 68/push 0/imm32/name -19874 68/push 0x11/imm32/alloc-id:fake:payload -19875 89/<- %ecx 4/r32/esp -19876 $test-emit-subx-stmt-select-primitive:initialize-var-name: -19877 # var-foo->name = "foo" -19878 8d/copy-address *(ecx+4) 0/r32/eax # Var-name + 4 -19879 (copy-array Heap "foo" %eax) -19880 $test-emit-subx-stmt-select-primitive:initialize-var-register: -19881 # var-foo->register = "eax" -19882 8d/copy-address *(ecx+0x1c) 0/r32/eax # Var-register + 4 -19883 (copy-array Heap "eax" %eax) -19884 $test-emit-subx-stmt-select-primitive:initialize-stmt-var: -19885 # var operand/ebx: (payload stmt-var) -19886 68/push 0/imm32/is-deref:false -19887 68/push 0/imm32/next -19888 68/push 0/imm32/next -19889 51/push-ecx/var-foo -19890 68/push 0x11/imm32/alloc-id:fake -19891 68/push 0x11/imm32/alloc-id:fake:payload -19892 89/<- %ebx 4/r32/esp -19893 $test-emit-subx-stmt-select-primitive:initialize-stmt: -19894 # var stmt/esi: (addr statement) -19895 53/push-ebx/outputs -19896 68/push 0x11/imm32/alloc-id:fake -19897 68/push 0/imm32/no-inouts -19898 68/push 0/imm32/no-inouts -19899 68/push 0/imm32/operation -19900 68/push 0/imm32/operation -19901 68/push 1/imm32 -19902 89/<- %esi 4/r32/esp -19903 $test-emit-subx-stmt-select-primitive:initialize-stmt-operation: -19904 # stmt->operation = "increment" -19905 8d/copy-address *(esi+4) 0/r32/eax # Stmt1-operation -19906 (copy-array Heap "increment" %eax) -19907 $test-emit-subx-stmt-select-primitive:initialize-formal-var: -19908 # var formal-var/ebx: (payload var) -19909 68/push 0/imm32/register -19910 68/push 0/imm32/register -19911 68/push 0/imm32/no-stack-offset -19912 68/push 1/imm32/block-depth -19913 ff 6/subop/push *(ecx+0x10) # Var-type + payload alloc id + handle alloc id -19914 68/push 0x11/imm32/alloc-id:fake -19915 68/push 0/imm32/name -19916 68/push 0/imm32/name -19917 68/push 0x11/imm32/alloc-id:fake:payload -19918 89/<- %ebx 4/r32/esp -19919 $test-emit-subx-stmt-select-primitive:initialize-formal-var-name: -19920 # formal-var->name = "dummy" -19921 8d/copy-address *(ebx+4) 0/r32/eax # Var-name + 4 -19922 (copy-array Heap "dummy" %eax) -19923 $test-emit-subx-stmt-select-primitive:initialize-formal-register: -19924 # formal-var->register = "*" -19925 8d/copy-address *(ebx+0x1c) 0/r32/eax # Var-register + 4 -19926 (copy-array Heap "*" %eax) # Any-register -19927 $test-emit-subx-stmt-select-primitive:initialize-var-list: -19928 # var formal-outputs/ebx: (payload list var) -19929 68/push 0/imm32/next -19930 68/push 0/imm32/next -19931 53/push-ebx/formal-var -19932 68/push 0x11/imm32/alloc-id:fake -19933 68/push 0x11/imm32/alloc-id:fake:payload -19934 89/<- %ebx 4/r32/esp -19935 $test-emit-subx-stmt-select-primitive:initialize-primitive2: -19936 # var primitive2/edi: (payload primitive) -19937 68/push 0/imm32/next -19938 68/push 0/imm32/next -19939 68/push 0/imm32/output-is-write-only -19940 68/push 0/imm32/no-disp32 -19941 68/push 0/imm32/no-imm8 -19942 68/push 0/imm32/no-imm32 -19943 68/push 0/imm32/no-r32 -19944 68/push 3/imm32/rm32-is-first-output -19945 68/push 0/imm32/subx-name -19946 68/push 0/imm32/subx-name -19947 53/push-ebx/outputs -19948 68/push 0x11/imm32/alloc-id:fake -19949 68/push 0/imm32/no-inouts -19950 68/push 0/imm32/no-inouts -19951 68/push 0/imm32/name -19952 68/push 0/imm32/name -19953 68/push 0x11/imm32/alloc-id:fake:payload -19954 89/<- %edi 4/r32/esp -19955 $test-emit-subx-stmt-select-primitive:initialize-primitive2-name: -19956 # primitives->name = "increment" -19957 8d/copy-address *(edi+4) 0/r32/eax # Primitive-name + 4 -19958 (copy-array Heap "increment" %eax) -19959 $test-emit-subx-stmt-select-primitive:initialize-primitive2-subx-name: -19960 # primitives->subx-name = "ff 0/subop/increment" -19961 8d/copy-address *(edi+0x1c) 0/r32/eax # Primitive-subx-name + 4 -19962 (copy-array Heap "ff 0/subop/increment" %eax) -19963 $test-emit-subx-stmt-select-primitive:initialize-primitive: -19964 # var primitives/ebx: (addr primitive) -19965 57/push-edi -19966 68/push 0x11/imm32/alloc-id:fake -19967 68/push 0/imm32/output-is-write-only -19968 68/push 0/imm32/no-disp32 -19969 68/push 0/imm32/no-imm8 -19970 68/push 0/imm32/no-imm32 -19971 68/push 0/imm32/no-r32 -19972 68/push 1/imm32/rm32-is-first-inout -19973 68/push 0/imm32/subx-name -19974 68/push 0/imm32/subx-name -19975 68/push 0/imm32/no-outputs -19976 68/push 0/imm32/no-outputs -19977 53/push-ebx/inouts # hack: reuse stmt-var from call stmt as (list var) in function declaration -19978 68/push 0x11/imm32/alloc-id:fake -19979 68/push 0/imm32/name -19980 68/push 0/imm32/name -19981 89/<- %ebx 4/r32/esp -19982 $test-emit-subx-stmt-select-primitive:initialize-primitive-name: -19983 # primitives->name = "increment" -19984 (copy-array Heap "increment" %ebx) # Primitive-name -19985 $test-emit-subx-stmt-select-primitive:initialize-primitive-subx-name: -19986 # primitives->subx-name = "ff 0/subop/increment" -19987 8d/copy-address *(ebx+0x18) 0/r32/eax # Primitive-subx-name -19988 (copy-array Heap "ff 0/subop/increment" %eax) -19989 # convert -19990 c7 0/subop/copy *Curr-block-depth 0/imm32 -19991 (emit-subx-stmt _test-output-buffered-file %esi %ebx Stderr 0) -19992 (flush _test-output-buffered-file) -19993 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- -19999 # check output -20000 (check-next-stream-line-equal _test-output-stream "ff 0/subop/increment %eax" "F - test-emit-subx-stmt-select-primitive") -20001 # . epilogue -20002 89/<- %esp 5/r32/ebp -20003 5d/pop-to-ebp -20004 c3/return -20005 -20006 test-emit-subx-stmt-select-primitive-2: -20007 # Select the right primitive between overloads. -20008 # increment foo -20009 # => -20010 # ff 0/subop/increment %eax # sub-optimal, but should suffice -20011 # -20012 # There's a variable on the var stack as follows: -20013 # name: 'foo' -20014 # type: int -20015 # register: 'eax' -20016 # -20017 # There's two primitives, as follows: -20018 # - name: 'increment' -20019 # out: int/reg -20020 # value: 'ff 0/subop/increment' -20021 # - name: 'increment' -20022 # inout: int/mem -20023 # value: 'ff 0/subop/increment' -20024 # -20025 # . prologue -20026 55/push-ebp -20027 89/<- %ebp 4/r32/esp -20028 # setup -20029 (clear-stream _test-output-stream) -20030 (clear-stream $_test-output-buffered-file->buffer) -20031 $test-emit-subx-stmt-select-primitive-2:initialize-type: -20032 # var type/ecx: (payload type-tree) = int -20033 68/push 0/imm32/right:null -20034 68/push 0/imm32/right:null -20035 68/push 0/imm32/left:unused -20036 68/push 1/imm32/value:int -20037 68/push 1/imm32/is-atom?:true -20038 68/push 0x11/imm32/alloc-id:fake:payload -20039 89/<- %ecx 4/r32/esp -20040 $test-emit-subx-stmt-select-primitive-2:initialize-var: -20041 # var var-foo/ecx: (payload var) -20042 68/push 0/imm32/register -20043 68/push 0/imm32/register -20044 68/push 0/imm32/no-stack-offset -20045 68/push 1/imm32/block-depth -20046 51/push-ecx -20047 68/push 0x11/imm32/alloc-id:fake -20048 68/push 0/imm32/name -20049 68/push 0/imm32/name -20050 68/push 0x11/imm32/alloc-id:fake:payload -20051 89/<- %ecx 4/r32/esp -20052 $test-emit-subx-stmt-select-primitive-2:initialize-var-name: -20053 # var-foo->name = "foo" -20054 8d/copy-address *(ecx+4) 0/r32/eax # Var-name + 4 -20055 (copy-array Heap "foo" %eax) -20056 $test-emit-subx-stmt-select-primitive-2:initialize-var-register: -20057 # var-foo->register = "eax" -20058 8d/copy-address *(ecx+0x1c) 0/r32/eax # Var-register + 4 -20059 (copy-array Heap "eax" %eax) -20060 $test-emit-subx-stmt-select-primitive-2:initialize-stmt-var: -20061 # var operand/ebx: (payload stmt-var) -20062 68/push 0/imm32/is-deref:false -20063 68/push 0/imm32/next -20064 68/push 0/imm32/next -20065 51/push-ecx/var-foo -20066 68/push 0x11/imm32/alloc-id:fake -20067 68/push 0x11/imm32/alloc-id:fake:payload -20068 89/<- %ebx 4/r32/esp -20069 $test-emit-subx-stmt-select-primitive-2:initialize-stmt: -20070 # var stmt/esi: (addr statement) -20071 68/push 0/imm32/no-outputs -20072 68/push 0/imm32/no-outputs -20073 53/push-ebx/inouts -20074 68/push 0x11/imm32/alloc-id:fake -20075 68/push 0/imm32/operation -20076 68/push 0/imm32/operation -20077 68/push 1/imm32 -20078 89/<- %esi 4/r32/esp -20079 $test-emit-subx-stmt-select-primitive-2:initialize-stmt-operation: -20080 # stmt->operation = "increment" -20081 8d/copy-address *(esi+4) 0/r32/eax # Stmt1-operation -20082 (copy-array Heap "increment" %eax) -20083 $test-emit-subx-stmt-select-primitive-2:initialize-formal-var: -20084 # var formal-var/ebx: (payload var) -20085 68/push 0/imm32/register -20086 68/push 0/imm32/register -20087 68/push 0/imm32/no-stack-offset -20088 68/push 1/imm32/block-depth -20089 ff 6/subop/push *(ecx+0x10) # Var-type + payload alloc id + handle alloc id -20090 68/push 0x11/imm32/alloc-id:fake -20091 68/push 0/imm32/name -20092 68/push 0/imm32/name -20093 68/push 0x11/imm32/alloc-id:fake:payload -20094 89/<- %ebx 4/r32/esp -20095 $test-emit-subx-stmt-select-primitive-2:initialize-formal-var-name: -20096 # formal-var->name = "dummy" -20097 8d/copy-address *(ebx+4) 0/r32/eax # Var-name + 4 -20098 (copy-array Heap "dummy" %eax) -20099 $test-emit-subx-stmt-select-primitive-2:initialize-formal-register: -20100 # formal-var->register = "*" -20101 8d/copy-address *(ebx+0x1c) 0/r32/eax # Var-register + 4 -20102 (copy-array Heap "*" %eax) # Any-register -20103 $test-emit-subx-stmt-select-primitive-2:initialize-var-list: -20104 # var formal-outputs/ebx: (payload list stmt-var) -20105 68/push 0/imm32/next -20106 68/push 0/imm32/next -20107 53/push-ebx/formal-var -20108 68/push 0x11/imm32/alloc-id:fake -20109 68/push 0x11/imm32/alloc-id:fake:payload -20110 89/<- %ebx 4/r32/esp -20111 $test-emit-subx-stmt-select-primitive-2:initialize-primitive2: -20112 # var primitive2/edi: (payload primitive) -20113 68/push 0/imm32/next -20114 68/push 0/imm32/next -20115 68/push 0/imm32/output-is-write-only -20116 68/push 0/imm32/no-disp32 -20117 68/push 0/imm32/no-imm8 -20118 68/push 0/imm32/no-imm32 -20119 68/push 0/imm32/no-r32 -20120 68/push 3/imm32/rm32-is-first-output -20121 68/push 0/imm32/subx-name -20122 68/push 0/imm32/subx-name -20123 53/push-ebx/outputs -20124 68/push 0x11/imm32/alloc-id:fake -20125 68/push 0/imm32/no-inouts -20126 68/push 0/imm32/no-inouts -20127 68/push 0/imm32/name -20128 68/push 0/imm32/name -20129 68/push 0x11/imm32/alloc-id:fake:payload -20130 89/<- %edi 4/r32/esp -20131 $test-emit-subx-stmt-select-primitive-2:initialize-primitive2-name: -20132 # primitives->name = "increment" -20133 8d/copy-address *(edi+4) 0/r32/eax # Primitive-name + 4 -20134 (copy-array Heap "increment" %eax) -20135 $test-emit-subx-stmt-select-primitive-2:initialize-primitive2-subx-name: -20136 # primitives->subx-name = "ff 0/subop/increment" -20137 8d/copy-address *(edi+0x1c) 0/r32/eax # Primitive-subx-name + 4 -20138 (copy-array Heap "ff 0/subop/increment" %eax) -20139 $test-emit-subx-stmt-select-primitive-2:initialize-primitive: -20140 # var primitives/ebx: (addr primitive) -20141 57/push-edi +19132 50/push-eax +19133 51/push-ecx +19134 # if (l == 0) return +19135 81 7/subop/compare *(ebp+0xc) 0/imm32 +19136 0f 84/jump-if-= $emit-subx-r32:end/disp32 +19137 # var v/eax: (addr stmt-var) +19138 (get-stmt-operand-from-arg-location *(ebp+0x10) *(ebp+0xc)) # => eax +19139 (lookup *eax *(eax+4)) # Stmt-var-value Stmt-var-value => eax +19140 (lookup *(eax+0x18) *(eax+0x1c)) # Var-register Var-register => eax +19141 (maybe-get Mu-registers %eax 0xc) # => eax: (addr register-index) +19142 (write-buffered *(ebp+8) Space) +19143 (write-int32-hex-buffered *(ebp+8) *eax) +19144 (write-buffered *(ebp+8) "/r32") +19145 $emit-subx-r32:end: +19146 # . restore registers +19147 59/pop-to-ecx +19148 58/pop-to-eax +19149 # . epilogue +19150 89/<- %esp 5/r32/ebp +19151 5d/pop-to-ebp +19152 c3/return +19153 +19154 emit-subx-imm32: # out: (addr buffered-file), l: arg-location, stmt: (addr stmt) +19155 # . prologue +19156 55/push-ebp +19157 89/<- %ebp 4/r32/esp +19158 # . save registers +19159 50/push-eax +19160 51/push-ecx +19161 # if (l == 0) return +19162 81 7/subop/compare *(ebp+0xc) 0/imm32 +19163 0f 84/jump-if-= $emit-subx-imm32:end/disp32 +19164 # var v/eax: (handle var) +19165 (get-stmt-operand-from-arg-location *(ebp+0x10) *(ebp+0xc)) # => eax +19166 (lookup *eax *(eax+4)) # Stmt-var-value Stmt-var-value => eax +19167 (lookup *eax *(eax+4)) # Var-name Var-name => eax +19168 (write-buffered *(ebp+8) Space) +19169 (write-buffered *(ebp+8) %eax) +19170 (write-buffered *(ebp+8) "/imm32") +19171 $emit-subx-imm32:end: +19172 # . restore registers +19173 59/pop-to-ecx +19174 58/pop-to-eax +19175 # . epilogue +19176 89/<- %esp 5/r32/ebp +19177 5d/pop-to-ebp +19178 c3/return +19179 +19180 emit-subx-imm8: # out: (addr buffered-file), l: arg-location, stmt: (addr stmt) +19181 # . prologue +19182 55/push-ebp +19183 89/<- %ebp 4/r32/esp +19184 # . save registers +19185 50/push-eax +19186 51/push-ecx +19187 # if (l == 0) return +19188 81 7/subop/compare *(ebp+0xc) 0/imm32 +19189 0f 84/jump-if-= $emit-subx-imm32:end/disp32 +19190 # var v/eax: (handle var) +19191 (get-stmt-operand-from-arg-location *(ebp+0x10) *(ebp+0xc)) # => eax +19192 (lookup *eax *(eax+4)) # Stmt-var-value Stmt-var-value => eax +19193 (lookup *eax *(eax+4)) # Var-name Var-name => eax +19194 (write-buffered *(ebp+8) Space) +19195 (write-buffered *(ebp+8) %eax) +19196 (write-buffered *(ebp+8) "/imm8") +19197 $emit-subx-imm8:end: +19198 # . restore registers +19199 59/pop-to-ecx +19200 58/pop-to-eax +19201 # . epilogue +19202 89/<- %esp 5/r32/ebp +19203 5d/pop-to-ebp +19204 c3/return +19205 +19206 emit-subx-disp32: # out: (addr buffered-file), l: arg-location, stmt: (addr stmt), err: (addr buffered-file), ed: (addr exit-descriptor) +19207 # . prologue +19208 55/push-ebp +19209 89/<- %ebp 4/r32/esp +19210 # . save registers +19211 50/push-eax +19212 51/push-ecx +19213 # if (location == 0) return +19214 81 7/subop/compare *(ebp+0xc) 0/imm32 +19215 0f 84/jump-if-= $emit-subx-disp32:end/disp32 +19216 # var v/eax: (addr stmt-var) +19217 (get-stmt-operand-from-arg-location *(ebp+0x10) *(ebp+0xc) *(ebp+0x14) *(ebp+0x18)) # => eax +19218 (lookup *eax *(eax+4)) # Stmt-var-value Stmt-var-value => eax +19219 (lookup *eax *(eax+4)) # Var-name Var-name => eax +19220 (write-buffered *(ebp+8) Space) +19221 (write-buffered *(ebp+8) %eax) +19222 # hack: if instruction operation starts with "break", emit ":break" +19223 # var name/ecx: (addr array byte) = lookup(stmt->operation) +19224 8b/-> *(ebp+0x10) 0/r32/eax +19225 (lookup *(eax+4) *(eax+8)) # Stmt1-operation Stmt1-operation => eax +19226 89/<- %ecx 0/r32/eax +19227 { +19228 (string-starts-with? %ecx "break") # => eax +19229 3d/compare-eax-and 0/imm32/false +19230 74/jump-if-= break/disp8 +19231 (write-buffered *(ebp+8) ":break") +19232 } +19233 # hack: if instruction operation starts with "loop", emit ":loop" +19234 { +19235 (string-starts-with? %ecx "loop") # => eax +19236 3d/compare-eax-and 0/imm32/false +19237 74/jump-if-= break/disp8 +19238 (write-buffered *(ebp+8) ":loop") +19239 } +19240 (write-buffered *(ebp+8) "/disp32") +19241 $emit-subx-disp32:end: +19242 # . restore registers +19243 59/pop-to-ecx +19244 58/pop-to-eax +19245 # . epilogue +19246 89/<- %esp 5/r32/ebp +19247 5d/pop-to-ebp +19248 c3/return +19249 +19250 emit-call: # out: (addr buffered-file), stmt: (addr stmt) +19251 # . prologue +19252 55/push-ebp +19253 89/<- %ebp 4/r32/esp +19254 # . save registers +19255 50/push-eax +19256 51/push-ecx +19257 # +19258 (emit-indent *(ebp+8) *Curr-block-depth) +19259 (write-buffered *(ebp+8) "(") +19260 # ecx = stmt +19261 8b/-> *(ebp+0xc) 1/r32/ecx +19262 # - emit function name +19263 (lookup *(ecx+4) *(ecx+8)) # Stmt1-operation Stmt1-operation => eax +19264 (write-buffered *(ebp+8) %eax) +19265 # - emit arguments +19266 # var curr/eax: (addr stmt-var) = lookup(stmt->inouts) +19267 (lookup *(ecx+0xc) *(ecx+0x10)) # Stmt1-inouts Stmt1-inouts => eax +19268 { +19269 # if (curr == null) break +19270 3d/compare-eax-and 0/imm32 +19271 74/jump-if-= break/disp8 +19272 # +19273 (emit-subx-call-operand *(ebp+8) %eax) +19274 # curr = lookup(curr->next) +19275 (lookup *(eax+8) *(eax+0xc)) # Stmt-var-next Stmt-var-next => eax +19276 eb/jump loop/disp8 +19277 } +19278 # +19279 (write-buffered *(ebp+8) ")\n") +19280 $emit-call:end: +19281 # . restore registers +19282 59/pop-to-ecx +19283 58/pop-to-eax +19284 # . epilogue +19285 89/<- %esp 5/r32/ebp +19286 5d/pop-to-ebp +19287 c3/return +19288 +19289 emit-subx-call-operand: # out: (addr buffered-file), s: (addr stmt-var) +19290 # shares code with emit-subx-var-as-rm32 +19291 # . prologue +19292 55/push-ebp +19293 89/<- %ebp 4/r32/esp +19294 # . save registers +19295 50/push-eax +19296 51/push-ecx +19297 56/push-esi +19298 # ecx = s +19299 8b/-> *(ebp+0xc) 1/r32/ecx +19300 # var operand/esi: (addr var) = lookup(s->value) +19301 (lookup *ecx *(ecx+4)) # Stmt-var-value Stmt-var-value => eax +19302 89/<- %esi 0/r32/eax +19303 # if (operand->register && !s->is-deref?) emit "%__" +19304 { +19305 $emit-subx-call-operand:check-for-register-direct: +19306 81 7/subop/compare *(esi+0x18) 0/imm32 # Var-register +19307 74/jump-if-= break/disp8 +19308 81 7/subop/compare *(ecx+0x10) 0/imm32/false # Stmt-var-is-deref +19309 75/jump-if-!= break/disp8 +19310 $emit-subx-call-operand:register-direct: +19311 (write-buffered *(ebp+8) " %") +19312 (lookup *(esi+0x18) *(esi+0x1c)) # Var-register Var-register => eax +19313 (write-buffered *(ebp+8) %eax) +19314 e9/jump $emit-subx-call-operand:end/disp32 +19315 } +19316 # else if (operand->register && s->is-deref?) emit "*__" +19317 { +19318 $emit-subx-call-operand:check-for-register-indirect: +19319 81 7/subop/compare *(esi+0x18) 0/imm32 # Var-register +19320 74/jump-if-= break/disp8 +19321 81 7/subop/compare *(ecx+0x10) 0/imm32/false # Stmt-var-is-deref +19322 74/jump-if-= break/disp8 +19323 $emit-subx-call-operand:register-indirect: +19324 (emit-subx-call-operand-register-indirect *(ebp+8) %esi) +19325 e9/jump $emit-subx-call-operand:end/disp32 +19326 } +19327 # else if (operand->stack-offset) emit "*(ebp+__)" +19328 { +19329 81 7/subop/compare *(esi+0x14) 0/imm32 # Var-offset +19330 74/jump-if-= break/disp8 +19331 $emit-subx-call-operand:stack: +19332 (emit-subx-call-operand-stack *(ebp+8) %esi) +19333 e9/jump $emit-subx-call-operand:end/disp32 +19334 } +19335 # else if (operand->type == literal) emit "__" +19336 { +19337 (lookup *(esi+8) *(esi+0xc)) # Var-type Var-type => eax +19338 81 7/subop/compare *(eax+4) 0/imm32 # Type-tree-left +19339 75/jump-if-!= break/disp8 +19340 $emit-subx-call-operand:literal: +19341 (write-buffered *(ebp+8) Space) +19342 (lookup *esi *(esi+4)) # Var-name Var-name => eax +19343 (write-buffered *(ebp+8) %eax) +19344 } +19345 $emit-subx-call-operand:end: +19346 # . restore registers +19347 5e/pop-to-esi +19348 59/pop-to-ecx +19349 58/pop-to-eax +19350 # . epilogue +19351 89/<- %esp 5/r32/ebp +19352 5d/pop-to-ebp +19353 c3/return +19354 +19355 emit-subx-call-operand-register-indirect: # out: (addr buffered-file), v: (addr var) +19356 # . prologue +19357 55/push-ebp +19358 89/<- %ebp 4/r32/esp +19359 # . save registers +19360 50/push-eax +19361 51/push-ecx +19362 56/push-esi +19363 # esi = v +19364 8b/-> *(ebp+0xc) 6/r32/esi +19365 # var size/ecx: int = size-of-deref(v) +19366 (size-of-deref %esi) # => eax +19367 89/<- %ecx 0/r32/eax +19368 # var reg-name/esi: (addr array byte) = lookup(v->register) +19369 (lookup *(esi+0x18) *(esi+0x1c)) # Var-register Var-register => eax +19370 89/<- %esi 0/r32/eax +19371 # TODO: assert size is a multiple of 4 +19372 # var i/eax: int = 0 +19373 b8/copy-to-eax 0/imm32 +19374 { +19375 $emit-subx-call-operand-register-indirect:loop: +19376 # if (i >= size) break +19377 39/compare %eax 1/r32/ecx +19378 7d/jump-if->= break/disp8 +19379 # emit " *(" v->register "+" i ")" +19380 (write-buffered *(ebp+8) " *(") +19381 (write-buffered *(ebp+8) %esi) +19382 (write-buffered *(ebp+8) "+") +19383 (write-int32-hex-buffered *(ebp+8) %eax) +19384 (write-buffered *(ebp+8) ")") +19385 # i += 4 +19386 05/add-to-eax 4/imm32 +19387 # +19388 eb/jump loop/disp8 +19389 } +19390 $emit-subx-call-operand-register-indirect:end: +19391 # . restore registers +19392 5e/pop-to-esi +19393 59/pop-to-ecx +19394 58/pop-to-eax +19395 # . epilogue +19396 89/<- %esp 5/r32/ebp +19397 5d/pop-to-ebp +19398 c3/return +19399 +19400 emit-subx-call-operand-stack: # out: (addr buffered-file), v: (addr var) +19401 # . prologue +19402 55/push-ebp +19403 89/<- %ebp 4/r32/esp +19404 # . save registers +19405 50/push-eax +19406 51/push-ecx +19407 56/push-esi +19408 # esi = v +19409 8b/-> *(ebp+0xc) 6/r32/esi +19410 # var curr/ecx: int = v->offset +19411 8b/-> *(esi+0x14) 1/r32/ecx # Var-offset +19412 # var max/eax: int = v->offset + size-of(v) +19413 (size-of %esi) # => eax +19414 # TODO: assert size is a multiple of 4 +19415 01/add-to %eax 1/r32/ecx +19416 { +19417 $emit-subx-call-operand-stack:loop: +19418 # if (curr >= max) break +19419 39/compare %ecx 0/r32/eax +19420 7d/jump-if->= break/disp8 +19421 # emit " *(ebp+" curr ")" +19422 (write-buffered *(ebp+8) " *(ebp+") +19423 (write-int32-hex-buffered *(ebp+8) %ecx) +19424 (write-buffered *(ebp+8) ")") +19425 # i += 4 +19426 81 0/subop/add %ecx 4/imm32 +19427 # +19428 eb/jump loop/disp8 +19429 } +19430 $emit-subx-call-operand-stack:end: +19431 # . restore registers +19432 5e/pop-to-esi +19433 59/pop-to-ecx +19434 58/pop-to-eax +19435 # . epilogue +19436 89/<- %esp 5/r32/ebp +19437 5d/pop-to-ebp +19438 c3/return +19439 +19440 emit-subx-var-as-rm32: # out: (addr buffered-file), s: (addr stmt-var) +19441 # . prologue +19442 55/push-ebp +19443 89/<- %ebp 4/r32/esp +19444 # . save registers +19445 50/push-eax +19446 51/push-ecx +19447 56/push-esi +19448 # ecx = s +19449 8b/-> *(ebp+0xc) 1/r32/ecx +19450 # var operand/esi: (addr var) = lookup(s->value) +19451 (lookup *ecx *(ecx+4)) # Stmt-var-value Stmt-var-value => eax +19452 89/<- %esi 0/r32/eax +19453 # if (operand->register && s->is-deref?) emit "*__" +19454 { +19455 $emit-subx-var-as-rm32:check-for-register-indirect: +19456 81 7/subop/compare *(esi+0x18) 0/imm32 # Var-register +19457 74/jump-if-= break/disp8 +19458 81 7/subop/compare *(ecx+0x10) 0/imm32/false # Stmt-var-is-deref +19459 74/jump-if-= break/disp8 +19460 $emit-subx-var-as-rm32:register-indirect: +19461 (write-buffered *(ebp+8) " *") +19462 (lookup *(esi+0x18) *(esi+0x1c)) # Var-register Var-register => eax +19463 (write-buffered *(ebp+8) %eax) +19464 e9/jump $emit-subx-var-as-rm32:end/disp32 +19465 } +19466 # if (operand->register && !s->is-deref?) emit "%__" +19467 { +19468 $emit-subx-var-as-rm32:check-for-register-direct: +19469 81 7/subop/compare *(esi+0x18) 0/imm32 # Var-register +19470 74/jump-if-= break/disp8 +19471 81 7/subop/compare *(ecx+0x10) 0/imm32/false # Stmt-var-is-deref +19472 75/jump-if-!= break/disp8 +19473 $emit-subx-var-as-rm32:register-direct: +19474 (write-buffered *(ebp+8) " %") +19475 (lookup *(esi+0x18) *(esi+0x1c)) # Var-register Var-register => eax +19476 (write-buffered *(ebp+8) %eax) +19477 e9/jump $emit-subx-var-as-rm32:end/disp32 +19478 } +19479 # else if (operand->stack-offset) emit "*(ebp+__)" +19480 { +19481 81 7/subop/compare *(esi+0x14) 0/imm32 # Var-offset +19482 74/jump-if-= break/disp8 +19483 $emit-subx-var-as-rm32:stack: +19484 (write-buffered *(ebp+8) Space) +19485 (write-buffered *(ebp+8) "*(ebp+") +19486 (write-int32-hex-buffered *(ebp+8) *(esi+0x14)) # Var-offset +19487 (write-buffered *(ebp+8) ")") +19488 } +19489 $emit-subx-var-as-rm32:end: +19490 # . restore registers +19491 5e/pop-to-esi +19492 59/pop-to-ecx +19493 58/pop-to-eax +19494 # . epilogue +19495 89/<- %esp 5/r32/ebp +19496 5d/pop-to-ebp +19497 c3/return +19498 +19499 find-matching-primitive: # primitives: (addr primitive), stmt: (addr stmt) -> result/eax: (addr primitive) +19500 # . prologue +19501 55/push-ebp +19502 89/<- %ebp 4/r32/esp +19503 # . save registers +19504 51/push-ecx +19505 # var curr/ecx: (addr primitive) = primitives +19506 8b/-> *(ebp+8) 1/r32/ecx +19507 { +19508 $find-matching-primitive:loop: +19509 # if (curr == null) break +19510 81 7/subop/compare %ecx 0/imm32 +19511 74/jump-if-= break/disp8 +19512 # if match(curr, stmt) return curr +19513 { +19514 (mu-stmt-matches-primitive? *(ebp+0xc) %ecx) # => eax +19515 3d/compare-eax-and 0/imm32/false +19516 74/jump-if-= break/disp8 +19517 89/<- %eax 1/r32/ecx +19518 eb/jump $find-matching-primitive:end/disp8 +19519 } +19520 $find-matching-primitive:next-primitive: +19521 # curr = curr->next +19522 (lookup *(ecx+0x38) *(ecx+0x3c)) # Primitive-next Primitive-next => eax +19523 89/<- %ecx 0/r32/eax +19524 # +19525 e9/jump loop/disp32 +19526 } +19527 # return null +19528 b8/copy-to-eax 0/imm32 +19529 $find-matching-primitive:end: +19530 # . restore registers +19531 59/pop-to-ecx +19532 # . epilogue +19533 89/<- %esp 5/r32/ebp +19534 5d/pop-to-ebp +19535 c3/return +19536 +19537 mu-stmt-matches-primitive?: # stmt: (addr stmt), primitive: (addr primitive) -> result/eax: boolean +19538 # A mu stmt matches a primitive if the name matches, all the inout vars +19539 # match, and all the output vars match. +19540 # Vars match if types match and registers match. +19541 # In addition, a stmt output matches a primitive's output if types match +19542 # and the primitive has a wildcard register. +19543 # . prologue +19544 55/push-ebp +19545 89/<- %ebp 4/r32/esp +19546 # . save registers +19547 51/push-ecx +19548 52/push-edx +19549 53/push-ebx +19550 56/push-esi +19551 57/push-edi +19552 # ecx = stmt +19553 8b/-> *(ebp+8) 1/r32/ecx +19554 # edx = primitive +19555 8b/-> *(ebp+0xc) 2/r32/edx +19556 { +19557 $mu-stmt-matches-primitive?:check-name: +19558 # if (primitive->name != stmt->operation) return false +19559 # . var esi: (addr array byte) = lookup(stmt->operation) +19560 (lookup *(ecx+4) *(ecx+8)) # Stmt1-operation Stmt1-operation => eax +19561 89/<- %esi 0/r32/eax +19562 # . var edi: (addr array byte) = lookup(primitive->name) +19563 (lookup *edx *(edx+4)) # Primitive-name Primitive-name => eax +19564 89/<- %edi 0/r32/eax +19565 (string-equal? %esi %edi) # => eax +19566 3d/compare-eax-and 0/imm32/false +19567 75/jump-if-!= break/disp8 +19568 b8/copy-to-eax 0/imm32 +19569 e9/jump $mu-stmt-matches-primitive?:end/disp32 +19570 } +19571 # var curr/esi: (addr stmt-var) = lookup(stmt->inouts) +19572 (lookup *(ecx+0xc) *(ecx+0x10)) # Stmt1-inouts Stmt1-inouts => eax +19573 89/<- %esi 0/r32/eax +19574 # var curr2/edi: (addr list var) = lookup(primitive->inouts) +19575 (lookup *(edx+8) *(edx+0xc)) # Primitive-inouts Primitive-inouts => eax +19576 89/<- %edi 0/r32/eax +19577 { +19578 $mu-stmt-matches-primitive?:inouts-loop: +19579 # if (curr == 0 && curr2 == 0) move on to check outputs +19580 { +19581 $mu-stmt-matches-primitive?:check-both-inouts-null: +19582 81 7/subop/compare %esi 0/imm32 +19583 75/jump-if-!= break/disp8 +19584 $mu-stmt-matches-primitive?:stmt-inout-null: +19585 81 7/subop/compare %edi 0/imm32 +19586 0f 84/jump-if-= $mu-stmt-matches-primitive?:check-outputs/disp32 +19587 $mu-stmt-matches-primitive?:stmt-inout-null-and-prim-inout-not-null: +19588 # return false +19589 b8/copy-to-eax 0/imm32/false +19590 e9/jump $mu-stmt-matches-primitive?:end/disp32 +19591 } +19592 # if (curr2 == 0) return false +19593 { +19594 $mu-stmt-matches-primitive?:check-prim-inout-null: +19595 81 7/subop/compare %edi 0/imm32 +19596 75/jump-if-!= break/disp8 +19597 $mu-stmt-matches-primitive?:prim-inout-null: +19598 b8/copy-to-eax 0/imm32/false +19599 e9/jump $mu-stmt-matches-primitive?:end/disp32 +19600 } +19601 # if (curr != curr2) return false +19602 { +19603 $mu-stmt-matches-primitive?:check-inouts-match: +19604 (lookup *edi *(edi+4)) # List-value List-value => eax +19605 (operand-matches-primitive? %esi %eax) # => eax +19606 3d/compare-eax-and 0/imm32/false +19607 75/jump-if-!= break/disp8 +19608 $mu-stmt-matches-primitive?:inouts-match: +19609 b8/copy-to-eax 0/imm32/false +19610 e9/jump $mu-stmt-matches-primitive?:end/disp32 +19611 } +19612 $mu-stmt-matches-primitive?:next-inout: +19613 # curr = lookup(curr->next) +19614 (lookup *(esi+8) *(esi+0xc)) # Stmt-var-next Stmt-var-next => eax +19615 89/<- %esi 0/r32/eax +19616 # curr2 = lookup(curr2->next) +19617 (lookup *(edi+8) *(edi+0xc)) # List-next List-next => eax +19618 89/<- %edi 0/r32/eax +19619 # +19620 e9/jump loop/disp32 +19621 } +19622 $mu-stmt-matches-primitive?:check-outputs: +19623 # var curr/esi: (addr stmt-var) = lookup(stmt->outputs) +19624 (lookup *(ecx+0x14) *(ecx+0x18)) # Stmt1-outputs Stmt1-outputs => eax +19625 89/<- %esi 0/r32/eax +19626 # var curr2/edi: (addr list var) = lookup(primitive->outputs) +19627 (lookup *(edx+0x10) *(edx+0x14)) # Primitive-outputs Primitive-outputs => eax +19628 89/<- %edi 0/r32/eax +19629 { +19630 $mu-stmt-matches-primitive?:outputs-loop: +19631 # if (curr == 0) return (curr2 == 0) +19632 { +19633 $mu-stmt-matches-primitive?:check-both-outputs-null: +19634 81 7/subop/compare %esi 0/imm32 +19635 75/jump-if-!= break/disp8 +19636 { +19637 $mu-stmt-matches-primitive?:stmt-output-null: +19638 81 7/subop/compare %edi 0/imm32 +19639 75/jump-if-!= break/disp8 +19640 $mu-stmt-matches-primitive?:both-outputs-null: +19641 # return true +19642 b8/copy-to-eax 1/imm32 +19643 e9/jump $mu-stmt-matches-primitive?:end/disp32 +19644 } +19645 $mu-stmt-matches-primitive?:stmt-output-null-and-prim-output-not-null: +19646 # return false +19647 b8/copy-to-eax 0/imm32 +19648 e9/jump $mu-stmt-matches-primitive?:end/disp32 +19649 } +19650 # if (curr2 == 0) return false +19651 { +19652 $mu-stmt-matches-primitive?:check-prim-output-null: +19653 81 7/subop/compare %edi 0/imm32 +19654 75/jump-if-!= break/disp8 +19655 $mu-stmt-matches-primitive?:prim-output-is-null: +19656 b8/copy-to-eax 0/imm32 +19657 e9/jump $mu-stmt-matches-primitive?:end/disp32 +19658 } +19659 # if (curr != curr2) return false +19660 { +19661 $mu-stmt-matches-primitive?:check-outputs-match: +19662 (lookup *edi *(edi+4)) # List-value List-value => eax +19663 (operand-matches-primitive? %esi %eax) # => eax +19664 3d/compare-eax-and 0/imm32/false +19665 75/jump-if-!= break/disp8 +19666 $mu-stmt-matches-primitive?:outputs-match: +19667 b8/copy-to-eax 0/imm32 +19668 e9/jump $mu-stmt-matches-primitive?:end/disp32 +19669 } +19670 $mu-stmt-matches-primitive?:next-output: +19671 # curr = lookup(curr->next) +19672 (lookup *(esi+8) *(esi+0xc)) # Stmt-var-next Stmt-var-next => eax +19673 89/<- %esi 0/r32/eax +19674 # curr2 = lookup(curr2->next) +19675 (lookup *(edi+8) *(edi+0xc)) # List-next List-next => eax +19676 89/<- %edi 0/r32/eax +19677 # +19678 e9/jump loop/disp32 +19679 } +19680 $mu-stmt-matches-primitive?:return-true: +19681 b8/copy-to-eax 1/imm32 +19682 $mu-stmt-matches-primitive?:end: +19683 # . restore registers +19684 5f/pop-to-edi +19685 5e/pop-to-esi +19686 5b/pop-to-ebx +19687 5a/pop-to-edx +19688 59/pop-to-ecx +19689 # . epilogue +19690 89/<- %esp 5/r32/ebp +19691 5d/pop-to-ebp +19692 c3/return +19693 +19694 operand-matches-primitive?: # s: (addr stmt-var), prim-var: (addr var) -> result/eax: boolean +19695 # . prologue +19696 55/push-ebp +19697 89/<- %ebp 4/r32/esp +19698 # . save registers +19699 51/push-ecx +19700 52/push-edx +19701 53/push-ebx +19702 56/push-esi +19703 57/push-edi +19704 # ecx = s +19705 8b/-> *(ebp+8) 1/r32/ecx +19706 # var var/esi: (addr var) = lookup(s->value) +19707 (lookup *ecx *(ecx+4)) # Stmt-var-value Stmt-var-value => eax +19708 89/<- %esi 0/r32/eax +19709 # edi = prim-var +19710 8b/-> *(ebp+0xc) 7/r32/edi +19711 $operand-matches-primitive?:check-type: +19712 # if !category-match?(var->type, prim-var->type) return false +19713 # . var vtype/ebx: (addr type-tree) = lookup(var->type) +19714 (lookup *(esi+8) *(esi+0xc)) # Var-type Var-type => eax +19715 89/<- %ebx 0/r32/eax +19716 # . var ptype/eax: (addr type-tree) = lookup(prim-var->type) +19717 (lookup *(edi+8) *(edi+0xc)) # Var-type Var-type => eax +19718 (subx-type-category-match? %ebx %eax) # => eax +19719 3d/compare-eax-and 0/imm32/false +19720 0f 84/jump-if-= $operand-matches-primitive?:return-false/disp32 +19721 { +19722 $operand-matches-primitive?:check-register: +19723 # if prim-var is in memory and var is in register but dereference, match +19724 { +19725 81 7/subop/compare *(edi+0x18) 0/imm32 # Var-register +19726 0f 85/jump-if-!= break/disp32 +19727 81 7/subop/compare *(esi+0x18) 0/imm32 # Var-register +19728 74/jump-if-= break/disp8 +19729 81 7/subop/compare *(ecx+0x10) 0/imm32/false # Stmt-var-is-deref +19730 74/jump-if-= break/disp8 +19731 $operand-matches-primitive?:var-deref-match: +19732 e9/jump $operand-matches-primitive?:return-true/disp32 +19733 } +19734 # if prim-var is in register and var is in register but dereference, no match +19735 { +19736 81 7/subop/compare *(edi+0x18) 0/imm32 # Var-register +19737 0f 84/jump-if-= break/disp32 +19738 81 7/subop/compare *(esi+0x18) 0/imm32 # Var-register +19739 0f 84/jump-if-= break/disp32 +19740 81 7/subop/compare *(ecx+0x10) 0/imm32/false # Stmt-var-is-deref +19741 74/jump-if-= break/disp8 +19742 $operand-matches-primitive?:var-deref-no-match: +19743 e9/jump $operand-matches-primitive?:return-false/disp32 +19744 } +19745 # return false if var->register doesn't match prim-var->register +19746 { +19747 # if register addresses are equal, it's a match +19748 # var vreg/ebx: (addr array byte) = lookup(var->register) +19749 (lookup *(esi+0x18) *(esi+0x1c)) # Var-register Var-register => eax +19750 89/<- %ebx 0/r32/eax +19751 # var preg/ecx: (addr array byte) = lookup(prim-var->register) +19752 (lookup *(edi+0x18) *(edi+0x1c)) # Var-register Var-register => eax +19753 89/<- %ecx 0/r32/eax +19754 # if (vreg == preg) break +19755 39/compare %ecx 3/r32/ebx +19756 74/jump-if-= break/disp8 +19757 $operand-matches-primitive?:var-register-no-match: +19758 # if either address is 0, return false +19759 81 7/subop/compare %ebx 0/imm32 +19760 74/jump-if-= $operand-matches-primitive?:return-false/disp8 +19761 81 7/subop/compare %ecx 0/imm32 +19762 74/jump-if-= $operand-matches-primitive?:return-false/disp8 +19763 # if prim-var->register is wildcard, it's a match +19764 (string-equal? %ecx "*") # Any-register => eax +19765 3d/compare-eax-and 0/imm32/false +19766 75/jump-if-!= break/disp8 +19767 $operand-matches-primitive?:wildcard-no-match: +19768 # if string contents aren't equal, return false +19769 (string-equal? %ecx %ebx) # => eax +19770 3d/compare-eax-and 0/imm32/false +19771 74/jump-if-= $operand-matches-primitive?:return-false/disp8 +19772 } +19773 } +19774 $operand-matches-primitive?:return-true: +19775 b8/copy-to-eax 1/imm32/true +19776 eb/jump $operand-matches-primitive?:end/disp8 +19777 $operand-matches-primitive?:return-false: +19778 b8/copy-to-eax 0/imm32/false +19779 $operand-matches-primitive?:end: +19780 # . restore registers +19781 5f/pop-to-edi +19782 5e/pop-to-esi +19783 5b/pop-to-ebx +19784 5a/pop-to-edx +19785 59/pop-to-ecx +19786 # . epilogue +19787 89/<- %esp 5/r32/ebp +19788 5d/pop-to-ebp +19789 c3/return +19790 +19791 find-matching-function: # functions: (addr function), stmt: (addr stmt) -> result/eax: (addr function) +19792 # . prologue +19793 55/push-ebp +19794 89/<- %ebp 4/r32/esp +19795 # . save registers +19796 51/push-ecx +19797 # var curr/ecx: (handle function) = functions +19798 8b/-> *(ebp+8) 1/r32/ecx +19799 { +19800 # if (curr == null) break +19801 81 7/subop/compare %ecx 0/imm32 +19802 74/jump-if-= break/disp8 +19803 #? (write-buffered Stderr "iter\n") +19804 #? (flush Stderr) +19805 # if match(stmt, curr) return curr +19806 { +19807 (mu-stmt-matches-function? *(ebp+0xc) %ecx) # => eax +19808 3d/compare-eax-and 0/imm32/false +19809 74/jump-if-= break/disp8 +19810 89/<- %eax 1/r32/ecx +19811 eb/jump $find-matching-function:end/disp8 +19812 } +19813 # curr = curr->next +19814 (lookup *(ecx+0x20) *(ecx+0x24)) # Function-next Function-next => eax +19815 89/<- %ecx 0/r32/eax +19816 # +19817 eb/jump loop/disp8 +19818 } +19819 # return null +19820 b8/copy-to-eax 0/imm32 +19821 $find-matching-function:end: +19822 # . restore registers +19823 59/pop-to-ecx +19824 # . epilogue +19825 89/<- %esp 5/r32/ebp +19826 5d/pop-to-ebp +19827 c3/return +19828 +19829 # Just compare names; user-defined functions don't support overloading yet. +19830 mu-stmt-matches-function?: # stmt: (addr stmt1), function: (addr function) -> result/eax: boolean +19831 # . prologue +19832 55/push-ebp +19833 89/<- %ebp 4/r32/esp +19834 # . save registers +19835 51/push-ecx +19836 # return function->name == stmt->operation +19837 # ecx = lookup(stmt->operation) +19838 8b/-> *(ebp+8) 0/r32/eax +19839 (lookup *(eax+4) *(eax+8)) # Stmt1-operation Stmt1-operation => eax +19840 89/<- %ecx 0/r32/eax +19841 # eax = lookup(function->name) +19842 8b/-> *(ebp+0xc) 0/r32/eax +19843 (lookup *eax *(eax+4)) # Function-name Function-name => eax +19844 (string-equal? %eax %ecx) # => eax +19845 $mu-stmt-matches-function?:end: +19846 # . restore registers +19847 59/pop-to-ecx +19848 # . epilogue +19849 89/<- %esp 5/r32/ebp +19850 5d/pop-to-ebp +19851 c3/return +19852 +19853 # Type-checking happens elsewhere. This method is for selecting between +19854 # primitives. +19855 subx-type-category-match?: # a: (addr type-tree), b: (addr type-tree) -> result/eax: boolean +19856 # . prologue +19857 55/push-ebp +19858 89/<- %ebp 4/r32/esp +19859 # . save registers +19860 51/push-ecx +19861 # var alit/ecx: boolean = is-literal-type?(a) +19862 (is-simple-mu-type? *(ebp+8) 0) # => eax +19863 89/<- %ecx 0/r32/eax +19864 # var blit/eax: boolean = is-literal-type?(b) +19865 (is-simple-mu-type? *(ebp+0xc) 0) # => eax +19866 # return alit == blit +19867 39/compare %eax 1/r32/ecx +19868 0f 94/set-byte-if-= %al +19869 81 4/subop/and %eax 0xff/imm32 +19870 $subx-type-category-match?:end: +19871 # . restore registers +19872 59/pop-to-ecx +19873 # . epilogue +19874 89/<- %esp 5/r32/ebp +19875 5d/pop-to-ebp +19876 c3/return +19877 +19878 is-simple-mu-type?: # a: (addr type-tree), n: type-id -> result/eax: boolean +19879 # . prologue +19880 55/push-ebp +19881 89/<- %ebp 4/r32/esp +19882 # . save registers +19883 51/push-ecx +19884 # ecx = n +19885 8b/-> *(ebp+0xc) 1/r32/ecx +19886 # return (a->value == n) +19887 8b/-> *(ebp+8) 0/r32/eax +19888 39/compare *(eax+4) 1/r32/ecx # Type-tree-value +19889 0f 94/set-byte-if-= %al +19890 81 4/subop/and %eax 0xff/imm32 +19891 $is-simple-mu-type?:end: +19892 # . restore registers +19893 59/pop-to-ecx +19894 # . epilogue +19895 89/<- %esp 5/r32/ebp +19896 5d/pop-to-ebp +19897 c3/return +19898 +19899 is-mu-addr-type?: # a: (addr type-tree) -> result/eax: boolean +19900 # . prologue +19901 55/push-ebp +19902 89/<- %ebp 4/r32/esp +19903 # eax = a +19904 8b/-> *(ebp+8) 0/r32/eax +19905 # if (!a->is-atom?) a = a->left +19906 81 7/subop/compare *eax 0/imm32/false # Type-tree-is-atom +19907 { +19908 75/jump-if-!= break/disp8 +19909 (lookup *(eax+4) *(eax+8)) # Type-tree-left Type-tree-left => eax +19910 } +19911 # return (a->value == addr) +19912 81 7/subop/compare *(eax+4) 2/imm32/addr # Type-tree-value +19913 0f 94/set-byte-if-= %al +19914 81 4/subop/and %eax 0xff/imm32 +19915 $is-mu-addr-type?:end: +19916 # . epilogue +19917 89/<- %esp 5/r32/ebp +19918 5d/pop-to-ebp +19919 c3/return +19920 +19921 is-mu-array-type?: # a: (addr type-tree) -> result/eax: boolean +19922 # . prologue +19923 55/push-ebp +19924 89/<- %ebp 4/r32/esp +19925 # eax = a +19926 8b/-> *(ebp+8) 0/r32/eax +19927 # if (!a->is-atom?) a = a->left +19928 81 7/subop/compare *eax 0/imm32/false # Type-tree-is-atom +19929 { +19930 75/jump-if-!= break/disp8 +19931 (lookup *(eax+4) *(eax+8)) # Type-tree-left Type-tree-left => eax +19932 } +19933 # return (a->value == array) +19934 81 7/subop/compare *(eax+4) 3/imm32/array # Type-tree-value +19935 0f 94/set-byte-if-= %al +19936 81 4/subop/and %eax 0xff/imm32 +19937 $is-mu-array-type?:end: +19938 # . epilogue +19939 89/<- %esp 5/r32/ebp +19940 5d/pop-to-ebp +19941 c3/return +19942 +19943 is-mu-stream-type?: # a: (addr type-tree) -> result/eax: boolean +19944 # . prologue +19945 55/push-ebp +19946 89/<- %ebp 4/r32/esp +19947 # eax = a +19948 8b/-> *(ebp+8) 0/r32/eax +19949 # if (!a->is-atom?) a = a->left +19950 81 7/subop/compare *eax 0/imm32/false # Type-tree-is-atom +19951 { +19952 75/jump-if-!= break/disp8 +19953 (lookup *(eax+4) *(eax+8)) # Type-tree-left Type-tree-left => eax +19954 } +19955 # return (a->value == stream) +19956 81 7/subop/compare *(eax+4) 0xb/imm32/stream # Type-tree-value +19957 0f 94/set-byte-if-= %al +19958 81 4/subop/and %eax 0xff/imm32 +19959 $is-mu-stream-type?:end: +19960 # . epilogue +19961 89/<- %esp 5/r32/ebp +19962 5d/pop-to-ebp +19963 c3/return +19964 +19965 test-emit-subx-stmt-primitive: +19966 # Primitive operation on a variable on the stack. +19967 # increment foo +19968 # => +19969 # ff 0/subop/increment *(ebp-8) +19970 # +19971 # There's a variable on the var stack as follows: +19972 # name: 'foo' +19973 # type: int +19974 # stack-offset: -8 +19975 # +19976 # There's a primitive with this info: +19977 # name: 'increment' +19978 # inouts: int/mem +19979 # value: 'ff 0/subop/increment' +19980 # +19981 # . prologue +19982 55/push-ebp +19983 89/<- %ebp 4/r32/esp +19984 # setup +19985 (clear-stream _test-output-stream) +19986 (clear-stream $_test-output-buffered-file->buffer) +19987 # simulate allocated payloads starting with an initial fake alloc-id (0x11) +19988 $test-emit-subx-stmt-primitive:initialize-type: +19989 # var type/ecx: (payload type-tree) = int +19990 68/push 0/imm32/right:null +19991 68/push 0/imm32/right:null +19992 68/push 0/imm32/left:unused +19993 68/push 1/imm32/value:int +19994 68/push 1/imm32/is-atom?:true +19995 68/push 0x11/imm32/alloc-id:fake:payload +19996 89/<- %ecx 4/r32/esp +19997 $test-emit-subx-stmt-primitive:initialize-var: +19998 # var var-foo/ecx: (payload var) = var(type) +19999 68/push 0/imm32/no-register +20000 68/push 0/imm32/no-register +20001 68/push -8/imm32/stack-offset +20002 68/push 1/imm32/block-depth +20003 51/push-ecx/type +20004 68/push 0x11/imm32/alloc-id:fake +20005 68/push 0/imm32/name +20006 68/push 0/imm32/name +20007 68/push 0x11/imm32/alloc-id:fake:payload +20008 89/<- %ecx 4/r32/esp +20009 $test-emit-subx-stmt-primitive:initialize-var-name: +20010 # var-foo->name = "foo" +20011 8d/copy-address *(ecx+4) 0/r32/eax # Var-name + 4 +20012 (copy-array Heap "foo" %eax) +20013 $test-emit-subx-stmt-primitive:initialize-stmt-var: +20014 # var operand/ebx: (payload stmt-var) = stmt-var(var-foo) +20015 68/push 0/imm32/is-deref:false +20016 68/push 0/imm32/next +20017 68/push 0/imm32/next +20018 51/push-ecx/var-foo +20019 68/push 0x11/imm32/alloc-id:fake +20020 68/push 0x11/imm32/alloc-id:fake:payload +20021 89/<- %ebx 4/r32/esp +20022 $test-emit-subx-stmt-primitive:initialize-stmt: +20023 # var stmt/esi: (addr statement) +20024 68/push 0/imm32/no-outputs +20025 68/push 0/imm32/no-outputs +20026 53/push-ebx/inouts +20027 68/push 0x11/imm32/alloc-id:fake +20028 68/push 0/imm32/operation +20029 68/push 0/imm32/operation +20030 68/push 1/imm32/tag +20031 89/<- %esi 4/r32/esp +20032 $test-emit-subx-stmt-primitive:initialize-stmt-operation: +20033 # stmt->operation = "increment" +20034 8d/copy-address *(esi+4) 0/r32/eax # Stmt1-operation +20035 (copy-array Heap "increment" %eax) +20036 $test-emit-subx-stmt-primitive:initialize-primitive: +20037 # var primitives/ebx: (addr primitive) +20038 68/push 0/imm32/next +20039 68/push 0/imm32/next +20040 68/push 0/imm32/output-is-write-only +20041 68/push 0/imm32/no-disp32 +20042 68/push 0/imm32/no-imm8 +20043 68/push 0/imm32/no-imm32 +20044 68/push 0/imm32/no-r32 +20045 68/push 1/imm32/rm32-is-first-inout +20046 68/push 0/imm32/subx-name +20047 68/push 0/imm32/subx-name +20048 68/push 0/imm32/no-outputs +20049 68/push 0/imm32/no-outputs +20050 53/push-ebx/inouts # hack: reuse stmt-var from call stmt as (list var) in function declaration +20051 68/push 0x11/imm32/alloc-id:fake +20052 68/push 0/imm32/name +20053 68/push 0/imm32/name +20054 89/<- %ebx 4/r32/esp +20055 $test-emit-subx-stmt-primitive:initialize-primitive-name: +20056 # primitives->name = "increment" +20057 (copy-array Heap "increment" %ebx) # Primitive-name +20058 $test-emit-subx-stmt-primitive:initialize-primitive-subx-name: +20059 # primitives->subx-name = "ff 0/subop/increment" +20060 8d/copy-address *(ebx+0x18) 0/r32/eax # Primitive-subx-name +20061 (copy-array Heap "ff 0/subop/increment" %eax) +20062 # convert +20063 c7 0/subop/copy *Curr-block-depth 0/imm32 +20064 (emit-subx-stmt _test-output-buffered-file %esi %ebx Stderr 0) +20065 (flush _test-output-buffered-file) +20066 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- +20072 # check output +20073 (check-next-stream-line-equal _test-output-stream "ff 0/subop/increment *(ebp+0xfffffff8)" "F - test-emit-subx-stmt-primitive") +20074 # . epilogue +20075 89/<- %esp 5/r32/ebp +20076 5d/pop-to-ebp +20077 c3/return +20078 +20079 test-emit-subx-stmt-primitive-register: +20080 # Primitive operation on a variable in a register. +20081 # foo <- increment +20082 # => +20083 # ff 0/subop/increment %eax # sub-optimal, but should suffice +20084 # +20085 # There's a variable on the var stack as follows: +20086 # name: 'foo' +20087 # type: int +20088 # register: 'eax' +20089 # +20090 # There's a primitive with this info: +20091 # name: 'increment' +20092 # out: int/reg +20093 # value: 'ff 0/subop/increment' +20094 # +20095 # . prologue +20096 55/push-ebp +20097 89/<- %ebp 4/r32/esp +20098 # setup +20099 (clear-stream _test-output-stream) +20100 (clear-stream $_test-output-buffered-file->buffer) +20101 $test-emit-subx-stmt-primitive-register:initialize-type: +20102 # var type/ecx: (payload type-tree) = int +20103 68/push 0/imm32/right:null +20104 68/push 0/imm32/right:null +20105 68/push 0/imm32/left:unused +20106 68/push 1/imm32/value:int +20107 68/push 1/imm32/is-atom?:true +20108 68/push 0x11/imm32/alloc-id:fake:payload +20109 89/<- %ecx 4/r32/esp +20110 $test-emit-subx-stmt-primitive-register:initialize-var: +20111 # var var-foo/ecx: (payload var) +20112 68/push 0/imm32/register +20113 68/push 0/imm32/register +20114 68/push 0/imm32/no-stack-offset +20115 68/push 1/imm32/block-depth +20116 51/push-ecx +20117 68/push 0x11/imm32/alloc-id:fake +20118 68/push 0/imm32/name +20119 68/push 0/imm32/name +20120 68/push 0x11/imm32/alloc-id:fake:payload +20121 89/<- %ecx 4/r32/esp +20122 $test-emit-subx-stmt-primitive-register:initialize-var-name: +20123 # var-foo->name = "foo" +20124 8d/copy-address *(ecx+4) 0/r32/eax # Var-name + 4 +20125 (copy-array Heap "foo" %eax) +20126 $test-emit-subx-stmt-primitive-register:initialize-var-register: +20127 # var-foo->register = "eax" +20128 8d/copy-address *(ecx+0x1c) 0/r32/eax # Var-register + 4 +20129 (copy-array Heap "eax" %eax) +20130 $test-emit-subx-stmt-primitive-register:initialize-stmt-var: +20131 # var operand/ebx: (payload stmt-var) +20132 68/push 0/imm32/is-deref:false +20133 68/push 0/imm32/next +20134 68/push 0/imm32/next +20135 51/push-ecx/var-foo +20136 68/push 0x11/imm32/alloc-id:fake +20137 68/push 0x11/imm32/alloc-id:fake:payload +20138 89/<- %ebx 4/r32/esp +20139 $test-emit-subx-stmt-primitive-register:initialize-stmt: +20140 # var stmt/esi: (addr statement) +20141 53/push-ebx/outputs 20142 68/push 0x11/imm32/alloc-id:fake -20143 68/push 0/imm32/output-is-write-only -20144 68/push 0/imm32/no-disp32 -20145 68/push 0/imm32/no-imm8 -20146 68/push 0/imm32/no-imm32 -20147 68/push 0/imm32/no-r32 -20148 68/push 1/imm32/rm32-is-first-inout -20149 68/push 0/imm32/subx-name -20150 68/push 0/imm32/subx-name -20151 68/push 0/imm32/no-outputs -20152 68/push 0/imm32/no-outputs -20153 53/push-ebx/inouts # hack: reuse stmt-var from call stmt as (list var) in function declaration -20154 68/push 0x11/imm32/alloc-id:fake -20155 68/push 0/imm32/name -20156 68/push 0/imm32/name -20157 89/<- %ebx 4/r32/esp -20158 $test-emit-subx-stmt-select-primitive-2:initialize-primitive-name: -20159 # primitives->name = "increment" -20160 (copy-array Heap "increment" %ebx) # Primitive-name -20161 $test-emit-subx-stmt-select-primitive-2:initialize-primitive-subx-name: -20162 # primitives->subx-name = "ff 0/subop/increment" -20163 8d/copy-address *(ebx+0x18) 0/r32/eax # Primitive-subx-name -20164 (copy-array Heap "ff 0/subop/increment" %eax) -20165 # convert -20166 c7 0/subop/copy *Curr-block-depth 0/imm32 -20167 (emit-subx-stmt _test-output-buffered-file %esi %ebx Stderr 0) -20168 (flush _test-output-buffered-file) -20169 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- -20175 # check output -20176 (check-next-stream-line-equal _test-output-stream "ff 0/subop/increment %eax" "F - test-emit-subx-stmt-select-primitive-2") -20177 # . epilogue -20178 89/<- %esp 5/r32/ebp -20179 5d/pop-to-ebp -20180 c3/return -20181 -20182 test-increment-register: -20183 # Select the right register between overloads. -20184 # foo <- increment -20185 # => -20186 # 50/increment-eax -20187 # -20188 # There's a variable on the var stack as follows: -20189 # name: 'foo' -20190 # type: int -20191 # register: 'eax' -20192 # -20193 # Primitives are the global definitions. -20194 # -20195 # . prologue -20196 55/push-ebp -20197 89/<- %ebp 4/r32/esp -20198 # setup -20199 (clear-stream _test-output-stream) -20200 (clear-stream $_test-output-buffered-file->buffer) -20201 $test-increment-register:initialize-type: -20202 # var type/ecx: (payload type-tree) = int -20203 68/push 0/imm32/right:null -20204 68/push 0/imm32/right:null -20205 68/push 0/imm32/left:unused -20206 68/push 1/imm32/value:int -20207 68/push 1/imm32/is-atom?:true -20208 68/push 0x11/imm32/alloc-id:fake:payload -20209 89/<- %ecx 4/r32/esp -20210 $test-increment-register:initialize-var: -20211 # var var-foo/ecx: (payload var) -20212 68/push 0/imm32/register -20213 68/push 0/imm32/register -20214 68/push 0/imm32/no-stack-offset -20215 68/push 1/imm32/block-depth -20216 51/push-ecx -20217 68/push 0x11/imm32/alloc-id:fake -20218 68/push 0/imm32/name -20219 68/push 0/imm32/name -20220 68/push 0x11/imm32/alloc-id:fake:payload -20221 89/<- %ecx 4/r32/esp -20222 $test-increment-register:initialize-var-name: -20223 # var-foo->name = "foo" -20224 8d/copy-address *(ecx+4) 0/r32/eax # Var-name + 4 -20225 (copy-array Heap "foo" %eax) -20226 $test-increment-register:initialize-var-register: -20227 # var-foo->register = "eax" -20228 8d/copy-address *(ecx+0x1c) 0/r32/eax # Var-register + 4 -20229 (copy-array Heap "eax" %eax) -20230 $test-increment-register:initialize-stmt-var: -20231 # var operand/ebx: (payload stmt-var) -20232 68/push 0/imm32/is-deref:false -20233 68/push 0/imm32/next -20234 68/push 0/imm32/next -20235 51/push-ecx/var-foo -20236 68/push 0x11/imm32/alloc-id:fake -20237 68/push 0x11/imm32/alloc-id:fake:payload -20238 89/<- %ebx 4/r32/esp -20239 $test-increment-register:initialize-stmt: -20240 # var stmt/esi: (addr statement) -20241 53/push-ebx/outputs -20242 68/push 0x11/imm32/alloc-id:fake -20243 68/push 0/imm32/no-inouts -20244 68/push 0/imm32/no-inouts -20245 68/push 0/imm32/operation -20246 68/push 0/imm32/operation -20247 68/push 1/imm32 -20248 89/<- %esi 4/r32/esp -20249 $test-increment-register:initialize-stmt-operation: -20250 # stmt->operation = "increment" -20251 8d/copy-address *(esi+4) 0/r32/eax # Stmt1-operation -20252 (copy-array Heap "increment" %eax) -20253 # convert -20254 c7 0/subop/copy *Curr-block-depth 0/imm32 -20255 (emit-subx-stmt _test-output-buffered-file %esi Primitives Stderr 0) -20256 (flush _test-output-buffered-file) -20257 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- -20263 # check output -20264 (check-next-stream-line-equal _test-output-stream "40/increment-eax" "F - test-increment-register") -20265 # . epilogue -20266 89/<- %esp 5/r32/ebp -20267 5d/pop-to-ebp -20268 c3/return -20269 -20270 test-add-reg-to-reg: -20271 # var1/reg <- add var2/reg -20272 # => -20273 # 01/add-to %var1 var2 -20274 # -20275 # . prologue -20276 55/push-ebp -20277 89/<- %ebp 4/r32/esp -20278 # setup -20279 (clear-stream _test-output-stream) -20280 (clear-stream $_test-output-buffered-file->buffer) -20281 $test-add-reg-to-reg:initialize-type: -20282 # var type/ecx: (payload type-tree) = int -20283 68/push 0/imm32/right:null -20284 68/push 0/imm32/right:null -20285 68/push 0/imm32/left:unused -20286 68/push 1/imm32/value:int -20287 68/push 1/imm32/is-atom?:true -20288 68/push 0x11/imm32/alloc-id:fake:payload -20289 89/<- %ecx 4/r32/esp -20290 $test-add-reg-to-reg:initialize-var1: -20291 # var var1/ecx: (payload var) -20292 68/push 0/imm32/register -20293 68/push 0/imm32/register -20294 68/push 0/imm32/no-stack-offset -20295 68/push 1/imm32/block-depth -20296 51/push-ecx -20297 68/push 0x11/imm32/alloc-id:fake -20298 68/push 0/imm32/name -20299 68/push 0/imm32/name -20300 68/push 0x11/imm32/alloc-id:fake:payload -20301 89/<- %ecx 4/r32/esp -20302 $test-add-reg-to-reg:initialize-var1-name: -20303 # var1->name = "var1" -20304 8d/copy-address *(ecx+4) 0/r32/eax # Var-name + 4 -20305 (copy-array Heap "var1" %eax) -20306 $test-add-reg-to-reg:initialize-var1-register: -20307 # var1->register = "eax" -20308 8d/copy-address *(ecx+0x1c) 0/r32/eax # Var-register + 4 -20309 (copy-array Heap "eax" %eax) -20310 $test-add-reg-to-reg:initialize-var2: -20311 # var var2/edx: (payload var) -20312 68/push 0/imm32/register -20313 68/push 0/imm32/register -20314 68/push 0/imm32/no-stack-offset -20315 68/push 1/imm32/block-depth -20316 ff 6/subop/push *(ecx+0x10) -20317 68/push 0x11/imm32/alloc-id:fake -20318 68/push 0/imm32/name -20319 68/push 0/imm32/name -20320 68/push 0x11/imm32/alloc-id:fake:payload -20321 89/<- %edx 4/r32/esp -20322 $test-add-reg-to-reg:initialize-var2-name: -20323 # var2->name = "var2" -20324 8d/copy-address *(edx+4) 0/r32/eax # Var-name + 4 -20325 (copy-array Heap "var2" %eax) -20326 $test-add-reg-to-reg:initialize-var2-register: -20327 # var2->register = "ecx" -20328 8d/copy-address *(edx+0x1c) 0/r32/eax # Var-register + 4 -20329 (copy-array Heap "ecx" %eax) -20330 $test-add-reg-to-reg:initialize-inouts: -20331 # var inouts/esi: (payload stmt-var) = [var2] -20332 68/push 0/imm32/is-deref:false -20333 68/push 0/imm32/next -20334 68/push 0/imm32/next -20335 52/push-edx/var2 -20336 68/push 0x11/imm32/alloc-id:fake -20337 68/push 0x11/imm32/alloc-id:fake:payload -20338 89/<- %esi 4/r32/esp -20339 $test-add-reg-to-reg:initialize-outputs: -20340 # var outputs/edi: (payload stmt-var) = [var1] -20341 68/push 0/imm32/is-deref:false -20342 68/push 0/imm32/next -20343 68/push 0/imm32/next -20344 51/push-ecx/var1 -20345 68/push 0x11/imm32/alloc-id:fake -20346 68/push 0x11/imm32/alloc-id:fake:payload -20347 89/<- %edi 4/r32/esp -20348 $test-add-reg-to-reg:initialize-stmt: -20349 # var stmt/esi: (addr statement) -20350 68/push 0/imm32/next -20351 68/push 0/imm32/next -20352 57/push-edi/outputs -20353 68/push 0x11/imm32/alloc-id:fake -20354 56/push-esi/inouts -20355 68/push 0x11/imm32/alloc-id:fake -20356 68/push 0/imm32/operation -20357 68/push 0/imm32/operation -20358 68/push 1/imm32/tag:stmt1 -20359 89/<- %esi 4/r32/esp -20360 $test-add-reg-to-reg:initialize-stmt-operation: -20361 # stmt->operation = "add" -20362 8d/copy-address *(esi+4) 0/r32/eax # Stmt1-operation -20363 (copy-array Heap "add" %eax) -20364 # convert -20365 c7 0/subop/copy *Curr-block-depth 0/imm32 -20366 (emit-subx-stmt _test-output-buffered-file %esi Primitives Stderr 0) -20367 (flush _test-output-buffered-file) -20368 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- -20374 # check output -20375 (check-next-stream-line-equal _test-output-stream "01/add-to %eax 0x00000001/r32" "F - test-add-reg-to-reg") -20376 # . epilogue -20377 89/<- %esp 5/r32/ebp -20378 5d/pop-to-ebp -20379 c3/return -20380 -20381 test-add-reg-to-mem: -20382 # add-to var1 var2/reg -20383 # => -20384 # 01/add-to *(ebp+__) var2 -20385 # -20386 # . prologue -20387 55/push-ebp -20388 89/<- %ebp 4/r32/esp -20389 # setup -20390 (clear-stream _test-output-stream) -20391 (clear-stream $_test-output-buffered-file->buffer) -20392 $test-add-reg-to-mem:initialize-type: -20393 # var type/ecx: (payload type-tree) = int -20394 68/push 0/imm32/right:null -20395 68/push 0/imm32/right:null -20396 68/push 0/imm32/left:unused -20397 68/push 1/imm32/value:int -20398 68/push 1/imm32/is-atom?:true -20399 68/push 0x11/imm32/alloc-id:fake:payload -20400 89/<- %ecx 4/r32/esp -20401 $test-add-reg-to-mem:initialize-var1: -20402 # var var1/ecx: (payload var) -20403 68/push 0/imm32/register -20404 68/push 0/imm32/register -20405 68/push 8/imm32/stack-offset -20406 68/push 1/imm32/block-depth -20407 51/push-ecx -20408 68/push 0x11/imm32/alloc-id:fake -20409 68/push 0/imm32/name -20410 68/push 0/imm32/name -20411 68/push 0x11/imm32/alloc-id:fake:payload -20412 89/<- %ecx 4/r32/esp -20413 $test-add-reg-to-mem:initialize-var1-name: -20414 # var1->name = "var1" -20415 8d/copy-address *(ecx+4) 0/r32/eax # Var-name + 4 -20416 (copy-array Heap "var1" %eax) -20417 $test-add-reg-to-mem:initialize-var2: -20418 # var var2/edx: (payload var) -20419 68/push 0/imm32/register -20420 68/push 0/imm32/register -20421 68/push 0/imm32/no-stack-offset -20422 68/push 1/imm32/block-depth -20423 ff 6/subop/push *(ecx+0x10) -20424 68/push 0x11/imm32/alloc-id:fake -20425 68/push 0/imm32/name -20426 68/push 0/imm32/name -20427 68/push 0x11/imm32/alloc-id:fake:payload -20428 89/<- %edx 4/r32/esp -20429 $test-add-reg-to-mem:initialize-var2-name: -20430 # var2->name = "var2" -20431 8d/copy-address *(edx+4) 0/r32/eax # Var-name + 4 -20432 (copy-array Heap "var2" %eax) -20433 $test-add-reg-to-mem:initialize-var2-register: -20434 # var2->register = "ecx" -20435 8d/copy-address *(edx+0x1c) 0/r32/eax # Var-register + 4 -20436 (copy-array Heap "ecx" %eax) -20437 $test-add-reg-to-mem:initialize-inouts: -20438 # var inouts/esi: (payload stmt-var) = [var2] -20439 68/push 0/imm32/is-deref:false -20440 68/push 0/imm32/next -20441 68/push 0/imm32/next -20442 52/push-edx/var2 -20443 68/push 0x11/imm32/alloc-id:fake +20143 68/push 0/imm32/no-inouts +20144 68/push 0/imm32/no-inouts +20145 68/push 0/imm32/operation +20146 68/push 0/imm32/operation +20147 68/push 1/imm32 +20148 89/<- %esi 4/r32/esp +20149 $test-emit-subx-stmt-primitive-register:initialize-stmt-operation: +20150 # stmt->operation = "increment" +20151 8d/copy-address *(esi+4) 0/r32/eax # Stmt1-operation +20152 (copy-array Heap "increment" %eax) +20153 $test-emit-subx-stmt-primitive-register:initialize-formal-var: +20154 # var formal-var/ebx: (payload var) +20155 68/push 0/imm32/register +20156 68/push 0/imm32/register +20157 68/push 0/imm32/no-stack-offset +20158 68/push 1/imm32/block-depth +20159 ff 6/subop/push *(ecx+0x10) # Var-type + payload alloc id + handle alloc id +20160 68/push 0x11/imm32/alloc-id:fake +20161 68/push 0/imm32/name +20162 68/push 0/imm32/name +20163 68/push 0x11/imm32/alloc-id:fake:payload +20164 89/<- %ebx 4/r32/esp +20165 $test-emit-subx-stmt-primitive-register:initialize-formal-var-name: +20166 # formal-var->name = "dummy" +20167 8d/copy-address *(ebx+4) 0/r32/eax # Var-name + 4 +20168 (copy-array Heap "dummy" %eax) +20169 $test-emit-subx-stmt-primitive-register:initialize-formal-register: +20170 # formal-var->register = "*" +20171 8d/copy-address *(ebx+0x1c) 0/r32/eax # Var-register + 4 +20172 (copy-array Heap "*" %eax) # Any-register +20173 $test-emit-subx-stmt-primitive-register:initialize-var-list: +20174 # var formal-outputs/ebx: (payload list var) +20175 68/push 0/imm32/next +20176 68/push 0/imm32/next +20177 53/push-ebx/formal-var +20178 68/push 0x11/imm32/alloc-id:fake +20179 68/push 0x11/imm32/alloc-id:fake:payload +20180 89/<- %ebx 4/r32/esp +20181 $test-emit-subx-stmt-primitive-register:initialize-primitive: +20182 # var primitives/ebx: (addr primitive) +20183 68/push 0/imm32/next +20184 68/push 0/imm32/next +20185 68/push 0/imm32/output-is-write-only +20186 68/push 0/imm32/no-disp32 +20187 68/push 0/imm32/no-imm8 +20188 68/push 0/imm32/no-imm32 +20189 68/push 0/imm32/no-r32 +20190 68/push 3/imm32/rm32-is-first-output +20191 68/push 0/imm32/subx-name +20192 68/push 0/imm32/subx-name +20193 53/push-ebx/outputs +20194 68/push 0x11/imm32/alloc-id:fake +20195 68/push 0/imm32/no-inouts +20196 68/push 0/imm32/no-inouts +20197 68/push 0/imm32/name +20198 68/push 0/imm32/name +20199 89/<- %ebx 4/r32/esp +20200 $test-emit-subx-stmt-primitive-register:initialize-primitive-name: +20201 # primitives->name = "increment" +20202 (copy-array Heap "increment" %ebx) # Primitive-name +20203 $test-emit-subx-stmt-primitive-register:initialize-primitive-subx-name: +20204 # primitives->subx-name = "ff 0/subop/increment" +20205 8d/copy-address *(ebx+0x18) 0/r32/eax # Primitive-subx-name +20206 (copy-array Heap "ff 0/subop/increment" %eax) +20207 # convert +20208 c7 0/subop/copy *Curr-block-depth 0/imm32 +20209 (emit-subx-stmt _test-output-buffered-file %esi %ebx Stderr 0) +20210 (flush _test-output-buffered-file) +20211 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- +20217 # check output +20218 (check-next-stream-line-equal _test-output-stream "ff 0/subop/increment %eax" "F - test-emit-subx-stmt-primitive-register") +20219 # . epilogue +20220 89/<- %esp 5/r32/ebp +20221 5d/pop-to-ebp +20222 c3/return +20223 +20224 test-emit-subx-stmt-select-primitive: +20225 # Select the right primitive between overloads. +20226 # foo <- increment +20227 # => +20228 # ff 0/subop/increment %eax # sub-optimal, but should suffice +20229 # +20230 # There's a variable on the var stack as follows: +20231 # name: 'foo' +20232 # type: int +20233 # register: 'eax' +20234 # +20235 # There's two primitives, as follows: +20236 # - name: 'increment' +20237 # out: int/reg +20238 # value: 'ff 0/subop/increment' +20239 # - name: 'increment' +20240 # inout: int/mem +20241 # value: 'ff 0/subop/increment' +20242 # +20243 # . prologue +20244 55/push-ebp +20245 89/<- %ebp 4/r32/esp +20246 # setup +20247 (clear-stream _test-output-stream) +20248 (clear-stream $_test-output-buffered-file->buffer) +20249 $test-emit-subx-stmt-select-primitive:initialize-type: +20250 # var type/ecx: (payload type-tree) = int +20251 68/push 0/imm32/right:null +20252 68/push 0/imm32/right:null +20253 68/push 0/imm32/left:unused +20254 68/push 1/imm32/value:int +20255 68/push 1/imm32/is-atom?:true +20256 68/push 0x11/imm32/alloc-id:fake:payload +20257 89/<- %ecx 4/r32/esp +20258 $test-emit-subx-stmt-select-primitive:initialize-var: +20259 # var var-foo/ecx: (payload var) +20260 68/push 0/imm32/register +20261 68/push 0/imm32/register +20262 68/push 0/imm32/no-stack-offset +20263 68/push 1/imm32/block-depth +20264 51/push-ecx +20265 68/push 0x11/imm32/alloc-id:fake +20266 68/push 0/imm32/name +20267 68/push 0/imm32/name +20268 68/push 0x11/imm32/alloc-id:fake:payload +20269 89/<- %ecx 4/r32/esp +20270 $test-emit-subx-stmt-select-primitive:initialize-var-name: +20271 # var-foo->name = "foo" +20272 8d/copy-address *(ecx+4) 0/r32/eax # Var-name + 4 +20273 (copy-array Heap "foo" %eax) +20274 $test-emit-subx-stmt-select-primitive:initialize-var-register: +20275 # var-foo->register = "eax" +20276 8d/copy-address *(ecx+0x1c) 0/r32/eax # Var-register + 4 +20277 (copy-array Heap "eax" %eax) +20278 $test-emit-subx-stmt-select-primitive:initialize-stmt-var: +20279 # var operand/ebx: (payload stmt-var) +20280 68/push 0/imm32/is-deref:false +20281 68/push 0/imm32/next +20282 68/push 0/imm32/next +20283 51/push-ecx/var-foo +20284 68/push 0x11/imm32/alloc-id:fake +20285 68/push 0x11/imm32/alloc-id:fake:payload +20286 89/<- %ebx 4/r32/esp +20287 $test-emit-subx-stmt-select-primitive:initialize-stmt: +20288 # var stmt/esi: (addr statement) +20289 53/push-ebx/outputs +20290 68/push 0x11/imm32/alloc-id:fake +20291 68/push 0/imm32/no-inouts +20292 68/push 0/imm32/no-inouts +20293 68/push 0/imm32/operation +20294 68/push 0/imm32/operation +20295 68/push 1/imm32 +20296 89/<- %esi 4/r32/esp +20297 $test-emit-subx-stmt-select-primitive:initialize-stmt-operation: +20298 # stmt->operation = "increment" +20299 8d/copy-address *(esi+4) 0/r32/eax # Stmt1-operation +20300 (copy-array Heap "increment" %eax) +20301 $test-emit-subx-stmt-select-primitive:initialize-formal-var: +20302 # var formal-var/ebx: (payload var) +20303 68/push 0/imm32/register +20304 68/push 0/imm32/register +20305 68/push 0/imm32/no-stack-offset +20306 68/push 1/imm32/block-depth +20307 ff 6/subop/push *(ecx+0x10) # Var-type + payload alloc id + handle alloc id +20308 68/push 0x11/imm32/alloc-id:fake +20309 68/push 0/imm32/name +20310 68/push 0/imm32/name +20311 68/push 0x11/imm32/alloc-id:fake:payload +20312 89/<- %ebx 4/r32/esp +20313 $test-emit-subx-stmt-select-primitive:initialize-formal-var-name: +20314 # formal-var->name = "dummy" +20315 8d/copy-address *(ebx+4) 0/r32/eax # Var-name + 4 +20316 (copy-array Heap "dummy" %eax) +20317 $test-emit-subx-stmt-select-primitive:initialize-formal-register: +20318 # formal-var->register = "*" +20319 8d/copy-address *(ebx+0x1c) 0/r32/eax # Var-register + 4 +20320 (copy-array Heap "*" %eax) # Any-register +20321 $test-emit-subx-stmt-select-primitive:initialize-var-list: +20322 # var formal-outputs/ebx: (payload list var) +20323 68/push 0/imm32/next +20324 68/push 0/imm32/next +20325 53/push-ebx/formal-var +20326 68/push 0x11/imm32/alloc-id:fake +20327 68/push 0x11/imm32/alloc-id:fake:payload +20328 89/<- %ebx 4/r32/esp +20329 $test-emit-subx-stmt-select-primitive:initialize-primitive2: +20330 # var primitive2/edi: (payload primitive) +20331 68/push 0/imm32/next +20332 68/push 0/imm32/next +20333 68/push 0/imm32/output-is-write-only +20334 68/push 0/imm32/no-disp32 +20335 68/push 0/imm32/no-imm8 +20336 68/push 0/imm32/no-imm32 +20337 68/push 0/imm32/no-r32 +20338 68/push 3/imm32/rm32-is-first-output +20339 68/push 0/imm32/subx-name +20340 68/push 0/imm32/subx-name +20341 53/push-ebx/outputs +20342 68/push 0x11/imm32/alloc-id:fake +20343 68/push 0/imm32/no-inouts +20344 68/push 0/imm32/no-inouts +20345 68/push 0/imm32/name +20346 68/push 0/imm32/name +20347 68/push 0x11/imm32/alloc-id:fake:payload +20348 89/<- %edi 4/r32/esp +20349 $test-emit-subx-stmt-select-primitive:initialize-primitive2-name: +20350 # primitives->name = "increment" +20351 8d/copy-address *(edi+4) 0/r32/eax # Primitive-name + 4 +20352 (copy-array Heap "increment" %eax) +20353 $test-emit-subx-stmt-select-primitive:initialize-primitive2-subx-name: +20354 # primitives->subx-name = "ff 0/subop/increment" +20355 8d/copy-address *(edi+0x1c) 0/r32/eax # Primitive-subx-name + 4 +20356 (copy-array Heap "ff 0/subop/increment" %eax) +20357 $test-emit-subx-stmt-select-primitive:initialize-primitive: +20358 # var primitives/ebx: (addr primitive) +20359 57/push-edi +20360 68/push 0x11/imm32/alloc-id:fake +20361 68/push 0/imm32/output-is-write-only +20362 68/push 0/imm32/no-disp32 +20363 68/push 0/imm32/no-imm8 +20364 68/push 0/imm32/no-imm32 +20365 68/push 0/imm32/no-r32 +20366 68/push 1/imm32/rm32-is-first-inout +20367 68/push 0/imm32/subx-name +20368 68/push 0/imm32/subx-name +20369 68/push 0/imm32/no-outputs +20370 68/push 0/imm32/no-outputs +20371 53/push-ebx/inouts # hack: reuse stmt-var from call stmt as (list var) in function declaration +20372 68/push 0x11/imm32/alloc-id:fake +20373 68/push 0/imm32/name +20374 68/push 0/imm32/name +20375 89/<- %ebx 4/r32/esp +20376 $test-emit-subx-stmt-select-primitive:initialize-primitive-name: +20377 # primitives->name = "increment" +20378 (copy-array Heap "increment" %ebx) # Primitive-name +20379 $test-emit-subx-stmt-select-primitive:initialize-primitive-subx-name: +20380 # primitives->subx-name = "ff 0/subop/increment" +20381 8d/copy-address *(ebx+0x18) 0/r32/eax # Primitive-subx-name +20382 (copy-array Heap "ff 0/subop/increment" %eax) +20383 # convert +20384 c7 0/subop/copy *Curr-block-depth 0/imm32 +20385 (emit-subx-stmt _test-output-buffered-file %esi %ebx Stderr 0) +20386 (flush _test-output-buffered-file) +20387 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- +20393 # check output +20394 (check-next-stream-line-equal _test-output-stream "ff 0/subop/increment %eax" "F - test-emit-subx-stmt-select-primitive") +20395 # . epilogue +20396 89/<- %esp 5/r32/ebp +20397 5d/pop-to-ebp +20398 c3/return +20399 +20400 test-emit-subx-stmt-select-primitive-2: +20401 # Select the right primitive between overloads. +20402 # increment foo +20403 # => +20404 # ff 0/subop/increment %eax # sub-optimal, but should suffice +20405 # +20406 # There's a variable on the var stack as follows: +20407 # name: 'foo' +20408 # type: int +20409 # register: 'eax' +20410 # +20411 # There's two primitives, as follows: +20412 # - name: 'increment' +20413 # out: int/reg +20414 # value: 'ff 0/subop/increment' +20415 # - name: 'increment' +20416 # inout: int/mem +20417 # value: 'ff 0/subop/increment' +20418 # +20419 # . prologue +20420 55/push-ebp +20421 89/<- %ebp 4/r32/esp +20422 # setup +20423 (clear-stream _test-output-stream) +20424 (clear-stream $_test-output-buffered-file->buffer) +20425 $test-emit-subx-stmt-select-primitive-2:initialize-type: +20426 # var type/ecx: (payload type-tree) = int +20427 68/push 0/imm32/right:null +20428 68/push 0/imm32/right:null +20429 68/push 0/imm32/left:unused +20430 68/push 1/imm32/value:int +20431 68/push 1/imm32/is-atom?:true +20432 68/push 0x11/imm32/alloc-id:fake:payload +20433 89/<- %ecx 4/r32/esp +20434 $test-emit-subx-stmt-select-primitive-2:initialize-var: +20435 # var var-foo/ecx: (payload var) +20436 68/push 0/imm32/register +20437 68/push 0/imm32/register +20438 68/push 0/imm32/no-stack-offset +20439 68/push 1/imm32/block-depth +20440 51/push-ecx +20441 68/push 0x11/imm32/alloc-id:fake +20442 68/push 0/imm32/name +20443 68/push 0/imm32/name 20444 68/push 0x11/imm32/alloc-id:fake:payload -20445 89/<- %esi 4/r32/esp -20446 # inouts = [var1, var2] -20447 68/push 0/imm32/is-deref:false -20448 56/push-esi/next -20449 68/push 0x11/imm32/alloc-id:fake -20450 51/push-ecx/var1 -20451 68/push 0x11/imm32/alloc-id:fake -20452 68/push 0x11/imm32/alloc-id:fake:payload -20453 89/<- %esi 4/r32/esp -20454 $test-add-reg-to-mem:initialize-stmt: -20455 # var stmt/esi: (addr statement) -20456 68/push 0/imm32/next +20445 89/<- %ecx 4/r32/esp +20446 $test-emit-subx-stmt-select-primitive-2:initialize-var-name: +20447 # var-foo->name = "foo" +20448 8d/copy-address *(ecx+4) 0/r32/eax # Var-name + 4 +20449 (copy-array Heap "foo" %eax) +20450 $test-emit-subx-stmt-select-primitive-2:initialize-var-register: +20451 # var-foo->register = "eax" +20452 8d/copy-address *(ecx+0x1c) 0/r32/eax # Var-register + 4 +20453 (copy-array Heap "eax" %eax) +20454 $test-emit-subx-stmt-select-primitive-2:initialize-stmt-var: +20455 # var operand/ebx: (payload stmt-var) +20456 68/push 0/imm32/is-deref:false 20457 68/push 0/imm32/next -20458 68/push 0/imm32/outputs -20459 68/push 0/imm32/outputs -20460 56/push-esi/inouts -20461 68/push 0x11/imm32/alloc-id:fake -20462 68/push 0/imm32/operation -20463 68/push 0/imm32/operation -20464 68/push 1/imm32/tag:stmt1 -20465 89/<- %esi 4/r32/esp -20466 $test-add-reg-to-mem:initialize-stmt-operation: -20467 # stmt->operation = "add-to" -20468 8d/copy-address *(esi+4) 0/r32/eax # Stmt1-operation -20469 (copy-array Heap "add-to" %eax) -20470 # convert -20471 c7 0/subop/copy *Curr-block-depth 0/imm32 -20472 (emit-subx-stmt _test-output-buffered-file %esi Primitives Stderr 0) -20473 (flush _test-output-buffered-file) -20474 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- -20480 # check output -20481 (check-next-stream-line-equal _test-output-stream "01/add-to *(ebp+0x00000008) 0x00000001/r32" "F - test-add-reg-to-mem") -20482 # . epilogue -20483 89/<- %esp 5/r32/ebp -20484 5d/pop-to-ebp -20485 c3/return -20486 -20487 test-add-mem-to-reg: -20488 # var1/reg <- add var2 -20489 # => -20490 # 03/add *(ebp+__) var1 -20491 # -20492 # . prologue -20493 55/push-ebp -20494 89/<- %ebp 4/r32/esp -20495 # setup -20496 (clear-stream _test-output-stream) -20497 (clear-stream $_test-output-buffered-file->buffer) -20498 $test-add-mem-to-reg:initialize-type: -20499 # var type/ecx: (payload type-tree) = int -20500 68/push 0/imm32/right:null -20501 68/push 0/imm32/right:null -20502 68/push 0/imm32/left:unused -20503 68/push 1/imm32/value:int -20504 68/push 1/imm32/is-atom?:true -20505 68/push 0x11/imm32/alloc-id:fake:payload -20506 89/<- %ecx 4/r32/esp -20507 $test-add-mem-to-reg:initialize-var: -20508 # var var1/ecx: (payload var) -20509 68/push 0/imm32/register -20510 68/push 0/imm32/register -20511 68/push 0/imm32/no-stack-offset -20512 68/push 1/imm32/block-depth -20513 51/push-ecx -20514 68/push 0x11/imm32/alloc-id:fake -20515 68/push 0/imm32/name -20516 68/push 0/imm32/name -20517 68/push 0x11/imm32/alloc-id:fake:payload -20518 89/<- %ecx 4/r32/esp -20519 $test-add-mem-to-reg:initialize-var-name: -20520 # var1->name = "foo" -20521 8d/copy-address *(ecx+4) 0/r32/eax # Var-name + 4 -20522 (copy-array Heap "var1" %eax) -20523 $test-add-mem-to-reg:initialize-var-register: -20524 # var1->register = "eax" -20525 8d/copy-address *(ecx+0x1c) 0/r32/eax # Var-register + 4 -20526 (copy-array Heap "eax" %eax) -20527 $test-add-mem-to-reg:initialize-var2: -20528 # var var2/edx: (payload var) -20529 68/push 0/imm32/register -20530 68/push 0/imm32/register -20531 68/push 8/imm32/stack-offset -20532 68/push 1/imm32/block-depth -20533 ff 6/subop/push *(ecx+0x10) -20534 68/push 0x11/imm32/alloc-id:fake -20535 68/push 0/imm32/name -20536 68/push 0/imm32/name -20537 68/push 0x11/imm32/alloc-id:fake:payload -20538 89/<- %edx 4/r32/esp -20539 $test-add-mem-to-reg:initialize-var2-name: -20540 # var2->name = "var2" -20541 8d/copy-address *(edx+4) 0/r32/eax # Var-name + 4 -20542 (copy-array Heap "var2" %eax) -20543 $test-add-mem-to-reg:initialize-inouts: -20544 # var inouts/esi: (payload stmt-var) = [var2] -20545 68/push 0/imm32/is-deref:false -20546 68/push 0/imm32/next -20547 68/push 0/imm32/next -20548 52/push-edx/var2 -20549 68/push 0x11/imm32/alloc-id:fake -20550 68/push 0x11/imm32/alloc-id:fake:payload -20551 89/<- %esi 4/r32/esp -20552 $test-add-mem-to-reg:initialize-outputs: -20553 # var outputs/edi: (payload stmt-var) = [var1] -20554 68/push 0/imm32/is-deref:false -20555 68/push 0/imm32/next -20556 68/push 0/imm32/next -20557 51/push-ecx/var1 -20558 68/push 0x11/imm32/alloc-id:fake -20559 68/push 0x11/imm32/alloc-id:fake:payload -20560 89/<- %edi 4/r32/esp -20561 $test-add-mem-to-reg:initialize-stmt: -20562 # var stmt/esi: (addr statement) -20563 68/push 0/imm32/next -20564 68/push 0/imm32/next -20565 57/push-edi/outputs -20566 68/push 0x11/imm32/alloc-id:fake -20567 56/push-esi/inouts -20568 68/push 0x11/imm32/alloc-id:fake -20569 68/push 0/imm32/operation -20570 68/push 0/imm32/operation -20571 68/push 1/imm32/tag:stmt1 -20572 89/<- %esi 4/r32/esp -20573 $test-add-mem-to-reg:initialize-stmt-operation: -20574 # stmt->operation = "add" -20575 8d/copy-address *(esi+4) 0/r32/eax # Stmt1-operation -20576 (copy-array Heap "add" %eax) -20577 # convert -20578 c7 0/subop/copy *Curr-block-depth 0/imm32 -20579 (emit-subx-stmt _test-output-buffered-file %esi Primitives Stderr 0) -20580 (flush _test-output-buffered-file) -20581 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- -20587 # check output -20588 (check-next-stream-line-equal _test-output-stream "03/add *(ebp+0x00000008) 0x00000000/r32" "F - test-add-mem-to-reg") -20589 # . epilogue -20590 89/<- %esp 5/r32/ebp -20591 5d/pop-to-ebp -20592 c3/return -20593 -20594 test-add-literal-to-eax: -20595 # var1/eax <- add 0x34 -20596 # => -20597 # 05/add-to-eax 0x34/imm32 -20598 # -20599 # . prologue -20600 55/push-ebp -20601 89/<- %ebp 4/r32/esp -20602 # setup -20603 (clear-stream _test-output-stream) -20604 (clear-stream $_test-output-buffered-file->buffer) -20605 $test-add-literal-to-eax:initialize-var-type: -20606 # var type/ecx: (payload type-tree) = int -20607 68/push 0/imm32/right:null -20608 68/push 0/imm32/right:null -20609 68/push 0/imm32/left:unused -20610 68/push 1/imm32/value:int -20611 68/push 1/imm32/is-atom?:true -20612 68/push 0x11/imm32/alloc-id:fake:payload -20613 89/<- %ecx 4/r32/esp -20614 $test-add-literal-to-eax:initialize-var: -20615 # var v/ecx: (payload var) -20616 68/push 0/imm32/register -20617 68/push 0/imm32/register -20618 68/push 0/imm32/no-stack-offset -20619 68/push 1/imm32/block-depth -20620 51/push-ecx -20621 68/push 0x11/imm32/alloc-id:fake -20622 68/push 0/imm32/name -20623 68/push 0/imm32/name -20624 68/push 0x11/imm32/alloc-id:fake:payload -20625 89/<- %ecx 4/r32/esp -20626 $test-add-literal-to-eax:initialize-var-name: -20627 # v->name = "v" -20628 8d/copy-address *(ecx+4) 0/r32/eax # Var-name + 4 -20629 (copy-array Heap "v" %eax) -20630 $test-add-literal-to-eax:initialize-var-register: -20631 # v->register = "eax" -20632 8d/copy-address *(ecx+0x1c) 0/r32/eax # Var-register + 4 -20633 (copy-array Heap "eax" %eax) -20634 $test-add-literal-to-eax:initialize-literal-type: -20635 # var type/edx: (payload type-tree) = literal -20636 68/push 0/imm32/right:null -20637 68/push 0/imm32/right:null -20638 68/push 0/imm32/left:unused -20639 68/push 0/imm32/value:literal -20640 68/push 1/imm32/is-atom?:true -20641 68/push 0x11/imm32/alloc-id:fake:payload -20642 89/<- %edx 4/r32/esp -20643 $test-add-literal-to-eax:initialize-literal: -20644 # var l/edx: (payload var) -20645 68/push 0/imm32/register -20646 68/push 0/imm32/register -20647 68/push 0/imm32/no-stack-offset -20648 68/push 1/imm32/block-depth -20649 52/push-edx -20650 68/push 0x11/imm32/alloc-id:fake -20651 68/push 0/imm32/name -20652 68/push 0/imm32/name -20653 68/push 0x11/imm32/alloc-id:fake:payload -20654 89/<- %edx 4/r32/esp -20655 $test-add-literal-to-eax:initialize-literal-value: -20656 # l->name = "0x34" -20657 8d/copy-address *(edx+4) 0/r32/eax # Var-name + 4 -20658 (copy-array Heap "0x34" %eax) -20659 $test-add-literal-to-eax:initialize-inouts: -20660 # var inouts/esi: (payload stmt-var) = [l] -20661 68/push 0/imm32/is-deref:false -20662 68/push 0/imm32/next -20663 68/push 0/imm32/next -20664 52/push-edx/l -20665 68/push 0x11/imm32/alloc-id:fake -20666 68/push 0x11/imm32/alloc-id:fake:payload -20667 89/<- %esi 4/r32/esp -20668 $test-add-literal-to-eax:initialize-outputs: -20669 # var outputs/edi: (payload stmt-var) = [v] -20670 68/push 0/imm32/is-deref:false -20671 68/push 0/imm32/next -20672 68/push 0/imm32/next -20673 51/push-ecx/v -20674 68/push 0x11/imm32/alloc-id:fake -20675 68/push 0x11/imm32/alloc-id:fake:payload -20676 89/<- %edi 4/r32/esp -20677 $test-add-literal-to-eax:initialize-stmt: -20678 # var stmt/esi: (addr statement) -20679 68/push 0/imm32/next -20680 68/push 0/imm32/next -20681 57/push-edi/outputs -20682 68/push 0x11/imm32/alloc-id:fake -20683 56/push-esi/inouts -20684 68/push 0x11/imm32/alloc-id:fake -20685 68/push 0/imm32/operation -20686 68/push 0/imm32/operation -20687 68/push 1/imm32/tag:stmt1 -20688 89/<- %esi 4/r32/esp -20689 $test-add-literal-to-eax:initialize-stmt-operation: -20690 # stmt->operation = "add" -20691 8d/copy-address *(esi+4) 0/r32/eax # Stmt1-operation -20692 (copy-array Heap "add" %eax) -20693 # convert -20694 c7 0/subop/copy *Curr-block-depth 0/imm32 -20695 (emit-subx-stmt _test-output-buffered-file %esi Primitives Stderr 0) -20696 (flush _test-output-buffered-file) -20697 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- -20703 # check output -20704 (check-next-stream-line-equal _test-output-stream "05/add-to-eax 0x34/imm32" "F - test-add-literal-to-eax") -20705 # . epilogue -20706 89/<- %esp 5/r32/ebp -20707 5d/pop-to-ebp -20708 c3/return -20709 -20710 test-add-literal-to-reg: -20711 # var1/ecx <- add 0x34 -20712 # => -20713 # 81 0/subop/add %ecx 0x34/imm32 -20714 # -20715 # . prologue -20716 55/push-ebp -20717 89/<- %ebp 4/r32/esp -20718 # setup -20719 (clear-stream _test-output-stream) -20720 (clear-stream $_test-output-buffered-file->buffer) -20721 $test-add-literal-to-reg:initialize-var-type: -20722 # var type/ecx: (payload type-tree) = int -20723 68/push 0/imm32/right:null -20724 68/push 0/imm32/right:null -20725 68/push 0/imm32/left:unused -20726 68/push 1/imm32/value:int -20727 68/push 1/imm32/is-atom?:true -20728 68/push 0x11/imm32/alloc-id:fake:payload -20729 89/<- %ecx 4/r32/esp -20730 $test-add-literal-to-reg:initialize-var: -20731 # var v/ecx: (payload var) -20732 68/push 0/imm32/register -20733 68/push 0/imm32/register -20734 68/push 0/imm32/no-stack-offset -20735 68/push 1/imm32/block-depth -20736 51/push-ecx -20737 68/push 0x11/imm32/alloc-id:fake -20738 68/push 0/imm32/name -20739 68/push 0/imm32/name +20458 68/push 0/imm32/next +20459 51/push-ecx/var-foo +20460 68/push 0x11/imm32/alloc-id:fake +20461 68/push 0x11/imm32/alloc-id:fake:payload +20462 89/<- %ebx 4/r32/esp +20463 $test-emit-subx-stmt-select-primitive-2:initialize-stmt: +20464 # var stmt/esi: (addr statement) +20465 68/push 0/imm32/no-outputs +20466 68/push 0/imm32/no-outputs +20467 53/push-ebx/inouts +20468 68/push 0x11/imm32/alloc-id:fake +20469 68/push 0/imm32/operation +20470 68/push 0/imm32/operation +20471 68/push 1/imm32 +20472 89/<- %esi 4/r32/esp +20473 $test-emit-subx-stmt-select-primitive-2:initialize-stmt-operation: +20474 # stmt->operation = "increment" +20475 8d/copy-address *(esi+4) 0/r32/eax # Stmt1-operation +20476 (copy-array Heap "increment" %eax) +20477 $test-emit-subx-stmt-select-primitive-2:initialize-formal-var: +20478 # var formal-var/ebx: (payload var) +20479 68/push 0/imm32/register +20480 68/push 0/imm32/register +20481 68/push 0/imm32/no-stack-offset +20482 68/push 1/imm32/block-depth +20483 ff 6/subop/push *(ecx+0x10) # Var-type + payload alloc id + handle alloc id +20484 68/push 0x11/imm32/alloc-id:fake +20485 68/push 0/imm32/name +20486 68/push 0/imm32/name +20487 68/push 0x11/imm32/alloc-id:fake:payload +20488 89/<- %ebx 4/r32/esp +20489 $test-emit-subx-stmt-select-primitive-2:initialize-formal-var-name: +20490 # formal-var->name = "dummy" +20491 8d/copy-address *(ebx+4) 0/r32/eax # Var-name + 4 +20492 (copy-array Heap "dummy" %eax) +20493 $test-emit-subx-stmt-select-primitive-2:initialize-formal-register: +20494 # formal-var->register = "*" +20495 8d/copy-address *(ebx+0x1c) 0/r32/eax # Var-register + 4 +20496 (copy-array Heap "*" %eax) # Any-register +20497 $test-emit-subx-stmt-select-primitive-2:initialize-var-list: +20498 # var formal-outputs/ebx: (payload list stmt-var) +20499 68/push 0/imm32/next +20500 68/push 0/imm32/next +20501 53/push-ebx/formal-var +20502 68/push 0x11/imm32/alloc-id:fake +20503 68/push 0x11/imm32/alloc-id:fake:payload +20504 89/<- %ebx 4/r32/esp +20505 $test-emit-subx-stmt-select-primitive-2:initialize-primitive2: +20506 # var primitive2/edi: (payload primitive) +20507 68/push 0/imm32/next +20508 68/push 0/imm32/next +20509 68/push 0/imm32/output-is-write-only +20510 68/push 0/imm32/no-disp32 +20511 68/push 0/imm32/no-imm8 +20512 68/push 0/imm32/no-imm32 +20513 68/push 0/imm32/no-r32 +20514 68/push 3/imm32/rm32-is-first-output +20515 68/push 0/imm32/subx-name +20516 68/push 0/imm32/subx-name +20517 53/push-ebx/outputs +20518 68/push 0x11/imm32/alloc-id:fake +20519 68/push 0/imm32/no-inouts +20520 68/push 0/imm32/no-inouts +20521 68/push 0/imm32/name +20522 68/push 0/imm32/name +20523 68/push 0x11/imm32/alloc-id:fake:payload +20524 89/<- %edi 4/r32/esp +20525 $test-emit-subx-stmt-select-primitive-2:initialize-primitive2-name: +20526 # primitives->name = "increment" +20527 8d/copy-address *(edi+4) 0/r32/eax # Primitive-name + 4 +20528 (copy-array Heap "increment" %eax) +20529 $test-emit-subx-stmt-select-primitive-2:initialize-primitive2-subx-name: +20530 # primitives->subx-name = "ff 0/subop/increment" +20531 8d/copy-address *(edi+0x1c) 0/r32/eax # Primitive-subx-name + 4 +20532 (copy-array Heap "ff 0/subop/increment" %eax) +20533 $test-emit-subx-stmt-select-primitive-2:initialize-primitive: +20534 # var primitives/ebx: (addr primitive) +20535 57/push-edi +20536 68/push 0x11/imm32/alloc-id:fake +20537 68/push 0/imm32/output-is-write-only +20538 68/push 0/imm32/no-disp32 +20539 68/push 0/imm32/no-imm8 +20540 68/push 0/imm32/no-imm32 +20541 68/push 0/imm32/no-r32 +20542 68/push 1/imm32/rm32-is-first-inout +20543 68/push 0/imm32/subx-name +20544 68/push 0/imm32/subx-name +20545 68/push 0/imm32/no-outputs +20546 68/push 0/imm32/no-outputs +20547 53/push-ebx/inouts # hack: reuse stmt-var from call stmt as (list var) in function declaration +20548 68/push 0x11/imm32/alloc-id:fake +20549 68/push 0/imm32/name +20550 68/push 0/imm32/name +20551 89/<- %ebx 4/r32/esp +20552 $test-emit-subx-stmt-select-primitive-2:initialize-primitive-name: +20553 # primitives->name = "increment" +20554 (copy-array Heap "increment" %ebx) # Primitive-name +20555 $test-emit-subx-stmt-select-primitive-2:initialize-primitive-subx-name: +20556 # primitives->subx-name = "ff 0/subop/increment" +20557 8d/copy-address *(ebx+0x18) 0/r32/eax # Primitive-subx-name +20558 (copy-array Heap "ff 0/subop/increment" %eax) +20559 # convert +20560 c7 0/subop/copy *Curr-block-depth 0/imm32 +20561 (emit-subx-stmt _test-output-buffered-file %esi %ebx Stderr 0) +20562 (flush _test-output-buffered-file) +20563 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- +20569 # check output +20570 (check-next-stream-line-equal _test-output-stream "ff 0/subop/increment %eax" "F - test-emit-subx-stmt-select-primitive-2") +20571 # . epilogue +20572 89/<- %esp 5/r32/ebp +20573 5d/pop-to-ebp +20574 c3/return +20575 +20576 test-increment-register: +20577 # Select the right register between overloads. +20578 # foo <- increment +20579 # => +20580 # 50/increment-eax +20581 # +20582 # There's a variable on the var stack as follows: +20583 # name: 'foo' +20584 # type: int +20585 # register: 'eax' +20586 # +20587 # Primitives are the global definitions. +20588 # +20589 # . prologue +20590 55/push-ebp +20591 89/<- %ebp 4/r32/esp +20592 # setup +20593 (clear-stream _test-output-stream) +20594 (clear-stream $_test-output-buffered-file->buffer) +20595 $test-increment-register:initialize-type: +20596 # var type/ecx: (payload type-tree) = int +20597 68/push 0/imm32/right:null +20598 68/push 0/imm32/right:null +20599 68/push 0/imm32/left:unused +20600 68/push 1/imm32/value:int +20601 68/push 1/imm32/is-atom?:true +20602 68/push 0x11/imm32/alloc-id:fake:payload +20603 89/<- %ecx 4/r32/esp +20604 $test-increment-register:initialize-var: +20605 # var var-foo/ecx: (payload var) +20606 68/push 0/imm32/register +20607 68/push 0/imm32/register +20608 68/push 0/imm32/no-stack-offset +20609 68/push 1/imm32/block-depth +20610 51/push-ecx +20611 68/push 0x11/imm32/alloc-id:fake +20612 68/push 0/imm32/name +20613 68/push 0/imm32/name +20614 68/push 0x11/imm32/alloc-id:fake:payload +20615 89/<- %ecx 4/r32/esp +20616 $test-increment-register:initialize-var-name: +20617 # var-foo->name = "foo" +20618 8d/copy-address *(ecx+4) 0/r32/eax # Var-name + 4 +20619 (copy-array Heap "foo" %eax) +20620 $test-increment-register:initialize-var-register: +20621 # var-foo->register = "eax" +20622 8d/copy-address *(ecx+0x1c) 0/r32/eax # Var-register + 4 +20623 (copy-array Heap "eax" %eax) +20624 $test-increment-register:initialize-stmt-var: +20625 # var operand/ebx: (payload stmt-var) +20626 68/push 0/imm32/is-deref:false +20627 68/push 0/imm32/next +20628 68/push 0/imm32/next +20629 51/push-ecx/var-foo +20630 68/push 0x11/imm32/alloc-id:fake +20631 68/push 0x11/imm32/alloc-id:fake:payload +20632 89/<- %ebx 4/r32/esp +20633 $test-increment-register:initialize-stmt: +20634 # var stmt/esi: (addr statement) +20635 53/push-ebx/outputs +20636 68/push 0x11/imm32/alloc-id:fake +20637 68/push 0/imm32/no-inouts +20638 68/push 0/imm32/no-inouts +20639 68/push 0/imm32/operation +20640 68/push 0/imm32/operation +20641 68/push 1/imm32 +20642 89/<- %esi 4/r32/esp +20643 $test-increment-register:initialize-stmt-operation: +20644 # stmt->operation = "increment" +20645 8d/copy-address *(esi+4) 0/r32/eax # Stmt1-operation +20646 (copy-array Heap "increment" %eax) +20647 # convert +20648 c7 0/subop/copy *Curr-block-depth 0/imm32 +20649 (emit-subx-stmt _test-output-buffered-file %esi Primitives Stderr 0) +20650 (flush _test-output-buffered-file) +20651 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- +20657 # check output +20658 (check-next-stream-line-equal _test-output-stream "40/increment-eax" "F - test-increment-register") +20659 # . epilogue +20660 89/<- %esp 5/r32/ebp +20661 5d/pop-to-ebp +20662 c3/return +20663 +20664 test-add-reg-to-reg: +20665 # var1/reg <- add var2/reg +20666 # => +20667 # 01/add-to %var1 var2 +20668 # +20669 # . prologue +20670 55/push-ebp +20671 89/<- %ebp 4/r32/esp +20672 # setup +20673 (clear-stream _test-output-stream) +20674 (clear-stream $_test-output-buffered-file->buffer) +20675 $test-add-reg-to-reg:initialize-type: +20676 # var type/ecx: (payload type-tree) = int +20677 68/push 0/imm32/right:null +20678 68/push 0/imm32/right:null +20679 68/push 0/imm32/left:unused +20680 68/push 1/imm32/value:int +20681 68/push 1/imm32/is-atom?:true +20682 68/push 0x11/imm32/alloc-id:fake:payload +20683 89/<- %ecx 4/r32/esp +20684 $test-add-reg-to-reg:initialize-var1: +20685 # var var1/ecx: (payload var) +20686 68/push 0/imm32/register +20687 68/push 0/imm32/register +20688 68/push 0/imm32/no-stack-offset +20689 68/push 1/imm32/block-depth +20690 51/push-ecx +20691 68/push 0x11/imm32/alloc-id:fake +20692 68/push 0/imm32/name +20693 68/push 0/imm32/name +20694 68/push 0x11/imm32/alloc-id:fake:payload +20695 89/<- %ecx 4/r32/esp +20696 $test-add-reg-to-reg:initialize-var1-name: +20697 # var1->name = "var1" +20698 8d/copy-address *(ecx+4) 0/r32/eax # Var-name + 4 +20699 (copy-array Heap "var1" %eax) +20700 $test-add-reg-to-reg:initialize-var1-register: +20701 # var1->register = "eax" +20702 8d/copy-address *(ecx+0x1c) 0/r32/eax # Var-register + 4 +20703 (copy-array Heap "eax" %eax) +20704 $test-add-reg-to-reg:initialize-var2: +20705 # var var2/edx: (payload var) +20706 68/push 0/imm32/register +20707 68/push 0/imm32/register +20708 68/push 0/imm32/no-stack-offset +20709 68/push 1/imm32/block-depth +20710 ff 6/subop/push *(ecx+0x10) +20711 68/push 0x11/imm32/alloc-id:fake +20712 68/push 0/imm32/name +20713 68/push 0/imm32/name +20714 68/push 0x11/imm32/alloc-id:fake:payload +20715 89/<- %edx 4/r32/esp +20716 $test-add-reg-to-reg:initialize-var2-name: +20717 # var2->name = "var2" +20718 8d/copy-address *(edx+4) 0/r32/eax # Var-name + 4 +20719 (copy-array Heap "var2" %eax) +20720 $test-add-reg-to-reg:initialize-var2-register: +20721 # var2->register = "ecx" +20722 8d/copy-address *(edx+0x1c) 0/r32/eax # Var-register + 4 +20723 (copy-array Heap "ecx" %eax) +20724 $test-add-reg-to-reg:initialize-inouts: +20725 # var inouts/esi: (payload stmt-var) = [var2] +20726 68/push 0/imm32/is-deref:false +20727 68/push 0/imm32/next +20728 68/push 0/imm32/next +20729 52/push-edx/var2 +20730 68/push 0x11/imm32/alloc-id:fake +20731 68/push 0x11/imm32/alloc-id:fake:payload +20732 89/<- %esi 4/r32/esp +20733 $test-add-reg-to-reg:initialize-outputs: +20734 # var outputs/edi: (payload stmt-var) = [var1] +20735 68/push 0/imm32/is-deref:false +20736 68/push 0/imm32/next +20737 68/push 0/imm32/next +20738 51/push-ecx/var1 +20739 68/push 0x11/imm32/alloc-id:fake 20740 68/push 0x11/imm32/alloc-id:fake:payload -20741 89/<- %ecx 4/r32/esp -20742 $test-add-literal-to-reg:initialize-var-name: -20743 # v->name = "v" -20744 8d/copy-address *(ecx+4) 0/r32/eax # Var-name + 4 -20745 (copy-array Heap "v" %eax) -20746 $test-add-literal-to-reg:initialize-var-register: -20747 # v->register = "ecx" -20748 8d/copy-address *(ecx+0x1c) 0/r32/eax # Var-register + 4 -20749 (copy-array Heap "ecx" %eax) -20750 $test-add-literal-to-reg:initialize-literal-type: -20751 # var type/edx: (payload type-tree) = literal -20752 68/push 0/imm32/right:null -20753 68/push 0/imm32/right:null -20754 68/push 0/imm32/left:unused -20755 68/push 0/imm32/value:literal -20756 68/push 1/imm32/is-atom?:true -20757 68/push 0x11/imm32/alloc-id:fake:payload -20758 89/<- %edx 4/r32/esp -20759 $test-add-literal-to-reg:initialize-literal: -20760 # var l/edx: (payload var) -20761 68/push 0/imm32/register -20762 68/push 0/imm32/register -20763 68/push 0/imm32/no-stack-offset -20764 68/push 1/imm32/block-depth -20765 52/push-edx -20766 68/push 0x11/imm32/alloc-id:fake -20767 68/push 0/imm32/name -20768 68/push 0/imm32/name -20769 68/push 0x11/imm32/alloc-id:fake:payload -20770 89/<- %edx 4/r32/esp -20771 $test-add-literal-to-reg:initialize-literal-value: -20772 # l->name = "0x34" -20773 8d/copy-address *(edx+4) 0/r32/eax # Var-name + 4 -20774 (copy-array Heap "0x34" %eax) -20775 $test-add-literal-to-reg:initialize-inouts: -20776 # var inouts/esi: (payload stmt-var) = [l] -20777 68/push 0/imm32/is-deref:false -20778 68/push 0/imm32/next -20779 68/push 0/imm32/next -20780 52/push-edx/l -20781 68/push 0x11/imm32/alloc-id:fake -20782 68/push 0x11/imm32/alloc-id:fake:payload -20783 89/<- %esi 4/r32/esp -20784 $test-add-literal-to-reg:initialize-outputs: -20785 # var outputs/edi: (payload stmt-var) = [v] -20786 68/push 0/imm32/is-deref:false -20787 68/push 0/imm32/next -20788 68/push 0/imm32/next -20789 51/push-ecx/v -20790 68/push 0x11/imm32/alloc-id:fake -20791 68/push 0x11/imm32/alloc-id:fake:payload -20792 89/<- %edi 4/r32/esp -20793 $test-add-literal-to-reg:initialize-stmt: -20794 # var stmt/esi: (addr statement) -20795 68/push 0/imm32/next -20796 68/push 0/imm32/next -20797 57/push-edi/outputs -20798 68/push 0x11/imm32/alloc-id:fake -20799 56/push-esi/inouts -20800 68/push 0x11/imm32/alloc-id:fake -20801 68/push 0/imm32/operation -20802 68/push 0/imm32/operation -20803 68/push 1/imm32/tag:stmt1 -20804 89/<- %esi 4/r32/esp -20805 $test-add-literal-to-reg:initialize-stmt-operation: -20806 # stmt->operation = "add" -20807 8d/copy-address *(esi+4) 0/r32/eax # Stmt1-operation -20808 (copy-array Heap "add" %eax) -20809 # convert -20810 c7 0/subop/copy *Curr-block-depth 0/imm32 -20811 (emit-subx-stmt _test-output-buffered-file %esi Primitives Stderr 0) -20812 (flush _test-output-buffered-file) -20813 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- -20819 # check output -20820 (check-next-stream-line-equal _test-output-stream "81 0/subop/add %ecx 0x34/imm32" "F - test-add-literal-to-reg") -20821 # . epilogue -20822 89/<- %esp 5/r32/ebp -20823 5d/pop-to-ebp -20824 c3/return -20825 -20826 test-add-literal-to-mem: -20827 # add-to var1, 0x34 -20828 # => -20829 # 81 0/subop/add %eax 0x34/imm32 -20830 # -20831 # . prologue -20832 55/push-ebp -20833 89/<- %ebp 4/r32/esp -20834 # setup -20835 (clear-stream _test-output-stream) -20836 (clear-stream $_test-output-buffered-file->buffer) -20837 $test-add-literal-to-mem:initialize-type: -20838 # var type/ecx: (payload type-tree) = int -20839 68/push 0/imm32/right:null -20840 68/push 0/imm32/right:null -20841 68/push 0/imm32/left:unused -20842 68/push 1/imm32/value:int -20843 68/push 1/imm32/is-atom?:true -20844 68/push 0x11/imm32/alloc-id:fake:payload -20845 89/<- %ecx 4/r32/esp -20846 $test-add-literal-to-mem:initialize-var1: -20847 # var var1/ecx: (payload var) -20848 68/push 0/imm32/register -20849 68/push 0/imm32/register -20850 68/push 8/imm32/stack-offset -20851 68/push 1/imm32/block-depth -20852 51/push-ecx -20853 68/push 0x11/imm32/alloc-id:fake -20854 68/push 0/imm32/name -20855 68/push 0/imm32/name -20856 68/push 0x11/imm32/alloc-id:fake:payload -20857 89/<- %ecx 4/r32/esp -20858 $test-add-literal-to-mem:initialize-var1-name: -20859 # var1->name = "var1" -20860 8d/copy-address *(ecx+4) 0/r32/eax # Var-name + 4 -20861 (copy-array Heap "var1" %eax) -20862 $test-add-literal-to-mem:initialize-literal-type: -20863 # var type/edx: (payload type-tree) = literal -20864 68/push 0/imm32/right:null -20865 68/push 0/imm32/right:null -20866 68/push 0/imm32/left:unused -20867 68/push 0/imm32/value:literal -20868 68/push 1/imm32/is-atom?:true -20869 68/push 0x11/imm32/alloc-id:fake:payload -20870 89/<- %edx 4/r32/esp -20871 $test-add-literal-to-mem:initialize-literal: -20872 # var l/edx: (payload var) -20873 68/push 0/imm32/register -20874 68/push 0/imm32/register -20875 68/push 0/imm32/no-stack-offset -20876 68/push 1/imm32/block-depth -20877 52/push-edx -20878 68/push 0x11/imm32/alloc-id:fake -20879 68/push 0/imm32/name -20880 68/push 0/imm32/name -20881 68/push 0x11/imm32/alloc-id:fake:payload -20882 89/<- %edx 4/r32/esp -20883 $test-add-literal-to-mem:initialize-literal-value: -20884 # l->name = "0x34" -20885 8d/copy-address *(edx+4) 0/r32/eax # Var-name + 4 -20886 (copy-array Heap "0x34" %eax) -20887 $test-add-literal-to-mem:initialize-inouts: -20888 # var inouts/esi: (payload stmt-var) = [l] -20889 68/push 0/imm32/is-deref:false -20890 68/push 0/imm32/next -20891 68/push 0/imm32/next -20892 52/push-edx/l -20893 68/push 0x11/imm32/alloc-id:fake -20894 68/push 0x11/imm32/alloc-id:fake:payload -20895 89/<- %esi 4/r32/esp -20896 # var inouts = (handle stmt-var) = [var1, var2] -20897 68/push 0/imm32/is-deref:false -20898 56/push-esi/next -20899 68/push 0x11/imm32/alloc-id:fake -20900 51/push-ecx/var1 -20901 68/push 0x11/imm32/alloc-id:fake -20902 68/push 0x11/imm32/alloc-id:fake:payload -20903 89/<- %esi 4/r32/esp -20904 $test-add-literal-to-mem:initialize-stmt: -20905 # var stmt/esi: (addr statement) -20906 68/push 0/imm32/next -20907 68/push 0/imm32/next -20908 68/push 0/imm32/outputs -20909 68/push 0/imm32/outputs -20910 56/push-esi/inouts -20911 68/push 0x11/imm32/alloc-id:fake -20912 68/push 0/imm32/operation -20913 68/push 0/imm32/operation -20914 68/push 1/imm32/tag:stmt1 -20915 89/<- %esi 4/r32/esp -20916 $test-add-literal-to-mem:initialize-stmt-operation: -20917 # stmt->operation = "add-to" -20918 8d/copy-address *(esi+4) 0/r32/eax # Stmt1-operation -20919 (copy-array Heap "add-to" %eax) -20920 # convert -20921 c7 0/subop/copy *Curr-block-depth 0/imm32 -20922 (emit-subx-stmt _test-output-buffered-file %esi Primitives Stderr 0) -20923 (flush _test-output-buffered-file) -20924 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- -20930 # check output -20931 (check-next-stream-line-equal _test-output-stream "81 0/subop/add *(ebp+0x00000008) 0x34/imm32" "F - test-add-literal-to-mem") -20932 # . epilogue -20933 89/<- %esp 5/r32/ebp -20934 5d/pop-to-ebp -20935 c3/return -20936 -20937 test-shift-reg-by-literal: -20938 # var1/ecx <- shift-left 2 -20939 # => -20940 # c1/shift 4/subop/left %ecx 2/imm8 -20941 # -20942 # . prologue -20943 55/push-ebp -20944 89/<- %ebp 4/r32/esp -20945 # setup -20946 (clear-stream _test-output-stream) -20947 (clear-stream $_test-output-buffered-file->buffer) -20948 $test-shift-reg-by-literal:initialize-var-type: -20949 # var type/ecx: (payload type-tree) = int -20950 68/push 0/imm32/right:null -20951 68/push 0/imm32/right:null -20952 68/push 0/imm32/left:unused -20953 68/push 1/imm32/value:int -20954 68/push 1/imm32/is-atom?:true -20955 68/push 0x11/imm32/alloc-id:fake:payload -20956 89/<- %ecx 4/r32/esp -20957 $test-shift-reg-by-literal:initialize-var: -20958 # var v/ecx: (payload var) -20959 68/push 0/imm32/register -20960 68/push 0/imm32/register -20961 68/push 0/imm32/no-stack-offset -20962 68/push 1/imm32/block-depth -20963 51/push-ecx -20964 68/push 0x11/imm32/alloc-id:fake -20965 68/push 0/imm32/name -20966 68/push 0/imm32/name -20967 68/push 0x11/imm32/alloc-id:fake:payload -20968 89/<- %ecx 4/r32/esp -20969 $test-shift-reg-by-literal:initialize-var-name: -20970 # v->name = "v" -20971 8d/copy-address *(ecx+4) 0/r32/eax # Var-name + 4 -20972 (copy-array Heap "v" %eax) -20973 $test-shift-reg-by-literal:initialize-var-register: -20974 # v->register = "ecx" -20975 8d/copy-address *(ecx+0x1c) 0/r32/eax # Var-register + 4 -20976 (copy-array Heap "ecx" %eax) -20977 $test-shift-reg-by-literal:initialize-literal-type: -20978 # var type/edx: (payload type-tree) = literal -20979 68/push 0/imm32/right:null -20980 68/push 0/imm32/right:null -20981 68/push 0/imm32/left:unused -20982 68/push 0/imm32/value:literal -20983 68/push 1/imm32/is-atom?:true -20984 68/push 0x11/imm32/alloc-id:fake:payload -20985 89/<- %edx 4/r32/esp -20986 $test-shift-reg-by-literal:initialize-literal: -20987 # var l/edx: (payload var) -20988 68/push 0/imm32/register -20989 68/push 0/imm32/register -20990 68/push 0/imm32/no-stack-offset -20991 68/push 1/imm32/block-depth -20992 52/push-edx -20993 68/push 0x11/imm32/alloc-id:fake -20994 68/push 0/imm32/name -20995 68/push 0/imm32/name -20996 68/push 0x11/imm32/alloc-id:fake:payload -20997 89/<- %edx 4/r32/esp -20998 $test-shift-reg-by-literal:initialize-literal-value: -20999 # l->name = "2" -21000 8d/copy-address *(edx+4) 0/r32/eax # Var-name + 4 -21001 (copy-array Heap "2" %eax) -21002 $test-shift-reg-by-literal:initialize-inouts: -21003 # var inouts/esi: (payload stmt-var) = [l] -21004 68/push 0/imm32/is-deref:false -21005 68/push 0/imm32/next -21006 68/push 0/imm32/next -21007 52/push-edx/l -21008 68/push 0x11/imm32/alloc-id:fake -21009 68/push 0x11/imm32/alloc-id:fake:payload -21010 89/<- %esi 4/r32/esp -21011 $test-shift-reg-by-literal:initialize-outputs: -21012 # var outputs/edi: (payload stmt-var) = [v] -21013 68/push 0/imm32/is-deref:false -21014 68/push 0/imm32/next -21015 68/push 0/imm32/next -21016 51/push-ecx/v -21017 68/push 0x11/imm32/alloc-id:fake +20741 89/<- %edi 4/r32/esp +20742 $test-add-reg-to-reg:initialize-stmt: +20743 # var stmt/esi: (addr statement) +20744 68/push 0/imm32/next +20745 68/push 0/imm32/next +20746 57/push-edi/outputs +20747 68/push 0x11/imm32/alloc-id:fake +20748 56/push-esi/inouts +20749 68/push 0x11/imm32/alloc-id:fake +20750 68/push 0/imm32/operation +20751 68/push 0/imm32/operation +20752 68/push 1/imm32/tag:stmt1 +20753 89/<- %esi 4/r32/esp +20754 $test-add-reg-to-reg:initialize-stmt-operation: +20755 # stmt->operation = "add" +20756 8d/copy-address *(esi+4) 0/r32/eax # Stmt1-operation +20757 (copy-array Heap "add" %eax) +20758 # convert +20759 c7 0/subop/copy *Curr-block-depth 0/imm32 +20760 (emit-subx-stmt _test-output-buffered-file %esi Primitives Stderr 0) +20761 (flush _test-output-buffered-file) +20762 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- +20768 # check output +20769 (check-next-stream-line-equal _test-output-stream "01/add-to %eax 0x00000001/r32" "F - test-add-reg-to-reg") +20770 # . epilogue +20771 89/<- %esp 5/r32/ebp +20772 5d/pop-to-ebp +20773 c3/return +20774 +20775 test-add-reg-to-mem: +20776 # add-to var1 var2/reg +20777 # => +20778 # 01/add-to *(ebp+__) var2 +20779 # +20780 # . prologue +20781 55/push-ebp +20782 89/<- %ebp 4/r32/esp +20783 # setup +20784 (clear-stream _test-output-stream) +20785 (clear-stream $_test-output-buffered-file->buffer) +20786 $test-add-reg-to-mem:initialize-type: +20787 # var type/ecx: (payload type-tree) = int +20788 68/push 0/imm32/right:null +20789 68/push 0/imm32/right:null +20790 68/push 0/imm32/left:unused +20791 68/push 1/imm32/value:int +20792 68/push 1/imm32/is-atom?:true +20793 68/push 0x11/imm32/alloc-id:fake:payload +20794 89/<- %ecx 4/r32/esp +20795 $test-add-reg-to-mem:initialize-var1: +20796 # var var1/ecx: (payload var) +20797 68/push 0/imm32/register +20798 68/push 0/imm32/register +20799 68/push 8/imm32/stack-offset +20800 68/push 1/imm32/block-depth +20801 51/push-ecx +20802 68/push 0x11/imm32/alloc-id:fake +20803 68/push 0/imm32/name +20804 68/push 0/imm32/name +20805 68/push 0x11/imm32/alloc-id:fake:payload +20806 89/<- %ecx 4/r32/esp +20807 $test-add-reg-to-mem:initialize-var1-name: +20808 # var1->name = "var1" +20809 8d/copy-address *(ecx+4) 0/r32/eax # Var-name + 4 +20810 (copy-array Heap "var1" %eax) +20811 $test-add-reg-to-mem:initialize-var2: +20812 # var var2/edx: (payload var) +20813 68/push 0/imm32/register +20814 68/push 0/imm32/register +20815 68/push 0/imm32/no-stack-offset +20816 68/push 1/imm32/block-depth +20817 ff 6/subop/push *(ecx+0x10) +20818 68/push 0x11/imm32/alloc-id:fake +20819 68/push 0/imm32/name +20820 68/push 0/imm32/name +20821 68/push 0x11/imm32/alloc-id:fake:payload +20822 89/<- %edx 4/r32/esp +20823 $test-add-reg-to-mem:initialize-var2-name: +20824 # var2->name = "var2" +20825 8d/copy-address *(edx+4) 0/r32/eax # Var-name + 4 +20826 (copy-array Heap "var2" %eax) +20827 $test-add-reg-to-mem:initialize-var2-register: +20828 # var2->register = "ecx" +20829 8d/copy-address *(edx+0x1c) 0/r32/eax # Var-register + 4 +20830 (copy-array Heap "ecx" %eax) +20831 $test-add-reg-to-mem:initialize-inouts: +20832 # var inouts/esi: (payload stmt-var) = [var2] +20833 68/push 0/imm32/is-deref:false +20834 68/push 0/imm32/next +20835 68/push 0/imm32/next +20836 52/push-edx/var2 +20837 68/push 0x11/imm32/alloc-id:fake +20838 68/push 0x11/imm32/alloc-id:fake:payload +20839 89/<- %esi 4/r32/esp +20840 # inouts = [var1, var2] +20841 68/push 0/imm32/is-deref:false +20842 56/push-esi/next +20843 68/push 0x11/imm32/alloc-id:fake +20844 51/push-ecx/var1 +20845 68/push 0x11/imm32/alloc-id:fake +20846 68/push 0x11/imm32/alloc-id:fake:payload +20847 89/<- %esi 4/r32/esp +20848 $test-add-reg-to-mem:initialize-stmt: +20849 # var stmt/esi: (addr statement) +20850 68/push 0/imm32/next +20851 68/push 0/imm32/next +20852 68/push 0/imm32/outputs +20853 68/push 0/imm32/outputs +20854 56/push-esi/inouts +20855 68/push 0x11/imm32/alloc-id:fake +20856 68/push 0/imm32/operation +20857 68/push 0/imm32/operation +20858 68/push 1/imm32/tag:stmt1 +20859 89/<- %esi 4/r32/esp +20860 $test-add-reg-to-mem:initialize-stmt-operation: +20861 # stmt->operation = "add-to" +20862 8d/copy-address *(esi+4) 0/r32/eax # Stmt1-operation +20863 (copy-array Heap "add-to" %eax) +20864 # convert +20865 c7 0/subop/copy *Curr-block-depth 0/imm32 +20866 (emit-subx-stmt _test-output-buffered-file %esi Primitives Stderr 0) +20867 (flush _test-output-buffered-file) +20868 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- +20874 # check output +20875 (check-next-stream-line-equal _test-output-stream "01/add-to *(ebp+0x00000008) 0x00000001/r32" "F - test-add-reg-to-mem") +20876 # . epilogue +20877 89/<- %esp 5/r32/ebp +20878 5d/pop-to-ebp +20879 c3/return +20880 +20881 test-add-mem-to-reg: +20882 # var1/reg <- add var2 +20883 # => +20884 # 03/add *(ebp+__) var1 +20885 # +20886 # . prologue +20887 55/push-ebp +20888 89/<- %ebp 4/r32/esp +20889 # setup +20890 (clear-stream _test-output-stream) +20891 (clear-stream $_test-output-buffered-file->buffer) +20892 $test-add-mem-to-reg:initialize-type: +20893 # var type/ecx: (payload type-tree) = int +20894 68/push 0/imm32/right:null +20895 68/push 0/imm32/right:null +20896 68/push 0/imm32/left:unused +20897 68/push 1/imm32/value:int +20898 68/push 1/imm32/is-atom?:true +20899 68/push 0x11/imm32/alloc-id:fake:payload +20900 89/<- %ecx 4/r32/esp +20901 $test-add-mem-to-reg:initialize-var: +20902 # var var1/ecx: (payload var) +20903 68/push 0/imm32/register +20904 68/push 0/imm32/register +20905 68/push 0/imm32/no-stack-offset +20906 68/push 1/imm32/block-depth +20907 51/push-ecx +20908 68/push 0x11/imm32/alloc-id:fake +20909 68/push 0/imm32/name +20910 68/push 0/imm32/name +20911 68/push 0x11/imm32/alloc-id:fake:payload +20912 89/<- %ecx 4/r32/esp +20913 $test-add-mem-to-reg:initialize-var-name: +20914 # var1->name = "foo" +20915 8d/copy-address *(ecx+4) 0/r32/eax # Var-name + 4 +20916 (copy-array Heap "var1" %eax) +20917 $test-add-mem-to-reg:initialize-var-register: +20918 # var1->register = "eax" +20919 8d/copy-address *(ecx+0x1c) 0/r32/eax # Var-register + 4 +20920 (copy-array Heap "eax" %eax) +20921 $test-add-mem-to-reg:initialize-var2: +20922 # var var2/edx: (payload var) +20923 68/push 0/imm32/register +20924 68/push 0/imm32/register +20925 68/push 8/imm32/stack-offset +20926 68/push 1/imm32/block-depth +20927 ff 6/subop/push *(ecx+0x10) +20928 68/push 0x11/imm32/alloc-id:fake +20929 68/push 0/imm32/name +20930 68/push 0/imm32/name +20931 68/push 0x11/imm32/alloc-id:fake:payload +20932 89/<- %edx 4/r32/esp +20933 $test-add-mem-to-reg:initialize-var2-name: +20934 # var2->name = "var2" +20935 8d/copy-address *(edx+4) 0/r32/eax # Var-name + 4 +20936 (copy-array Heap "var2" %eax) +20937 $test-add-mem-to-reg:initialize-inouts: +20938 # var inouts/esi: (payload stmt-var) = [var2] +20939 68/push 0/imm32/is-deref:false +20940 68/push 0/imm32/next +20941 68/push 0/imm32/next +20942 52/push-edx/var2 +20943 68/push 0x11/imm32/alloc-id:fake +20944 68/push 0x11/imm32/alloc-id:fake:payload +20945 89/<- %esi 4/r32/esp +20946 $test-add-mem-to-reg:initialize-outputs: +20947 # var outputs/edi: (payload stmt-var) = [var1] +20948 68/push 0/imm32/is-deref:false +20949 68/push 0/imm32/next +20950 68/push 0/imm32/next +20951 51/push-ecx/var1 +20952 68/push 0x11/imm32/alloc-id:fake +20953 68/push 0x11/imm32/alloc-id:fake:payload +20954 89/<- %edi 4/r32/esp +20955 $test-add-mem-to-reg:initialize-stmt: +20956 # var stmt/esi: (addr statement) +20957 68/push 0/imm32/next +20958 68/push 0/imm32/next +20959 57/push-edi/outputs +20960 68/push 0x11/imm32/alloc-id:fake +20961 56/push-esi/inouts +20962 68/push 0x11/imm32/alloc-id:fake +20963 68/push 0/imm32/operation +20964 68/push 0/imm32/operation +20965 68/push 1/imm32/tag:stmt1 +20966 89/<- %esi 4/r32/esp +20967 $test-add-mem-to-reg:initialize-stmt-operation: +20968 # stmt->operation = "add" +20969 8d/copy-address *(esi+4) 0/r32/eax # Stmt1-operation +20970 (copy-array Heap "add" %eax) +20971 # convert +20972 c7 0/subop/copy *Curr-block-depth 0/imm32 +20973 (emit-subx-stmt _test-output-buffered-file %esi Primitives Stderr 0) +20974 (flush _test-output-buffered-file) +20975 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- +20981 # check output +20982 (check-next-stream-line-equal _test-output-stream "03/add *(ebp+0x00000008) 0x00000000/r32" "F - test-add-mem-to-reg") +20983 # . epilogue +20984 89/<- %esp 5/r32/ebp +20985 5d/pop-to-ebp +20986 c3/return +20987 +20988 test-add-literal-to-eax: +20989 # var1/eax <- add 0x34 +20990 # => +20991 # 05/add-to-eax 0x34/imm32 +20992 # +20993 # . prologue +20994 55/push-ebp +20995 89/<- %ebp 4/r32/esp +20996 # setup +20997 (clear-stream _test-output-stream) +20998 (clear-stream $_test-output-buffered-file->buffer) +20999 $test-add-literal-to-eax:initialize-var-type: +21000 # var type/ecx: (payload type-tree) = int +21001 68/push 0/imm32/right:null +21002 68/push 0/imm32/right:null +21003 68/push 0/imm32/left:unused +21004 68/push 1/imm32/value:int +21005 68/push 1/imm32/is-atom?:true +21006 68/push 0x11/imm32/alloc-id:fake:payload +21007 89/<- %ecx 4/r32/esp +21008 $test-add-literal-to-eax:initialize-var: +21009 # var v/ecx: (payload var) +21010 68/push 0/imm32/register +21011 68/push 0/imm32/register +21012 68/push 0/imm32/no-stack-offset +21013 68/push 1/imm32/block-depth +21014 51/push-ecx +21015 68/push 0x11/imm32/alloc-id:fake +21016 68/push 0/imm32/name +21017 68/push 0/imm32/name 21018 68/push 0x11/imm32/alloc-id:fake:payload -21019 89/<- %edi 4/r32/esp -21020 $test-shift-reg-by-literal:initialize-stmt: -21021 # var stmt/esi: (addr statement) -21022 68/push 0/imm32/next -21023 68/push 0/imm32/next -21024 57/push-edi/outputs -21025 68/push 0x11/imm32/alloc-id:fake -21026 56/push-esi/inouts -21027 68/push 0x11/imm32/alloc-id:fake -21028 68/push 0/imm32/operation -21029 68/push 0/imm32/operation -21030 68/push 1/imm32/tag:stmt1 -21031 89/<- %esi 4/r32/esp -21032 $test-shift-reg-by-literal:initialize-stmt-operation: -21033 # stmt->operation = "shift-left" -21034 8d/copy-address *(esi+4) 0/r32/eax # Stmt1-operation -21035 (copy-array Heap "shift-left" %eax) -21036 # convert -21037 c7 0/subop/copy *Curr-block-depth 0/imm32 -21038 (emit-subx-stmt _test-output-buffered-file %esi Primitives Stderr 0) -21039 (flush _test-output-buffered-file) -21040 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- -21046 # check output -21047 (check-next-stream-line-equal _test-output-stream "c1/shift 4/subop/left %ecx 2/imm8" "F - test-shift-reg-by-literal") -21048 # . epilogue -21049 89/<- %esp 5/r32/ebp -21050 5d/pop-to-ebp -21051 c3/return -21052 -21053 test-shift-mem-by-literal: -21054 # shift-left var 3 -21055 # => -21056 # c1/shift 4/subop/left *(ebp+8) 3/imm8 -21057 # -21058 # . prologue -21059 55/push-ebp -21060 89/<- %ebp 4/r32/esp -21061 # setup -21062 (clear-stream _test-output-stream) -21063 (clear-stream $_test-output-buffered-file->buffer) -21064 $test-shift-mem-by-literal:initialize-type: -21065 # var type/ecx: (payload type-tree) = int -21066 68/push 0/imm32/right:null -21067 68/push 0/imm32/right:null -21068 68/push 0/imm32/left:unused -21069 68/push 1/imm32/value:int -21070 68/push 1/imm32/is-atom?:true -21071 68/push 0x11/imm32/alloc-id:fake:payload -21072 89/<- %ecx 4/r32/esp -21073 $test-shift-mem-by-literal:initialize-var1: -21074 # var var1/ecx: (payload var) -21075 68/push 0/imm32/register -21076 68/push 0/imm32/register -21077 68/push 8/imm32/stack-offset -21078 68/push 1/imm32/block-depth -21079 51/push-ecx -21080 68/push 0x11/imm32/alloc-id:fake -21081 68/push 0/imm32/name -21082 68/push 0/imm32/name -21083 68/push 0x11/imm32/alloc-id:fake:payload -21084 89/<- %ecx 4/r32/esp -21085 $test-shift-mem-by-literal:initialize-var1-name: -21086 # var1->name = "var1" -21087 8d/copy-address *(ecx+4) 0/r32/eax # Var-name + 4 -21088 (copy-array Heap "var1" %eax) -21089 $test-shift-mem-by-literal:initialize-literal-type: -21090 # var type/edx: (payload type-tree) = literal -21091 68/push 0/imm32/right:null -21092 68/push 0/imm32/right:null -21093 68/push 0/imm32/left:unused -21094 68/push 0/imm32/value:literal -21095 68/push 1/imm32/is-atom?:true -21096 68/push 0x11/imm32/alloc-id:fake:payload -21097 89/<- %edx 4/r32/esp -21098 $test-shift-mem-by-literal:initialize-literal: -21099 # var l/edx: (payload var) -21100 68/push 0/imm32/register -21101 68/push 0/imm32/register -21102 68/push 0/imm32/no-stack-offset -21103 68/push 1/imm32/block-depth -21104 52/push-edx -21105 68/push 0x11/imm32/alloc-id:fake -21106 68/push 0/imm32/name -21107 68/push 0/imm32/name -21108 68/push 0x11/imm32/alloc-id:fake:payload -21109 89/<- %edx 4/r32/esp -21110 $test-shift-mem-by-literal:initialize-literal-value: -21111 # l->name = "3" -21112 8d/copy-address *(edx+4) 0/r32/eax # Var-name + 4 -21113 (copy-array Heap "3" %eax) -21114 $test-shift-mem-by-literal:initialize-inouts: -21115 # var inouts/esi: (payload stmt-var) = [l] -21116 68/push 0/imm32/is-deref:false -21117 68/push 0/imm32/next -21118 68/push 0/imm32/next -21119 52/push-edx/l -21120 68/push 0x11/imm32/alloc-id:fake -21121 68/push 0x11/imm32/alloc-id:fake:payload -21122 89/<- %esi 4/r32/esp -21123 # var inouts = (handle stmt-var) = [var1, var2] -21124 68/push 0/imm32/is-deref:false -21125 56/push-esi/next -21126 68/push 0x11/imm32/alloc-id:fake -21127 51/push-ecx/var1 -21128 68/push 0x11/imm32/alloc-id:fake -21129 68/push 0x11/imm32/alloc-id:fake:payload -21130 89/<- %esi 4/r32/esp -21131 $test-shift-mem-by-literal:initialize-stmt: -21132 # var stmt/esi: (addr statement) -21133 68/push 0/imm32/next -21134 68/push 0/imm32/next -21135 68/push 0/imm32/outputs -21136 68/push 0/imm32/outputs -21137 56/push-esi/inouts -21138 68/push 0x11/imm32/alloc-id:fake -21139 68/push 0/imm32/operation -21140 68/push 0/imm32/operation -21141 68/push 1/imm32/tag:stmt1 -21142 89/<- %esi 4/r32/esp -21143 $test-shift-mem-by-literal:initialize-stmt-operation: -21144 # stmt->operation = "shift-left" -21145 8d/copy-address *(esi+4) 0/r32/eax # Stmt1-operation -21146 (copy-array Heap "shift-left" %eax) -21147 # convert -21148 c7 0/subop/copy *Curr-block-depth 0/imm32 -21149 (emit-subx-stmt _test-output-buffered-file %esi Primitives Stderr 0) -21150 (flush _test-output-buffered-file) -21151 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- -21157 # check output -21158 (check-next-stream-line-equal _test-output-stream "c1/shift 4/subop/left *(ebp+0x00000008) 3/imm8" "F - test-shift-mem-by-literal") -21159 # . epilogue -21160 89/<- %esp 5/r32/ebp -21161 5d/pop-to-ebp -21162 c3/return -21163 -21164 test-compare-reg-with-reg: -21165 # compare var1/ecx, var2/eax -21166 # => -21167 # 39/compare %ecx 0/r32/eax -21168 # -21169 # . prologue -21170 55/push-ebp -21171 89/<- %ebp 4/r32/esp -21172 # setup -21173 (clear-stream _test-output-stream) -21174 (clear-stream $_test-output-buffered-file->buffer) -21175 $test-compare-reg-with-reg:initialize-type: -21176 # var type/ecx: (payload type-tree) = int -21177 68/push 0/imm32/right:null -21178 68/push 0/imm32/right:null -21179 68/push 0/imm32/left:unused -21180 68/push 1/imm32/value:int -21181 68/push 1/imm32/is-atom?:true -21182 68/push 0x11/imm32/alloc-id:fake:payload -21183 89/<- %ecx 4/r32/esp -21184 $test-compare-reg-with-reg:initialize-var1: -21185 # var var1/ecx: (payload var) -21186 68/push 0/imm32/register -21187 68/push 0/imm32/register -21188 68/push 0/imm32/no-stack-offset -21189 68/push 1/imm32/block-depth -21190 51/push-ecx -21191 68/push 0x11/imm32/alloc-id:fake -21192 68/push 0/imm32/name -21193 68/push 0/imm32/name -21194 68/push 0x11/imm32/alloc-id:fake:payload -21195 89/<- %ecx 4/r32/esp -21196 $test-compare-reg-with-reg:initialize-var1-name: -21197 # var1->name = "var1" -21198 8d/copy-address *(ecx+4) 0/r32/eax # Var-name + 4 -21199 (copy-array Heap "var1" %eax) -21200 $test-compare-reg-with-reg:initialize-var1-register: -21201 # var1->register = "ecx" -21202 8d/copy-address *(ecx+0x1c) 0/r32/eax # Var-register + 4 -21203 (copy-array Heap "ecx" %eax) -21204 $test-compare-reg-with-reg:initialize-var2: -21205 # var var2/edx: (payload var) -21206 68/push 0/imm32/register -21207 68/push 0/imm32/register -21208 68/push 0/imm32/no-stack-offset -21209 68/push 1/imm32/block-depth -21210 ff 6/subop/push *(ecx+0x10) -21211 68/push 0x11/imm32/alloc-id:fake -21212 68/push 0/imm32/name -21213 68/push 0/imm32/name -21214 68/push 0x11/imm32/alloc-id:fake:payload -21215 89/<- %edx 4/r32/esp -21216 $test-compare-reg-with-reg:initialize-var2-name: -21217 # var2->name = "var2" -21218 8d/copy-address *(edx+4) 0/r32/eax # Var-name + 4 -21219 (copy-array Heap "var2" %eax) -21220 $test-compare-reg-with-reg:initialize-var2-register: -21221 # var2->register = "eax" -21222 8d/copy-address *(edx+0x1c) 0/r32/eax # Var-register + 4 -21223 (copy-array Heap "eax" %eax) -21224 $test-compare-reg-with-reg:initialize-inouts: -21225 # var inouts/esi: (payload stmt-var) = [var2] -21226 68/push 0/imm32/is-deref:false -21227 68/push 0/imm32/next -21228 68/push 0/imm32/next -21229 52/push-edx/var2 -21230 68/push 0x11/imm32/alloc-id:fake -21231 68/push 0x11/imm32/alloc-id:fake:payload -21232 89/<- %esi 4/r32/esp -21233 # inouts = [var1, var2] -21234 68/push 0/imm32/is-deref:false -21235 56/push-esi/next -21236 68/push 0x11/imm32/alloc-id:fake -21237 51/push-ecx/var1 -21238 68/push 0x11/imm32/alloc-id:fake -21239 68/push 0x11/imm32/alloc-id:fake:payload -21240 89/<- %esi 4/r32/esp -21241 $test-compare-reg-with-reg:initialize-stmt: -21242 # var stmt/esi: (addr statement) -21243 68/push 0/imm32/next -21244 68/push 0/imm32/next -21245 68/push 0/imm32/outputs -21246 68/push 0/imm32/outputs -21247 56/push-esi/inouts -21248 68/push 0x11/imm32/alloc-id:fake -21249 68/push 0/imm32/operation -21250 68/push 0/imm32/operation -21251 68/push 1/imm32/tag:stmt1 -21252 89/<- %esi 4/r32/esp -21253 $test-compare-reg-with-reg:initialize-stmt-operation: -21254 # stmt->operation = "compare" -21255 8d/copy-address *(esi+4) 0/r32/eax # Stmt1-operation -21256 (copy-array Heap "compare" %eax) -21257 # convert -21258 c7 0/subop/copy *Curr-block-depth 0/imm32 -21259 (emit-subx-stmt _test-output-buffered-file %esi Primitives Stderr 0) -21260 (flush _test-output-buffered-file) -21261 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- -21267 # check output -21268 (check-next-stream-line-equal _test-output-stream "39/compare-> %ecx 0x00000000/r32" "F - test-compare-reg-with-reg") -21269 # . epilogue -21270 89/<- %esp 5/r32/ebp -21271 5d/pop-to-ebp -21272 c3/return -21273 -21274 test-compare-mem-with-reg: -21275 # compare var1, var2/eax -21276 # => -21277 # 39/compare *(ebp+___) 0/r32/eax -21278 # -21279 # . prologue -21280 55/push-ebp -21281 89/<- %ebp 4/r32/esp -21282 # setup -21283 (clear-stream _test-output-stream) -21284 (clear-stream $_test-output-buffered-file->buffer) -21285 $test-compare-mem-with-reg:initialize-type: -21286 # var type/ecx: (payload type-tree) = int -21287 68/push 0/imm32/right:null -21288 68/push 0/imm32/right:null -21289 68/push 0/imm32/left:unused -21290 68/push 1/imm32/value:int -21291 68/push 1/imm32/is-atom?:true -21292 68/push 0x11/imm32/alloc-id:fake:payload -21293 89/<- %ecx 4/r32/esp -21294 $test-compare-mem-with-reg:initialize-var1: -21295 # var var1/ecx: (payload var) -21296 68/push 0/imm32/register -21297 68/push 0/imm32/register -21298 68/push 8/imm32/stack-offset -21299 68/push 1/imm32/block-depth -21300 51/push-ecx -21301 68/push 0x11/imm32/alloc-id:fake -21302 68/push 0/imm32/name -21303 68/push 0/imm32/name -21304 68/push 0x11/imm32/alloc-id:fake:payload -21305 89/<- %ecx 4/r32/esp -21306 $test-compare-mem-with-reg:initialize-var1-name: -21307 # var1->name = "var1" -21308 8d/copy-address *(ecx+4) 0/r32/eax # Var-name + 4 -21309 (copy-array Heap "var1" %eax) -21310 $test-compare-mem-with-reg:initialize-var2: -21311 # var var2/edx: (payload var) -21312 68/push 0/imm32/register -21313 68/push 0/imm32/register -21314 68/push 0/imm32/no-stack-offset -21315 68/push 1/imm32/block-depth -21316 ff 6/subop/push *(ecx+0x10) -21317 68/push 0x11/imm32/alloc-id:fake -21318 68/push 0/imm32/name -21319 68/push 0/imm32/name -21320 68/push 0x11/imm32/alloc-id:fake:payload -21321 89/<- %edx 4/r32/esp -21322 $test-compare-mem-with-reg:initialize-var2-name: -21323 # var2->name = "var2" -21324 8d/copy-address *(edx+4) 0/r32/eax # Var-name + 4 -21325 (copy-array Heap "var2" %eax) -21326 $test-compare-mem-with-reg:initialize-var2-register: -21327 # var2->register = "eax" -21328 8d/copy-address *(edx+0x1c) 0/r32/eax # Var-register + 4 -21329 (copy-array Heap "eax" %eax) -21330 $test-compare-mem-with-reg:initialize-inouts: -21331 # var inouts/esi: (payload stmt-var) = [var2] -21332 68/push 0/imm32/is-deref:false -21333 68/push 0/imm32/next -21334 68/push 0/imm32/next -21335 52/push-edx/var2 -21336 68/push 0x11/imm32/alloc-id:fake -21337 68/push 0x11/imm32/alloc-id:fake:payload -21338 89/<- %esi 4/r32/esp -21339 # inouts = [var1, var2] -21340 68/push 0/imm32/is-deref:false -21341 56/push-esi/next -21342 68/push 0x11/imm32/alloc-id:fake -21343 51/push-ecx/var1 -21344 68/push 0x11/imm32/alloc-id:fake -21345 68/push 0x11/imm32/alloc-id:fake:payload -21346 89/<- %esi 4/r32/esp -21347 $test-compare-mem-with-reg:initialize-stmt: -21348 # var stmt/esi: (addr statement) -21349 68/push 0/imm32/next -21350 68/push 0/imm32/next -21351 68/push 0/imm32/outputs -21352 68/push 0/imm32/outputs -21353 56/push-esi/inouts -21354 68/push 0x11/imm32/alloc-id:fake -21355 68/push 0/imm32/operation -21356 68/push 0/imm32/operation -21357 68/push 1/imm32/tag:stmt1 -21358 89/<- %esi 4/r32/esp -21359 $test-compare-mem-with-reg:initialize-stmt-operation: -21360 # stmt->operation = "compare" -21361 8d/copy-address *(esi+4) 0/r32/eax # Stmt1-operation -21362 (copy-array Heap "compare" %eax) -21363 # convert -21364 c7 0/subop/copy *Curr-block-depth 0/imm32 -21365 (emit-subx-stmt _test-output-buffered-file %esi Primitives Stderr 0) -21366 (flush _test-output-buffered-file) -21367 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- -21373 # check output -21374 (check-next-stream-line-equal _test-output-stream "39/compare-> *(ebp+0x00000008) 0x00000000/r32" "F - test-compare-mem-with-reg") -21375 # . epilogue -21376 89/<- %esp 5/r32/ebp -21377 5d/pop-to-ebp -21378 c3/return -21379 -21380 test-compare-reg-with-mem: -21381 # compare var1/eax, var2 -21382 # => -21383 # 3b/compare<- *(ebp+___) 0/r32/eax -21384 # -21385 # . prologue -21386 55/push-ebp -21387 89/<- %ebp 4/r32/esp -21388 # setup -21389 (clear-stream _test-output-stream) -21390 (clear-stream $_test-output-buffered-file->buffer) -21391 $test-compare-reg-with-mem:initialize-type: -21392 # var type/ecx: (payload type-tree) = int -21393 68/push 0/imm32/right:null -21394 68/push 0/imm32/right:null -21395 68/push 0/imm32/left:unused -21396 68/push 1/imm32/value:int -21397 68/push 1/imm32/is-atom?:true -21398 68/push 0x11/imm32/alloc-id:fake:payload -21399 89/<- %ecx 4/r32/esp -21400 $test-compare-reg-with-mem:initialize-var1: -21401 # var var1/ecx: (payload var) -21402 68/push 0/imm32/register -21403 68/push 0/imm32/register -21404 68/push 0/imm32/no-stack-offset -21405 68/push 1/imm32/block-depth -21406 51/push-ecx -21407 68/push 0x11/imm32/alloc-id:fake -21408 68/push 0/imm32/name -21409 68/push 0/imm32/name -21410 68/push 0x11/imm32/alloc-id:fake:payload -21411 89/<- %ecx 4/r32/esp -21412 $test-compare-reg-with-mem:initialize-var1-name: -21413 # var1->name = "var1" -21414 8d/copy-address *(ecx+4) 0/r32/eax # Var-name + 4 -21415 (copy-array Heap "var1" %eax) -21416 $test-compare-reg-with-mem:initialize-var1-register: -21417 # var1->register = "eax" -21418 8d/copy-address *(ecx+0x1c) 0/r32/eax # Var-register + 4 -21419 (copy-array Heap "eax" %eax) -21420 $test-compare-reg-with-mem:initialize-var2: -21421 # var var2/edx: (payload var) -21422 68/push 0/imm32/register -21423 68/push 0/imm32/register -21424 68/push 8/imm32/stack-offset -21425 68/push 1/imm32/block-depth -21426 ff 6/subop/push *(ecx+0x10) -21427 68/push 0x11/imm32/alloc-id:fake -21428 68/push 0/imm32/name -21429 68/push 0/imm32/name -21430 68/push 0x11/imm32/alloc-id:fake:payload -21431 89/<- %edx 4/r32/esp -21432 $test-compare-reg-with-mem:initialize-var2-name: -21433 # var2->name = "var2" -21434 8d/copy-address *(edx+4) 0/r32/eax # Var-name + 4 -21435 (copy-array Heap "var2" %eax) -21436 $test-compare-reg-with-mem:initialize-inouts: -21437 # var inouts/esi: (payload stmt-var) = [var2] -21438 68/push 0/imm32/is-deref:false -21439 68/push 0/imm32/next -21440 68/push 0/imm32/next -21441 52/push-edx/var2 -21442 68/push 0x11/imm32/alloc-id:fake -21443 68/push 0x11/imm32/alloc-id:fake:payload -21444 89/<- %esi 4/r32/esp -21445 # inouts = [var1, var2] -21446 68/push 0/imm32/is-deref:false -21447 56/push-esi/next -21448 68/push 0x11/imm32/alloc-id:fake -21449 51/push-ecx/var1 -21450 68/push 0x11/imm32/alloc-id:fake -21451 68/push 0x11/imm32/alloc-id:fake:payload -21452 89/<- %esi 4/r32/esp -21453 $test-compare-reg-with-mem:initialize-stmt: -21454 # var stmt/esi: (addr statement) -21455 68/push 0/imm32/next -21456 68/push 0/imm32/next -21457 68/push 0/imm32/outputs -21458 68/push 0/imm32/outputs -21459 56/push-esi/inouts -21460 68/push 0x11/imm32/alloc-id:fake -21461 68/push 0/imm32/operation -21462 68/push 0/imm32/operation -21463 68/push 1/imm32/tag:stmt1 -21464 89/<- %esi 4/r32/esp -21465 $test-compare-reg-with-mem:initialize-stmt-operation: -21466 # stmt->operation = "compare" -21467 8d/copy-address *(esi+4) 0/r32/eax # Stmt1-operation -21468 (copy-array Heap "compare" %eax) -21469 # convert -21470 c7 0/subop/copy *Curr-block-depth 0/imm32 -21471 (emit-subx-stmt _test-output-buffered-file %esi Primitives Stderr 0) -21472 (flush _test-output-buffered-file) -21473 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- -21479 # check output -21480 (check-next-stream-line-equal _test-output-stream "3b/compare<- *(ebp+0x00000008) 0x00000000/r32" "F - test-compare-reg-with-mem") -21481 # . epilogue -21482 89/<- %esp 5/r32/ebp -21483 5d/pop-to-ebp -21484 c3/return -21485 -21486 test-compare-mem-with-literal: -21487 # compare var1, 0x34 -21488 # => -21489 # 81 7/subop/compare *(ebp+___) 0x34/imm32 -21490 # -21491 # . prologue -21492 55/push-ebp -21493 89/<- %ebp 4/r32/esp -21494 # setup -21495 (clear-stream _test-output-stream) -21496 (clear-stream $_test-output-buffered-file->buffer) -21497 $test-compare-mem-with-literal:initialize-type: -21498 # var type/ecx: (payload type-tree) = int -21499 68/push 0/imm32/right:null -21500 68/push 0/imm32/right:null -21501 68/push 0/imm32/left:unused -21502 68/push 1/imm32/value:int -21503 68/push 1/imm32/is-atom?:true -21504 68/push 0x11/imm32/alloc-id:fake:payload -21505 89/<- %ecx 4/r32/esp -21506 $test-compare-mem-with-literal:initialize-var1: -21507 # var var1/ecx: (payload var) -21508 68/push 0/imm32/register -21509 68/push 0/imm32/register -21510 68/push 8/imm32/stack-offset -21511 68/push 1/imm32/block-depth -21512 51/push-ecx -21513 68/push 0x11/imm32/alloc-id:fake -21514 68/push 0/imm32/name -21515 68/push 0/imm32/name -21516 68/push 0x11/imm32/alloc-id:fake:payload -21517 89/<- %ecx 4/r32/esp -21518 $test-compare-mem-with-literal:initialize-var1-name: -21519 # var1->name = "var1" -21520 8d/copy-address *(ecx+4) 0/r32/eax # Var-name + 4 -21521 (copy-array Heap "var1" %eax) -21522 $test-compare-mem-with-literal:initialize-literal-type: -21523 # var type/edx: (payload type-tree) = literal -21524 68/push 0/imm32/right:null -21525 68/push 0/imm32/right:null -21526 68/push 0/imm32/left:unused -21527 68/push 0/imm32/value:literal -21528 68/push 1/imm32/is-atom?:true -21529 68/push 0x11/imm32/alloc-id:fake:payload -21530 89/<- %edx 4/r32/esp -21531 $test-compare-mem-with-literal:initialize-literal: -21532 # var l/edx: (payload var) -21533 68/push 0/imm32/register -21534 68/push 0/imm32/register -21535 68/push 0/imm32/no-stack-offset -21536 68/push 1/imm32/block-depth -21537 52/push-edx -21538 68/push 0x11/imm32/alloc-id:fake -21539 68/push 0/imm32/name -21540 68/push 0/imm32/name -21541 68/push 0x11/imm32/alloc-id:fake:payload -21542 89/<- %edx 4/r32/esp -21543 $test-compare-mem-with-literal:initialize-literal-value: -21544 # l->name = "0x34" -21545 8d/copy-address *(edx+4) 0/r32/eax # Var-name + 4 -21546 (copy-array Heap "0x34" %eax) -21547 $test-compare-mem-with-literal:initialize-inouts: -21548 # var inouts/esi: (payload stmt-var) = [l] -21549 68/push 0/imm32/is-deref:false -21550 68/push 0/imm32/next -21551 68/push 0/imm32/next -21552 52/push-edx/l -21553 68/push 0x11/imm32/alloc-id:fake -21554 68/push 0x11/imm32/alloc-id:fake:payload -21555 89/<- %esi 4/r32/esp -21556 # var inouts = (handle stmt-var) = [var1, var2] -21557 68/push 0/imm32/is-deref:false -21558 56/push-esi/next -21559 68/push 0x11/imm32/alloc-id:fake -21560 51/push-ecx/var1 -21561 68/push 0x11/imm32/alloc-id:fake -21562 68/push 0x11/imm32/alloc-id:fake:payload -21563 89/<- %esi 4/r32/esp -21564 $test-compare-mem-with-literal:initialize-stmt: -21565 # var stmt/esi: (addr statement) -21566 68/push 0/imm32/next -21567 68/push 0/imm32/next -21568 68/push 0/imm32/outputs -21569 68/push 0/imm32/outputs -21570 56/push-esi/inouts -21571 68/push 0x11/imm32/alloc-id:fake -21572 68/push 0/imm32/operation -21573 68/push 0/imm32/operation -21574 68/push 1/imm32/tag:stmt1 -21575 89/<- %esi 4/r32/esp -21576 $test-compare-mem-with-literal:initialize-stmt-operation: -21577 # stmt->operation = "compare" -21578 8d/copy-address *(esi+4) 0/r32/eax # Stmt1-operation -21579 (copy-array Heap "compare" %eax) -21580 # convert -21581 c7 0/subop/copy *Curr-block-depth 0/imm32 -21582 (emit-subx-stmt _test-output-buffered-file %esi Primitives Stderr 0) -21583 (flush _test-output-buffered-file) -21584 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- -21590 # check output -21591 (check-next-stream-line-equal _test-output-stream "81 7/subop/compare *(ebp+0x00000008) 0x34/imm32" "F - test-compare-mem-with-literal") -21592 # . epilogue -21593 89/<- %esp 5/r32/ebp -21594 5d/pop-to-ebp -21595 c3/return -21596 -21597 test-compare-eax-with-literal: -21598 # compare var1/eax 0x34 -21599 # => -21600 # 3d/compare-eax-with 0x34/imm32 -21601 # -21602 # . prologue -21603 55/push-ebp -21604 89/<- %ebp 4/r32/esp -21605 # setup -21606 (clear-stream _test-output-stream) -21607 (clear-stream $_test-output-buffered-file->buffer) -21608 $test-compare-eax-with-literal:initialize-type: -21609 # var type/ecx: (payload type-tree) = int -21610 68/push 0/imm32/right:null -21611 68/push 0/imm32/right:null -21612 68/push 0/imm32/left:unused -21613 68/push 1/imm32/value:int -21614 68/push 1/imm32/is-atom?:true -21615 68/push 0x11/imm32/alloc-id:fake:payload -21616 89/<- %ecx 4/r32/esp -21617 $test-compare-eax-with-literal:initialize-var1: -21618 # var var1/ecx: (payload var) -21619 68/push 0/imm32/register -21620 68/push 0/imm32/register -21621 68/push 0/imm32/no-stack-offset -21622 68/push 1/imm32/block-depth -21623 51/push-ecx +21019 89/<- %ecx 4/r32/esp +21020 $test-add-literal-to-eax:initialize-var-name: +21021 # v->name = "v" +21022 8d/copy-address *(ecx+4) 0/r32/eax # Var-name + 4 +21023 (copy-array Heap "v" %eax) +21024 $test-add-literal-to-eax:initialize-var-register: +21025 # v->register = "eax" +21026 8d/copy-address *(ecx+0x1c) 0/r32/eax # Var-register + 4 +21027 (copy-array Heap "eax" %eax) +21028 $test-add-literal-to-eax:initialize-literal-type: +21029 # var type/edx: (payload type-tree) = literal +21030 68/push 0/imm32/right:null +21031 68/push 0/imm32/right:null +21032 68/push 0/imm32/left:unused +21033 68/push 0/imm32/value:literal +21034 68/push 1/imm32/is-atom?:true +21035 68/push 0x11/imm32/alloc-id:fake:payload +21036 89/<- %edx 4/r32/esp +21037 $test-add-literal-to-eax:initialize-literal: +21038 # var l/edx: (payload var) +21039 68/push 0/imm32/register +21040 68/push 0/imm32/register +21041 68/push 0/imm32/no-stack-offset +21042 68/push 1/imm32/block-depth +21043 52/push-edx +21044 68/push 0x11/imm32/alloc-id:fake +21045 68/push 0/imm32/name +21046 68/push 0/imm32/name +21047 68/push 0x11/imm32/alloc-id:fake:payload +21048 89/<- %edx 4/r32/esp +21049 $test-add-literal-to-eax:initialize-literal-value: +21050 # l->name = "0x34" +21051 8d/copy-address *(edx+4) 0/r32/eax # Var-name + 4 +21052 (copy-array Heap "0x34" %eax) +21053 $test-add-literal-to-eax:initialize-inouts: +21054 # var inouts/esi: (payload stmt-var) = [l] +21055 68/push 0/imm32/is-deref:false +21056 68/push 0/imm32/next +21057 68/push 0/imm32/next +21058 52/push-edx/l +21059 68/push 0x11/imm32/alloc-id:fake +21060 68/push 0x11/imm32/alloc-id:fake:payload +21061 89/<- %esi 4/r32/esp +21062 $test-add-literal-to-eax:initialize-outputs: +21063 # var outputs/edi: (payload stmt-var) = [v] +21064 68/push 0/imm32/is-deref:false +21065 68/push 0/imm32/next +21066 68/push 0/imm32/next +21067 51/push-ecx/v +21068 68/push 0x11/imm32/alloc-id:fake +21069 68/push 0x11/imm32/alloc-id:fake:payload +21070 89/<- %edi 4/r32/esp +21071 $test-add-literal-to-eax:initialize-stmt: +21072 # var stmt/esi: (addr statement) +21073 68/push 0/imm32/next +21074 68/push 0/imm32/next +21075 57/push-edi/outputs +21076 68/push 0x11/imm32/alloc-id:fake +21077 56/push-esi/inouts +21078 68/push 0x11/imm32/alloc-id:fake +21079 68/push 0/imm32/operation +21080 68/push 0/imm32/operation +21081 68/push 1/imm32/tag:stmt1 +21082 89/<- %esi 4/r32/esp +21083 $test-add-literal-to-eax:initialize-stmt-operation: +21084 # stmt->operation = "add" +21085 8d/copy-address *(esi+4) 0/r32/eax # Stmt1-operation +21086 (copy-array Heap "add" %eax) +21087 # convert +21088 c7 0/subop/copy *Curr-block-depth 0/imm32 +21089 (emit-subx-stmt _test-output-buffered-file %esi Primitives Stderr 0) +21090 (flush _test-output-buffered-file) +21091 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- +21097 # check output +21098 (check-next-stream-line-equal _test-output-stream "05/add-to-eax 0x34/imm32" "F - test-add-literal-to-eax") +21099 # . epilogue +21100 89/<- %esp 5/r32/ebp +21101 5d/pop-to-ebp +21102 c3/return +21103 +21104 test-add-literal-to-reg: +21105 # var1/ecx <- add 0x34 +21106 # => +21107 # 81 0/subop/add %ecx 0x34/imm32 +21108 # +21109 # . prologue +21110 55/push-ebp +21111 89/<- %ebp 4/r32/esp +21112 # setup +21113 (clear-stream _test-output-stream) +21114 (clear-stream $_test-output-buffered-file->buffer) +21115 $test-add-literal-to-reg:initialize-var-type: +21116 # var type/ecx: (payload type-tree) = int +21117 68/push 0/imm32/right:null +21118 68/push 0/imm32/right:null +21119 68/push 0/imm32/left:unused +21120 68/push 1/imm32/value:int +21121 68/push 1/imm32/is-atom?:true +21122 68/push 0x11/imm32/alloc-id:fake:payload +21123 89/<- %ecx 4/r32/esp +21124 $test-add-literal-to-reg:initialize-var: +21125 # var v/ecx: (payload var) +21126 68/push 0/imm32/register +21127 68/push 0/imm32/register +21128 68/push 0/imm32/no-stack-offset +21129 68/push 1/imm32/block-depth +21130 51/push-ecx +21131 68/push 0x11/imm32/alloc-id:fake +21132 68/push 0/imm32/name +21133 68/push 0/imm32/name +21134 68/push 0x11/imm32/alloc-id:fake:payload +21135 89/<- %ecx 4/r32/esp +21136 $test-add-literal-to-reg:initialize-var-name: +21137 # v->name = "v" +21138 8d/copy-address *(ecx+4) 0/r32/eax # Var-name + 4 +21139 (copy-array Heap "v" %eax) +21140 $test-add-literal-to-reg:initialize-var-register: +21141 # v->register = "ecx" +21142 8d/copy-address *(ecx+0x1c) 0/r32/eax # Var-register + 4 +21143 (copy-array Heap "ecx" %eax) +21144 $test-add-literal-to-reg:initialize-literal-type: +21145 # var type/edx: (payload type-tree) = literal +21146 68/push 0/imm32/right:null +21147 68/push 0/imm32/right:null +21148 68/push 0/imm32/left:unused +21149 68/push 0/imm32/value:literal +21150 68/push 1/imm32/is-atom?:true +21151 68/push 0x11/imm32/alloc-id:fake:payload +21152 89/<- %edx 4/r32/esp +21153 $test-add-literal-to-reg:initialize-literal: +21154 # var l/edx: (payload var) +21155 68/push 0/imm32/register +21156 68/push 0/imm32/register +21157 68/push 0/imm32/no-stack-offset +21158 68/push 1/imm32/block-depth +21159 52/push-edx +21160 68/push 0x11/imm32/alloc-id:fake +21161 68/push 0/imm32/name +21162 68/push 0/imm32/name +21163 68/push 0x11/imm32/alloc-id:fake:payload +21164 89/<- %edx 4/r32/esp +21165 $test-add-literal-to-reg:initialize-literal-value: +21166 # l->name = "0x34" +21167 8d/copy-address *(edx+4) 0/r32/eax # Var-name + 4 +21168 (copy-array Heap "0x34" %eax) +21169 $test-add-literal-to-reg:initialize-inouts: +21170 # var inouts/esi: (payload stmt-var) = [l] +21171 68/push 0/imm32/is-deref:false +21172 68/push 0/imm32/next +21173 68/push 0/imm32/next +21174 52/push-edx/l +21175 68/push 0x11/imm32/alloc-id:fake +21176 68/push 0x11/imm32/alloc-id:fake:payload +21177 89/<- %esi 4/r32/esp +21178 $test-add-literal-to-reg:initialize-outputs: +21179 # var outputs/edi: (payload stmt-var) = [v] +21180 68/push 0/imm32/is-deref:false +21181 68/push 0/imm32/next +21182 68/push 0/imm32/next +21183 51/push-ecx/v +21184 68/push 0x11/imm32/alloc-id:fake +21185 68/push 0x11/imm32/alloc-id:fake:payload +21186 89/<- %edi 4/r32/esp +21187 $test-add-literal-to-reg:initialize-stmt: +21188 # var stmt/esi: (addr statement) +21189 68/push 0/imm32/next +21190 68/push 0/imm32/next +21191 57/push-edi/outputs +21192 68/push 0x11/imm32/alloc-id:fake +21193 56/push-esi/inouts +21194 68/push 0x11/imm32/alloc-id:fake +21195 68/push 0/imm32/operation +21196 68/push 0/imm32/operation +21197 68/push 1/imm32/tag:stmt1 +21198 89/<- %esi 4/r32/esp +21199 $test-add-literal-to-reg:initialize-stmt-operation: +21200 # stmt->operation = "add" +21201 8d/copy-address *(esi+4) 0/r32/eax # Stmt1-operation +21202 (copy-array Heap "add" %eax) +21203 # convert +21204 c7 0/subop/copy *Curr-block-depth 0/imm32 +21205 (emit-subx-stmt _test-output-buffered-file %esi Primitives Stderr 0) +21206 (flush _test-output-buffered-file) +21207 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- +21213 # check output +21214 (check-next-stream-line-equal _test-output-stream "81 0/subop/add %ecx 0x34/imm32" "F - test-add-literal-to-reg") +21215 # . epilogue +21216 89/<- %esp 5/r32/ebp +21217 5d/pop-to-ebp +21218 c3/return +21219 +21220 test-add-literal-to-mem: +21221 # add-to var1, 0x34 +21222 # => +21223 # 81 0/subop/add %eax 0x34/imm32 +21224 # +21225 # . prologue +21226 55/push-ebp +21227 89/<- %ebp 4/r32/esp +21228 # setup +21229 (clear-stream _test-output-stream) +21230 (clear-stream $_test-output-buffered-file->buffer) +21231 $test-add-literal-to-mem:initialize-type: +21232 # var type/ecx: (payload type-tree) = int +21233 68/push 0/imm32/right:null +21234 68/push 0/imm32/right:null +21235 68/push 0/imm32/left:unused +21236 68/push 1/imm32/value:int +21237 68/push 1/imm32/is-atom?:true +21238 68/push 0x11/imm32/alloc-id:fake:payload +21239 89/<- %ecx 4/r32/esp +21240 $test-add-literal-to-mem:initialize-var1: +21241 # var var1/ecx: (payload var) +21242 68/push 0/imm32/register +21243 68/push 0/imm32/register +21244 68/push 8/imm32/stack-offset +21245 68/push 1/imm32/block-depth +21246 51/push-ecx +21247 68/push 0x11/imm32/alloc-id:fake +21248 68/push 0/imm32/name +21249 68/push 0/imm32/name +21250 68/push 0x11/imm32/alloc-id:fake:payload +21251 89/<- %ecx 4/r32/esp +21252 $test-add-literal-to-mem:initialize-var1-name: +21253 # var1->name = "var1" +21254 8d/copy-address *(ecx+4) 0/r32/eax # Var-name + 4 +21255 (copy-array Heap "var1" %eax) +21256 $test-add-literal-to-mem:initialize-literal-type: +21257 # var type/edx: (payload type-tree) = literal +21258 68/push 0/imm32/right:null +21259 68/push 0/imm32/right:null +21260 68/push 0/imm32/left:unused +21261 68/push 0/imm32/value:literal +21262 68/push 1/imm32/is-atom?:true +21263 68/push 0x11/imm32/alloc-id:fake:payload +21264 89/<- %edx 4/r32/esp +21265 $test-add-literal-to-mem:initialize-literal: +21266 # var l/edx: (payload var) +21267 68/push 0/imm32/register +21268 68/push 0/imm32/register +21269 68/push 0/imm32/no-stack-offset +21270 68/push 1/imm32/block-depth +21271 52/push-edx +21272 68/push 0x11/imm32/alloc-id:fake +21273 68/push 0/imm32/name +21274 68/push 0/imm32/name +21275 68/push 0x11/imm32/alloc-id:fake:payload +21276 89/<- %edx 4/r32/esp +21277 $test-add-literal-to-mem:initialize-literal-value: +21278 # l->name = "0x34" +21279 8d/copy-address *(edx+4) 0/r32/eax # Var-name + 4 +21280 (copy-array Heap "0x34" %eax) +21281 $test-add-literal-to-mem:initialize-inouts: +21282 # var inouts/esi: (payload stmt-var) = [l] +21283 68/push 0/imm32/is-deref:false +21284 68/push 0/imm32/next +21285 68/push 0/imm32/next +21286 52/push-edx/l +21287 68/push 0x11/imm32/alloc-id:fake +21288 68/push 0x11/imm32/alloc-id:fake:payload +21289 89/<- %esi 4/r32/esp +21290 # var inouts = (handle stmt-var) = [var1, var2] +21291 68/push 0/imm32/is-deref:false +21292 56/push-esi/next +21293 68/push 0x11/imm32/alloc-id:fake +21294 51/push-ecx/var1 +21295 68/push 0x11/imm32/alloc-id:fake +21296 68/push 0x11/imm32/alloc-id:fake:payload +21297 89/<- %esi 4/r32/esp +21298 $test-add-literal-to-mem:initialize-stmt: +21299 # var stmt/esi: (addr statement) +21300 68/push 0/imm32/next +21301 68/push 0/imm32/next +21302 68/push 0/imm32/outputs +21303 68/push 0/imm32/outputs +21304 56/push-esi/inouts +21305 68/push 0x11/imm32/alloc-id:fake +21306 68/push 0/imm32/operation +21307 68/push 0/imm32/operation +21308 68/push 1/imm32/tag:stmt1 +21309 89/<- %esi 4/r32/esp +21310 $test-add-literal-to-mem:initialize-stmt-operation: +21311 # stmt->operation = "add-to" +21312 8d/copy-address *(esi+4) 0/r32/eax # Stmt1-operation +21313 (copy-array Heap "add-to" %eax) +21314 # convert +21315 c7 0/subop/copy *Curr-block-depth 0/imm32 +21316 (emit-subx-stmt _test-output-buffered-file %esi Primitives Stderr 0) +21317 (flush _test-output-buffered-file) +21318 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- +21324 # check output +21325 (check-next-stream-line-equal _test-output-stream "81 0/subop/add *(ebp+0x00000008) 0x34/imm32" "F - test-add-literal-to-mem") +21326 # . epilogue +21327 89/<- %esp 5/r32/ebp +21328 5d/pop-to-ebp +21329 c3/return +21330 +21331 test-shift-reg-by-literal: +21332 # var1/ecx <- shift-left 2 +21333 # => +21334 # c1/shift 4/subop/left %ecx 2/imm8 +21335 # +21336 # . prologue +21337 55/push-ebp +21338 89/<- %ebp 4/r32/esp +21339 # setup +21340 (clear-stream _test-output-stream) +21341 (clear-stream $_test-output-buffered-file->buffer) +21342 $test-shift-reg-by-literal:initialize-var-type: +21343 # var type/ecx: (payload type-tree) = int +21344 68/push 0/imm32/right:null +21345 68/push 0/imm32/right:null +21346 68/push 0/imm32/left:unused +21347 68/push 1/imm32/value:int +21348 68/push 1/imm32/is-atom?:true +21349 68/push 0x11/imm32/alloc-id:fake:payload +21350 89/<- %ecx 4/r32/esp +21351 $test-shift-reg-by-literal:initialize-var: +21352 # var v/ecx: (payload var) +21353 68/push 0/imm32/register +21354 68/push 0/imm32/register +21355 68/push 0/imm32/no-stack-offset +21356 68/push 1/imm32/block-depth +21357 51/push-ecx +21358 68/push 0x11/imm32/alloc-id:fake +21359 68/push 0/imm32/name +21360 68/push 0/imm32/name +21361 68/push 0x11/imm32/alloc-id:fake:payload +21362 89/<- %ecx 4/r32/esp +21363 $test-shift-reg-by-literal:initialize-var-name: +21364 # v->name = "v" +21365 8d/copy-address *(ecx+4) 0/r32/eax # Var-name + 4 +21366 (copy-array Heap "v" %eax) +21367 $test-shift-reg-by-literal:initialize-var-register: +21368 # v->register = "ecx" +21369 8d/copy-address *(ecx+0x1c) 0/r32/eax # Var-register + 4 +21370 (copy-array Heap "ecx" %eax) +21371 $test-shift-reg-by-literal:initialize-literal-type: +21372 # var type/edx: (payload type-tree) = literal +21373 68/push 0/imm32/right:null +21374 68/push 0/imm32/right:null +21375 68/push 0/imm32/left:unused +21376 68/push 0/imm32/value:literal +21377 68/push 1/imm32/is-atom?:true +21378 68/push 0x11/imm32/alloc-id:fake:payload +21379 89/<- %edx 4/r32/esp +21380 $test-shift-reg-by-literal:initialize-literal: +21381 # var l/edx: (payload var) +21382 68/push 0/imm32/register +21383 68/push 0/imm32/register +21384 68/push 0/imm32/no-stack-offset +21385 68/push 1/imm32/block-depth +21386 52/push-edx +21387 68/push 0x11/imm32/alloc-id:fake +21388 68/push 0/imm32/name +21389 68/push 0/imm32/name +21390 68/push 0x11/imm32/alloc-id:fake:payload +21391 89/<- %edx 4/r32/esp +21392 $test-shift-reg-by-literal:initialize-literal-value: +21393 # l->name = "2" +21394 8d/copy-address *(edx+4) 0/r32/eax # Var-name + 4 +21395 (copy-array Heap "2" %eax) +21396 $test-shift-reg-by-literal:initialize-inouts: +21397 # var inouts/esi: (payload stmt-var) = [l] +21398 68/push 0/imm32/is-deref:false +21399 68/push 0/imm32/next +21400 68/push 0/imm32/next +21401 52/push-edx/l +21402 68/push 0x11/imm32/alloc-id:fake +21403 68/push 0x11/imm32/alloc-id:fake:payload +21404 89/<- %esi 4/r32/esp +21405 $test-shift-reg-by-literal:initialize-outputs: +21406 # var outputs/edi: (payload stmt-var) = [v] +21407 68/push 0/imm32/is-deref:false +21408 68/push 0/imm32/next +21409 68/push 0/imm32/next +21410 51/push-ecx/v +21411 68/push 0x11/imm32/alloc-id:fake +21412 68/push 0x11/imm32/alloc-id:fake:payload +21413 89/<- %edi 4/r32/esp +21414 $test-shift-reg-by-literal:initialize-stmt: +21415 # var stmt/esi: (addr statement) +21416 68/push 0/imm32/next +21417 68/push 0/imm32/next +21418 57/push-edi/outputs +21419 68/push 0x11/imm32/alloc-id:fake +21420 56/push-esi/inouts +21421 68/push 0x11/imm32/alloc-id:fake +21422 68/push 0/imm32/operation +21423 68/push 0/imm32/operation +21424 68/push 1/imm32/tag:stmt1 +21425 89/<- %esi 4/r32/esp +21426 $test-shift-reg-by-literal:initialize-stmt-operation: +21427 # stmt->operation = "shift-left" +21428 8d/copy-address *(esi+4) 0/r32/eax # Stmt1-operation +21429 (copy-array Heap "shift-left" %eax) +21430 # convert +21431 c7 0/subop/copy *Curr-block-depth 0/imm32 +21432 (emit-subx-stmt _test-output-buffered-file %esi Primitives Stderr 0) +21433 (flush _test-output-buffered-file) +21434 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- +21440 # check output +21441 (check-next-stream-line-equal _test-output-stream "c1/shift 4/subop/left %ecx 2/imm8" "F - test-shift-reg-by-literal") +21442 # . epilogue +21443 89/<- %esp 5/r32/ebp +21444 5d/pop-to-ebp +21445 c3/return +21446 +21447 test-shift-mem-by-literal: +21448 # shift-left var 3 +21449 # => +21450 # c1/shift 4/subop/left *(ebp+8) 3/imm8 +21451 # +21452 # . prologue +21453 55/push-ebp +21454 89/<- %ebp 4/r32/esp +21455 # setup +21456 (clear-stream _test-output-stream) +21457 (clear-stream $_test-output-buffered-file->buffer) +21458 $test-shift-mem-by-literal:initialize-type: +21459 # var type/ecx: (payload type-tree) = int +21460 68/push 0/imm32/right:null +21461 68/push 0/imm32/right:null +21462 68/push 0/imm32/left:unused +21463 68/push 1/imm32/value:int +21464 68/push 1/imm32/is-atom?:true +21465 68/push 0x11/imm32/alloc-id:fake:payload +21466 89/<- %ecx 4/r32/esp +21467 $test-shift-mem-by-literal:initialize-var1: +21468 # var var1/ecx: (payload var) +21469 68/push 0/imm32/register +21470 68/push 0/imm32/register +21471 68/push 8/imm32/stack-offset +21472 68/push 1/imm32/block-depth +21473 51/push-ecx +21474 68/push 0x11/imm32/alloc-id:fake +21475 68/push 0/imm32/name +21476 68/push 0/imm32/name +21477 68/push 0x11/imm32/alloc-id:fake:payload +21478 89/<- %ecx 4/r32/esp +21479 $test-shift-mem-by-literal:initialize-var1-name: +21480 # var1->name = "var1" +21481 8d/copy-address *(ecx+4) 0/r32/eax # Var-name + 4 +21482 (copy-array Heap "var1" %eax) +21483 $test-shift-mem-by-literal:initialize-literal-type: +21484 # var type/edx: (payload type-tree) = literal +21485 68/push 0/imm32/right:null +21486 68/push 0/imm32/right:null +21487 68/push 0/imm32/left:unused +21488 68/push 0/imm32/value:literal +21489 68/push 1/imm32/is-atom?:true +21490 68/push 0x11/imm32/alloc-id:fake:payload +21491 89/<- %edx 4/r32/esp +21492 $test-shift-mem-by-literal:initialize-literal: +21493 # var l/edx: (payload var) +21494 68/push 0/imm32/register +21495 68/push 0/imm32/register +21496 68/push 0/imm32/no-stack-offset +21497 68/push 1/imm32/block-depth +21498 52/push-edx +21499 68/push 0x11/imm32/alloc-id:fake +21500 68/push 0/imm32/name +21501 68/push 0/imm32/name +21502 68/push 0x11/imm32/alloc-id:fake:payload +21503 89/<- %edx 4/r32/esp +21504 $test-shift-mem-by-literal:initialize-literal-value: +21505 # l->name = "3" +21506 8d/copy-address *(edx+4) 0/r32/eax # Var-name + 4 +21507 (copy-array Heap "3" %eax) +21508 $test-shift-mem-by-literal:initialize-inouts: +21509 # var inouts/esi: (payload stmt-var) = [l] +21510 68/push 0/imm32/is-deref:false +21511 68/push 0/imm32/next +21512 68/push 0/imm32/next +21513 52/push-edx/l +21514 68/push 0x11/imm32/alloc-id:fake +21515 68/push 0x11/imm32/alloc-id:fake:payload +21516 89/<- %esi 4/r32/esp +21517 # var inouts = (handle stmt-var) = [var1, var2] +21518 68/push 0/imm32/is-deref:false +21519 56/push-esi/next +21520 68/push 0x11/imm32/alloc-id:fake +21521 51/push-ecx/var1 +21522 68/push 0x11/imm32/alloc-id:fake +21523 68/push 0x11/imm32/alloc-id:fake:payload +21524 89/<- %esi 4/r32/esp +21525 $test-shift-mem-by-literal:initialize-stmt: +21526 # var stmt/esi: (addr statement) +21527 68/push 0/imm32/next +21528 68/push 0/imm32/next +21529 68/push 0/imm32/outputs +21530 68/push 0/imm32/outputs +21531 56/push-esi/inouts +21532 68/push 0x11/imm32/alloc-id:fake +21533 68/push 0/imm32/operation +21534 68/push 0/imm32/operation +21535 68/push 1/imm32/tag:stmt1 +21536 89/<- %esi 4/r32/esp +21537 $test-shift-mem-by-literal:initialize-stmt-operation: +21538 # stmt->operation = "shift-left" +21539 8d/copy-address *(esi+4) 0/r32/eax # Stmt1-operation +21540 (copy-array Heap "shift-left" %eax) +21541 # convert +21542 c7 0/subop/copy *Curr-block-depth 0/imm32 +21543 (emit-subx-stmt _test-output-buffered-file %esi Primitives Stderr 0) +21544 (flush _test-output-buffered-file) +21545 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- +21551 # check output +21552 (check-next-stream-line-equal _test-output-stream "c1/shift 4/subop/left *(ebp+0x00000008) 3/imm8" "F - test-shift-mem-by-literal") +21553 # . epilogue +21554 89/<- %esp 5/r32/ebp +21555 5d/pop-to-ebp +21556 c3/return +21557 +21558 test-compare-reg-with-reg: +21559 # compare var1/ecx, var2/eax +21560 # => +21561 # 39/compare %ecx 0/r32/eax +21562 # +21563 # . prologue +21564 55/push-ebp +21565 89/<- %ebp 4/r32/esp +21566 # setup +21567 (clear-stream _test-output-stream) +21568 (clear-stream $_test-output-buffered-file->buffer) +21569 $test-compare-reg-with-reg:initialize-type: +21570 # var type/ecx: (payload type-tree) = int +21571 68/push 0/imm32/right:null +21572 68/push 0/imm32/right:null +21573 68/push 0/imm32/left:unused +21574 68/push 1/imm32/value:int +21575 68/push 1/imm32/is-atom?:true +21576 68/push 0x11/imm32/alloc-id:fake:payload +21577 89/<- %ecx 4/r32/esp +21578 $test-compare-reg-with-reg:initialize-var1: +21579 # var var1/ecx: (payload var) +21580 68/push 0/imm32/register +21581 68/push 0/imm32/register +21582 68/push 0/imm32/no-stack-offset +21583 68/push 1/imm32/block-depth +21584 51/push-ecx +21585 68/push 0x11/imm32/alloc-id:fake +21586 68/push 0/imm32/name +21587 68/push 0/imm32/name +21588 68/push 0x11/imm32/alloc-id:fake:payload +21589 89/<- %ecx 4/r32/esp +21590 $test-compare-reg-with-reg:initialize-var1-name: +21591 # var1->name = "var1" +21592 8d/copy-address *(ecx+4) 0/r32/eax # Var-name + 4 +21593 (copy-array Heap "var1" %eax) +21594 $test-compare-reg-with-reg:initialize-var1-register: +21595 # var1->register = "ecx" +21596 8d/copy-address *(ecx+0x1c) 0/r32/eax # Var-register + 4 +21597 (copy-array Heap "ecx" %eax) +21598 $test-compare-reg-with-reg:initialize-var2: +21599 # var var2/edx: (payload var) +21600 68/push 0/imm32/register +21601 68/push 0/imm32/register +21602 68/push 0/imm32/no-stack-offset +21603 68/push 1/imm32/block-depth +21604 ff 6/subop/push *(ecx+0x10) +21605 68/push 0x11/imm32/alloc-id:fake +21606 68/push 0/imm32/name +21607 68/push 0/imm32/name +21608 68/push 0x11/imm32/alloc-id:fake:payload +21609 89/<- %edx 4/r32/esp +21610 $test-compare-reg-with-reg:initialize-var2-name: +21611 # var2->name = "var2" +21612 8d/copy-address *(edx+4) 0/r32/eax # Var-name + 4 +21613 (copy-array Heap "var2" %eax) +21614 $test-compare-reg-with-reg:initialize-var2-register: +21615 # var2->register = "eax" +21616 8d/copy-address *(edx+0x1c) 0/r32/eax # Var-register + 4 +21617 (copy-array Heap "eax" %eax) +21618 $test-compare-reg-with-reg:initialize-inouts: +21619 # var inouts/esi: (payload stmt-var) = [var2] +21620 68/push 0/imm32/is-deref:false +21621 68/push 0/imm32/next +21622 68/push 0/imm32/next +21623 52/push-edx/var2 21624 68/push 0x11/imm32/alloc-id:fake -21625 68/push 0/imm32/name -21626 68/push 0/imm32/name -21627 68/push 0x11/imm32/alloc-id:fake:payload -21628 89/<- %ecx 4/r32/esp -21629 $test-compare-eax-with-literal:initialize-var1-name: -21630 # var1->name = "var1" -21631 8d/copy-address *(ecx+4) 0/r32/eax # Var-name + 4 -21632 (copy-array Heap "var1" %eax) -21633 $test-compare-eax-with-literal:initialize-var1-register: -21634 # v->register = "eax" -21635 8d/copy-address *(ecx+0x1c) 0/r32/eax # Var-register + 4 -21636 (copy-array Heap "eax" %eax) -21637 $test-compare-eax-with-literal:initialize-literal-type: -21638 # var type/edx: (payload type-tree) = literal -21639 68/push 0/imm32/right:null -21640 68/push 0/imm32/right:null -21641 68/push 0/imm32/left:unused -21642 68/push 0/imm32/value:literal -21643 68/push 1/imm32/is-atom?:true -21644 68/push 0x11/imm32/alloc-id:fake:payload -21645 89/<- %edx 4/r32/esp -21646 $test-compare-eax-with-literal:initialize-literal: -21647 # var l/edx: (payload var) -21648 68/push 0/imm32/register -21649 68/push 0/imm32/register -21650 68/push 0/imm32/no-stack-offset -21651 68/push 1/imm32/block-depth -21652 52/push-edx -21653 68/push 0x11/imm32/alloc-id:fake -21654 68/push 0/imm32/name -21655 68/push 0/imm32/name -21656 68/push 0x11/imm32/alloc-id:fake:payload -21657 89/<- %edx 4/r32/esp -21658 $test-compare-eax-with-literal:initialize-literal-value: -21659 # l->name = "0x34" -21660 8d/copy-address *(edx+4) 0/r32/eax # Var-name + 4 -21661 (copy-array Heap "0x34" %eax) -21662 $test-compare-eax-with-literal:initialize-inouts: -21663 # var inouts/esi: (payload stmt-var) = [l] -21664 68/push 0/imm32/is-deref:false -21665 68/push 0/imm32/next -21666 68/push 0/imm32/next -21667 52/push-edx/l -21668 68/push 0x11/imm32/alloc-id:fake -21669 68/push 0x11/imm32/alloc-id:fake:payload -21670 89/<- %esi 4/r32/esp -21671 # var inouts = (handle stmt-var) = [var1, var2] -21672 68/push 0/imm32/is-deref:false -21673 56/push-esi/next -21674 68/push 0x11/imm32/alloc-id:fake -21675 51/push-ecx/var1 -21676 68/push 0x11/imm32/alloc-id:fake -21677 68/push 0x11/imm32/alloc-id:fake:payload -21678 89/<- %esi 4/r32/esp -21679 $test-compare-eax-with-literal:initialize-stmt: -21680 # var stmt/esi: (addr statement) -21681 68/push 0/imm32/next -21682 68/push 0/imm32/next -21683 68/push 0/imm32/outputs -21684 68/push 0/imm32/outputs -21685 56/push-esi/inouts -21686 68/push 0x11/imm32/alloc-id:fake -21687 68/push 0/imm32/operation -21688 68/push 0/imm32/operation -21689 68/push 1/imm32/tag:stmt1 -21690 89/<- %esi 4/r32/esp -21691 $test-compare-eax-with-literal:initialize-stmt-operation: -21692 # stmt->operation = "compare" -21693 8d/copy-address *(esi+4) 0/r32/eax # Stmt1-operation -21694 (copy-array Heap "compare" %eax) -21695 # convert -21696 c7 0/subop/copy *Curr-block-depth 0/imm32 -21697 (emit-subx-stmt _test-output-buffered-file %esi Primitives Stderr 0) -21698 (flush _test-output-buffered-file) -21699 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- -21705 # check output -21706 (check-next-stream-line-equal _test-output-stream "3d/compare-eax-with 0x34/imm32" "F - test-compare-eax-with-literal") -21707 # . epilogue -21708 89/<- %esp 5/r32/ebp -21709 5d/pop-to-ebp -21710 c3/return -21711 -21712 test-compare-reg-with-literal: -21713 # compare var1/ecx 0x34 -21714 # => -21715 # 81 7/subop/compare %ecx 0x34/imm32 -21716 # -21717 # . prologue -21718 55/push-ebp -21719 89/<- %ebp 4/r32/esp -21720 # setup -21721 (clear-stream _test-output-stream) -21722 (clear-stream $_test-output-buffered-file->buffer) -21723 $test-compare-reg-with-literal:initialize-type: -21724 # var type/ecx: (payload type-tree) = int -21725 68/push 0/imm32/right:null -21726 68/push 0/imm32/right:null -21727 68/push 0/imm32/left:unused -21728 68/push 1/imm32/value:int -21729 68/push 1/imm32/is-atom?:true -21730 68/push 0x11/imm32/alloc-id:fake:payload -21731 89/<- %ecx 4/r32/esp -21732 $test-compare-reg-with-literal:initialize-var1: -21733 # var var1/ecx: (payload var) -21734 68/push 0/imm32/register -21735 68/push 0/imm32/register -21736 68/push 0/imm32/no-stack-offset -21737 68/push 1/imm32/block-depth -21738 51/push-ecx -21739 68/push 0x11/imm32/alloc-id:fake -21740 68/push 0/imm32/name -21741 68/push 0/imm32/name -21742 68/push 0x11/imm32/alloc-id:fake:payload -21743 89/<- %ecx 4/r32/esp -21744 $test-compare-reg-with-literal:initialize-var1-name: -21745 # var1->name = "var1" -21746 8d/copy-address *(ecx+4) 0/r32/eax # Var-name + 4 -21747 (copy-array Heap "var1" %eax) -21748 $test-compare-reg-with-literal:initialize-var1-register: -21749 # v->register = "ecx" -21750 8d/copy-address *(ecx+0x1c) 0/r32/eax # Var-register + 4 -21751 (copy-array Heap "ecx" %eax) -21752 $test-compare-reg-with-literal:initialize-literal-type: -21753 # var type/edx: (payload type-tree) = literal -21754 68/push 0/imm32/right:null -21755 68/push 0/imm32/right:null -21756 68/push 0/imm32/left:unused -21757 68/push 0/imm32/value:literal -21758 68/push 1/imm32/is-atom?:true -21759 68/push 0x11/imm32/alloc-id:fake:payload -21760 89/<- %edx 4/r32/esp -21761 $test-compare-reg-with-literal:initialize-literal: -21762 # var l/edx: (payload var) -21763 68/push 0/imm32/register -21764 68/push 0/imm32/register -21765 68/push 0/imm32/no-stack-offset -21766 68/push 1/imm32/block-depth -21767 52/push-edx -21768 68/push 0x11/imm32/alloc-id:fake -21769 68/push 0/imm32/name -21770 68/push 0/imm32/name -21771 68/push 0x11/imm32/alloc-id:fake:payload -21772 89/<- %edx 4/r32/esp -21773 $test-compare-reg-with-literal:initialize-literal-value: -21774 # l->name = "0x34" -21775 8d/copy-address *(edx+4) 0/r32/eax # Var-name + 4 -21776 (copy-array Heap "0x34" %eax) -21777 $test-compare-reg-with-literal:initialize-inouts: -21778 # var inouts/esi: (payload stmt-var) = [l] -21779 68/push 0/imm32/is-deref:false -21780 68/push 0/imm32/next -21781 68/push 0/imm32/next -21782 52/push-edx/l -21783 68/push 0x11/imm32/alloc-id:fake -21784 68/push 0x11/imm32/alloc-id:fake:payload -21785 89/<- %esi 4/r32/esp -21786 # var inouts = (handle stmt-var) = [var1, var2] -21787 68/push 0/imm32/is-deref:false -21788 56/push-esi/next -21789 68/push 0x11/imm32/alloc-id:fake -21790 51/push-ecx/var1 -21791 68/push 0x11/imm32/alloc-id:fake +21625 68/push 0x11/imm32/alloc-id:fake:payload +21626 89/<- %esi 4/r32/esp +21627 # inouts = [var1, var2] +21628 68/push 0/imm32/is-deref:false +21629 56/push-esi/next +21630 68/push 0x11/imm32/alloc-id:fake +21631 51/push-ecx/var1 +21632 68/push 0x11/imm32/alloc-id:fake +21633 68/push 0x11/imm32/alloc-id:fake:payload +21634 89/<- %esi 4/r32/esp +21635 $test-compare-reg-with-reg:initialize-stmt: +21636 # var stmt/esi: (addr statement) +21637 68/push 0/imm32/next +21638 68/push 0/imm32/next +21639 68/push 0/imm32/outputs +21640 68/push 0/imm32/outputs +21641 56/push-esi/inouts +21642 68/push 0x11/imm32/alloc-id:fake +21643 68/push 0/imm32/operation +21644 68/push 0/imm32/operation +21645 68/push 1/imm32/tag:stmt1 +21646 89/<- %esi 4/r32/esp +21647 $test-compare-reg-with-reg:initialize-stmt-operation: +21648 # stmt->operation = "compare" +21649 8d/copy-address *(esi+4) 0/r32/eax # Stmt1-operation +21650 (copy-array Heap "compare" %eax) +21651 # convert +21652 c7 0/subop/copy *Curr-block-depth 0/imm32 +21653 (emit-subx-stmt _test-output-buffered-file %esi Primitives Stderr 0) +21654 (flush _test-output-buffered-file) +21655 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- +21661 # check output +21662 (check-next-stream-line-equal _test-output-stream "39/compare-> %ecx 0x00000000/r32" "F - test-compare-reg-with-reg") +21663 # . epilogue +21664 89/<- %esp 5/r32/ebp +21665 5d/pop-to-ebp +21666 c3/return +21667 +21668 test-compare-mem-with-reg: +21669 # compare var1, var2/eax +21670 # => +21671 # 39/compare *(ebp+___) 0/r32/eax +21672 # +21673 # . prologue +21674 55/push-ebp +21675 89/<- %ebp 4/r32/esp +21676 # setup +21677 (clear-stream _test-output-stream) +21678 (clear-stream $_test-output-buffered-file->buffer) +21679 $test-compare-mem-with-reg:initialize-type: +21680 # var type/ecx: (payload type-tree) = int +21681 68/push 0/imm32/right:null +21682 68/push 0/imm32/right:null +21683 68/push 0/imm32/left:unused +21684 68/push 1/imm32/value:int +21685 68/push 1/imm32/is-atom?:true +21686 68/push 0x11/imm32/alloc-id:fake:payload +21687 89/<- %ecx 4/r32/esp +21688 $test-compare-mem-with-reg:initialize-var1: +21689 # var var1/ecx: (payload var) +21690 68/push 0/imm32/register +21691 68/push 0/imm32/register +21692 68/push 8/imm32/stack-offset +21693 68/push 1/imm32/block-depth +21694 51/push-ecx +21695 68/push 0x11/imm32/alloc-id:fake +21696 68/push 0/imm32/name +21697 68/push 0/imm32/name +21698 68/push 0x11/imm32/alloc-id:fake:payload +21699 89/<- %ecx 4/r32/esp +21700 $test-compare-mem-with-reg:initialize-var1-name: +21701 # var1->name = "var1" +21702 8d/copy-address *(ecx+4) 0/r32/eax # Var-name + 4 +21703 (copy-array Heap "var1" %eax) +21704 $test-compare-mem-with-reg:initialize-var2: +21705 # var var2/edx: (payload var) +21706 68/push 0/imm32/register +21707 68/push 0/imm32/register +21708 68/push 0/imm32/no-stack-offset +21709 68/push 1/imm32/block-depth +21710 ff 6/subop/push *(ecx+0x10) +21711 68/push 0x11/imm32/alloc-id:fake +21712 68/push 0/imm32/name +21713 68/push 0/imm32/name +21714 68/push 0x11/imm32/alloc-id:fake:payload +21715 89/<- %edx 4/r32/esp +21716 $test-compare-mem-with-reg:initialize-var2-name: +21717 # var2->name = "var2" +21718 8d/copy-address *(edx+4) 0/r32/eax # Var-name + 4 +21719 (copy-array Heap "var2" %eax) +21720 $test-compare-mem-with-reg:initialize-var2-register: +21721 # var2->register = "eax" +21722 8d/copy-address *(edx+0x1c) 0/r32/eax # Var-register + 4 +21723 (copy-array Heap "eax" %eax) +21724 $test-compare-mem-with-reg:initialize-inouts: +21725 # var inouts/esi: (payload stmt-var) = [var2] +21726 68/push 0/imm32/is-deref:false +21727 68/push 0/imm32/next +21728 68/push 0/imm32/next +21729 52/push-edx/var2 +21730 68/push 0x11/imm32/alloc-id:fake +21731 68/push 0x11/imm32/alloc-id:fake:payload +21732 89/<- %esi 4/r32/esp +21733 # inouts = [var1, var2] +21734 68/push 0/imm32/is-deref:false +21735 56/push-esi/next +21736 68/push 0x11/imm32/alloc-id:fake +21737 51/push-ecx/var1 +21738 68/push 0x11/imm32/alloc-id:fake +21739 68/push 0x11/imm32/alloc-id:fake:payload +21740 89/<- %esi 4/r32/esp +21741 $test-compare-mem-with-reg:initialize-stmt: +21742 # var stmt/esi: (addr statement) +21743 68/push 0/imm32/next +21744 68/push 0/imm32/next +21745 68/push 0/imm32/outputs +21746 68/push 0/imm32/outputs +21747 56/push-esi/inouts +21748 68/push 0x11/imm32/alloc-id:fake +21749 68/push 0/imm32/operation +21750 68/push 0/imm32/operation +21751 68/push 1/imm32/tag:stmt1 +21752 89/<- %esi 4/r32/esp +21753 $test-compare-mem-with-reg:initialize-stmt-operation: +21754 # stmt->operation = "compare" +21755 8d/copy-address *(esi+4) 0/r32/eax # Stmt1-operation +21756 (copy-array Heap "compare" %eax) +21757 # convert +21758 c7 0/subop/copy *Curr-block-depth 0/imm32 +21759 (emit-subx-stmt _test-output-buffered-file %esi Primitives Stderr 0) +21760 (flush _test-output-buffered-file) +21761 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- +21767 # check output +21768 (check-next-stream-line-equal _test-output-stream "39/compare-> *(ebp+0x00000008) 0x00000000/r32" "F - test-compare-mem-with-reg") +21769 # . epilogue +21770 89/<- %esp 5/r32/ebp +21771 5d/pop-to-ebp +21772 c3/return +21773 +21774 test-compare-reg-with-mem: +21775 # compare var1/eax, var2 +21776 # => +21777 # 3b/compare<- *(ebp+___) 0/r32/eax +21778 # +21779 # . prologue +21780 55/push-ebp +21781 89/<- %ebp 4/r32/esp +21782 # setup +21783 (clear-stream _test-output-stream) +21784 (clear-stream $_test-output-buffered-file->buffer) +21785 $test-compare-reg-with-mem:initialize-type: +21786 # var type/ecx: (payload type-tree) = int +21787 68/push 0/imm32/right:null +21788 68/push 0/imm32/right:null +21789 68/push 0/imm32/left:unused +21790 68/push 1/imm32/value:int +21791 68/push 1/imm32/is-atom?:true 21792 68/push 0x11/imm32/alloc-id:fake:payload -21793 89/<- %esi 4/r32/esp -21794 $test-compare-reg-with-literal:initialize-stmt: -21795 # var stmt/esi: (addr statement) -21796 68/push 0/imm32/next -21797 68/push 0/imm32/next -21798 68/push 0/imm32/outputs -21799 68/push 0/imm32/outputs -21800 56/push-esi/inouts +21793 89/<- %ecx 4/r32/esp +21794 $test-compare-reg-with-mem:initialize-var1: +21795 # var var1/ecx: (payload var) +21796 68/push 0/imm32/register +21797 68/push 0/imm32/register +21798 68/push 0/imm32/no-stack-offset +21799 68/push 1/imm32/block-depth +21800 51/push-ecx 21801 68/push 0x11/imm32/alloc-id:fake -21802 68/push 0/imm32/operation -21803 68/push 0/imm32/operation -21804 68/push 1/imm32/tag:stmt1 -21805 89/<- %esi 4/r32/esp -21806 $test-compare-reg-with-literal:initialize-stmt-operation: -21807 # stmt->operation = "compare" -21808 8d/copy-address *(esi+4) 0/r32/eax # Stmt1-operation -21809 (copy-array Heap "compare" %eax) -21810 # convert -21811 c7 0/subop/copy *Curr-block-depth 0/imm32 -21812 (emit-subx-stmt _test-output-buffered-file %esi Primitives Stderr 0) -21813 (flush _test-output-buffered-file) -21814 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- -21820 # check output -21821 (check-next-stream-line-equal _test-output-stream "81 7/subop/compare %ecx 0x34/imm32" "F - test-compare-reg-with-literal") -21822 # . epilogue -21823 89/<- %esp 5/r32/ebp -21824 5d/pop-to-ebp -21825 c3/return -21826 -21827 test-emit-subx-stmt-function-call: -21828 # Call a function on a variable on the stack. -21829 # f foo -21830 # => -21831 # (f *(ebp-8)) -21832 # (Changing the function name supports overloading in general, but here it -21833 # just serves to help disambiguate things.) -21834 # -21835 # There's a variable on the var stack as follows: -21836 # name: 'foo' -21837 # type: int -21838 # stack-offset: -8 -21839 # -21840 # There's nothing in primitives. -21841 # -21842 # We don't perform any checking here on the type of 'f'. -21843 # -21844 # . prologue -21845 55/push-ebp -21846 89/<- %ebp 4/r32/esp -21847 # setup -21848 (clear-stream _test-output-stream) -21849 (clear-stream $_test-output-buffered-file->buffer) -21850 $test-emit-subx-function-call:initialize-type: -21851 # var type/ecx: (payload type-tree) = int -21852 68/push 0/imm32/right:null -21853 68/push 0/imm32/right:null -21854 68/push 0/imm32/left:unused -21855 68/push 1/imm32/value:int -21856 68/push 1/imm32/is-atom?:true -21857 68/push 0x11/imm32/alloc-id:fake:payload -21858 89/<- %ecx 4/r32/esp -21859 $test-emit-subx-function-call:initialize-var: -21860 # var var-foo/ecx: (payload var) = var(type) -21861 68/push 0/imm32/no-register -21862 68/push 0/imm32/no-register -21863 68/push -8/imm32/stack-offset -21864 68/push 1/imm32/block-depth -21865 51/push-ecx/type -21866 68/push 0x11/imm32/alloc-id:fake -21867 68/push 0/imm32/name -21868 68/push 0/imm32/name -21869 68/push 0x11/imm32/alloc-id:fake:payload -21870 89/<- %ecx 4/r32/esp -21871 $test-emit-subx-function-call:initialize-var-name: -21872 # var-foo->name = "foo" -21873 8d/copy-address *(ecx+4) 0/r32/eax # Var-name + 4 -21874 (copy-array Heap "foo" %eax) -21875 $test-emit-subx-function-call:initialize-stmt-var: -21876 # var operand/ebx: (payload stmt-var) = stmt-var(var-foo) -21877 68/push 0/imm32/is-deref:false -21878 68/push 0/imm32/next -21879 68/push 0/imm32/next -21880 51/push-ecx/var-foo -21881 68/push 0x11/imm32/alloc-id:fake -21882 68/push 0x11/imm32/alloc-id:fake:payload -21883 89/<- %ebx 4/r32/esp -21884 $test-emit-subx-function-call:initialize-stmt: -21885 # var stmt/esi: (addr statement) -21886 68/push 0/imm32/no-outputs -21887 68/push 0/imm32/no-outputs -21888 53/push-ebx/inouts -21889 68/push 0x11/imm32/alloc-id:fake -21890 68/push 0/imm32/operation -21891 68/push 0/imm32/operation -21892 68/push 1/imm32/tag -21893 89/<- %esi 4/r32/esp -21894 $test-emit-subx-function-call:initialize-stmt-operation: -21895 # stmt->operation = "f" -21896 8d/copy-address *(esi+4) 0/r32/eax # Stmt1-operation -21897 (copy-array Heap "f" %eax) -21898 # convert -21899 c7 0/subop/copy *Curr-block-depth 0/imm32 -21900 (emit-subx-stmt _test-output-buffered-file %esi 0 Stderr 0) -21901 (flush _test-output-buffered-file) -21902 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- -21908 # check output -21909 (check-next-stream-line-equal _test-output-stream "(f *(ebp+0xfffffff8))" "F - test-emit-subx-stmt-function-call") -21910 # . epilogue -21911 89/<- %esp 5/r32/ebp -21912 5d/pop-to-ebp -21913 c3/return -21914 -21915 test-emit-subx-stmt-function-call-with-literal-arg: -21916 # Call a function on a literal. -21917 # f 0x34 -21918 # => -21919 # (f2 0x34) -21920 # -21921 # . prologue -21922 55/push-ebp -21923 89/<- %ebp 4/r32/esp -21924 # setup -21925 (clear-stream _test-output-stream) -21926 (clear-stream $_test-output-buffered-file->buffer) -21927 $test-emit-subx-function-call-with-literal-arg:initialize-type: -21928 # var type/ecx: (payload type-tree) = int -21929 68/push 0/imm32/right:null -21930 68/push 0/imm32/right:null -21931 68/push 0/imm32/left:unused -21932 68/push 0/imm32/value:literal -21933 68/push 1/imm32/is-atom?:true -21934 68/push 0x11/imm32/alloc-id:fake:payload -21935 89/<- %ecx 4/r32/esp -21936 $test-emit-subx-function-call-with-literal-arg:initialize-var: -21937 # var var-foo/ecx: (payload var) = var(lit) -21938 68/push 0/imm32/no-register -21939 68/push 0/imm32/no-register -21940 68/push 0/imm32/no-stack-offset -21941 68/push 1/imm32/block-depth -21942 51/push-ecx/type -21943 68/push 0x11/imm32/alloc-id:fake -21944 68/push 0/imm32/name -21945 68/push 0/imm32/name -21946 68/push 0x11/imm32/alloc-id:fake:payload -21947 89/<- %ecx 4/r32/esp -21948 $test-emit-subx-function-call-with-literal-arg:initialize-var-name: -21949 # var-foo->name = "0x34" -21950 8d/copy-address *(ecx+4) 0/r32/eax # Var-name + 4 -21951 (copy-array Heap "0x34" %eax) -21952 $test-emit-subx-function-call-with-literal-arg:initialize-stmt-var: -21953 # var operand/ebx: (payload stmt-var) = stmt-var(var-foo) -21954 68/push 0/imm32/is-deref:false -21955 68/push 0/imm32/next -21956 68/push 0/imm32/next -21957 51/push-ecx/var-foo -21958 68/push 0x11/imm32/alloc-id:fake -21959 68/push 0x11/imm32/alloc-id:fake:payload -21960 89/<- %ebx 4/r32/esp -21961 $test-emit-subx-function-call-with-literal-arg:initialize-stmt: -21962 # var stmt/esi: (addr statement) -21963 68/push 0/imm32/no-outputs -21964 68/push 0/imm32/no-outputs -21965 53/push-ebx/inouts -21966 68/push 0x11/imm32/alloc-id:fake +21802 68/push 0/imm32/name +21803 68/push 0/imm32/name +21804 68/push 0x11/imm32/alloc-id:fake:payload +21805 89/<- %ecx 4/r32/esp +21806 $test-compare-reg-with-mem:initialize-var1-name: +21807 # var1->name = "var1" +21808 8d/copy-address *(ecx+4) 0/r32/eax # Var-name + 4 +21809 (copy-array Heap "var1" %eax) +21810 $test-compare-reg-with-mem:initialize-var1-register: +21811 # var1->register = "eax" +21812 8d/copy-address *(ecx+0x1c) 0/r32/eax # Var-register + 4 +21813 (copy-array Heap "eax" %eax) +21814 $test-compare-reg-with-mem:initialize-var2: +21815 # var var2/edx: (payload var) +21816 68/push 0/imm32/register +21817 68/push 0/imm32/register +21818 68/push 8/imm32/stack-offset +21819 68/push 1/imm32/block-depth +21820 ff 6/subop/push *(ecx+0x10) +21821 68/push 0x11/imm32/alloc-id:fake +21822 68/push 0/imm32/name +21823 68/push 0/imm32/name +21824 68/push 0x11/imm32/alloc-id:fake:payload +21825 89/<- %edx 4/r32/esp +21826 $test-compare-reg-with-mem:initialize-var2-name: +21827 # var2->name = "var2" +21828 8d/copy-address *(edx+4) 0/r32/eax # Var-name + 4 +21829 (copy-array Heap "var2" %eax) +21830 $test-compare-reg-with-mem:initialize-inouts: +21831 # var inouts/esi: (payload stmt-var) = [var2] +21832 68/push 0/imm32/is-deref:false +21833 68/push 0/imm32/next +21834 68/push 0/imm32/next +21835 52/push-edx/var2 +21836 68/push 0x11/imm32/alloc-id:fake +21837 68/push 0x11/imm32/alloc-id:fake:payload +21838 89/<- %esi 4/r32/esp +21839 # inouts = [var1, var2] +21840 68/push 0/imm32/is-deref:false +21841 56/push-esi/next +21842 68/push 0x11/imm32/alloc-id:fake +21843 51/push-ecx/var1 +21844 68/push 0x11/imm32/alloc-id:fake +21845 68/push 0x11/imm32/alloc-id:fake:payload +21846 89/<- %esi 4/r32/esp +21847 $test-compare-reg-with-mem:initialize-stmt: +21848 # var stmt/esi: (addr statement) +21849 68/push 0/imm32/next +21850 68/push 0/imm32/next +21851 68/push 0/imm32/outputs +21852 68/push 0/imm32/outputs +21853 56/push-esi/inouts +21854 68/push 0x11/imm32/alloc-id:fake +21855 68/push 0/imm32/operation +21856 68/push 0/imm32/operation +21857 68/push 1/imm32/tag:stmt1 +21858 89/<- %esi 4/r32/esp +21859 $test-compare-reg-with-mem:initialize-stmt-operation: +21860 # stmt->operation = "compare" +21861 8d/copy-address *(esi+4) 0/r32/eax # Stmt1-operation +21862 (copy-array Heap "compare" %eax) +21863 # convert +21864 c7 0/subop/copy *Curr-block-depth 0/imm32 +21865 (emit-subx-stmt _test-output-buffered-file %esi Primitives Stderr 0) +21866 (flush _test-output-buffered-file) +21867 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- +21873 # check output +21874 (check-next-stream-line-equal _test-output-stream "3b/compare<- *(ebp+0x00000008) 0x00000000/r32" "F - test-compare-reg-with-mem") +21875 # . epilogue +21876 89/<- %esp 5/r32/ebp +21877 5d/pop-to-ebp +21878 c3/return +21879 +21880 test-compare-mem-with-literal: +21881 # compare var1, 0x34 +21882 # => +21883 # 81 7/subop/compare *(ebp+___) 0x34/imm32 +21884 # +21885 # . prologue +21886 55/push-ebp +21887 89/<- %ebp 4/r32/esp +21888 # setup +21889 (clear-stream _test-output-stream) +21890 (clear-stream $_test-output-buffered-file->buffer) +21891 $test-compare-mem-with-literal:initialize-type: +21892 # var type/ecx: (payload type-tree) = int +21893 68/push 0/imm32/right:null +21894 68/push 0/imm32/right:null +21895 68/push 0/imm32/left:unused +21896 68/push 1/imm32/value:int +21897 68/push 1/imm32/is-atom?:true +21898 68/push 0x11/imm32/alloc-id:fake:payload +21899 89/<- %ecx 4/r32/esp +21900 $test-compare-mem-with-literal:initialize-var1: +21901 # var var1/ecx: (payload var) +21902 68/push 0/imm32/register +21903 68/push 0/imm32/register +21904 68/push 8/imm32/stack-offset +21905 68/push 1/imm32/block-depth +21906 51/push-ecx +21907 68/push 0x11/imm32/alloc-id:fake +21908 68/push 0/imm32/name +21909 68/push 0/imm32/name +21910 68/push 0x11/imm32/alloc-id:fake:payload +21911 89/<- %ecx 4/r32/esp +21912 $test-compare-mem-with-literal:initialize-var1-name: +21913 # var1->name = "var1" +21914 8d/copy-address *(ecx+4) 0/r32/eax # Var-name + 4 +21915 (copy-array Heap "var1" %eax) +21916 $test-compare-mem-with-literal:initialize-literal-type: +21917 # var type/edx: (payload type-tree) = literal +21918 68/push 0/imm32/right:null +21919 68/push 0/imm32/right:null +21920 68/push 0/imm32/left:unused +21921 68/push 0/imm32/value:literal +21922 68/push 1/imm32/is-atom?:true +21923 68/push 0x11/imm32/alloc-id:fake:payload +21924 89/<- %edx 4/r32/esp +21925 $test-compare-mem-with-literal:initialize-literal: +21926 # var l/edx: (payload var) +21927 68/push 0/imm32/register +21928 68/push 0/imm32/register +21929 68/push 0/imm32/no-stack-offset +21930 68/push 1/imm32/block-depth +21931 52/push-edx +21932 68/push 0x11/imm32/alloc-id:fake +21933 68/push 0/imm32/name +21934 68/push 0/imm32/name +21935 68/push 0x11/imm32/alloc-id:fake:payload +21936 89/<- %edx 4/r32/esp +21937 $test-compare-mem-with-literal:initialize-literal-value: +21938 # l->name = "0x34" +21939 8d/copy-address *(edx+4) 0/r32/eax # Var-name + 4 +21940 (copy-array Heap "0x34" %eax) +21941 $test-compare-mem-with-literal:initialize-inouts: +21942 # var inouts/esi: (payload stmt-var) = [l] +21943 68/push 0/imm32/is-deref:false +21944 68/push 0/imm32/next +21945 68/push 0/imm32/next +21946 52/push-edx/l +21947 68/push 0x11/imm32/alloc-id:fake +21948 68/push 0x11/imm32/alloc-id:fake:payload +21949 89/<- %esi 4/r32/esp +21950 # var inouts = (handle stmt-var) = [var1, var2] +21951 68/push 0/imm32/is-deref:false +21952 56/push-esi/next +21953 68/push 0x11/imm32/alloc-id:fake +21954 51/push-ecx/var1 +21955 68/push 0x11/imm32/alloc-id:fake +21956 68/push 0x11/imm32/alloc-id:fake:payload +21957 89/<- %esi 4/r32/esp +21958 $test-compare-mem-with-literal:initialize-stmt: +21959 # var stmt/esi: (addr statement) +21960 68/push 0/imm32/next +21961 68/push 0/imm32/next +21962 68/push 0/imm32/outputs +21963 68/push 0/imm32/outputs +21964 56/push-esi/inouts +21965 68/push 0x11/imm32/alloc-id:fake +21966 68/push 0/imm32/operation 21967 68/push 0/imm32/operation -21968 68/push 0/imm32/operation -21969 68/push 1/imm32/tag -21970 89/<- %esi 4/r32/esp -21971 $test-emit-subx-function-call-with-literal-arg:initialize-stmt-operation: -21972 # stmt->operation = "f" -21973 8d/copy-address *(esi+4) 0/r32/eax # Stmt1-operation -21974 (copy-array Heap "f" %eax) -21975 # convert -21976 c7 0/subop/copy *Curr-block-depth 0/imm32 -21977 (emit-subx-stmt _test-output-buffered-file %esi 0 %ebx Stderr 0) -21978 (flush _test-output-buffered-file) -21979 +-- 6 lines: #? # dump _test-output-stream -------------------------------------------------------------------------------------------------------------------------------------------------------------------- -21985 # check output -21986 (check-next-stream-line-equal _test-output-stream "(f 0x34)" "F - test-emit-subx-stmt-function-call-with-literal-arg") -21987 # . epilogue -21988 89/<- %esp 5/r32/ebp -21989 5d/pop-to-ebp -21990 c3/return -21991 -21992 emit-indent: # out: (addr buffered-file), n: int -21993 # . prologue -21994 55/push-ebp -21995 89/<- %ebp 4/r32/esp -21996 # . save registers -21997 50/push-eax -21998 # var i/eax: int = n -21999 8b/-> *(ebp+0xc) 0/r32/eax -22000 { -22001 # if (i <= 0) break -22002 3d/compare-eax-with 0/imm32 -22003 7e/jump-if-<= break/disp8 -22004 (write-buffered *(ebp+8) " ") -22005 48/decrement-eax -22006 eb/jump loop/disp8 -22007 } -22008 $emit-indent:end: -22009 # . restore registers -22010 58/pop-to-eax -22011 # . epilogue -22012 89/<- %esp 5/r32/ebp -22013 5d/pop-to-ebp -22014 c3/return -22015 -22016 emit-subx-prologue: # out: (addr buffered-file) -22017 # . prologue -22018 55/push-ebp -22019 89/<- %ebp 4/r32/esp -22020 # -22021 (write-buffered *(ebp+8) " # . prologue\n") -22022 (write-buffered *(ebp+8) " 55/push-ebp\n") -22023 (write-buffered *(ebp+8) " 89/<- %ebp 4/r32/esp\n") -22024 $emit-subx-prologue:end: -22025 # . epilogue -22026 89/<- %esp 5/r32/ebp -22027 5d/pop-to-ebp -22028 c3/return -22029 -22030 emit-subx-epilogue: # out: (addr buffered-file) -22031 # . prologue -22032 55/push-ebp -22033 89/<- %ebp 4/r32/esp -22034 # -22035 (write-buffered *(ebp+8) " # . epilogue\n") -22036 (write-buffered *(ebp+8) " 89/<- %esp 5/r32/ebp\n") -22037 (write-buffered *(ebp+8) " 5d/pop-to-ebp\n") -22038 (write-buffered *(ebp+8) " c3/return\n") -22039 $emit-subx-epilogue:end: -22040 # . epilogue -22041 89/<- %esp 5/r32/ebp -22042 5d/pop-to-ebp -22043 c3/return +21968 68/push 1/imm32/tag:stmt1 +21969 89/<- %esi 4/r32/esp +21970 $test-compare-mem-with-literal:initialize-stmt-operation: +21971 # stmt->operation = "compare" +21972 8d/copy-address *(esi+4) 0/r32/eax # Stmt1-operation +21973 (copy-array Heap "compare" %eax) +21974 # convert +21975 c7 0/subop/copy *Curr-block-depth 0/imm32 +21976 (emit-subx-stmt _test-output-buffered-file %esi Primitives Stderr 0) +21977 (flush _test-output-buffered-file) +21978 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- +21984 # check output +21985 (check-next-stream-line-equal _test-output-stream "81 7/subop/compare *(ebp+0x00000008) 0x34/imm32" "F - test-compare-mem-with-literal") +21986 # . epilogue +21987 89/<- %esp 5/r32/ebp +21988 5d/pop-to-ebp +21989 c3/return +21990 +21991 test-compare-eax-with-literal: +21992 # compare var1/eax 0x34 +21993 # => +21994 # 3d/compare-eax-with 0x34/imm32 +21995 # +21996 # . prologue +21997 55/push-ebp +21998 89/<- %ebp 4/r32/esp +21999 # setup +22000 (clear-stream _test-output-stream) +22001 (clear-stream $_test-output-buffered-file->buffer) +22002 $test-compare-eax-with-literal:initialize-type: +22003 # var type/ecx: (payload type-tree) = int +22004 68/push 0/imm32/right:null +22005 68/push 0/imm32/right:null +22006 68/push 0/imm32/left:unused +22007 68/push 1/imm32/value:int +22008 68/push 1/imm32/is-atom?:true +22009 68/push 0x11/imm32/alloc-id:fake:payload +22010 89/<- %ecx 4/r32/esp +22011 $test-compare-eax-with-literal:initialize-var1: +22012 # var var1/ecx: (payload var) +22013 68/push 0/imm32/register +22014 68/push 0/imm32/register +22015 68/push 0/imm32/no-stack-offset +22016 68/push 1/imm32/block-depth +22017 51/push-ecx +22018 68/push 0x11/imm32/alloc-id:fake +22019 68/push 0/imm32/name +22020 68/push 0/imm32/name +22021 68/push 0x11/imm32/alloc-id:fake:payload +22022 89/<- %ecx 4/r32/esp +22023 $test-compare-eax-with-literal:initialize-var1-name: +22024 # var1->name = "var1" +22025 8d/copy-address *(ecx+4) 0/r32/eax # Var-name + 4 +22026 (copy-array Heap "var1" %eax) +22027 $test-compare-eax-with-literal:initialize-var1-register: +22028 # v->register = "eax" +22029 8d/copy-address *(ecx+0x1c) 0/r32/eax # Var-register + 4 +22030 (copy-array Heap "eax" %eax) +22031 $test-compare-eax-with-literal:initialize-literal-type: +22032 # var type/edx: (payload type-tree) = literal +22033 68/push 0/imm32/right:null +22034 68/push 0/imm32/right:null +22035 68/push 0/imm32/left:unused +22036 68/push 0/imm32/value:literal +22037 68/push 1/imm32/is-atom?:true +22038 68/push 0x11/imm32/alloc-id:fake:payload +22039 89/<- %edx 4/r32/esp +22040 $test-compare-eax-with-literal:initialize-literal: +22041 # var l/edx: (payload var) +22042 68/push 0/imm32/register +22043 68/push 0/imm32/register +22044 68/push 0/imm32/no-stack-offset +22045 68/push 1/imm32/block-depth +22046 52/push-edx +22047 68/push 0x11/imm32/alloc-id:fake +22048 68/push 0/imm32/name +22049 68/push 0/imm32/name +22050 68/push 0x11/imm32/alloc-id:fake:payload +22051 89/<- %edx 4/r32/esp +22052 $test-compare-eax-with-literal:initialize-literal-value: +22053 # l->name = "0x34" +22054 8d/copy-address *(edx+4) 0/r32/eax # Var-name + 4 +22055 (copy-array Heap "0x34" %eax) +22056 $test-compare-eax-with-literal:initialize-inouts: +22057 # var inouts/esi: (payload stmt-var) = [l] +22058 68/push 0/imm32/is-deref:false +22059 68/push 0/imm32/next +22060 68/push 0/imm32/next +22061 52/push-edx/l +22062 68/push 0x11/imm32/alloc-id:fake +22063 68/push 0x11/imm32/alloc-id:fake:payload +22064 89/<- %esi 4/r32/esp +22065 # var inouts = (handle stmt-var) = [var1, var2] +22066 68/push 0/imm32/is-deref:false +22067 56/push-esi/next +22068 68/push 0x11/imm32/alloc-id:fake +22069 51/push-ecx/var1 +22070 68/push 0x11/imm32/alloc-id:fake +22071 68/push 0x11/imm32/alloc-id:fake:payload +22072 89/<- %esi 4/r32/esp +22073 $test-compare-eax-with-literal:initialize-stmt: +22074 # var stmt/esi: (addr statement) +22075 68/push 0/imm32/next +22076 68/push 0/imm32/next +22077 68/push 0/imm32/outputs +22078 68/push 0/imm32/outputs +22079 56/push-esi/inouts +22080 68/push 0x11/imm32/alloc-id:fake +22081 68/push 0/imm32/operation +22082 68/push 0/imm32/operation +22083 68/push 1/imm32/tag:stmt1 +22084 89/<- %esi 4/r32/esp +22085 $test-compare-eax-with-literal:initialize-stmt-operation: +22086 # stmt->operation = "compare" +22087 8d/copy-address *(esi+4) 0/r32/eax # Stmt1-operation +22088 (copy-array Heap "compare" %eax) +22089 # convert +22090 c7 0/subop/copy *Curr-block-depth 0/imm32 +22091 (emit-subx-stmt _test-output-buffered-file %esi Primitives Stderr 0) +22092 (flush _test-output-buffered-file) +22093 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- +22099 # check output +22100 (check-next-stream-line-equal _test-output-stream "3d/compare-eax-with 0x34/imm32" "F - test-compare-eax-with-literal") +22101 # . epilogue +22102 89/<- %esp 5/r32/ebp +22103 5d/pop-to-ebp +22104 c3/return +22105 +22106 test-compare-reg-with-literal: +22107 # compare var1/ecx 0x34 +22108 # => +22109 # 81 7/subop/compare %ecx 0x34/imm32 +22110 # +22111 # . prologue +22112 55/push-ebp +22113 89/<- %ebp 4/r32/esp +22114 # setup +22115 (clear-stream _test-output-stream) +22116 (clear-stream $_test-output-buffered-file->buffer) +22117 $test-compare-reg-with-literal:initialize-type: +22118 # var type/ecx: (payload type-tree) = int +22119 68/push 0/imm32/right:null +22120 68/push 0/imm32/right:null +22121 68/push 0/imm32/left:unused +22122 68/push 1/imm32/value:int +22123 68/push 1/imm32/is-atom?:true +22124 68/push 0x11/imm32/alloc-id:fake:payload +22125 89/<- %ecx 4/r32/esp +22126 $test-compare-reg-with-literal:initialize-var1: +22127 # var var1/ecx: (payload var) +22128 68/push 0/imm32/register +22129 68/push 0/imm32/register +22130 68/push 0/imm32/no-stack-offset +22131 68/push 1/imm32/block-depth +22132 51/push-ecx +22133 68/push 0x11/imm32/alloc-id:fake +22134 68/push 0/imm32/name +22135 68/push 0/imm32/name +22136 68/push 0x11/imm32/alloc-id:fake:payload +22137 89/<- %ecx 4/r32/esp +22138 $test-compare-reg-with-literal:initialize-var1-name: +22139 # var1->name = "var1" +22140 8d/copy-address *(ecx+4) 0/r32/eax # Var-name + 4 +22141 (copy-array Heap "var1" %eax) +22142 $test-compare-reg-with-literal:initialize-var1-register: +22143 # v->register = "ecx" +22144 8d/copy-address *(ecx+0x1c) 0/r32/eax # Var-register + 4 +22145 (copy-array Heap "ecx" %eax) +22146 $test-compare-reg-with-literal:initialize-literal-type: +22147 # var type/edx: (payload type-tree) = literal +22148 68/push 0/imm32/right:null +22149 68/push 0/imm32/right:null +22150 68/push 0/imm32/left:unused +22151 68/push 0/imm32/value:literal +22152 68/push 1/imm32/is-atom?:true +22153 68/push 0x11/imm32/alloc-id:fake:payload +22154 89/<- %edx 4/r32/esp +22155 $test-compare-reg-with-literal:initialize-literal: +22156 # var l/edx: (payload var) +22157 68/push 0/imm32/register +22158 68/push 0/imm32/register +22159 68/push 0/imm32/no-stack-offset +22160 68/push 1/imm32/block-depth +22161 52/push-edx +22162 68/push 0x11/imm32/alloc-id:fake +22163 68/push 0/imm32/name +22164 68/push 0/imm32/name +22165 68/push 0x11/imm32/alloc-id:fake:payload +22166 89/<- %edx 4/r32/esp +22167 $test-compare-reg-with-literal:initialize-literal-value: +22168 # l->name = "0x34" +22169 8d/copy-address *(edx+4) 0/r32/eax # Var-name + 4 +22170 (copy-array Heap "0x34" %eax) +22171 $test-compare-reg-with-literal:initialize-inouts: +22172 # var inouts/esi: (payload stmt-var) = [l] +22173 68/push 0/imm32/is-deref:false +22174 68/push 0/imm32/next +22175 68/push 0/imm32/next +22176 52/push-edx/l +22177 68/push 0x11/imm32/alloc-id:fake +22178 68/push 0x11/imm32/alloc-id:fake:payload +22179 89/<- %esi 4/r32/esp +22180 # var inouts = (handle stmt-var) = [var1, var2] +22181 68/push 0/imm32/is-deref:false +22182 56/push-esi/next +22183 68/push 0x11/imm32/alloc-id:fake +22184 51/push-ecx/var1 +22185 68/push 0x11/imm32/alloc-id:fake +22186 68/push 0x11/imm32/alloc-id:fake:payload +22187 89/<- %esi 4/r32/esp +22188 $test-compare-reg-with-literal:initialize-stmt: +22189 # var stmt/esi: (addr statement) +22190 68/push 0/imm32/next +22191 68/push 0/imm32/next +22192 68/push 0/imm32/outputs +22193 68/push 0/imm32/outputs +22194 56/push-esi/inouts +22195 68/push 0x11/imm32/alloc-id:fake +22196 68/push 0/imm32/operation +22197 68/push 0/imm32/operation +22198 68/push 1/imm32/tag:stmt1 +22199 89/<- %esi 4/r32/esp +22200 $test-compare-reg-with-literal:initialize-stmt-operation: +22201 # stmt->operation = "compare" +22202 8d/copy-address *(esi+4) 0/r32/eax # Stmt1-operation +22203 (copy-array Heap "compare" %eax) +22204 # convert +22205 c7 0/subop/copy *Curr-block-depth 0/imm32 +22206 (emit-subx-stmt _test-output-buffered-file %esi Primitives Stderr 0) +22207 (flush _test-output-buffered-file) +22208 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- +22214 # check output +22215 (check-next-stream-line-equal _test-output-stream "81 7/subop/compare %ecx 0x34/imm32" "F - test-compare-reg-with-literal") +22216 # . epilogue +22217 89/<- %esp 5/r32/ebp +22218 5d/pop-to-ebp +22219 c3/return +22220 +22221 test-emit-subx-stmt-function-call: +22222 # Call a function on a variable on the stack. +22223 # f foo +22224 # => +22225 # (f *(ebp-8)) +22226 # (Changing the function name supports overloading in general, but here it +22227 # just serves to help disambiguate things.) +22228 # +22229 # There's a variable on the var stack as follows: +22230 # name: 'foo' +22231 # type: int +22232 # stack-offset: -8 +22233 # +22234 # There's nothing in primitives. +22235 # +22236 # We don't perform any checking here on the type of 'f'. +22237 # +22238 # . prologue +22239 55/push-ebp +22240 89/<- %ebp 4/r32/esp +22241 # setup +22242 (clear-stream _test-output-stream) +22243 (clear-stream $_test-output-buffered-file->buffer) +22244 $test-emit-subx-function-call:initialize-type: +22245 # var type/ecx: (payload type-tree) = int +22246 68/push 0/imm32/right:null +22247 68/push 0/imm32/right:null +22248 68/push 0/imm32/left:unused +22249 68/push 1/imm32/value:int +22250 68/push 1/imm32/is-atom?:true +22251 68/push 0x11/imm32/alloc-id:fake:payload +22252 89/<- %ecx 4/r32/esp +22253 $test-emit-subx-function-call:initialize-var: +22254 # var var-foo/ecx: (payload var) = var(type) +22255 68/push 0/imm32/no-register +22256 68/push 0/imm32/no-register +22257 68/push -8/imm32/stack-offset +22258 68/push 1/imm32/block-depth +22259 51/push-ecx/type +22260 68/push 0x11/imm32/alloc-id:fake +22261 68/push 0/imm32/name +22262 68/push 0/imm32/name +22263 68/push 0x11/imm32/alloc-id:fake:payload +22264 89/<- %ecx 4/r32/esp +22265 $test-emit-subx-function-call:initialize-var-name: +22266 # var-foo->name = "foo" +22267 8d/copy-address *(ecx+4) 0/r32/eax # Var-name + 4 +22268 (copy-array Heap "foo" %eax) +22269 $test-emit-subx-function-call:initialize-stmt-var: +22270 # var operand/ebx: (payload stmt-var) = stmt-var(var-foo) +22271 68/push 0/imm32/is-deref:false +22272 68/push 0/imm32/next +22273 68/push 0/imm32/next +22274 51/push-ecx/var-foo +22275 68/push 0x11/imm32/alloc-id:fake +22276 68/push 0x11/imm32/alloc-id:fake:payload +22277 89/<- %ebx 4/r32/esp +22278 $test-emit-subx-function-call:initialize-stmt: +22279 # var stmt/esi: (addr statement) +22280 68/push 0/imm32/no-outputs +22281 68/push 0/imm32/no-outputs +22282 53/push-ebx/inouts +22283 68/push 0x11/imm32/alloc-id:fake +22284 68/push 0/imm32/operation +22285 68/push 0/imm32/operation +22286 68/push 1/imm32/tag +22287 89/<- %esi 4/r32/esp +22288 $test-emit-subx-function-call:initialize-stmt-operation: +22289 # stmt->operation = "f" +22290 8d/copy-address *(esi+4) 0/r32/eax # Stmt1-operation +22291 (copy-array Heap "f" %eax) +22292 # convert +22293 c7 0/subop/copy *Curr-block-depth 0/imm32 +22294 (emit-subx-stmt _test-output-buffered-file %esi 0 Stderr 0) +22295 (flush _test-output-buffered-file) +22296 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- +22302 # check output +22303 (check-next-stream-line-equal _test-output-stream "(f *(ebp+0xfffffff8))" "F - test-emit-subx-stmt-function-call") +22304 # . epilogue +22305 89/<- %esp 5/r32/ebp +22306 5d/pop-to-ebp +22307 c3/return +22308 +22309 test-emit-subx-stmt-function-call-with-literal-arg: +22310 # Call a function on a literal. +22311 # f 0x34 +22312 # => +22313 # (f2 0x34) +22314 # +22315 # . prologue +22316 55/push-ebp +22317 89/<- %ebp 4/r32/esp +22318 # setup +22319 (clear-stream _test-output-stream) +22320 (clear-stream $_test-output-buffered-file->buffer) +22321 $test-emit-subx-function-call-with-literal-arg:initialize-type: +22322 # var type/ecx: (payload type-tree) = int +22323 68/push 0/imm32/right:null +22324 68/push 0/imm32/right:null +22325 68/push 0/imm32/left:unused +22326 68/push 0/imm32/value:literal +22327 68/push 1/imm32/is-atom?:true +22328 68/push 0x11/imm32/alloc-id:fake:payload +22329 89/<- %ecx 4/r32/esp +22330 $test-emit-subx-function-call-with-literal-arg:initialize-var: +22331 # var var-foo/ecx: (payload var) = var(lit) +22332 68/push 0/imm32/no-register +22333 68/push 0/imm32/no-register +22334 68/push 0/imm32/no-stack-offset +22335 68/push 1/imm32/block-depth +22336 51/push-ecx/type +22337 68/push 0x11/imm32/alloc-id:fake +22338 68/push 0/imm32/name +22339 68/push 0/imm32/name +22340 68/push 0x11/imm32/alloc-id:fake:payload +22341 89/<- %ecx 4/r32/esp +22342 $test-emit-subx-function-call-with-literal-arg:initialize-var-name: +22343 # var-foo->name = "0x34" +22344 8d/copy-address *(ecx+4) 0/r32/eax # Var-name + 4 +22345 (copy-array Heap "0x34" %eax) +22346 $test-emit-subx-function-call-with-literal-arg:initialize-stmt-var: +22347 # var operand/ebx: (payload stmt-var) = stmt-var(var-foo) +22348 68/push 0/imm32/is-deref:false +22349 68/push 0/imm32/next +22350 68/push 0/imm32/next +22351 51/push-ecx/var-foo +22352 68/push 0x11/imm32/alloc-id:fake +22353 68/push 0x11/imm32/alloc-id:fake:payload +22354 89/<- %ebx 4/r32/esp +22355 $test-emit-subx-function-call-with-literal-arg:initialize-stmt: +22356 # var stmt/esi: (addr statement) +22357 68/push 0/imm32/no-outputs +22358 68/push 0/imm32/no-outputs +22359 53/push-ebx/inouts +22360 68/push 0x11/imm32/alloc-id:fake +22361 68/push 0/imm32/operation +22362 68/push 0/imm32/operation +22363 68/push 1/imm32/tag +22364 89/<- %esi 4/r32/esp +22365 $test-emit-subx-function-call-with-literal-arg:initialize-stmt-operation: +22366 # stmt->operation = "f" +22367 8d/copy-address *(esi+4) 0/r32/eax # Stmt1-operation +22368 (copy-array Heap "f" %eax) +22369 # convert +22370 c7 0/subop/copy *Curr-block-depth 0/imm32 +22371 (emit-subx-stmt _test-output-buffered-file %esi 0 %ebx Stderr 0) +22372 (flush _test-output-buffered-file) +22373 +-- 6 lines: #? # dump _test-output-stream ----------------------------------------------------------------------------------------------------------------------------------------- +22379 # check output +22380 (check-next-stream-line-equal _test-output-stream "(f 0x34)" "F - test-emit-subx-stmt-function-call-with-literal-arg") +22381 # . epilogue +22382 89/<- %esp 5/r32/ebp +22383 5d/pop-to-ebp +22384 c3/return +22385 +22386 emit-indent: # out: (addr buffered-file), n: int +22387 # . prologue +22388 55/push-ebp +22389 89/<- %ebp 4/r32/esp +22390 # . save registers +22391 50/push-eax +22392 # var i/eax: int = n +22393 8b/-> *(ebp+0xc) 0/r32/eax +22394 { +22395 # if (i <= 0) break +22396 3d/compare-eax-with 0/imm32 +22397 7e/jump-if-<= break/disp8 +22398 (write-buffered *(ebp+8) " ") +22399 48/decrement-eax +22400 eb/jump loop/disp8 +22401 } +22402 $emit-indent:end: +22403 # . restore registers +22404 58/pop-to-eax +22405 # . epilogue +22406 89/<- %esp 5/r32/ebp +22407 5d/pop-to-ebp +22408 c3/return +22409 +22410 emit-subx-prologue: # out: (addr buffered-file) +22411 # . prologue +22412 55/push-ebp +22413 89/<- %ebp 4/r32/esp +22414 # +22415 (write-buffered *(ebp+8) " # . prologue\n") +22416 (write-buffered *(ebp+8) " 55/push-ebp\n") +22417 (write-buffered *(ebp+8) " 89/<- %ebp 4/r32/esp\n") +22418 $emit-subx-prologue:end: +22419 # . epilogue +22420 89/<- %esp 5/r32/ebp +22421 5d/pop-to-ebp +22422 c3/return +22423 +22424 emit-subx-epilogue: # out: (addr buffered-file) +22425 # . prologue +22426 55/push-ebp +22427 89/<- %ebp 4/r32/esp +22428 # +22429 (write-buffered *(ebp+8) " # . epilogue\n") +22430 (write-buffered *(ebp+8) " 89/<- %esp 5/r32/ebp\n") +22431 (write-buffered *(ebp+8) " 5d/pop-to-ebp\n") +22432 (write-buffered *(ebp+8) " c3/return\n") +22433 $emit-subx-epilogue:end: +22434 # . epilogue +22435 89/<- %esp 5/r32/ebp +22436 5d/pop-to-ebp +22437 c3/return diff --git a/html/apps/mulisp.subx.html b/html/apps/mulisp.subx.html deleted file mode 100644 index 62316dfb..00000000 --- a/html/apps/mulisp.subx.html +++ /dev/null @@ -1,295 +0,0 @@ - - - - -Mu - apps/mulisp.subx - - - - - - - - - - -https://github.com/akkartik/mu/blob/master/apps/mulisp.subx -
-  1 # Toy lisp interpreter. Incomplete.
-  2 #
-  3 # To run:
-  4 #   $ ./translate_subx init.linux 0*.subx apps/mulisp.subx
-  5 #   $ ./a.elf
-  6 #   42
-  7 #   => 42
-  8 #   ^D
-  9 #   $
- 10 
- 11 == code
- 12 
- 13 Entry:  # run tests if necessary, a REPL if not
- 14     # . prologue
- 15     89/<- %ebp 4/r32/esp
- 16     # initialize heap
- 17     (new-segment *Heap-size Heap)
- 18     {
- 19       # if (argc <= 1) break
- 20       81 7/subop/compare *ebp 1/imm32
- 21       7e/jump-if-<= break/disp8
- 22       # if (argv[1] != "test")) break
- 23       (kernel-string-equal? *(ebp+8) "test")  # => eax
- 24       3d/compare-eax-and 0/imm32/false
- 25       74/jump-if-= break/disp8
- 26       #
- 27       (run-tests)
- 28       # syscall(exit, *Num-test-failures)
- 29       8b/-> *Num-test-failures 3/r32/ebx
- 30       eb/jump $main:end/disp8
- 31     }
- 32     (repl Stdin Stdout)
- 33     # syscall(exit, 0)
- 34     bb/copy-to-ebx 0/imm32
- 35 $main:end:
- 36     e8/call  syscall_exit/disp32
- 37 
- 38 # Data structures
- 39 #
- 40 # Lisp is dynamically typed. Values always carry around knowledge of their
- 41 # type.
- 42 #
- 43 # There's several types of types in the description below, so we need a
- 44 # glossary and notational convention to disambiguate:
- 45 #   lisp type: what Lisp code can see. Looks how you type it at the prompt.
- 46 #     nil num char string symbol pair array
- 47 #   type tag: the numeric code for a lisp type. All caps.
- 48 #     NIL NUM CHAR STRING SYMBOL PAIR ARRAY
- 49 #   memory type: a type specifying memory layout at the SubX level. Starts
- 50 #   with a '$'.
- 51 #     $int $array $(addr _)
- 52 #
- 53 # Lisp values are represented in memory by the _cell_ data structure. A cell
- 54 # is 12 bytes long:
- 55 #   tag: $int (4 bytes; we're not concerned about wasting space)
- 56 #   data: 8 bytes whose contents and meaning depend on tag
- 57 #
- 58 # What values of the different Lisp types look like in memory:
- 59 #   - nil: cell{ tag: 0/NIL, data: 0 0 }
- 60 #   - num: cell{ tag: 1/NUM, data: $int 0 }
- 61 #     data contains the number
- 62 #   - char: cell{ tag: 2/CHAR, data: $int 0 }
- 63 #     data contains the utf-8 code of the character (no compound glyphs, no
- 64 #     modifiers, etc., etc.)
- 65 #   - string: cell{ tag: 3/STRING, data: $(addr stream byte)
- 66 #     data contains an (addr array byte) containing the string in utf-8
- 67 #   - symbol: cell{ tag: 4/SYMBOL, data: $(addr array byte) 0 }
- 68 #     data contains an (addr array byte) containing the name of the symbol in utf-8
- 69 #     alternatively, data could contain an index into the table of interned symbols
- 70 #   - pair: cell{ tag: 5/PAIR, data: $(addr cell) $(addr cell)  }
- 71 #     data contains pointers to car and cdr
- 72 #   - array: cell{ tag: 6/ARRAY, data: $tag $(addr stream data)
- 73 #     data contains a pointer to an array of 8-byte data fields and the common
- 74 #     tag for them all
- 75 
- 76 repl:  # in: (addr buffered-file), out: (addr buffered-file)
- 77     # . prologue
- 78     55/push-ebp
- 79     89/<- %ebp 4/r32/esp
- 80     # . save registers
- 81     50/push-eax
- 82     {
- 83       (lisp-read Stdin)  # => eax: (handle cell)
- 84       # if (eax == 0) break
- 85       3d/compare-eax-and 0/imm32
- 86       74/jump-if-= break/disp8
- 87       #
- 88       (lisp-eval %eax)  # => eax: (handle cell)
- 89       (lisp-print Stdout %eax)
- 90       eb/jump loop/disp8
- 91     }
- 92 $repl:end:
- 93     # . restore registers
- 94     58/pop-to-eax
- 95     # . epilogue
- 96     89/<- %esp 5/r32/ebp
- 97     5d/pop-to-ebp
- 98     c3/return
- 99 
-100 # numbers start with a digit and are always in hex
-101 # characters start with a backslash
-102 # pairs start with '('
-103 # arrays start with '['
-104 # symbols start with anything else but quote, backquote, unquote or splice
-105 # only one s-expression per line
-106 lisp-read:  # in: (addr buffered-file) -> eax: (handle cell)
-107     # . prologue
-108     55/push-ebp
-109     89/<- %ebp 4/r32/esp
-110     # . save registers
-111     51/push-ecx
-112     # var s/ecx: (stream byte 512)
-113     81 5/subop/subtract %esp 0x200/imm32
-114     68/push 0x200/imm32/size
-115     68/push 0/imm32/read
-116     68/push 0/imm32/write
-117     89/<- %ecx 4/r32/esp
-118     {
-119       # read line into s
-120       (clear-stream %ecx)
-121       (read-line-buffered *(ebp+8) %ecx)
-122       # if (s->write == 0) return null
-123       {
-124         81 7/subop/compare *ecx 0/imm32
-125         75/jump-if-!= break/disp8
-126         b8/copy-to-eax 0/imm32/eof
-127         eb/jump $lisp-read:end/disp8
-128       }
-129       # ...
-130 #?       eb/jump loop/disp8
-131     }
-132     # return s
-133     89/<- %eax 1/r32/ecx
-134 $lisp-read:end:
-135     # . reclaim locals
-136     81 0/subop/add %esp 0x20c/imm32
-137     # . restore registers
-138     59/pop-to-ecx
-139     # . epilogue
-140     89/<- %esp 5/r32/ebp
-141     5d/pop-to-ebp
-142     c3/return
-143 
-144 # lisp-read:  in: (addr buffered-file) -> (handle cell)
-145 #   token tmp = next-mulisp-token(in)
-146 #   if is-int(tmp) return cell(tmp)
-147 #   if is-string(tmp) return cell(tmp)
-148 #   if is-pair(tmp) ...
-149 #   if is-array(tmp) ...
-150 
-151 next-mulisp-token:  # in: (addr buffered-file), line: (addr stream byte), result: (addr slice)
-152     # pseudocode:
-153     #   if (line->read >= line->write)
-154     #     read-line-buffered(in, line)
-155     #     recurse
-156     #   if (line->data[line->read] == ' ')
-157     #     skip-chars-matching-whitespace(line)
-158     #     recurse
-159     #   if (line->data[line->read] == '#')
-160     #     read-line-buffered(in, line)
-161     #     recurse
-162     #   eax = line->data[line->read]
-163     #   if (eax == '"')
-164     #     result->start = &line->data[line->read]
-165     #     skip-string(in)
-166     #     result->end = &line->data[line->read]
-167     #     return
-168     #   if (is-digit(eax))
-169     #     result->start = &line->data[line->read]
-170     #     skip-hex-int(in)
-171     #     result->end = &line->data[line->read]
-172     #     return
-173     #   if (eax in '(' ')' '[' ']')
-174     #     result->start = &line->data[line->read]
-175     #     ++line->read
-176     #     result->en = &line->data[line->read]
-177     #     return
-178     #   else
-179     #     result->start = &line->data[line->read]
-180     #     skip-lisp-word(line)
-181     #     result->en = &line->data[line->read]
-182     #     return
-183     #
-184     # . prologue
-185     55/push-ebp
-186     89/<- %ebp 4/r32/esp
-187     # . save registers
-188 $next-mulisp-token:end:
-189     # . reclaim locals
-190     # . restore registers
-191     # . epilogue
-192     89/<- %esp 5/r32/ebp
-193     5d/pop-to-ebp
-194     c3/return
-195 
-196 new-int-cell:  # in: (addr slice) -> eax: (handle cell)
-197 
-198 new-string-cell:  # in: (addr slice) -> eax: (handle cell)
-199 
-200 lisp-eval:  # in: (addr cell) -> eax: (handle cell)
-201     # . prologue
-202     55/push-ebp
-203     89/<- %ebp 4/r32/esp
-204     # . save registers
-205     8b/-> *(ebp+8) 0/r32/eax
-206 $lisp-eval:end:
-207     # . restore registers
-208     # . epilogue
-209     89/<- %esp 5/r32/ebp
-210     5d/pop-to-ebp
-211     c3/return
-212 
-213 lisp-print:  # out: (addr buffered-file), x: (addr cell)
-214     # . prologue
-215     55/push-ebp
-216     89/<- %ebp 4/r32/esp
-217     # . save registers
-218     # write(x)
-219     (write-buffered Stdout "=> ")
-220     (write-stream-data Stdout *(ebp+0xc))
-221     (flush Stdout)
-222 $lisp-print:end:
-223     # . restore registers
-224     # . epilogue
-225     89/<- %esp 5/r32/ebp
-226     5d/pop-to-ebp
-227     c3/return
-228 
-229 == data
-230 
-231 Nil:
-232   0/imm32/tag
-233   0/imm32/data
-
- - - -- cgit 1.4.1-2-gfad0