chore: import upstream snapshot with attribution
Lint / lint (push) Waiting to run
CI / MacOS (push) Waiting to run
CI / Windows (push) Waiting to run

This commit is contained in:
wehub-resource-sync
2026-07-13 13:36:25 +08:00
commit 26446540fa
3151 changed files with 974126 additions and 0 deletions
@@ -0,0 +1,389 @@
# 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: F401, F841
from typing import Union
import tvm
import tvm.script
import tvm.testing
from tvm import IRModule, relax
from tvm.relax import Function
from tvm.script import ir as I
from tvm.script import relax as R
from tvm.script import tirx as T
def test_batch_norm_inference():
@I.ir_module
class Before:
@R.function
def main(
x: R.Tensor((1, 64, 112, 112), "float32"),
gamma: R.Tensor((64,), "float32"),
beta: R.Tensor((64,), "float32"),
moving_mean: R.Tensor((64,), "float32"),
moving_var: R.Tensor((64,), "float32"),
):
with R.dataflow():
bn = R.nn.batch_norm(
x,
gamma,
beta,
moving_mean,
moving_var,
axis=1,
epsilon=1e-5,
center=True,
scale=True,
)
gv = bn[0]
R.output(gv)
return gv
@I.ir_module
class Expected:
@R.function
def main(
x: R.Tensor((1, 64, 112, 112), dtype="float32"),
gamma: R.Tensor((64,), dtype="float32"),
beta: R.Tensor((64,), dtype="float32"),
moving_mean: R.Tensor((64,), dtype="float32"),
moving_var: R.Tensor((64,), dtype="float32"),
) -> R.Tensor((1, 64, 112, 112), dtype="float32"):
with R.dataflow():
lv: R.Tensor((1, 64, 1, 1), dtype="float32") = R.expand_dims(
moving_mean, axis=[0, 2, 3]
)
lv1: R.Tensor((1, 64, 112, 112), dtype="float32") = R.subtract(x, lv)
lv2: R.Tensor((1, 64, 1, 1), dtype="float32") = R.expand_dims(
moving_var, axis=[0, 2, 3]
)
lv3: R.Tensor((1, 64, 1, 1), dtype="float32") = R.add(
lv2, R.const(9.9999997473787516e-06, "float32")
)
lv4: R.Tensor((1, 64, 1, 1), dtype="float32") = R.sqrt(lv3)
lv5: R.Tensor((1, 64, 112, 112), dtype="float32") = R.divide(lv1, lv4)
lv6: R.Tensor((1, 64, 1, 1), dtype="float32") = R.expand_dims(gamma, axis=[0, 2, 3])
lv7: R.Tensor((1, 64, 112, 112), dtype="float32") = R.multiply(lv5, lv6)
lv8: R.Tensor((1, 64, 1, 1), dtype="float32") = R.expand_dims(beta, axis=[0, 2, 3])
lv9: R.Tensor((1, 64, 112, 112), dtype="float32") = R.add(lv7, lv8)
bn: R.Tuple(
R.Tensor((1, 64, 112, 112), dtype="float32"),
R.Tensor((64,), dtype="float32"),
R.Tensor((64,), dtype="float32"),
) = (lv9, moving_mean, moving_var)
gv: R.Tensor((1, 64, 112, 112), dtype="float32") = bn[0]
R.output(gv)
return gv
After = relax.transform.DecomposeOpsForInference("main")(Before)
tvm.ir.assert_structural_equal(Expected, After)
def test_batch_norm_training():
@I.ir_module
class Before:
@R.function
def main(
x: R.Tensor((1, 64, 112, 112), "float32"),
gamma: R.Tensor((64,), "float32"),
beta: R.Tensor((64,), "float32"),
moving_mean: R.Tensor((64,), "float32"),
moving_var: R.Tensor((64,), "float32"),
):
with R.dataflow():
bn = R.nn.batch_norm(
x,
gamma,
beta,
moving_mean,
moving_var,
axis=1,
epsilon=1e-5,
center=True,
scale=True,
momentum=0.1,
)
gv0 = bn[0]
gv1 = bn[1]
gv2 = bn[2]
R.output(gv0, gv1, gv2)
return gv0, gv1, gv2
@I.ir_module
class Expected:
@R.function
def main(
x: R.Tensor((1, 64, 112, 112), dtype="float32"),
gamma: R.Tensor((64,), dtype="float32"),
beta: R.Tensor((64,), dtype="float32"),
moving_mean: R.Tensor((64,), dtype="float32"),
moving_var: R.Tensor((64,), dtype="float32"),
) -> R.Tuple(
R.Tensor((1, 64, 112, 112), dtype="float32"),
R.Tensor((64,), dtype="float32"),
R.Tensor((64,), dtype="float32"),
):
with R.dataflow():
# This portion is training-specific, computing the
# mean/variance of the dataset.
lv = R.mean(x, axis=[0, 2, 3], keepdims=False)
lv3 = R.variance(x, axis=[0, 2, 3], keepdims=False)
# This portion is identical to the batch_norm run during inference
lv1 = R.expand_dims(lv, axis=[0, 2, 3])
lv2 = R.subtract(x, lv1)
lv4 = R.expand_dims(lv3, axis=[0, 2, 3])
lv5 = R.add(lv4, R.const(9.9999997473787516e-06, "float32"))
lv6 = R.sqrt(lv5)
lv7 = R.divide(lv2, lv6)
lv8 = R.expand_dims(gamma, axis=[0, 2, 3])
lv9 = R.multiply(lv7, lv8)
lv10 = R.expand_dims(beta, axis=[0, 2, 3])
lv11 = R.add(lv9, lv10)
inner_tuple = (lv11, lv, lv3)
# This is the result that would be returned from a
# batch_norm at inference.
# However, at training we need to update the moving
# mean/variance, and to return those updated values.
inner_res = inner_tuple[0]
lv12 = R.multiply(R.const(0.89999997615814209, "float32"), moving_mean)
lv13 = R.multiply(R.const(0.10000000149011612, "float32"), lv)
lv14 = R.add(lv12, lv13)
lv15 = R.multiply(R.const(0.89999997615814209, "float32"), moving_var)
lv16 = R.multiply(R.const(0.10000000149011612, "float32"), lv3)
lv17 = R.add(lv15, lv16)
bn = (inner_res, lv14, lv17)
gv0 = bn[0]
gv1 = bn[1]
gv2 = bn[2]
R.output(gv0, gv1, gv2)
return (gv0, gv1, gv2)
After = relax.transform.DecomposeOpsForTraining("main")(Before)
tvm.ir.assert_structural_equal(Expected, After)
def test_batch_norm_multiple_functions():
@I.ir_module
class Before:
@R.function
def main(
x: R.Tensor((1, 64, 112, 112), "float32"),
gamma: R.Tensor((64,), "float32"),
beta: R.Tensor((64,), "float32"),
moving_mean: R.Tensor((64,), "float32"),
moving_var: R.Tensor((64,), "float32"),
):
with R.dataflow():
bn = R.nn.batch_norm(
x,
gamma,
beta,
moving_mean,
moving_var,
axis=1,
epsilon=1e-5,
center=True,
scale=True,
)
gv = bn[0]
R.output(gv)
return gv
@R.function
def main1(
x: R.Tensor((1, 64, 112, 112), "float32"),
gamma: R.Tensor((64,), "float32"),
beta: R.Tensor((64,), "float32"),
moving_mean: R.Tensor((64,), "float32"),
moving_var: R.Tensor((64,), "float32"),
):
with R.dataflow():
bn = R.nn.batch_norm(
x,
gamma,
beta,
moving_mean,
moving_var,
axis=1,
epsilon=1e-5,
center=True,
scale=True,
)
gv = bn[0]
R.output(gv)
return gv
@I.ir_module
class Expected:
@R.function
def main1(
x: R.Tensor((1, 64, 112, 112), dtype="float32"),
gamma: R.Tensor((64,), dtype="float32"),
beta: R.Tensor((64,), dtype="float32"),
moving_mean: R.Tensor((64,), dtype="float32"),
moving_var: R.Tensor((64,), dtype="float32"),
) -> R.Tensor((1, 64, 112, 112), dtype="float32"):
with R.dataflow():
lv10: R.Tensor((1, 64, 1, 1), dtype="float32") = R.expand_dims(
moving_mean, axis=[0, 2, 3]
)
lv11: R.Tensor((1, 64, 112, 112), dtype="float32") = R.subtract(x, lv10)
lv12: R.Tensor((1, 64, 1, 1), dtype="float32") = R.expand_dims(
moving_var, axis=[0, 2, 3]
)
lv13: R.Tensor((1, 64, 1, 1), dtype="float32") = R.add(
lv12, R.const(9.9999997473787516e-06, "float32")
)
lv14: R.Tensor((1, 64, 1, 1), dtype="float32") = R.sqrt(lv13)
lv15: R.Tensor((1, 64, 112, 112), dtype="float32") = R.divide(lv11, lv14)
lv16: R.Tensor((1, 64, 1, 1), dtype="float32") = R.expand_dims(
gamma, axis=[0, 2, 3]
)
lv17: R.Tensor((1, 64, 112, 112), dtype="float32") = R.multiply(lv15, lv16)
lv18: R.Tensor((1, 64, 1, 1), dtype="float32") = R.expand_dims(beta, axis=[0, 2, 3])
lv19: R.Tensor((1, 64, 112, 112), dtype="float32") = R.add(lv17, lv18)
bn: R.Tuple(
R.Tensor((1, 64, 112, 112), dtype="float32"),
R.Tensor((64,), dtype="float32"),
R.Tensor((64,), dtype="float32"),
) = (lv19, moving_mean, moving_var)
gv: R.Tensor((1, 64, 112, 112), dtype="float32") = bn[0]
R.output(gv)
return gv
@R.function
def main(
x: R.Tensor((1, 64, 112, 112), dtype="float32"),
gamma: R.Tensor((64,), dtype="float32"),
beta: R.Tensor((64,), dtype="float32"),
moving_mean: R.Tensor((64,), dtype="float32"),
moving_var: R.Tensor((64,), dtype="float32"),
) -> R.Tensor((1, 64, 112, 112), dtype="float32"):
with R.dataflow():
lv: R.Tensor((1, 64, 1, 1), dtype="float32") = R.expand_dims(
moving_mean, axis=[0, 2, 3]
)
lv1: R.Tensor((1, 64, 112, 112), dtype="float32") = R.subtract(x, lv)
lv2: R.Tensor((1, 64, 1, 1), dtype="float32") = R.expand_dims(
moving_var, axis=[0, 2, 3]
)
lv3: R.Tensor((1, 64, 1, 1), dtype="float32") = R.add(
lv2, R.const(9.9999997473787516e-06, "float32")
)
lv4: R.Tensor((1, 64, 1, 1), dtype="float32") = R.sqrt(lv3)
lv5: R.Tensor((1, 64, 112, 112), dtype="float32") = R.divide(lv1, lv4)
lv6: R.Tensor((1, 64, 1, 1), dtype="float32") = R.expand_dims(gamma, axis=[0, 2, 3])
lv7: R.Tensor((1, 64, 112, 112), dtype="float32") = R.multiply(lv5, lv6)
lv8: R.Tensor((1, 64, 1, 1), dtype="float32") = R.expand_dims(beta, axis=[0, 2, 3])
lv9: R.Tensor((1, 64, 112, 112), dtype="float32") = R.add(lv7, lv8)
bn: R.Tuple(
R.Tensor((1, 64, 112, 112), dtype="float32"),
R.Tensor((64,), dtype="float32"),
R.Tensor((64,), dtype="float32"),
) = (lv9, moving_mean, moving_var)
gv: R.Tensor((1, 64, 112, 112), dtype="float32") = bn[0]
R.output(gv)
return gv
After = relax.transform.DecomposeOpsForInference()(Before)
tvm.ir.assert_structural_equal(Expected, After)
def test_layer_norm():
@I.ir_module
class Before:
@R.function
def main(
x: R.Tensor((4, 64, 112, 112), "float32"),
gamma: R.Tensor((112, 112), "float32"),
beta: R.Tensor((112, 112), "float32"),
):
with R.dataflow():
ln = R.nn.layer_norm(
x,
gamma,
beta,
axes=[-2, -1],
epsilon=1e-5,
center=True,
scale=True,
)
R.output(ln)
return ln
@I.ir_module
class Expected:
@R.function
def main(
x: R.Tensor((4, 64, 112, 112), dtype="float32"),
gamma: R.Tensor((112, 112), dtype="float32"),
beta: R.Tensor((112, 112), dtype="float32"),
) -> R.Tensor((4, 64, 112, 112), dtype="float32"):
with R.dataflow():
lv: R.Tensor((4, 64, 1, 1), dtype="float32") = R.mean(
x, axis=[-2, -1], keepdims=True
)
lv1: R.Tensor((4, 64, 112, 112), dtype="float32") = R.subtract(x, lv)
lv2: R.Tensor((4, 64, 1, 1), dtype="float32") = R.variance(
x, axis=[-2, -1], keepdims=True
)
lv3: R.Tensor((4, 64, 1, 1), dtype="float32") = R.add(
lv2, R.const(9.9999997473787516e-06, "float32")
)
lv4: R.Tensor((4, 64, 1, 1), dtype="float32") = R.sqrt(lv3)
lv5: R.Tensor((4, 64, 112, 112), dtype="float32") = R.divide(lv1, lv4)
lv6: R.Tensor((4, 64, 112, 112), dtype="float32") = R.multiply(lv5, gamma)
ln: R.Tensor((4, 64, 112, 112), dtype="float32") = R.add(lv6, beta)
R.output(ln)
return ln
After = relax.transform.DecomposeOpsForTraining()(Before)
tvm.ir.assert_structural_equal(Expected, After)
def test_op_tensor_to_shape():
@I.ir_module
class Before:
@R.function
def main(t: R.Tensor([3], dtype="int64")):
gv: R.Shape(ndim=3) = R.tensor_to_shape(t)
return gv
@I.ir_module
class Expected:
@R.function
def main(t: R.Tensor([3], dtype="int64")) -> R.Shape(ndim=3):
x = T.int64()
x_1 = T.int64()
x_2 = T.int64()
gv: R.Shape(ndim=3) = R.call_pure_packed(
"vm.builtin.tensor_to_shape", t, ty_args=(R.Shape(ndim=3),)
)
y: R.Shape([x, x_1, x_2]) = R.match_cast(gv, R.Shape([x, x_1, x_2]))
gv_1: R.Shape([x, x_1, x_2]) = R.shape([x, x_1, x_2])
return gv_1
After = relax.transform.DecomposeOpsForInference()(Before)
tvm.ir.assert_structural_equal(Expected, After)
if __name__ == "__main__":
tvm.testing.main()