# Licensed to the Apache Software Foundation (ASF) under one # or more contributor license agreements. See the NOTICE file # distributed with this work for additional information # regarding copyright ownership. The ASF licenses this file # to you 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. # ruff: noqa: F841 import pytest from tvm_ffi.access_path import AccessPath import tvm from tvm.ir import assert_structural_equal from tvm.script import ir as I from tvm.script import tirx as T def _error_message(exception): return str(exception) def _expected_result(func1, func2, objpath1, objpath2): return f"""StructuralEqual check failed, caused by lhs at {objpath1}: {func1.script(path_to_underline=[objpath1], syntax_sugar=False)} and rhs at {objpath2}: {func2.script(path_to_underline=[objpath2], syntax_sugar=False)}""" def test_prim_type_hidden_path_exact_message(): with pytest.raises(ValueError) as exc_info: assert_structural_equal(tvm.ir.PrimType("int32"), tvm.ir.PrimType("float32")) assert str(exc_info.value) == ( "StructuralEqual check failed, caused by lhs at .dtype:\n" "Access path: .dtype\n" "Note: The underlined object is the nearest visible parent of this path.\n\n" "T.int32\n" "^^^^^^^\n" "and rhs at .dtype:\n" "Access path: .dtype\n" "Note: The underlined object is the nearest visible parent of this path.\n\n" "T.float32\n" "^^^^^^^^^" ) def test_prim_func_buffer_map(): @T.prim_func(s_tir=True) def func1(a: T.handle, b: T.handle): A = T.match_buffer(a, (128, 128)) B = T.match_buffer(b, (128, 128)) @T.prim_func(s_tir=True) def func2(a: T.handle, b: T.handle): A = T.match_buffer(a, (128, 128)) B = T.match_buffer(b, (128, 256)) func1 = func1.with_attr("global_symbol", "main") func2 = func2.with_attr("global_symbol", "main") with pytest.raises(ValueError) as ve: assert_structural_equal(func1, func2) assert _error_message(ve.value) == _expected_result( func1, func2, AccessPath.root() .attr("buffer_map") .map_item(func1.params[1]) .attr("shape") .array_item(1) .attr("value"), AccessPath.root() .attr("buffer_map") .map_item(func2.params[1]) .attr("shape") .array_item(1) .attr("value"), ) def test_evaluate(): @I.ir_module(s_tir=True) class module1: @T.prim_func(s_tir=True) def func(): T.evaluate(0) @I.ir_module(s_tir=True) class module2: @T.prim_func(s_tir=True) def func(): T.evaluate(1) with pytest.raises(ValueError) as ve: assert_structural_equal(module1, module2) assert _error_message(ve.value) == _expected_result( module1, module2, AccessPath.root() .attr("functions") .map_item(module1.get_global_var("func")) .attr("body") .attr("value") .attr("value"), AccessPath.root() .attr("functions") .map_item(module2.get_global_var("func")) .attr("body") .attr("value") .attr("value"), ) def test_allocate(): @T.prim_func(s_tir=True) def func1(): a = T.alloc_buffer((128, 128), dtype="float32") @T.prim_func(s_tir=True) def func2(): a = T.alloc_buffer((256, 128), dtype="float32") func1 = func1.with_attr("global_symbol", "main") func2 = func2.with_attr("global_symbol", "main") with pytest.raises(ValueError) as ve: assert_structural_equal(func1, func2) assert _error_message(ve.value) == _expected_result( func1, func2, AccessPath.root().attr("body").attr("buffer").attr("shape").array_item(0).attr("value"), AccessPath.root().attr("body").attr("buffer").attr("shape").array_item(0).attr("value"), ) def test_for(): @T.prim_func(s_tir=True) def func1(): for i, j in T.grid(128, 128): with T.sblock(): pass @T.prim_func(s_tir=True) def func2(): for i, j, k in T.grid(128, 128, 128): with T.sblock(): pass func1 = func1.with_attr("global_symbol", "main") func2 = func2.with_attr("global_symbol", "main") with pytest.raises(ValueError) as ve: assert_structural_equal(func1, func2) assert _error_message(ve.value) == _expected_result( func1, func2, AccessPath.root().attr("body").attr("block").attr("body").attr("body").attr("body"), AccessPath.root().attr("body").attr("block").attr("body").attr("body").attr("body"), ) if __name__ == "__main__": tvm.testing.main()