diff --git a/llvm/test/CodeGen/SPIRV/extensions/SPV_INTEL_optnone.ll b/llvm/test/CodeGen/SPIRV/extensions/SPV_INTEL_optnone.ll index 99d22a4a2ee63..afbcaec9c5c52 100644 --- a/llvm/test/CodeGen/SPIRV/extensions/SPV_INTEL_optnone.ll +++ b/llvm/test/CodeGen/SPIRV/extensions/SPV_INTEL_optnone.ll @@ -1,19 +1,25 @@ -; RUN: llc -O0 -mtriple=spirv32-unknown-unknown --spirv-extensions=SPV_INTEL_optnone %s -o - | FileCheck %s --check-prefix=CHECK-EXTENSION -; RUN: llc -O0 -mtriple=spirv32-unknown-unknown %s -o - | FileCheck %s --check-prefix=CHECK-NO-EXTENSION +; NOTE: Assertions have been autogenerated by utils/update_llc_test_checks.py UTC_ARGS: --version 3 +; RUN: llc -O0 -mtriple=spirv32-unknown-unknown --spirv-extensions=SPV_INTEL_optnone %s -o - | FileCheck %s --check-prefixes=CHECK,CHECK-EXTENSION +; RUN: llc -O0 -mtriple=spirv32-unknown-unknown %s -o - | FileCheck %s --check-prefixes=CHECK,CHECK-NO-EXTENSION ; CHECK-EXTENSION: OpCapability OptNoneINTEL ; CHECK-EXTENSION: OpExtension "SPV_INTEL_optnone" ; CHECK-NO-EXTENSION-NOT: OpCapability OptNoneINTEL ; CHECK-NO-EXTENSION-NOT: OpExtension "SPV_INTEL_optnone" -;; Per SPIR-V spec: -;; FunctionControlDontInlineMask = 0x2 (2) -; CHECK-EXTENSION: %[[#]] = OpFunction %[[#]] DontInline - ; Function Attrs: nounwind optnone noinline define spir_func void @_Z3foov() #0 { +; CHECK-LABEL: _Z3foov +; CHECK: %4 = OpFunction %2 DontInline %3 +; CHECK-NEXT: %5 = OpLabel +; CHECK-NEXT: OpReturn +; CHECK-NEXT: OpFunctionEnd entry: ret void } attributes #0 = { nounwind optnone noinline } + +;; NOTE: These prefixes are unused and the list is autogenerated. Do not add tests below this line: +; CHECK-EXTENSION: {{.*}} +; CHECK-NO-EXTENSION: {{.*}} diff --git a/llvm/utils/UpdateTestChecks/asm.py b/llvm/utils/UpdateTestChecks/asm.py index 3357906513217..7c3c60032e213 100644 --- a/llvm/utils/UpdateTestChecks/asm.py +++ b/llvm/utils/UpdateTestChecks/asm.py @@ -15,6 +15,11 @@ class string: # RegEx: this is where the magic happens. ##### Assembly parser +# +# The set of per-arch regular expressions define several groups. +# The required groups are "func" (function name) and "body" (body of the function). +# Although some backends require some additional groups like: "directives" +# and "func_name_separator" ASM_FUNCTION_X86_RE = re.compile( r'^_?(?P[^:]+):[ \t]*#+[ \t]*(@"?(?P=func)"?| -- Begin function (?P=func))\n(?:\s*\.?Lfunc_begin[^:\n]*:\n)?' @@ -197,6 +202,14 @@ class string: flags=(re.M | re.S), ) +# We parse the function name from OpName, and grab the variable name 'var' +# for this function. Then we match that when the variable is assigned with +# OpFunction and match its body. +ASM_FUNCTION_SPIRV_RE = re.compile( + r'OpName (?P%[0-9]+) "(?P[^"]+)(?P)".*(?P(?P=var) = OpFunction.+?OpFunctionEnd)', + flags=(re.M | re.S), +) + ASM_FUNCTION_VE_RE = re.compile( r"^_?(?P[^:]+):[ \t]*#+[ \t]*@(?P=func)\n" r"(?:\s*\.?L(?P=func)\$local:\n)?" # optional .L$local: due to -fno-semantic-interposition @@ -433,6 +446,17 @@ def scrub_asm_sparc(asm, args): return asm +def scrub_asm_spirv(asm, args): + # Scrub runs of whitespace out of the assembly, but leave the leading + # whitespace in place. + asm = common.SCRUB_WHITESPACE_RE.sub(r" ", asm) + # Expand the tabs used for indentation. + asm = string.expandtabs(asm, 2) + # Strip trailing whitespace. + asm = common.SCRUB_TRAILING_WHITESPACE_RE.sub(r"", asm) + return asm + + def scrub_asm_systemz(asm, args): # Scrub runs of whitespace out of the assembly, but leave the leading # whitespace in place. @@ -547,6 +571,8 @@ def get_run_handler(triple): "riscv64": (scrub_asm_riscv, ASM_FUNCTION_RISCV_RE), "lanai": (scrub_asm_lanai, ASM_FUNCTION_LANAI_RE), "sparc": (scrub_asm_sparc, ASM_FUNCTION_SPARC_RE), + "spirv32": (scrub_asm_spirv, ASM_FUNCTION_SPIRV_RE), + "spirv64": (scrub_asm_spirv, ASM_FUNCTION_SPIRV_RE), "s390x": (scrub_asm_systemz, ASM_FUNCTION_SYSTEMZ_RE), "wasm32": (scrub_asm_wasm, ASM_FUNCTION_WASM_RE), "wasm64": (scrub_asm_wasm, ASM_FUNCTION_WASM_RE),