# Copyright (c) 2021-2022 Huawei Device Co., Ltd. # Licensed under the Apache License, Version 2.0 (the "License"); # you may not use this file except in compliance with the License. # You may obtain a copy of the License at # # http://www.apache.org/licenses/LICENSE-2.0 # # Unless required by applicable law or agreed to in writing, software # distributed under the License is distributed on an "AS IS" BASIS, # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. # See the License for the specific language governing permissions and # limitations under the License. definitions: - name: PandaAssembly template: | .language PandaAssembly - name: aoobe_p template: | .record panda.ArrayIndexOutOfBoundsException .record R {} - name: aoobe_j template: | .record panda.ArrayIndexOutOfBoundsException .record panda.String .record R {} - name: npe_p template: | .record panda.NullPointerException - name: npe_j template: | .record panda.NullPointerException tests: - file-name: "ldarr.obj" isa: title: Load from array description: > Load an element from array using accumulator as an index and puts it into accumulator. instructions: - sig: ldarr.obj v:in:ref[] acc: inout:i32->ref format: [op_v_8] commands: - file-name: "reg_number" isa: description: > Load an element from array using accumulator as an index and puts it into accumulator. runner-options: [compile-only] description: Check 'ldarr.obj' instruction with different register numbers. header-template: [] code-template: | # .function i32 main() { ldarr.obj %s check-type: exit-positive cases: - values: [v0] - values: [v16] - values: [v128] - values: [v255] - values: [v256] runner-options: [compile-failure] - values: [v65535] runner-options: [compile-failure] - case-template: | # .function void f1(i32 a0) { ldarr.obj a0 # valid name of register return.void } .function i32 main() { movi v0, 0 call.short f1, v0 - case-template: | # .function void f1(i32 a0) { ldarr.obj a1 # invalid name of register return.void } .function i32 main() { movi v0, 0 call.short f1, v0 runner-options: [compile-failure] - values: [a0] runner-options: [compile-failure] - values: [a255] runner-options: [compile-failure] - values: ['null'] runner-options: [compile-failure] - values: [0] runner-options: [compile-failure] - values: [1.1] runner-options: [compile-failure] - values: ['2.2'] runner-options: [compile-failure] - file-name: uninitialized_acc isa: verification: - acc_i32 description: Check 'ldarr.obj' with uninitialized accumulator tags: ['verifier'] runner-options: ['verifier-failure', 'verifier-config'] header-template: [] code-template: | # .record R {} .function void f1(R[] a0) { ldarr.obj a0 return.void } .function i32 main() { movi v1, 100 newarr v1, v1, R[] call.short f1, v1 check-type: exit-positive - file-name: uninitialized_reg isa: verification: - v1_array_type description: Check 'ldarr.obj' with uninitialized register tags: ['verifier'] runner-options: ['verifier-failure', 'verifier-config'] header-template: [] code-template: | # .function i32 main() { ldai 0 ldarr.obj v2 check-type: exit-positive - file-name: uninitialized_acc_and_reg isa: verification: - v1_array_type - acc_i32 description: Check 'ldarr.obj' with uninitialized register and accumulator tags: ['verifier'] runner-options: ['verifier-failure', 'verifier-config'] header-template: [] code-template: | # .function i32 main() { ldarr.obj v2 check-type: exit-positive - file-name: null_pointer_p isa: exceptions: - x_null description: Check 'ldarr.obj' behavior when array is null reference. tags: ['irtoc_ignore'] header-template: [npe_p] bugid: ['3228'] code-template: | .record R {} .function R[] get_null() { lda.null return.obj } .function i32 main() { call.short get_null sta.obj v0 ldai %s begin: ldarr.obj v0 end: ldai 1 # Should not reach this line return catch_NPE: ldai 0 # Expected panda.NullPointerException return catch_all: ldai 2 # Unexpected exception, test failed return .catch panda.NullPointerException, begin, end, catch_NPE .catchall begin, end, catch_all check-type: none cases: - values: [0] tags: ['tsan'] - values: [1] - values: [10] - values: [128] - values: [255] - values: [65535] tags: ['tsan'] - values: [0x7FFFFFFF] - values: [0xFFFFFFFF] - values: [0x80000000] - file-name: null_pointer_j isa: exceptions: - x_null description: Check 'ldarr.obj' behavior when array is null reference. tags: ['irtoc_ignore'] header-template: [PandaAssembly, npe_j] runner-options: [use-pa] bugid: ['3047', '3228'] code-template: | .record R {} .function R[] get_null() { lda.null return.obj } .function i32 main() { call.short get_null sta.obj v0 ldai %s begin: ldarr.obj v0 end: ldai 1 # Should not reach this line return catch_NPE: ldai 0 # Expected panda.NullPointerException return catch_all: ldai 2 # Unexpected exception, test failed return .catch panda.NullPointerException, begin, end, catch_NPE .catchall begin, end, catch_all check-type: none cases: - values: [0] tags: ['tsan'] - values: [1] - values: [10] - values: [128] - values: [255] - values: [65535] tags: ['tsan'] - values: [0x7FFFFFFF] - values: [0xFFFFFFFF] - values: [0x80000000] - file-name: array_out_of_bound_exception_p isa: exceptions: - x_bounds description: Check 'ldarr.obj' behavior when index is out of array bounds. header-template: [aoobe_p, main] tags: ['irtoc_ignore'] code-template: | # movi v0, *s newarr v0, v0, %s ldai *s begin: ldarr.obj v0 end: ldai 1 # Should not reach this line return catch_AOOBE: ldai 0 # Expected panda.ArrayIndexOutOfBoundsException return catch_all: ldai 2 # Unexpected exception, test failed return .catch panda.ArrayIndexOutOfBoundsException, begin, end, catch_AOOBE .catchall begin, end, catch_all check-type: none template-cases: - values: ['R[]'] - values: ['R[][][]'] cases: - values: [0, 0] tags: ['tsan'] - values: [0, 1] - values: [10, -10] - values: [10, 128] - values: [255, 255] - values: [254, 255] - values: [65535, 65535] tags: ['tsan'] - values: [65535, 65536] - values: [10, 0xFFFFFFFF] - values: [256, 0xFFFFFFFE] - values: [65536, 0xFFFFFFFD] tags: ['tsan'] - values: [0x100000, 0xFFFFFFFC] - values: [10, 0x80000000] - values: [256, 0x80000001] - values: [65536, 0x80000002] tags: ['tsan'] - values: [0x100000, 0x80000003] - file-name: array_out_of_bound_exception_j isa: exceptions: - x_bounds description: Check 'ldarr.obj' behavior when index is out of array bounds. runner-options: [use-pa] tags: ['irtoc_ignore'] header-template: [PandaAssembly, aoobe_j, main] bugid: ['3227'] code-template: | # movi v0, *s newarr v0, v0, %s ldai *s begin: ldarr.obj v0 end: ldai 1 # Should not reach this line return catch_AOOBE: ldai 0 # Expected panda.ArrayIndexOutOfBoundsException return catch_all: ldai 2 # Unexpected exception, test failed return .catch panda.ArrayIndexOutOfBoundsException, begin, end, catch_AOOBE .catchall begin, end, catch_all check-type: none template-cases: - values: ['R[]'] - values: ['panda.String[][][]'] cases: - values: [0, 0] tags: ['tsan'] - values: [0, 1] - values: [10, -10] - values: [10, 128] - values: [255, 255] - values: [254, 255] - values: [65535, 65535] tags: ['tsan'] - values: [65535, 65536] - values: [10, 0xFFFFFFFF] - values: [256, 0xFFFFFFFE] - values: [65536, 0xFFFFFFFD] tags: ['tsan'] - values: [0x100000, 0xFFFFFFFC] - values: [10, 0x80000000] - values: [256, 0x80000001] - values: [65536, 0x80000002] tags: ['tsan'] - values: [0x100000, 0x80000003] - file-name: "rejectable_primitive_types_p" isa: verification: - v1_array_type description: Check rejectable array of primitive types for ldarr.obj instruction in Panda Assembly context. code-template: | # movi v0, 1 newarr v0, v0, %s ldai 0 ldarr.obj v0 check-type: exit-positive tags: ['verifier'] runner-options: ['verifier-failure', 'verifier-config'] cases: - values: ['u1[]'] - values: ['i8[]'] - values: ['u8[]'] - values: ['i16[]'] - values: ['u16[]'] - values: ['i32[]'] - values: ['u32[]'] - values: ['i64[]'] - values: ['u64[]'] - values: ['f32[]'] - values: ['f64[]'] - file-name: "rejectable_primitive_types_j" isa: verification: - v1_array_type description: Check rejectable array of primitive types for ldarr.obj instruction in PandaAssembly context. header-template: [PandaAssembly, main] code-template: | # movi v0, 1 newarr v0, v0, %s ldai 0 ldarr.obj v0 check-type: exit-positive tags: [verifier, pa-verifier] bugid: ['3293', '5271'] runner-options: [verifier-failure, use-pa, verifier-config] cases: - values: ['u1[]'] - values: ['i8[]'] - values: ['u8[]'] - values: ['i16[]'] - values: ['u16[]'] - values: ['i32[]'] - values: ['u32[]'] - values: ['i64[]'] - values: ['u64[]'] - values: ['f32[]'] - values: ['f64[]'] - file-name: "acceptable_types_p" isa: verification: - v1_array_type description: Check acceptable array types for ldarr.obj instruction in Panda Assembly context. header-template: [] code-template: | .record R {} .record panda.Object .record panda.String .record panda.Class .function i32 main() { movi v0, 1 newarr v0, v0, %s ldai 0 ldarr.obj v0 check-type: exit-positive tags: ['verifier'] runner-options: ['verifier-only', 'verifier-config'] cases: - values: ['panda.Object[]'] - values: ['panda.String[]'] - values: ['panda.Class[]'] - values: ['R[]'] - values: ['panda.Object[][]'] - values: ['panda.String[][]'] - values: ['panda.Class[][]'] - values: ['R[][]'] - values: ['u1[][]'] - values: ['u32[][]'] - values: ['u64[][]'] - file-name: "acceptable_types_j" isa: verification: - v1_array_type description: Check acceptable array types for ldarr.obj instruction in PandaAssembly context. header-template: [PandaAssembly] bugid: ['3227'] code-template: | .record R {} .record I {} .record Q {} .record E {} .record A {} .record panda.Object .record panda.String .record panda.Class .function i32 main() { movi v0, 1 newarr v0, v0, %s ldai 0 ldarr.obj v0 check-type: exit-positive tags: [verifier, pa-verifier] runner-options: [verifier-only, use-pa, verifier-config] cases: - values: ['R[]'] - values: ['I[]'] - values: ['Q[]'] - values: ['E[]'] - values: ['A[]'] - values: ['panda.Object[]'] - values: ['panda.String[]'] - values: ['panda.Class[]'] - values: ['R[][]'] - values: ['I[][]'] - values: ['Q[][]'] - values: ['E[][]'] - values: ['A[][]'] - values: ['panda.Object[][]'] - values: ['panda.String[][]'] - values: ['panda.Class[][]'] - values: ['i8[][]'] - values: ['i32[][]'] - values: ['f64[][]'] - file-name: "arr_type" isa: verification: - v1_array_type tags: ['verifier'] runner-options: ['verifier-failure', 'verifier-config'] header-template: [] code-template: | # .record A {} .record panda.String .record panda.Object .function void panda.Object.ctor(panda.Object a0) .function i32 main() { %s ldai 0 ldarr.obj v0 check-type: exit-positive description: Check 'ldarr.obj' with incorrect array type. cases: - values: - movi v0, 0 - values: - movi.64 v0, 0 - values: - fmovi v0, 0 - values: - fmovi.64 v0, 0 - values: - | # lda.type A sta.obj v0 - values: - | # lda.type A[] sta.obj v0 - values: - | # lda.type panda.String sta.obj v0 - values: - | # lda.type panda.String[] sta.obj v0 - values: - | # lda.type panda.Object sta.obj v0 - values: - | # lda.type panda.Object[] sta.obj v0 - values: - | # lda.str "string" sta.obj v0 - values: - | # initobj panda.Object.ctor sta.obj v0 - file-name: "acc_type" isa: verification: - acc_i32 tags: ['verifier'] runner-options: ['verifier-failure', 'verifier-config'] header-template: [] code-template: | # .record A {} .record panda.String .record panda.Object .function void panda.Object.ctor(panda.Object a0) .function i32 main() { movi v0, 1 newarr v0, v0, A[] %s ldarr.obj v0 check-type: exit-positive description: Check 'ldarr.obj' with incorrect index type. cases: - values: - lda.null - values: - ldai.64 0 - values: - fldai 0 - values: - fldai.64 0 - values: - lda.type A - values: - lda.type A[] - values: - lda.type panda.String - values: - lda.type panda.String[] - values: - lda.type panda.Object - values: - lda.type panda.Object[] - values: - lda.str "string" - values: - | # movi v1, 1 newarr v1, v1, panda.Object[] lda.obj v1 - values: - | # movi v1, 1 newarr v1, v1, panda.String[] lda.obj v1 - values: - initobj panda.Object.ctor - file-name: "arr_acc_type" isa: verification: - v1_array_type - acc_i32 tags: ['verifier'] runner-options: ['verifier-failure', 'verifier-config'] header-template: [] code-template: | # .record A {} .record panda.String .record panda.Object .function void panda.Object.ctor(panda.Object a0) .function i32 main() { %s *s ldarr.obj v0 check-type: exit-positive description: Check 'ldarr.obj' with incorrect register and accumulator types. template-cases: - values: - movi v0, 0 - values: - movi.64 v0, 0 - values: - fmovi v0, 0 - values: - fmovi.64 v0, 0 - values: - | # lda.type A sta.obj v0 - values: - | # lda.type A[] sta.obj v0 - values: - | # lda.type panda.String sta.obj v0 - values: - | # lda.type panda.String[] sta.obj v0 - values: - | # lda.type panda.Object sta.obj v0 - values: - | # lda.type panda.Object[] sta.obj v0 - values: - | # lda.str "string" sta.obj v0 - values: - | # movi v0, 1 newarr v0, v0, panda.Object[] - values: - | # movi v0, 1 newarr v0, v0, panda.String[] - values: - | # initobj panda.Object.ctor sta.obj v0 cases: - values: - lda.null - values: - ldai.64 0 - values: - fldai 0 - values: - fldai.64 0 - values: - lda.type A - values: - lda.type A[] - values: - lda.type panda.String - values: - lda.type panda.String[] - values: - lda.type panda.Object - values: - lda.type panda.Object[] - values: - lda.str "string" - values: - | # movi v1, 1 newarr v1, v1, panda.Object[] lda.obj v1 - values: - | # movi v1, 1 newarr v1, v1, panda.String[] lda.obj v1 - values: - initobj panda.Object.ctor - file-name: "read_all_values" isa: description: > Load an element from array using accumulator as an index and puts it into accumulator. description: Check ldarr.obj reads correct items from array of objects. tags: ['irtoc_ignore'] header-template: [] check-type: exit-positive code-template: | %s .function i32 main() { movi v1, 0 # v1 - index movi v0, *s # v0 is array size mov v2, v0 # v2 is size too newarr v0, v0, A[] # v0 - testable array fill_array: lda v1 initobj A.ctor, v1 starr.obj v0, v1 # v0[v1] = acc inci v1, 1 # v1 = v1 + 1 lda v1 jne v2, fill_array movi v1, 0 # index check_array: lda v1 ldarr.obj v0 # acc = v0[acc] sta.obj v3 # v3 = acc call.virt.short A.cmp, v3, v1 jeqz ok ldai 1 return ok: inci v1, 1 lda v1 jne v2, check_array template-cases: - values: - | # .record A { i32 fi32 } .function void A.ctor(A a0, i32 a1) { lda a1 stobj a0, A.fi32 return.void } .function i32 A.cmp(A a0, i32 a1) { ldobj a0, A.fi32 jne a1, exit_failure ldai 0 return exit_failure: ldai 1 return } tags: ['tsan'] - values: - | # .record A { A fA } .function void A.ctor(A a0, i32 a1) { lda.obj a0 stobj.obj a0, A.fA return.void } .function i32 A.cmp(A a0, i32 a1) { ldobj.obj a0, A.fA jeq.obj a0, ret0 ldai 1 return ret0: ldai 0 return } cases: - values: - 10000 - file-name: "read_different_type_values_p" isa: description: > Load an element from array using accumulator as an index and puts it into accumulator. description: Check ldarr.obj reads correct items with various types from array of objects. header-template: [] check-type: exit-positive code-template: | %s .function i32 main() { movi v1, 1 newarr v0, v1, %s # v0 - testable array movi v1, 0 # v1 - index = 0 check_null: lda v1 ldarr.obj v0 # acc = v0[acc] jeqz.obj fill_array ldai 1 return fill_array: %s sta.obj v10 # v10 - saved object ref starr.obj v0, v1 # v0[v1] = acc check_ref: lda v1 ldarr.obj v0 # acc = v0[acc] jeq.obj v10, ok ldai 2 return ok: cases: - values: - .record A {} - A[] - lda.null - values: - | .record A {} .function void A.ctor(A a0) { return.void } - A[] - initobj A.ctor tags: ['tsan'] - values: - | .record panda.Class .record A {} - panda.Class[] - lda.type A bugid: ['3219'] - values: - .record panda.String - panda.String[] - lda.str "test string" - values: - | .record panda.Object .record A {} .function void A.ctor(A a0) { return.void } - panda.Object[] - initobj A.ctor tags: ['tsan'] - values: - .record A {} - A[][] - | # movi v4, 10 newarr v4, v4, A[] lda.obj v4 - file-name: "read_different_type_values_j" isa: description: > Load an element from array using accumulator as an index and puts it into accumulator. description: Check ldarr.obj reads correct items with various types from array of objects. header-template: [PandaAssembly] runner-options: [use-pa] check-type: exit-positive code-template: | %s .function i32 main() { movi v1, 1 newarr v0, v1, %s # v0 - testable array movi v1, 0 # v1 - index = 0 check_null: lda v1 ldarr.obj v0 # acc = v0[acc] jeqz.obj fill_array ldai 1 return fill_array: %s sta.obj v10 # v10 - saved object ref starr.obj v0, v1 # v0[v1] = acc check_ref: lda v1 ldarr.obj v0 # acc = v0[acc] jeq.obj v10, ok ldai 2 return ok: cases: - values: - .record panda.Object - panda.Object[] - lda.null - values: - | .record panda.Long .function void panda.Long.ctor(panda.Long a0, i64 a1) - panda.Long[] - | # movi.64 v7, 0x7FFFFFFFFFFFFFFF initobj panda.Long.ctor, v7 tags: ['tsan'] - values: - .record panda.Class - panda.Class[] - lda.type panda.Class - values: - .record panda.Object - panda.Object[] - lda.str "test string" tags: ['tsan'] - values: - .record panda.String - panda.String[][] - | # movi v4, 10 newarr v4, v4, panda.String[] lda.obj v4 bugid: ['3227']