From 33dcdcbde0e9a0da823b293736fc8d83638ce71e Mon Sep 17 00:00:00 2001 From: dan <70999565+belovdv@users.noreply.github.com> Date: Thu, 3 Sep 2026 14:23:29 +0300 Subject: [PATCH 1/7] [infra] modify testing --- .github/workflows/ci.yml | 82 +- .gitignore | 1 + python/tests/integration/__init__.py | 0 python/tests/integration/copy_.py | 14 + python/tests/integration/integration.yaml | 859 ------------------- python/tests/integration/test_integration.py | 26 - ruby/tests/integration/copy.rb | 11 + ruby/tests/integration/test_integration.rb | 28 - rust/Cargo.lock | 16 +- rust/Cargo.toml | 2 +- rust/copy/Cargo.toml | 8 + rust/copy/src/main.rs | 5 + rust/tests/Cargo.toml | 16 - rust/tests/README.md | 15 - rust/tests/integration/main.rs | 48 -- scripts/python.sh | 7 + scripts/round_trip.sh | 15 + scripts/ruby.sh | 9 + scripts/rust.sh | 6 + 19 files changed, 118 insertions(+), 1050 deletions(-) delete mode 100644 python/tests/integration/__init__.py create mode 100644 python/tests/integration/copy_.py delete mode 100644 python/tests/integration/integration.yaml delete mode 100644 python/tests/integration/test_integration.py create mode 100644 ruby/tests/integration/copy.rb delete mode 100644 ruby/tests/integration/test_integration.rb create mode 100644 rust/copy/Cargo.toml create mode 100644 rust/copy/src/main.rs delete mode 100644 rust/tests/Cargo.toml delete mode 100644 rust/tests/README.md delete mode 100644 rust/tests/integration/main.rs create mode 100644 scripts/python.sh create mode 100644 scripts/round_trip.sh create mode 100644 scripts/ruby.sh create mode 100644 scripts/rust.sh diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml index 15ef70c..ccbeff9 100644 --- a/.github/workflows/ci.yml +++ b/.github/workflows/ci.yml @@ -14,14 +14,9 @@ jobs: with: python-version: '3.10' - run: pip install ruamel.yaml pytest pytest-cov - - name: Unit tests - run: pytest python/tests/unit/ -v - - name: Unit coverage - run: pytest --cov=python/lira python/tests/unit/ --cov-report=term - - name: Integration tests - run: pytest python/tests/integration/ -v - - name: Diff integration output vs reference - run: diff python/tests/integration/integration.yaml tests/integration/reference.yaml + - run: pip install -e python/ + - name: Run Python tests (unit, integration, coverage) + run: bash scripts/python.sh ruby-tests: runs-on: ubuntu-latest @@ -35,18 +30,8 @@ jobs: python-version: '3.10' - run: pip install ruamel.yaml - run: gem install minitest simplecov - - name: Unit tests - run: | - ruby -I ruby -I ruby/lib ruby/tests/unit/test_ir_ser_txt.rb - ruby -I ruby -I ruby/lib ruby/tests/unit/test_arch_ser_yaml.rb - ruby -I ruby -I ruby/lib ruby/tests/unit/test_ir_builder.rb - - name: Unit coverage - run: | - ruby -r simplecov -I ruby -I ruby/lib -e 'SimpleCov.start; Dir["ruby/tests/unit/*.rb"].each { |f| require_relative f }' - - name: Integration tests - run: ruby -I ruby -I ruby/lib ruby/tests/integration/test_integration.rb - - name: Diff integration output vs reference - run: diff ruby/tests/integration/integration.yaml tests/integration/reference.yaml + - name: Run Ruby tests (unit, integration, coverage) + run: bash scripts/ruby.sh rust-tests: runs-on: ubuntu-latest @@ -56,36 +41,35 @@ jobs: - uses: actions/setup-python@v5 with: python-version: '3.10' + - run: sudo apt-get update && sudo apt-get install -y z3 - run: pip install ruamel.yaml - - name: Integration tests - run: cd rust && cargo test -p lira-tests --test integration - - name: Diff integration output vs reference - run: diff rust/tests/integration/integration.yaml tests/integration/reference.yaml + - name: Run Rust tests (integration, with coverage) + run: bash scripts/rust.sh - cross-language: - runs-on: ubuntu-latest - steps: - - uses: actions/checkout@v4 - - uses: actions/setup-python@v5 - with: - python-version: '3.10' - - uses: ruby/setup-ruby@v1 - with: - ruby-version: '3.3' - - uses: dtolnay/rust-toolchain@stable - - run: pip install ruamel.yaml pytest - - run: gem install minitest + # cross-language: + # runs-on: ubuntu-latest + # steps: + # - uses: actions/checkout@v4 + # - uses: actions/setup-python@v5 + # with: + # python-version: '3.10' + # - uses: ruby/setup-ruby@v1 + # with: + # ruby-version: '3.3' + # - uses: dtolnay/rust-toolchain@stable + # - run: pip install ruamel.yaml pytest + # - run: gem install minitest - - name: Python writes native YAML - run: pytest tests/cross_language/test_cross.py -k "write" -v - - name: Ruby writes native YAML - run: ruby -I ruby -I ruby/lib tests/cross_language/test_cross.rb --name test_ruby_write_and_self_read - - name: Rust writes native YAML - run: cd rust && cargo test -p lira-tests --test cross_language test_rust_write_and_self_read + # - name: Python writes native YAML + # run: pytest tests/cross_language/test_cross.py -k "write" -v + # - name: Ruby writes native YAML + # run: ruby -I ruby -I ruby/lib tests/cross_language/test_cross.rb --name test_ruby_write_and_self_read + # - name: Rust writes native YAML + # run: cd rust && cargo test -p lira-tests --test cross_language test_rust_write_and_self_read - - name: Python reads Ruby and Rust - run: pytest tests/cross_language/test_cross.py -k "reads" -v - - name: Ruby reads Python and Rust - run: ruby -I ruby -I ruby/lib tests/cross_language/test_cross.rb --name '/test_ruby_reads/' - - name: Rust reads Python and Ruby - run: cd rust && cargo test -p lira-tests --test cross_language test_rust_reads + # - name: Python reads Ruby and Rust + # run: pytest tests/cross_language/test_cross.py -k "reads" -v + # - name: Ruby reads Python and Rust + # run: ruby -I ruby -I ruby/lib tests/cross_language/test_cross.rb --name '/test_ruby_reads/' + # - name: Rust reads Python and Ruby + # run: cd rust && cargo test -p lira-tests --test cross_language test_rust_reads diff --git a/.gitignore b/.gitignore index 915133f..85ca188 100644 --- a/.gitignore +++ b/.gitignore @@ -38,3 +38,4 @@ htmlcov/ *.log .env build/ +tmp/ diff --git a/python/tests/integration/__init__.py b/python/tests/integration/__init__.py deleted file mode 100644 index e69de29..0000000 diff --git a/python/tests/integration/copy_.py b/python/tests/integration/copy_.py new file mode 100644 index 0000000..f584e6a --- /dev/null +++ b/python/tests/integration/copy_.py @@ -0,0 +1,14 @@ +assert __name__ == '__main__' + +import sys +from pathlib import Path + +from lira import arch_ser_yaml + +assert len(sys.argv) == 3, 'copy.py ' + +path_input = Path(sys.argv[1]) +path_output = Path(sys.argv[2]) + +ref_arch = arch_ser_yaml.read_arch(path_input) +arch_ser_yaml.write_arch(ref_arch, path_output) diff --git a/python/tests/integration/integration.yaml b/python/tests/integration/integration.yaml deleted file mode 100644 index cd13447..0000000 --- a/python/tests/integration/integration.yaml +++ /dev/null @@ -1,859 +0,0 @@ -name: TargetArch -attributes: [] -register_files: - - name: XRegs - attributes: [] - reg_size: - lanes_base: 32 - lanes_mult: - regs: - - name: x0 - attributes: - - zero - - name: x1 - attributes: [] - - name: x2 - attributes: [] - - name: x3 - attributes: [] - - name: x4 - attributes: [] - - name: x5 - attributes: [] - - name: x6 - attributes: [] - - name: x7 - attributes: [] - - name: x8 - attributes: [] - - name: SpecialRegs - attributes: [] - reg_size: - lanes_base: 32 - lanes_mult: - regs: - - name: pc - attributes: - - pc -system_registers: [] -environment_functions: - - name: sysCall - attributes: [] - inputs: [] - outputs: [] - - name: writeMem16 - attributes: [] - inputs: - - 32 - - 16 - outputs: [] - - name: readMem16 - attributes: [] - inputs: - - 32 - outputs: - - 16 - - name: getPC - attributes: [] - inputs: [] - outputs: - - 32 - - name: setPC - attributes: [] - inputs: - - 32 - outputs: [] -tables_int: [] -operations: - - name: add_32 - attributes: [] - inputs: - - 32 - - 32 - outputs: - - 32 - semantic_base: :add - semantic_func: - semantic_func_128: - semantic_table: - - name: lsr_32 - attributes: [] - inputs: - - 32 - - 32 - outputs: - - 32 - semantic_base: :lsr - semantic_func: - semantic_func_128: - semantic_table: - - name: extract_low_32_to_5 - attributes: [] - inputs: - - 32 - outputs: - - 5 - semantic_base: :extract_low - semantic_func: - semantic_func_128: - semantic_table: - - name: extend_zero_5_to_32 - attributes: [] - inputs: - - 5 - outputs: - - 32 - semantic_base: :extend_zero - semantic_func: - semantic_func_128: - semantic_table: - - name: extend_zero_1_to_32 - attributes: [] - inputs: - - 1 - outputs: - - 32 - semantic_base: :extend_zero - semantic_func: - semantic_func_128: - semantic_table: - - name: lsl_32 - attributes: [] - inputs: - - 32 - - 32 - outputs: - - 32 - semantic_base: :lsl - semantic_func: - semantic_func_128: - semantic_table: - - name: orr_32 - attributes: [] - inputs: - - 32 - - 32 - outputs: - - 32 - semantic_base: :orr - semantic_func: - semantic_func_128: - semantic_table: - - name: and_32 - attributes: [] - inputs: - - 32 - - 32 - outputs: - - 32 - semantic_base: :and - semantic_func: - semantic_func_128: - semantic_table: - - name: eq_32 - attributes: [] - inputs: - - 32 - - 32 - outputs: - - 1 - semantic_base: :eq - semantic_func: - semantic_func_128: - semantic_table: - - name: select_32 - attributes: [] - inputs: - - 1 - - 32 - - 32 - outputs: - - 32 - semantic_base: :select - semantic_func: - semantic_func_128: - semantic_table: - - name: extract_low_32_to_1 - attributes: [] - inputs: - - 32 - outputs: - - 1 - semantic_base: :extract_low - semantic_func: - semantic_func_128: - semantic_table: - - name: extend_zero_1_to_13 - attributes: [] - inputs: - - 1 - outputs: - - 13 - semantic_base: :extend_zero - semantic_func: - semantic_func_128: - semantic_table: - - name: extend_zero_13_to_32 - attributes: [] - inputs: - - 13 - outputs: - - 32 - semantic_base: :extend_zero - semantic_func: - semantic_func_128: - semantic_table: - - name: extract_low_32_to_6 - attributes: [] - inputs: - - 32 - outputs: - - 6 - semantic_base: :extract_low - semantic_func: - semantic_func_128: - semantic_table: - - name: extend_zero_6_to_13 - attributes: [] - inputs: - - 6 - outputs: - - 13 - semantic_base: :extend_zero - semantic_func: - semantic_func_128: - semantic_table: - - name: extract_low_32_to_4 - attributes: [] - inputs: - - 32 - outputs: - - 4 - semantic_base: :extract_low - semantic_func: - semantic_func_128: - semantic_table: - - name: extend_zero_4_to_13 - attributes: [] - inputs: - - 4 - outputs: - - 13 - semantic_base: :extend_zero - semantic_func: - semantic_func_128: - semantic_table: - - name: extract_low_32_to_13 - attributes: [] - inputs: - - 32 - outputs: - - 13 - semantic_base: :extract_low - semantic_func: - semantic_func_128: - semantic_table: - - name: extend_sign_13_to_32 - attributes: [] - inputs: - - 13 - outputs: - - 32 - semantic_base: :extend_sign - semantic_func: - semantic_func_128: - semantic_table: - - name: extract_low_32_to_12 - attributes: [] - inputs: - - 32 - outputs: - - 12 - semantic_base: :extract_low - semantic_func: - semantic_func_128: - semantic_table: - - name: extend_sign_12_to_32 - attributes: [] - inputs: - - 12 - outputs: - - 32 - semantic_base: :extend_sign - semantic_func: - semantic_func_128: - semantic_table: - - name: extract_low_32_to_16 - attributes: [] - inputs: - - 32 - outputs: - - 16 - semantic_base: :extract_low - semantic_func: - semantic_func_128: - semantic_table: - - name: extract_low_32_to_7 - attributes: [] - inputs: - - 32 - outputs: - - 7 - semantic_base: :extract_low - semantic_func: - semantic_func_128: - semantic_table: - - name: extend_zero_7_to_12 - attributes: [] - inputs: - - 7 - outputs: - - 12 - semantic_base: :extend_zero - semantic_func: - semantic_func_128: - semantic_table: - - name: extend_zero_12_to_32 - attributes: [] - inputs: - - 12 - outputs: - - 32 - semantic_base: :extend_zero - semantic_func: - semantic_func_128: - semantic_table: - - name: extend_zero_5_to_12 - attributes: [] - inputs: - - 5 - outputs: - - 12 - semantic_base: :extend_zero - semantic_func: - semantic_func_128: - semantic_table: - - name: extend_sign_16_to_32 - attributes: [] - inputs: - - 16 - outputs: - - 32 - semantic_base: :extend_sign - semantic_func: - semantic_func_128: - semantic_table: - - name: extend_zero_16_to_32 - attributes: [] - inputs: - - 16 - outputs: - - 32 - semantic_base: :extend_zero - semantic_func: - semantic_func_128: - semantic_table: -snippets: - - name: decode_0 - seq: | - 1 32 _t1 = input 0; - 1 32 _t3 = const 20; - 1 32 _t4 = op lsr_32 _t1 _t3; - 1 5 _t5 = op extract_low_32_to_5 _t4; - 1 32 _t6 = op extend_zero_5_to_32 _t5; - 1 = output 0 _t6; - - name: decode_1 - seq: | - 1 32 _t1 = input 0; - 1 32 _t3 = const 15; - 1 32 _t4 = op lsr_32 _t1 _t3; - 1 5 _t5 = op extract_low_32_to_5 _t4; - 1 32 _t6 = op extend_zero_5_to_32 _t5; - 1 = output 0 _t6; - - name: decode_2 - seq: | - 1 32 _t1 = input 0; - 1 32 _t3 = const 7; - 1 32 _t4 = op lsr_32 _t1 _t3; - 1 5 _t5 = op extract_low_32_to_5 _t4; - 1 32 _t6 = op extend_zero_5_to_32 _t5; - 1 = output 0 _t6; - - name: encode_0 - seq: | - 1 32 _t1 = input 0; - 1 32 _t2 = input 1; - 1 32 _t3 = input 2; - 1 32 _t4 = const 0; - 1 1 _t5 = const 51; - 1 32 _t6 = op extend_zero_1_to_32 _t5; - 1 32 _t7 = const 6; - 1 32 _t8 = op lsl_32 _t6 _t7; - 1 32 _t9 = op orr_32 _t4 _t8; - 1 32 _t10 = const 11; - 1 32 _t11 = op lsl_32 _t3 _t10; - 1 32 _t12 = op orr_32 _t9 _t11; - 1 1 _t13 = const 0; - 1 32 _t14 = op extend_zero_1_to_32 _t13; - 1 32 _t15 = const 14; - 1 32 _t16 = op lsl_32 _t14 _t15; - 1 32 _t17 = op orr_32 _t12 _t16; - 1 32 _t18 = const 19; - 1 32 _t19 = op lsl_32 _t2 _t18; - 1 32 _t20 = op orr_32 _t17 _t19; - 1 32 _t21 = const 24; - 1 32 _t22 = op lsl_32 _t1 _t21; - 1 32 _t23 = op orr_32 _t20 _t22; - 1 1 _t24 = const 0; - 1 32 _t25 = op extend_zero_1_to_32 _t24; - 1 32 _t26 = const 31; - 1 32 _t27 = op lsl_32 _t25 _t26; - 1 32 _t28 = op orr_32 _t23 _t27; - 1 = output 0 _t28; - - name: constraint_0 - seq: | - 1 32 _t1 = input 0; - 1 32 _t2 = const 4261441663; - 1 32 _t3 = op and_32 _t1 _t2; - 1 32 _t4 = const 51; - 1 1 _t5 = op eq_32 _t3 _t4; - 1 = output 0 _t5; - - name: decode_3 - seq: | - 1 32 _t1 = input 0; - 1 32 _t3 = const 31; - 1 32 _t4 = op lsr_32 _t1 _t3; - 1 1 _t5 = op extract_low_32_to_1 _t4; - 1 13 _t6 = op extend_zero_1_to_13 _t5; - 1 32 _t8 = const 12; - 1 32 _t9 = op extend_zero_13_to_32 _t6; - 1 32 _t10 = op lsl_32 _t9 _t8; - 1 32 _t12 = const 7; - 1 32 _t13 = op lsr_32 _t1 _t12; - 1 1 _t14 = op extract_low_32_to_1 _t13; - 1 13 _t15 = op extend_zero_1_to_13 _t14; - 1 32 _t17 = const 11; - 1 32 _t18 = op extend_zero_13_to_32 _t15; - 1 32 _t19 = op lsl_32 _t18 _t17; - 1 32 _t21 = op orr_32 _t10 _t19; - 1 32 _t23 = const 25; - 1 32 _t24 = op lsr_32 _t1 _t23; - 1 6 _t25 = op extract_low_32_to_6 _t24; - 1 13 _t26 = op extend_zero_6_to_13 _t25; - 1 32 _t28 = const 5; - 1 32 _t29 = op extend_zero_13_to_32 _t26; - 1 32 _t30 = op lsl_32 _t29 _t28; - 1 32 _t32 = op orr_32 _t21 _t30; - 1 32 _t34 = const 8; - 1 32 _t35 = op lsr_32 _t1 _t34; - 1 4 _t36 = op extract_low_32_to_4 _t35; - 1 13 _t37 = op extend_zero_4_to_13 _t36; - 1 32 _t39 = const 1; - 1 32 _t40 = op extend_zero_13_to_32 _t37; - 1 32 _t41 = op lsl_32 _t40 _t39; - 1 32 _t43 = op orr_32 _t32 _t41; - 1 13 _t45 = op extract_low_32_to_13 _t43; - 1 32 _t46 = op extend_sign_13_to_32 _t45; - 1 = output 0 _t46; - - name: encode_1 - seq: | - 1 32 _t1 = input 0; - 1 32 _t2 = input 1; - 1 32 _t3 = input 2; - 1 32 _t4 = const 0; - 1 1 _t5 = const 99; - 1 32 _t6 = op extend_zero_1_to_32 _t5; - 1 32 _t7 = const 6; - 1 32 _t8 = op lsl_32 _t6 _t7; - 1 32 _t9 = op orr_32 _t4 _t8; - 1 1 _t10 = const 0; - 1 32 _t11 = op extend_zero_1_to_32 _t10; - 1 32 _t12 = const 14; - 1 32 _t13 = op lsl_32 _t11 _t12; - 1 32 _t14 = op orr_32 _t9 _t13; - 1 32 _t15 = const 19; - 1 32 _t16 = op lsl_32 _t2 _t15; - 1 32 _t17 = op orr_32 _t14 _t16; - 1 32 _t18 = const 24; - 1 32 _t19 = op lsl_32 _t3 _t18; - 1 32 _t20 = op orr_32 _t17 _t19; - 1 = output 0 _t20; - - name: constraint_1 - seq: | - 1 32 _t1 = input 0; - 1 32 _t2 = const 28799; - 1 32 _t3 = op and_32 _t1 _t2; - 1 32 _t4 = const 99; - 1 1 _t5 = op eq_32 _t3 _t4; - 1 = output 0 _t5; - - name: decode_4 - seq: | - 1 32 _t1 = input 0; - 1 32 _t3 = const 20; - 1 32 _t4 = op lsr_32 _t1 _t3; - 1 12 _t5 = op extract_low_32_to_12 _t4; - 1 32 _t6 = op extend_sign_12_to_32 _t5; - 1 = output 0 _t6; - - name: encode_2 - seq: | - 1 32 _t1 = input 0; - 1 32 _t2 = input 1; - 1 32 _t3 = input 2; - 1 32 _t4 = const 0; - 1 1 _t5 = const 103; - 1 32 _t6 = op extend_zero_1_to_32 _t5; - 1 32 _t7 = const 6; - 1 32 _t8 = op lsl_32 _t6 _t7; - 1 32 _t9 = op orr_32 _t4 _t8; - 1 32 _t10 = const 11; - 1 32 _t11 = op lsl_32 _t3 _t10; - 1 32 _t12 = op orr_32 _t9 _t11; - 1 1 _t13 = const 0; - 1 32 _t14 = op extend_zero_1_to_32 _t13; - 1 32 _t15 = const 14; - 1 32 _t16 = op lsl_32 _t14 _t15; - 1 32 _t17 = op orr_32 _t12 _t16; - 1 32 _t18 = const 19; - 1 32 _t19 = op lsl_32 _t2 _t18; - 1 32 _t20 = op orr_32 _t17 _t19; - 1 32 _t21 = const 31; - 1 32 _t22 = op lsl_32 _t1 _t21; - 1 32 _t23 = op orr_32 _t20 _t22; - 1 = output 0 _t23; - - name: constraint_2 - seq: | - 1 32 _t1 = input 0; - 1 32 _t2 = const 28799; - 1 32 _t3 = op and_32 _t1 _t2; - 1 32 _t4 = const 103; - 1 1 _t5 = op eq_32 _t3 _t4; - 1 = output 0 _t5; - - name: decode_5 - seq: | - 1 32 _t1 = input 0; - 1 32 _t3 = const 25; - 1 32 _t4 = op lsr_32 _t1 _t3; - 1 7 _t5 = op extract_low_32_to_7 _t4; - 1 12 _t6 = op extend_zero_7_to_12 _t5; - 1 32 _t8 = const 5; - 1 32 _t9 = op extend_zero_12_to_32 _t6; - 1 32 _t10 = op lsl_32 _t9 _t8; - 1 32 _t12 = const 7; - 1 32 _t13 = op lsr_32 _t1 _t12; - 1 5 _t14 = op extract_low_32_to_5 _t13; - 1 12 _t15 = op extend_zero_5_to_12 _t14; - 1 32 _t17 = op extend_zero_12_to_32 _t15; - 1 32 _t18 = op orr_32 _t10 _t17; - 1 12 _t20 = op extract_low_32_to_12 _t18; - 1 32 _t21 = op extend_sign_12_to_32 _t20; - 1 = output 0 _t21; - - name: encode_3 - seq: | - 1 32 _t1 = input 0; - 1 32 _t2 = input 1; - 1 32 _t3 = input 2; - 1 32 _t4 = const 0; - 1 1 _t5 = const 35; - 1 32 _t6 = op extend_zero_1_to_32 _t5; - 1 32 _t7 = const 6; - 1 32 _t8 = op lsl_32 _t6 _t7; - 1 32 _t9 = op orr_32 _t4 _t8; - 1 1 _t10 = const 1; - 1 32 _t11 = op extend_zero_1_to_32 _t10; - 1 32 _t12 = const 14; - 1 32 _t13 = op lsl_32 _t11 _t12; - 1 32 _t14 = op orr_32 _t9 _t13; - 1 32 _t15 = const 19; - 1 32 _t16 = op lsl_32 _t2 _t15; - 1 32 _t17 = op orr_32 _t14 _t16; - 1 32 _t18 = const 24; - 1 32 _t19 = op lsl_32 _t3 _t18; - 1 32 _t20 = op orr_32 _t17 _t19; - 1 = output 0 _t20; - - name: constraint_3 - seq: | - 1 32 _t1 = input 0; - 1 32 _t2 = const 28799; - 1 32 _t3 = op and_32 _t1 _t2; - 1 32 _t4 = const 4131; - 1 1 _t5 = op eq_32 _t3 _t4; - 1 = output 0 _t5; - - name: encode_4 - seq: | - 1 32 _t1 = input 0; - 1 32 _t2 = input 1; - 1 32 _t3 = input 2; - 1 32 _t4 = const 0; - 1 1 _t5 = const 3; - 1 32 _t6 = op extend_zero_1_to_32 _t5; - 1 32 _t7 = const 6; - 1 32 _t8 = op lsl_32 _t6 _t7; - 1 32 _t9 = op orr_32 _t4 _t8; - 1 32 _t10 = const 11; - 1 32 _t11 = op lsl_32 _t3 _t10; - 1 32 _t12 = op orr_32 _t9 _t11; - 1 1 _t13 = const 1; - 1 32 _t14 = op extend_zero_1_to_32 _t13; - 1 32 _t15 = const 14; - 1 32 _t16 = op lsl_32 _t14 _t15; - 1 32 _t17 = op orr_32 _t12 _t16; - 1 32 _t18 = const 19; - 1 32 _t19 = op lsl_32 _t2 _t18; - 1 32 _t20 = op orr_32 _t17 _t19; - 1 32 _t21 = const 31; - 1 32 _t22 = op lsl_32 _t1 _t21; - 1 32 _t23 = op orr_32 _t20 _t22; - 1 = output 0 _t23; - - name: constraint_4 - seq: | - 1 32 _t1 = input 0; - 1 32 _t2 = const 28799; - 1 32 _t3 = op and_32 _t1 _t2; - 1 32 _t4 = const 4099; - 1 1 _t5 = op eq_32 _t3 _t4; - 1 = output 0 _t5; - - name: encode_5 - seq: | - 1 32 _t1 = input 0; - 1 32 _t2 = input 1; - 1 32 _t3 = input 2; - 1 32 _t4 = const 0; - 1 1 _t5 = const 3; - 1 32 _t6 = op extend_zero_1_to_32 _t5; - 1 32 _t7 = const 6; - 1 32 _t8 = op lsl_32 _t6 _t7; - 1 32 _t9 = op orr_32 _t4 _t8; - 1 32 _t10 = const 11; - 1 32 _t11 = op lsl_32 _t3 _t10; - 1 32 _t12 = op orr_32 _t9 _t11; - 1 1 _t13 = const 5; - 1 32 _t14 = op extend_zero_1_to_32 _t13; - 1 32 _t15 = const 14; - 1 32 _t16 = op lsl_32 _t14 _t15; - 1 32 _t17 = op orr_32 _t12 _t16; - 1 32 _t18 = const 19; - 1 32 _t19 = op lsl_32 _t2 _t18; - 1 32 _t20 = op orr_32 _t17 _t19; - 1 32 _t21 = const 31; - 1 32 _t22 = op lsl_32 _t1 _t21; - 1 32 _t23 = op orr_32 _t20 _t22; - 1 = output 0 _t23; - - name: constraint_5 - seq: | - 1 32 _t1 = input 0; - 1 32 _t2 = const 28799; - 1 32 _t3 = op and_32 _t1 _t2; - 1 32 _t4 = const 20483; - 1 1 _t5 = op eq_32 _t3 _t4; - 1 = output 0 _t5; - - name: constraint_6 - seq: | - 1 32 _t1 = input 0; - 1 32 _t2 = const 4294967295; - 1 32 _t3 = op and_32 _t1 _t2; - 1 32 _t4 = const 115; - 1 1 _t5 = op eq_32 _t3 _t4; - 1 = output 0 _t5; -instructions: - - name: add - attributes: [] - operand_sizes: - - 32 - - 32 - - 32 - operand_names: - - rs2 - - rs1 - - rd - encoding: - encoded_size: 32 - const_encoding_part: 51 - const_mask: 4261441663 - decode: - - decode_0 - - decode_1 - - decode_2 - encode: encode_0 - constraint_decode: constraint_0 - constraint_encode: '' - semantic: | - 1 32 _t3 = input 1; - 1 32 _t4 = read XRegs _t3; - 1 32 _t7 = input 0; - 1 32 _t8 = read XRegs _t7; - 1 32 _t10 = op add_32 _t4 _t8; - 1 32 _t11 = input 2; - 1 = write XRegs _t11 _t10; - - name: beq - attributes: [] - operand_sizes: - - 32 - - 32 - - 32 - operand_names: - - imm - - rs1 - - rs2 - encoding: - encoded_size: 32 - const_encoding_part: 99 - const_mask: 28799 - decode: - - decode_3 - - decode_1 - - decode_0 - encode: encode_1 - constraint_decode: constraint_1 - constraint_encode: '' - semantic: | - 1 32 _t3 = input 1; - 1 32 _t4 = read XRegs _t3; - 1 32 _t6 = input 2; - 1 32 _t7 = read XRegs _t6; - 1 1 _t8 = op eq_32 _t4 _t7; - 1 32 _t10 = env getPC; - 1 32 _t11 = input 0; - 1 32 _t12 = op add_32 _t10 _t11; - 1 32 _t14 = const 4; - 1 32 _t15 = op add_32 _t10 _t14; - 1 32 _t17 = op select_32 _t8 _t12 _t15; - 1 = env setPC _t17; - - name: jalr - attributes: [] - operand_sizes: - - 32 - - 32 - - 32 - operand_names: - - imm - - rs1 - - rd - encoding: - encoded_size: 32 - const_encoding_part: 103 - const_mask: 28799 - decode: - - decode_4 - - decode_1 - - decode_2 - encode: encode_2 - constraint_decode: constraint_2 - constraint_encode: '' - semantic: | - 1 32 _t2 = env getPC; - 1 32 _t3 = const 4; - 1 32 _t4 = op add_32 _t2 _t3; - 1 32 _t8 = input 1; - 1 32 _t9 = read XRegs _t8; - 1 32 _t10 = input 0; - 1 32 _t11 = op add_32 _t9 _t10; - 1 32 _t13 = const -2; - 1 32 _t14 = op and_32 _t11 _t13; - 1 = env setPC _t14; - 1 32 _t15 = input 2; - 1 = write XRegs _t15 _t4; - - name: sh - attributes: [] - operand_sizes: - - 32 - - 32 - - 32 - operand_names: - - imm - - rs1 - - rs2 - encoding: - encoded_size: 32 - const_encoding_part: 4131 - const_mask: 28799 - decode: - - decode_5 - - decode_1 - - decode_0 - encode: encode_3 - constraint_decode: constraint_3 - constraint_encode: '' - semantic: | - 1 32 _t3 = input 1; - 1 32 _t4 = read XRegs _t3; - 1 32 _t5 = input 0; - 1 32 _t6 = op add_32 _t4 _t5; - 1 32 _t9 = input 2; - 1 32 _t10 = read XRegs _t9; - 1 32 _t11 = const 0; - 1 32 _t12 = op lsr_32 _t10 _t11; - 1 16 _t13 = op extract_low_32_to_16 _t12; - 1 = env writeMem16 _t6 _t13; - - name: lh - attributes: [] - operand_sizes: - - 32 - - 32 - - 32 - operand_names: - - imm - - rs1 - - rd - encoding: - encoded_size: 32 - const_encoding_part: 4099 - const_mask: 28799 - decode: - - decode_4 - - decode_1 - - decode_2 - encode: encode_4 - constraint_decode: constraint_4 - constraint_encode: '' - semantic: | - 1 32 _t3 = input 1; - 1 32 _t4 = read XRegs _t3; - 1 32 _t5 = input 0; - 1 32 _t6 = op add_32 _t4 _t5; - 1 16 _t8 = env readMem16 _t6; - 1 32 _t10 = op extend_sign_16_to_32 _t8; - 1 32 _t11 = input 2; - 1 = write XRegs _t11 _t10; - - name: lhu - attributes: [] - operand_sizes: - - 32 - - 32 - - 32 - operand_names: - - imm - - rs1 - - rd - encoding: - encoded_size: 32 - const_encoding_part: 20483 - const_mask: 28799 - decode: - - decode_4 - - decode_1 - - decode_2 - encode: encode_5 - constraint_decode: constraint_5 - constraint_encode: '' - semantic: | - 1 32 _t3 = input 1; - 1 32 _t4 = read XRegs _t3; - 1 32 _t5 = input 0; - 1 32 _t6 = op add_32 _t4 _t5; - 1 16 _t8 = env readMem16 _t6; - 1 32 _t10 = op extend_zero_16_to_32 _t8; - 1 32 _t11 = input 2; - 1 = write XRegs _t11 _t10; - - name: ecall - attributes: [] - operand_sizes: [] - operand_names: [] - encoding: - encoded_size: 32 - const_encoding_part: 115 - const_mask: 4294967295 - decode: [] - encode: '' - constraint_decode: constraint_6 - constraint_encode: '' - semantic: | - 1 = env sysCall; diff --git a/python/tests/integration/test_integration.py b/python/tests/integration/test_integration.py deleted file mode 100644 index 6f79da7..0000000 --- a/python/tests/integration/test_integration.py +++ /dev/null @@ -1,26 +0,0 @@ -import subprocess, sys -from pathlib import Path - -from python.lira import arch_ser_yaml - -PROJECT_ROOT = Path(__file__).parent.parent.parent.parent -REFERENCE = PROJECT_ROOT / "tests" / "integration" / "reference.yaml" -CANONICALIZE = PROJECT_ROOT / "tools" / "yaml_canonicalize.py" - - -def test_integration(): - ref_arch = arch_ser_yaml.read_arch(REFERENCE) - - output = PROJECT_ROOT / "python" / "tests" / "integration" / "integration.yaml" - raw = output.with_suffix(".raw.yaml") - try: - arch_ser_yaml.write_arch(ref_arch, raw) - subprocess.run( - [sys.executable, str(CANONICALIZE), str(raw), str(output)], check=True - ) - raw.unlink() - - arch2 = arch_ser_yaml.read_arch(output) - assert ref_arch == arch2, "Round-trip failed" - finally: - raw.unlink(missing_ok=True) diff --git a/ruby/tests/integration/copy.rb b/ruby/tests/integration/copy.rb new file mode 100644 index 0000000..eef9673 --- /dev/null +++ b/ruby/tests/integration/copy.rb @@ -0,0 +1,11 @@ +$LOAD_PATH.unshift(File.expand_path('../..', __dir__)) +require 'lira' +include Lira + +if ARGV.length != 2 + $stderr.puts "Usage: #{$0} " + exit 1 +end + +arch = ArchSerYaml.read_arch(ARGV[0]) +ArchSerYaml.write_arch(arch, ARGV[1]) diff --git a/ruby/tests/integration/test_integration.rb b/ruby/tests/integration/test_integration.rb deleted file mode 100644 index b838a0b..0000000 --- a/ruby/tests/integration/test_integration.rb +++ /dev/null @@ -1,28 +0,0 @@ -$LOAD_PATH.unshift(File.expand_path('../..', __dir__)) -require 'lira' -require 'minitest/autorun' - -include Lira - -PROJECT_ROOT = File.expand_path('../../..', __dir__) -REFERENCE = File.join(PROJECT_ROOT, 'tests', 'integration', 'reference.yaml') -CANONICALIZE = File.join(PROJECT_ROOT, 'tools', 'yaml_canonicalize.py') -OUTPUT = File.join(__dir__, 'integration.yaml') - -class TestIntegration < Minitest::Test - def test_roundtrip_from_reference - ref_arch = ArchSerYaml.read_arch(REFERENCE) - - raw = "#{OUTPUT}.raw" - begin - ArchSerYaml.write_arch(ref_arch, raw) - system('python3', CANONICALIZE, raw, OUTPUT) - File.delete(raw) - - arch2 = ArchSerYaml.read_arch(OUTPUT) - assert_equal ref_arch, arch2, 'round-trip equality failed' - ensure - File.delete(raw) if File.exist?(raw) - end - end -end diff --git a/rust/Cargo.lock b/rust/Cargo.lock index 25f8382..1cc8834 100644 --- a/rust/Cargo.lock +++ b/rust/Cargo.lock @@ -166,6 +166,14 @@ version = "1.0.5" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "1d07550c9036bf2ae0c684c4297d503f838287c83c53686d05370d0e139ae570" +[[package]] +name = "copy" +version = "0.1.0" +dependencies = [ + "anyhow", + "lira", +] + [[package]] name = "crossbeam" version = "0.8.4" @@ -576,14 +584,6 @@ dependencies = [ "yaml-rust", ] -[[package]] -name = "lira-tests" -version = "0.1.0" -dependencies = [ - "anyhow", - "lira", -] - [[package]] name = "lira_trs" version = "0.1.0" diff --git a/rust/Cargo.toml b/rust/Cargo.toml index f534875..49d8487 100644 --- a/rust/Cargo.toml +++ b/rust/Cargo.toml @@ -1,7 +1,7 @@ [workspace] resolver = "3" -members = ["lira", "lira_trs", "tests"] +members = ["lira", "lira_trs", "copy"] [workspace.dependencies] anyhow = "1.0.102" diff --git a/rust/copy/Cargo.toml b/rust/copy/Cargo.toml new file mode 100644 index 0000000..d3dc32e --- /dev/null +++ b/rust/copy/Cargo.toml @@ -0,0 +1,8 @@ +[package] +name = "copy" +version = "0.1.0" +edition = "2024" + +[dependencies] +lira.path = "../lira" +anyhow = { workspace = true } diff --git a/rust/copy/src/main.rs b/rust/copy/src/main.rs new file mode 100644 index 0000000..14df81c --- /dev/null +++ b/rust/copy/src/main.rs @@ -0,0 +1,5 @@ +fn main() -> anyhow::Result<()> { + let args: Vec<_> = std::env::args().collect(); + assert!(args.len() == 3, "Usage: copy "); + lira::Arch::read_yaml(&args[1])?.write_yaml(&args[2]) +} diff --git a/rust/tests/Cargo.toml b/rust/tests/Cargo.toml deleted file mode 100644 index 8f595ab..0000000 --- a/rust/tests/Cargo.toml +++ /dev/null @@ -1,16 +0,0 @@ -[package] -name = "lira-tests" -version = "0.1.0" -edition = "2024" - -[[test]] -name = "cross_language" -path = "../../tests/cross_language/test_cross.rs" - -[[test]] -name = "integration" -path = "integration/main.rs" - -[dependencies] -lira = { path = "../lira" } -anyhow = { workspace = true } diff --git a/rust/tests/README.md b/rust/tests/README.md deleted file mode 100644 index 6a8ca21..0000000 --- a/rust/tests/README.md +++ /dev/null @@ -1,15 +0,0 @@ -# LIRA Rust Tests - -## Integration test - -Reads `tests/integration/reference.yaml`, writes back via [normalization script](../../tools/yaml_canonicalize.py), asserts round-trip equality. - -```bash -cargo test -p lira-tests --test integration -``` - -## All tests - -```bash -cargo test -p lira-tests -``` diff --git a/rust/tests/integration/main.rs b/rust/tests/integration/main.rs deleted file mode 100644 index 3d965a4..0000000 --- a/rust/tests/integration/main.rs +++ /dev/null @@ -1,48 +0,0 @@ -use std::path::PathBuf; - -use lira::*; - -fn project_root() -> PathBuf { - PathBuf::from(env!("CARGO_MANIFEST_DIR")) - .parent() - .unwrap() - .parent() - .unwrap() - .to_path_buf() -} - -#[test] -fn test_roundtrip_from_reference() { - let ref_path = project_root() - .join("tests") - .join("integration") - .join("reference.yaml"); - let ref_arch = Arch::read_yaml(&ref_path).unwrap(); - - let output = PathBuf::from(env!("CARGO_MANIFEST_DIR")) - .join("integration") - .join("integration.yaml"); - std::fs::create_dir_all(output.parent().unwrap()).ok(); - let raw = output.with_extension("raw.yaml"); - - ref_arch.write_yaml(&raw).unwrap(); - let canonicalize = project_root().join("tools").join("yaml_canonicalize.py"); - std::process::Command::new("python3") - .arg(&canonicalize) - .arg(&raw) - .arg(&output) - .status() - .unwrap(); - std::fs::remove_file(&raw).ok(); - - let arch2 = Arch::read_yaml(&output).unwrap(); - - assert_eq!(ref_arch.register_files, arch2.register_files); - assert_eq!(ref_arch.system_registers, arch2.system_registers); - assert_eq!(ref_arch.environment_functions, arch2.environment_functions); - assert_eq!(ref_arch.tables_int, arch2.tables_int); - assert_eq!(ref_arch.operations, arch2.operations); - assert_eq!(ref_arch.snippets, arch2.snippets); - assert_eq!(ref_arch.instructions, arch2.instructions); - assert_eq!(ref_arch, arch2); -} diff --git a/scripts/python.sh b/scripts/python.sh new file mode 100644 index 0000000..abf853b --- /dev/null +++ b/scripts/python.sh @@ -0,0 +1,7 @@ +#!/bin/bash +set -ex + +echo "=== Python tests ===" +pytest python/tests/unit/ -v +pytest --cov=python/lira python/tests/unit/ --cov-report=term +bash scripts/round_trip.sh "python python/tests/integration/copy_.py" diff --git a/scripts/round_trip.sh b/scripts/round_trip.sh new file mode 100644 index 0000000..73426f7 --- /dev/null +++ b/scripts/round_trip.sh @@ -0,0 +1,15 @@ +#!/bin/bash +set -e + +[ $# -eq 1 ] || { echo "Usage: $0 "; exit 1; } + +REF=tests/integration/reference.yaml + +mkdir -p tmp +$1 $REF tmp/raw1.yaml +$1 tmp/raw1.yaml tmp/raw2.yaml +# Round‑trip without canonicalization +diff tmp/raw1.yaml tmp/raw2.yaml +python tools/yaml_canonicalize.py tmp/raw1.yaml tmp/out.yaml +# Round‑trip with canonicalization +diff tmp/out.yaml $REF diff --git a/scripts/ruby.sh b/scripts/ruby.sh new file mode 100644 index 0000000..ce54bf9 --- /dev/null +++ b/scripts/ruby.sh @@ -0,0 +1,9 @@ +#!/bin/bash +set -ex + +echo "=== Ruby tests ===" +ruby -I ruby -I ruby/lib ruby/tests/unit/test_ir_ser_txt.rb +ruby -I ruby -I ruby/lib ruby/tests/unit/test_arch_ser_yaml.rb +ruby -I ruby -I ruby/lib ruby/tests/unit/test_ir_builder.rb +ruby -r simplecov -I ruby -I ruby/lib -e 'SimpleCov.start; Dir["ruby/tests/unit/*.rb"].each { |f| require_relative f }' +bash scripts/round_trip.sh "ruby ruby/tests/integration/copy.rb" diff --git a/scripts/rust.sh b/scripts/rust.sh new file mode 100644 index 0000000..9f77448 --- /dev/null +++ b/scripts/rust.sh @@ -0,0 +1,6 @@ +#!/bin/bash +set -ex + +echo "=== Rust tests ===" +cargo test --manifest-path rust/Cargo.toml +bash scripts/round_trip.sh "cargo run --manifest-path rust/Cargo.toml --bin copy --" From 5eee11815b4141be1d3fd80085a1a4887a29edb1 Mon Sep 17 00:00:00 2001 From: uslstenn Date: Tue, 8 Sep 2026 19:55:08 +0300 Subject: [PATCH 2/7] Restore cross-language testing & minor fixies --- .github/workflows/ci.yml | 50 ++++++++++---------- python/tests/integration/__init__.py | 0 python/tests/integration/test_integration.py | 27 +++++++++++ ruby/tests/integration/test_integration.rb | 30 ++++++++++++ rust/Cargo.lock | 8 ++++ rust/Cargo.toml | 2 +- rust/tests/Cargo.toml | 16 +++++++ rust/tests/README.md | 15 ++++++ rust/tests/integration/main.rs | 46 ++++++++++++++++++ scripts/python.sh | 2 +- scripts/round_trip.sh | 2 +- tests/cross_language/test_cross.py | 21 ++++---- tests/cross_language/test_cross.rb | 18 ++++--- tests/cross_language/test_cross.rs | 26 +++++----- 14 files changed, 208 insertions(+), 55 deletions(-) create mode 100644 python/tests/integration/__init__.py create mode 100644 python/tests/integration/test_integration.py create mode 100644 ruby/tests/integration/test_integration.rb create mode 100644 rust/tests/Cargo.toml create mode 100644 rust/tests/README.md create mode 100644 rust/tests/integration/main.rs diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml index ccbeff9..b7af4e1 100644 --- a/.github/workflows/ci.yml +++ b/.github/workflows/ci.yml @@ -46,30 +46,30 @@ jobs: - name: Run Rust tests (integration, with coverage) run: bash scripts/rust.sh - # cross-language: - # runs-on: ubuntu-latest - # steps: - # - uses: actions/checkout@v4 - # - uses: actions/setup-python@v5 - # with: - # python-version: '3.10' - # - uses: ruby/setup-ruby@v1 - # with: - # ruby-version: '3.3' - # - uses: dtolnay/rust-toolchain@stable - # - run: pip install ruamel.yaml pytest - # - run: gem install minitest + cross-language: + runs-on: ubuntu-latest + steps: + - uses: actions/checkout@v4 + - uses: actions/setup-python@v5 + with: + python-version: '3.10' + - uses: ruby/setup-ruby@v1 + with: + ruby-version: '3.3' + - uses: dtolnay/rust-toolchain@stable + - run: pip install ruamel.yaml pytest + - run: gem install minitest - # - name: Python writes native YAML - # run: pytest tests/cross_language/test_cross.py -k "write" -v - # - name: Ruby writes native YAML - # run: ruby -I ruby -I ruby/lib tests/cross_language/test_cross.rb --name test_ruby_write_and_self_read - # - name: Rust writes native YAML - # run: cd rust && cargo test -p lira-tests --test cross_language test_rust_write_and_self_read + - name: Python writes native YAML + run: pytest tests/cross_language/test_cross.py -k "write" -v + - name: Ruby writes native YAML + run: ruby -I ruby -I ruby/lib tests/cross_language/test_cross.rb --name test_ruby_write_and_self_read + - name: Rust writes native YAML + run: cd rust && cargo test -p lira-tests --test cross_language test_rust_write_and_self_read - # - name: Python reads Ruby and Rust - # run: pytest tests/cross_language/test_cross.py -k "reads" -v - # - name: Ruby reads Python and Rust - # run: ruby -I ruby -I ruby/lib tests/cross_language/test_cross.rb --name '/test_ruby_reads/' - # - name: Rust reads Python and Ruby - # run: cd rust && cargo test -p lira-tests --test cross_language test_rust_reads + - name: Python reads Ruby and Rust + run: pytest tests/cross_language/test_cross.py -k "reads" -v + - name: Ruby reads Python and Rust + run: ruby -I ruby -I ruby/lib tests/cross_language/test_cross.rb --name '/test_ruby_reads/' + - name: Rust reads Python and Ruby + run: cd rust && cargo test -p lira-tests --test cross_language test_rust_reads diff --git a/python/tests/integration/__init__.py b/python/tests/integration/__init__.py new file mode 100644 index 0000000..e69de29 diff --git a/python/tests/integration/test_integration.py b/python/tests/integration/test_integration.py new file mode 100644 index 0000000..4437cb1 --- /dev/null +++ b/python/tests/integration/test_integration.py @@ -0,0 +1,27 @@ +import subprocess, sys +from pathlib import Path + +from python.lira import arch_ser_yaml + +PROJECT_ROOT = Path(__file__).parent.parent.parent.parent +REFERENCE = PROJECT_ROOT / "tests" / "integration" / "reference.yaml" +CANONICALIZE = PROJECT_ROOT / "tools" / "yaml_canonicalize.py" + + +def test_integration(): + ref_arch = arch_ser_yaml.read_arch(REFERENCE) + + output = PROJECT_ROOT / "tmp" / "integration.yaml" + output.parent.mkdir(exist_ok=True) + raw = output.with_suffix(".raw.yaml") + try: + arch_ser_yaml.write_arch(ref_arch, raw) + subprocess.run( + [sys.executable, str(CANONICALIZE), str(raw), str(output)], check=True + ) + raw.unlink() + + arch2 = arch_ser_yaml.read_arch(output) + assert ref_arch == arch2, "Round-trip failed" + finally: + raw.unlink(missing_ok=True) diff --git a/ruby/tests/integration/test_integration.rb b/ruby/tests/integration/test_integration.rb new file mode 100644 index 0000000..a416f48 --- /dev/null +++ b/ruby/tests/integration/test_integration.rb @@ -0,0 +1,30 @@ +$LOAD_PATH.unshift(File.expand_path('../..', __dir__)) +require 'lira' +require 'minitest/autorun' +require 'fileutils' + +include Lira + +PROJECT_ROOT = File.expand_path('../../..', __dir__) +REFERENCE = File.join(PROJECT_ROOT, 'tests', 'integration', 'reference.yaml') +CANONICALIZE = File.join(PROJECT_ROOT, 'tools', 'yaml_canonicalize.py') +OUTPUT = File.join(PROJECT_ROOT, 'tmp', 'integration.yaml') +FileUtils.mkdir_p(File.dirname(OUTPUT)) + +class TestIntegration < Minitest::Test + def test_roundtrip_from_reference + ref_arch = ArchSerYaml.read_arch(REFERENCE) + + raw = "#{OUTPUT}.raw" + begin + ArchSerYaml.write_arch(ref_arch, raw) + system('python3', CANONICALIZE, raw, OUTPUT) + File.delete(raw) + + arch2 = ArchSerYaml.read_arch(OUTPUT) + assert_equal ref_arch, arch2, 'round-trip equality failed' + ensure + File.delete(raw) if File.exist?(raw) + end + end +end diff --git a/rust/Cargo.lock b/rust/Cargo.lock index 1cc8834..a53c18a 100644 --- a/rust/Cargo.lock +++ b/rust/Cargo.lock @@ -584,6 +584,14 @@ dependencies = [ "yaml-rust", ] +[[package]] +name = "lira-tests" +version = "0.1.0" +dependencies = [ + "anyhow", + "lira", +] + [[package]] name = "lira_trs" version = "0.1.0" diff --git a/rust/Cargo.toml b/rust/Cargo.toml index 49d8487..43c02f4 100644 --- a/rust/Cargo.toml +++ b/rust/Cargo.toml @@ -1,7 +1,7 @@ [workspace] resolver = "3" -members = ["lira", "lira_trs", "copy"] +members = ["lira", "lira_trs", "tests", "copy"] [workspace.dependencies] anyhow = "1.0.102" diff --git a/rust/tests/Cargo.toml b/rust/tests/Cargo.toml new file mode 100644 index 0000000..8f595ab --- /dev/null +++ b/rust/tests/Cargo.toml @@ -0,0 +1,16 @@ +[package] +name = "lira-tests" +version = "0.1.0" +edition = "2024" + +[[test]] +name = "cross_language" +path = "../../tests/cross_language/test_cross.rs" + +[[test]] +name = "integration" +path = "integration/main.rs" + +[dependencies] +lira = { path = "../lira" } +anyhow = { workspace = true } diff --git a/rust/tests/README.md b/rust/tests/README.md new file mode 100644 index 0000000..6a8ca21 --- /dev/null +++ b/rust/tests/README.md @@ -0,0 +1,15 @@ +# LIRA Rust Tests + +## Integration test + +Reads `tests/integration/reference.yaml`, writes back via [normalization script](../../tools/yaml_canonicalize.py), asserts round-trip equality. + +```bash +cargo test -p lira-tests --test integration +``` + +## All tests + +```bash +cargo test -p lira-tests +``` diff --git a/rust/tests/integration/main.rs b/rust/tests/integration/main.rs new file mode 100644 index 0000000..2457261 --- /dev/null +++ b/rust/tests/integration/main.rs @@ -0,0 +1,46 @@ +use std::path::PathBuf; + +use lira::*; + +fn project_root() -> PathBuf { + PathBuf::from(env!("CARGO_MANIFEST_DIR")) + .parent() + .unwrap() + .parent() + .unwrap() + .to_path_buf() +} + +#[test] +fn test_roundtrip_from_reference() { + let ref_path = project_root() + .join("tests") + .join("integration") + .join("reference.yaml"); + let ref_arch = Arch::read_yaml(&ref_path).unwrap(); + + let output = project_root().join("tmp").join("integration.yaml"); + std::fs::create_dir_all(output.parent().unwrap()).ok(); + let raw = output.with_extension("raw.yaml"); + + ref_arch.write_yaml(&raw).unwrap(); + let canonicalize = project_root().join("tools").join("yaml_canonicalize.py"); + std::process::Command::new("python3") + .arg(&canonicalize) + .arg(&raw) + .arg(&output) + .status() + .unwrap(); + std::fs::remove_file(&raw).ok(); + + let arch2 = Arch::read_yaml(&output).unwrap(); + + assert_eq!(ref_arch.register_files, arch2.register_files); + assert_eq!(ref_arch.system_registers, arch2.system_registers); + assert_eq!(ref_arch.environment_functions, arch2.environment_functions); + assert_eq!(ref_arch.tables_int, arch2.tables_int); + assert_eq!(ref_arch.operations, arch2.operations); + assert_eq!(ref_arch.snippets, arch2.snippets); + assert_eq!(ref_arch.instructions, arch2.instructions); + assert_eq!(ref_arch, arch2); +} diff --git a/scripts/python.sh b/scripts/python.sh index abf853b..f7e02db 100644 --- a/scripts/python.sh +++ b/scripts/python.sh @@ -4,4 +4,4 @@ set -ex echo "=== Python tests ===" pytest python/tests/unit/ -v pytest --cov=python/lira python/tests/unit/ --cov-report=term -bash scripts/round_trip.sh "python python/tests/integration/copy_.py" +bash scripts/round_trip.sh "python3 python/tests/integration/copy_.py" diff --git a/scripts/round_trip.sh b/scripts/round_trip.sh index 73426f7..65c58dd 100644 --- a/scripts/round_trip.sh +++ b/scripts/round_trip.sh @@ -10,6 +10,6 @@ $1 $REF tmp/raw1.yaml $1 tmp/raw1.yaml tmp/raw2.yaml # Round‑trip without canonicalization diff tmp/raw1.yaml tmp/raw2.yaml -python tools/yaml_canonicalize.py tmp/raw1.yaml tmp/out.yaml +python3 tools/yaml_canonicalize.py tmp/raw1.yaml tmp/out.yaml # Round‑trip with canonicalization diff tmp/out.yaml $REF diff --git a/tests/cross_language/test_cross.py b/tests/cross_language/test_cross.py index 88b9ebf..c47f417 100644 --- a/tests/cross_language/test_cross.py +++ b/tests/cross_language/test_cross.py @@ -3,16 +3,19 @@ import pytest -sys.path.insert(0, str(Path(__file__).parent.parent.parent)) +ROOT = Path(__file__).parent.parent.parent +sys.path.insert(0, str(ROOT)) from python.lira import arch_ser_yaml CROSS_DIR = Path(__file__).parent -REFERENCE = Path(__file__).parent.parent / "integration" / "reference.yaml" +REFERENCE = CROSS_DIR.parent / "integration" / "reference.yaml" +TMP_DIR = ROOT / "tmp" +TMP_DIR.mkdir(exist_ok=True) -PY_OUT = CROSS_DIR / "py_native.yaml" -RB_OUT = CROSS_DIR / "rb_native.yaml" -RS_OUT = CROSS_DIR / "rs_native.yaml" +PY_OUT = TMP_DIR / "py_native.yaml" +RB_OUT = TMP_DIR / "rb_native.yaml" +RS_OUT = TMP_DIR / "rs_native.yaml" def test_python_write_and_self_read(): @@ -26,8 +29,8 @@ def test_python_reads_ruby(): if not RB_OUT.exists(): pytest.skip("rb_native.yaml not found") arch = arch_ser_yaml.read_arch(RB_OUT) - arch_ser_yaml.write_arch(arch, CROSS_DIR / "py_from_rb.yaml") - arch2 = arch_ser_yaml.read_arch(CROSS_DIR / "py_from_rb.yaml") + arch_ser_yaml.write_arch(arch, TMP_DIR / "py_from_rb.yaml") + arch2 = arch_ser_yaml.read_arch(TMP_DIR / "py_from_rb.yaml") assert arch == arch2 @@ -35,6 +38,6 @@ def test_python_reads_rust(): if not RS_OUT.exists(): pytest.skip("rs_native.yaml not found") arch = arch_ser_yaml.read_arch(RS_OUT) - arch_ser_yaml.write_arch(arch, CROSS_DIR / "py_from_rs.yaml") - arch2 = arch_ser_yaml.read_arch(CROSS_DIR / "py_from_rs.yaml") + arch_ser_yaml.write_arch(arch, TMP_DIR / "py_from_rs.yaml") + arch2 = arch_ser_yaml.read_arch(TMP_DIR / "py_from_rs.yaml") assert arch == arch2 diff --git a/tests/cross_language/test_cross.rb b/tests/cross_language/test_cross.rb index da42114..14aaee7 100644 --- a/tests/cross_language/test_cross.rb +++ b/tests/cross_language/test_cross.rb @@ -2,15 +2,19 @@ $LOAD_PATH.unshift(File.expand_path('../..', __dir__)) require 'lira' require 'minitest/autorun' +require 'fileutils' include Lira +ROOT = File.expand_path('../..', __dir__) CROSS_DIR = File.expand_path(__dir__) REFERENCE = File.join(CROSS_DIR, '..', 'integration', 'reference.yaml') +TMP_DIR = File.join(ROOT, 'tmp') +FileUtils.mkdir_p(TMP_DIR) -RB_OUT = File.join(CROSS_DIR, 'rb_native.yaml') -PY_OUT = File.join(CROSS_DIR, 'py_native.yaml') -RS_OUT = File.join(CROSS_DIR, 'rs_native.yaml') +RB_OUT = File.join(TMP_DIR, 'rb_native.yaml') +PY_OUT = File.join(TMP_DIR, 'py_native.yaml') +RS_OUT = File.join(TMP_DIR, 'rs_native.yaml') class TestCrossLanguage < Minitest::Test def test_ruby_write_and_self_read @@ -23,16 +27,16 @@ def test_ruby_write_and_self_read def test_ruby_reads_python skip('py_native.yaml not found') unless File.exist?(PY_OUT) arch = ArchSerYaml.read_arch(PY_OUT) - ArchSerYaml.write_arch(arch, File.join(CROSS_DIR, 'rb_from_py.yaml')) - arch2 = ArchSerYaml.read_arch(File.join(CROSS_DIR, 'rb_from_py.yaml')) + ArchSerYaml.write_arch(arch, File.join(TMP_DIR, 'rb_from_py.yaml')) + arch2 = ArchSerYaml.read_arch(File.join(TMP_DIR, 'rb_from_py.yaml')) assert_equal arch, arch2 end def test_ruby_reads_rust skip('rs_native.yaml not found') unless File.exist?(RS_OUT) arch = ArchSerYaml.read_arch(RS_OUT) - ArchSerYaml.write_arch(arch, File.join(CROSS_DIR, 'rb_from_rs.yaml')) - arch2 = ArchSerYaml.read_arch(File.join(CROSS_DIR, 'rb_from_rs.yaml')) + ArchSerYaml.write_arch(arch, File.join(TMP_DIR, 'rb_from_rs.yaml')) + arch2 = ArchSerYaml.read_arch(File.join(TMP_DIR, 'rb_from_rs.yaml')) assert_equal arch, arch2 end end diff --git a/tests/cross_language/test_cross.rs b/tests/cross_language/test_cross.rs index 39e4c88..53b7d5d 100644 --- a/tests/cross_language/test_cross.rs +++ b/tests/cross_language/test_cross.rs @@ -2,20 +2,24 @@ use std::path::PathBuf; use lira::*; -fn cross_dir() -> PathBuf { +fn project_root() -> PathBuf { PathBuf::from(env!("CARGO_MANIFEST_DIR")) .parent() .unwrap() .parent() .unwrap() - .join("tests") - .join("cross_language") + .to_path_buf() +} + +fn tmp_dir() -> PathBuf { + let dir = project_root().join("tmp"); + std::fs::create_dir_all(&dir).ok(); + dir } fn reference() -> PathBuf { - cross_dir() - .parent() - .unwrap() + project_root() + .join("tests") .join("integration") .join("reference.yaml") } @@ -23,7 +27,7 @@ fn reference() -> PathBuf { #[test] fn test_rust_write_and_self_read() { let arch = Arch::read_yaml(&reference()).unwrap(); - let out = cross_dir().join("rs_native.yaml"); + let out = tmp_dir().join("rs_native.yaml"); arch.write_yaml(&out).unwrap(); let arch2 = Arch::read_yaml(&out).unwrap(); assert_eq!(arch, arch2); @@ -31,12 +35,12 @@ fn test_rust_write_and_self_read() { #[test] fn test_rust_reads_python() { - let py_out = cross_dir().join("py_native.yaml"); + let py_out = tmp_dir().join("py_native.yaml"); if !py_out.exists() { return; } let arch = Arch::read_yaml(&py_out).unwrap(); - let tmp = cross_dir().join("rs_from_py.yaml"); + let tmp = tmp_dir().join("rs_from_py.yaml"); arch.write_yaml(&tmp).unwrap(); let arch2 = Arch::read_yaml(&tmp).unwrap(); assert_eq!(arch, arch2); @@ -45,12 +49,12 @@ fn test_rust_reads_python() { #[test] fn test_rust_reads_ruby() { - let rb_out = cross_dir().join("rb_native.yaml"); + let rb_out = tmp_dir().join("rb_native.yaml"); if !rb_out.exists() { return; } let arch = Arch::read_yaml(&rb_out).unwrap(); - let tmp = cross_dir().join("rs_from_rb.yaml"); + let tmp = tmp_dir().join("rs_from_rb.yaml"); arch.write_yaml(&tmp).unwrap(); let arch2 = Arch::read_yaml(&tmp).unwrap(); assert_eq!(arch, arch2); From 1077f9b1052544d01f0f2a46a10b7d72cd456fdc Mon Sep 17 00:00:00 2001 From: uslstenn Date: Wed, 9 Sep 2026 00:33:19 +0300 Subject: [PATCH 3/7] [python, lib] Introduced copy arch method --- python/lira/__init__.py | 2 +- python/lira/arch_ser_yaml.py | 4 ++++ python/tests/integration/copy_.py | 16 ++++++++-------- python/tests/integration/test_integration.py | 2 +- tests/cross_language/test_cross.py | 6 +++--- 5 files changed, 17 insertions(+), 13 deletions(-) diff --git a/python/lira/__init__.py b/python/lira/__init__.py index ea7988d..5b84bd5 100644 --- a/python/lira/__init__.py +++ b/python/lira/__init__.py @@ -6,5 +6,5 @@ Instruction, InstructionEncoding, Snippet, SystemRegister, SystemRegisterField, TableInt, ) -from .arch_ser_yaml import write_arch, read_arch +from .arch_ser_yaml import write_arch, read_arch, copy_arch from .ir_ops import BaseOp diff --git a/python/lira/arch_ser_yaml.py b/python/lira/arch_ser_yaml.py index 6151ed7..ff6d7a0 100644 --- a/python/lira/arch_ser_yaml.py +++ b/python/lira/arch_ser_yaml.py @@ -55,3 +55,7 @@ def read_arch(filepath: Path) -> Arch: with open(filepath, 'r', encoding='utf-8') as f: data = yaml.load(f) return from_serializable(Arch, data) + + +def copy_arch(path_input: Path, path_output: Path) -> None: + write_arch(read_arch(path_input), path_output) diff --git a/python/tests/integration/copy_.py b/python/tests/integration/copy_.py index f584e6a..98d869e 100644 --- a/python/tests/integration/copy_.py +++ b/python/tests/integration/copy_.py @@ -1,14 +1,14 @@ -assert __name__ == '__main__' - import sys from pathlib import Path -from lira import arch_ser_yaml +ROOT = Path(__file__).resolve().parents[3] +if str(ROOT) not in sys.path: + sys.path.insert(0, str(ROOT)) -assert len(sys.argv) == 3, 'copy.py ' +from python.lira.arch_ser_yaml import copy_arch -path_input = Path(sys.argv[1]) -path_output = Path(sys.argv[2]) -ref_arch = arch_ser_yaml.read_arch(path_input) -arch_ser_yaml.write_arch(ref_arch, path_output) +if __name__ == '__main__': + if len(sys.argv) != 3: + sys.exit('Usage: copy_.py ') + copy_arch(Path(sys.argv[1]), Path(sys.argv[2])) diff --git a/python/tests/integration/test_integration.py b/python/tests/integration/test_integration.py index 4437cb1..3bbc0c5 100644 --- a/python/tests/integration/test_integration.py +++ b/python/tests/integration/test_integration.py @@ -15,7 +15,7 @@ def test_integration(): output.parent.mkdir(exist_ok=True) raw = output.with_suffix(".raw.yaml") try: - arch_ser_yaml.write_arch(ref_arch, raw) + arch_ser_yaml.copy_arch(REFERENCE, raw) subprocess.run( [sys.executable, str(CANONICALIZE), str(raw), str(output)], check=True ) diff --git a/tests/cross_language/test_cross.py b/tests/cross_language/test_cross.py index c47f417..76b3d81 100644 --- a/tests/cross_language/test_cross.py +++ b/tests/cross_language/test_cross.py @@ -20,7 +20,7 @@ def test_python_write_and_self_read(): arch = arch_ser_yaml.read_arch(REFERENCE) - arch_ser_yaml.write_arch(arch, PY_OUT) + arch_ser_yaml.copy_arch(REFERENCE, PY_OUT) arch2 = arch_ser_yaml.read_arch(PY_OUT) assert arch == arch2 @@ -29,7 +29,7 @@ def test_python_reads_ruby(): if not RB_OUT.exists(): pytest.skip("rb_native.yaml not found") arch = arch_ser_yaml.read_arch(RB_OUT) - arch_ser_yaml.write_arch(arch, TMP_DIR / "py_from_rb.yaml") + arch_ser_yaml.copy_arch(RB_OUT, TMP_DIR / "py_from_rb.yaml") arch2 = arch_ser_yaml.read_arch(TMP_DIR / "py_from_rb.yaml") assert arch == arch2 @@ -38,6 +38,6 @@ def test_python_reads_rust(): if not RS_OUT.exists(): pytest.skip("rs_native.yaml not found") arch = arch_ser_yaml.read_arch(RS_OUT) - arch_ser_yaml.write_arch(arch, TMP_DIR / "py_from_rs.yaml") + arch_ser_yaml.copy_arch(RS_OUT, TMP_DIR / "py_from_rs.yaml") arch2 = arch_ser_yaml.read_arch(TMP_DIR / "py_from_rs.yaml") assert arch == arch2 From f37e5b27bdbc863e2b646b0bfddd32efe533519c Mon Sep 17 00:00:00 2001 From: uslstenn Date: Wed, 9 Sep 2026 00:34:08 +0300 Subject: [PATCH 4/7] [ruby, lib] Introduced copy arch method --- ruby/lira/arch_ser_yaml.rb | 4 ++++ ruby/tests/integration/copy.rb | 3 +-- ruby/tests/integration/test_integration.rb | 2 +- tests/cross_language/test_cross.rb | 6 +++--- 4 files changed, 9 insertions(+), 6 deletions(-) diff --git a/ruby/lira/arch_ser_yaml.rb b/ruby/lira/arch_ser_yaml.rb index ba68c65..6ab6b44 100644 --- a/ruby/lira/arch_ser_yaml.rb +++ b/ruby/lira/arch_ser_yaml.rb @@ -56,5 +56,9 @@ def read_arch(filepath) data = YAML.load_file(filepath) from_serializable(Arch, data) end + + def copy_arch(src, dst) + write_arch(read_arch(src), dst) + end end end diff --git a/ruby/tests/integration/copy.rb b/ruby/tests/integration/copy.rb index eef9673..8ee9742 100644 --- a/ruby/tests/integration/copy.rb +++ b/ruby/tests/integration/copy.rb @@ -7,5 +7,4 @@ exit 1 end -arch = ArchSerYaml.read_arch(ARGV[0]) -ArchSerYaml.write_arch(arch, ARGV[1]) +ArchSerYaml.copy_arch(ARGV[0], ARGV[1]) diff --git a/ruby/tests/integration/test_integration.rb b/ruby/tests/integration/test_integration.rb index a416f48..da6ce6d 100644 --- a/ruby/tests/integration/test_integration.rb +++ b/ruby/tests/integration/test_integration.rb @@ -17,7 +17,7 @@ def test_roundtrip_from_reference raw = "#{OUTPUT}.raw" begin - ArchSerYaml.write_arch(ref_arch, raw) + ArchSerYaml.copy_arch(REFERENCE, raw) system('python3', CANONICALIZE, raw, OUTPUT) File.delete(raw) diff --git a/tests/cross_language/test_cross.rb b/tests/cross_language/test_cross.rb index 14aaee7..51e2ae4 100644 --- a/tests/cross_language/test_cross.rb +++ b/tests/cross_language/test_cross.rb @@ -19,7 +19,7 @@ class TestCrossLanguage < Minitest::Test def test_ruby_write_and_self_read arch = ArchSerYaml.read_arch(REFERENCE) - ArchSerYaml.write_arch(arch, RB_OUT) + ArchSerYaml.copy_arch(REFERENCE, RB_OUT) arch2 = ArchSerYaml.read_arch(RB_OUT) assert_equal arch, arch2 end @@ -27,7 +27,7 @@ def test_ruby_write_and_self_read def test_ruby_reads_python skip('py_native.yaml not found') unless File.exist?(PY_OUT) arch = ArchSerYaml.read_arch(PY_OUT) - ArchSerYaml.write_arch(arch, File.join(TMP_DIR, 'rb_from_py.yaml')) + ArchSerYaml.copy_arch(PY_OUT, File.join(TMP_DIR, 'rb_from_py.yaml')) arch2 = ArchSerYaml.read_arch(File.join(TMP_DIR, 'rb_from_py.yaml')) assert_equal arch, arch2 end @@ -35,7 +35,7 @@ def test_ruby_reads_python def test_ruby_reads_rust skip('rs_native.yaml not found') unless File.exist?(RS_OUT) arch = ArchSerYaml.read_arch(RS_OUT) - ArchSerYaml.write_arch(arch, File.join(TMP_DIR, 'rb_from_rs.yaml')) + ArchSerYaml.copy_arch(RS_OUT, File.join(TMP_DIR, 'rb_from_rs.yaml')) arch2 = ArchSerYaml.read_arch(File.join(TMP_DIR, 'rb_from_rs.yaml')) assert_equal arch, arch2 end From cd1d555252b6fce568580c5bd1d874a7f0f4d80b Mon Sep 17 00:00:00 2001 From: uslstenn Date: Wed, 9 Sep 2026 00:34:42 +0300 Subject: [PATCH 5/7] [rust, lib] Introduced copy arch method --- rust/Cargo.lock | 1 + rust/copy/src/lib.rs | 5 +++++ rust/copy/src/main.rs | 2 +- rust/tests/Cargo.toml | 1 + rust/tests/integration/main.rs | 2 +- tests/cross_language/test_cross.rs | 6 +++--- 6 files changed, 12 insertions(+), 5 deletions(-) create mode 100644 rust/copy/src/lib.rs diff --git a/rust/Cargo.lock b/rust/Cargo.lock index a53c18a..5e47705 100644 --- a/rust/Cargo.lock +++ b/rust/Cargo.lock @@ -589,6 +589,7 @@ name = "lira-tests" version = "0.1.0" dependencies = [ "anyhow", + "copy", "lira", ] diff --git a/rust/copy/src/lib.rs b/rust/copy/src/lib.rs new file mode 100644 index 0000000..6c92c9a --- /dev/null +++ b/rust/copy/src/lib.rs @@ -0,0 +1,5 @@ +use std::path::Path; + +pub fn copy_arch(src: &Path, dst: &Path) -> anyhow::Result<()> { + lira::Arch::read_yaml(src)?.write_yaml(dst) +} diff --git a/rust/copy/src/main.rs b/rust/copy/src/main.rs index 14df81c..4ffffaf 100644 --- a/rust/copy/src/main.rs +++ b/rust/copy/src/main.rs @@ -1,5 +1,5 @@ fn main() -> anyhow::Result<()> { let args: Vec<_> = std::env::args().collect(); assert!(args.len() == 3, "Usage: copy "); - lira::Arch::read_yaml(&args[1])?.write_yaml(&args[2]) + copy::copy_arch(std::path::Path::new(&args[1]), std::path::Path::new(&args[2])) } diff --git a/rust/tests/Cargo.toml b/rust/tests/Cargo.toml index 8f595ab..26092f0 100644 --- a/rust/tests/Cargo.toml +++ b/rust/tests/Cargo.toml @@ -13,4 +13,5 @@ path = "integration/main.rs" [dependencies] lira = { path = "../lira" } +copy = { path = "../copy" } anyhow = { workspace = true } diff --git a/rust/tests/integration/main.rs b/rust/tests/integration/main.rs index 2457261..36e1810 100644 --- a/rust/tests/integration/main.rs +++ b/rust/tests/integration/main.rs @@ -23,7 +23,7 @@ fn test_roundtrip_from_reference() { std::fs::create_dir_all(output.parent().unwrap()).ok(); let raw = output.with_extension("raw.yaml"); - ref_arch.write_yaml(&raw).unwrap(); + copy::copy_arch(&ref_path, &raw).unwrap(); let canonicalize = project_root().join("tools").join("yaml_canonicalize.py"); std::process::Command::new("python3") .arg(&canonicalize) diff --git a/tests/cross_language/test_cross.rs b/tests/cross_language/test_cross.rs index 53b7d5d..72eca08 100644 --- a/tests/cross_language/test_cross.rs +++ b/tests/cross_language/test_cross.rs @@ -28,7 +28,7 @@ fn reference() -> PathBuf { fn test_rust_write_and_self_read() { let arch = Arch::read_yaml(&reference()).unwrap(); let out = tmp_dir().join("rs_native.yaml"); - arch.write_yaml(&out).unwrap(); + copy::copy_arch(&reference(), &out).unwrap(); let arch2 = Arch::read_yaml(&out).unwrap(); assert_eq!(arch, arch2); } @@ -41,7 +41,7 @@ fn test_rust_reads_python() { } let arch = Arch::read_yaml(&py_out).unwrap(); let tmp = tmp_dir().join("rs_from_py.yaml"); - arch.write_yaml(&tmp).unwrap(); + copy::copy_arch(&py_out, &tmp).unwrap(); let arch2 = Arch::read_yaml(&tmp).unwrap(); assert_eq!(arch, arch2); std::fs::remove_file(&tmp).ok(); @@ -55,7 +55,7 @@ fn test_rust_reads_ruby() { } let arch = Arch::read_yaml(&rb_out).unwrap(); let tmp = tmp_dir().join("rs_from_rb.yaml"); - arch.write_yaml(&tmp).unwrap(); + copy::copy_arch(&rb_out, &tmp).unwrap(); let arch2 = Arch::read_yaml(&tmp).unwrap(); assert_eq!(arch, arch2); std::fs::remove_file(&tmp).ok(); From 59785d514101677128f6de9ee25bf58b63b77704 Mon Sep 17 00:00:00 2001 From: uslstenn Date: Wed, 9 Sep 2026 00:35:12 +0300 Subject: [PATCH 6/7] [scripts, integration] Run integration tests in scripts --- scripts/python.sh | 1 + scripts/ruby.sh | 1 + 2 files changed, 2 insertions(+) diff --git a/scripts/python.sh b/scripts/python.sh index f7e02db..53868fa 100644 --- a/scripts/python.sh +++ b/scripts/python.sh @@ -5,3 +5,4 @@ echo "=== Python tests ===" pytest python/tests/unit/ -v pytest --cov=python/lira python/tests/unit/ --cov-report=term bash scripts/round_trip.sh "python3 python/tests/integration/copy_.py" +pytest python/tests/integration/ -v diff --git a/scripts/ruby.sh b/scripts/ruby.sh index ce54bf9..47a8efe 100644 --- a/scripts/ruby.sh +++ b/scripts/ruby.sh @@ -7,3 +7,4 @@ ruby -I ruby -I ruby/lib ruby/tests/unit/test_arch_ser_yaml.rb ruby -I ruby -I ruby/lib ruby/tests/unit/test_ir_builder.rb ruby -r simplecov -I ruby -I ruby/lib -e 'SimpleCov.start; Dir["ruby/tests/unit/*.rb"].each { |f| require_relative f }' bash scripts/round_trip.sh "ruby ruby/tests/integration/copy.rb" +ruby -I ruby -I ruby/lib ruby/tests/integration/test_integration.rb From cf382de42b117a6325718916cb0ee202bd1f4ffc Mon Sep 17 00:00:00 2001 From: dan <70999565+belovdv@users.noreply.github.com> Date: Wed, 9 Sep 2026 11:22:17 +0300 Subject: [PATCH 7/7] Move testing scripts to tests directory --- .github/workflows/ci.yml | 6 +++--- scripts/rust.sh | 6 ------ {scripts => tests/scripts}/python.sh | 2 +- {scripts => tests/scripts}/round_trip.sh | 0 {scripts => tests/scripts}/ruby.sh | 2 +- tests/scripts/rust.sh | 6 ++++++ 6 files changed, 11 insertions(+), 11 deletions(-) delete mode 100644 scripts/rust.sh rename {scripts => tests/scripts}/python.sh (69%) rename {scripts => tests/scripts}/round_trip.sh (100%) rename {scripts => tests/scripts}/ruby.sh (85%) create mode 100644 tests/scripts/rust.sh diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml index b7af4e1..98bdee9 100644 --- a/.github/workflows/ci.yml +++ b/.github/workflows/ci.yml @@ -16,7 +16,7 @@ jobs: - run: pip install ruamel.yaml pytest pytest-cov - run: pip install -e python/ - name: Run Python tests (unit, integration, coverage) - run: bash scripts/python.sh + run: bash tests/scripts/python.sh ruby-tests: runs-on: ubuntu-latest @@ -31,7 +31,7 @@ jobs: - run: pip install ruamel.yaml - run: gem install minitest simplecov - name: Run Ruby tests (unit, integration, coverage) - run: bash scripts/ruby.sh + run: bash tests/scripts/ruby.sh rust-tests: runs-on: ubuntu-latest @@ -44,7 +44,7 @@ jobs: - run: sudo apt-get update && sudo apt-get install -y z3 - run: pip install ruamel.yaml - name: Run Rust tests (integration, with coverage) - run: bash scripts/rust.sh + run: bash tests/scripts/rust.sh cross-language: runs-on: ubuntu-latest diff --git a/scripts/rust.sh b/scripts/rust.sh deleted file mode 100644 index 9f77448..0000000 --- a/scripts/rust.sh +++ /dev/null @@ -1,6 +0,0 @@ -#!/bin/bash -set -ex - -echo "=== Rust tests ===" -cargo test --manifest-path rust/Cargo.toml -bash scripts/round_trip.sh "cargo run --manifest-path rust/Cargo.toml --bin copy --" diff --git a/scripts/python.sh b/tests/scripts/python.sh similarity index 69% rename from scripts/python.sh rename to tests/scripts/python.sh index 53868fa..dc856db 100644 --- a/scripts/python.sh +++ b/tests/scripts/python.sh @@ -4,5 +4,5 @@ set -ex echo "=== Python tests ===" pytest python/tests/unit/ -v pytest --cov=python/lira python/tests/unit/ --cov-report=term -bash scripts/round_trip.sh "python3 python/tests/integration/copy_.py" +bash tests/scripts/round_trip.sh "python3 python/tests/integration/copy_.py" pytest python/tests/integration/ -v diff --git a/scripts/round_trip.sh b/tests/scripts/round_trip.sh similarity index 100% rename from scripts/round_trip.sh rename to tests/scripts/round_trip.sh diff --git a/scripts/ruby.sh b/tests/scripts/ruby.sh similarity index 85% rename from scripts/ruby.sh rename to tests/scripts/ruby.sh index 47a8efe..8b7c18c 100644 --- a/scripts/ruby.sh +++ b/tests/scripts/ruby.sh @@ -6,5 +6,5 @@ ruby -I ruby -I ruby/lib ruby/tests/unit/test_ir_ser_txt.rb ruby -I ruby -I ruby/lib ruby/tests/unit/test_arch_ser_yaml.rb ruby -I ruby -I ruby/lib ruby/tests/unit/test_ir_builder.rb ruby -r simplecov -I ruby -I ruby/lib -e 'SimpleCov.start; Dir["ruby/tests/unit/*.rb"].each { |f| require_relative f }' -bash scripts/round_trip.sh "ruby ruby/tests/integration/copy.rb" +bash tests/scripts/round_trip.sh "ruby ruby/tests/integration/copy.rb" ruby -I ruby -I ruby/lib ruby/tests/integration/test_integration.rb diff --git a/tests/scripts/rust.sh b/tests/scripts/rust.sh new file mode 100644 index 0000000..2cbe3dd --- /dev/null +++ b/tests/scripts/rust.sh @@ -0,0 +1,6 @@ +#!/bin/bash +set -ex + +echo "=== Rust tests ===" +cargo test --manifest-path rust/Cargo.toml +bash tests/scripts/round_trip.sh "cargo run --manifest-path rust/Cargo.toml --bin copy --"