WebAssembly: don't omit dead vregs from locals
authorJF Bastien <jfb@google.com>
Sat, 17 Oct 2015 00:25:38 +0000 (00:25 +0000)
committerJF Bastien <jfb@google.com>
Sat, 17 Oct 2015 00:25:38 +0000 (00:25 +0000)
Summary:
This is a temporary hack until we get around to remapping the vreg
numbers to local numbers. Dead vregs cause bad numbering and make
consumers sad.

We could also just look at debug info an use named locals instead, but
vregs have to work properly anyways so there!

Reviewers: binji, sunfish

Subscribers: jfb, llvm-commits, dschuff

Differential Revision: http://reviews.llvm.org/D13839

git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@250594 91177308-0d34-0410-b5e6-96231b3b80d8

lib/Target/WebAssembly/WebAssemblyAsmPrinter.cpp
test/CodeGen/WebAssembly/dead-vreg.ll [new file with mode: 0644]

index 5c8fe57084714d441545ca404b22d9020dab882e..fda95a5e6a5d7fe7a1bbe42fc2e09e48152f8704 100644 (file)
@@ -226,14 +226,16 @@ void WebAssemblyAsmPrinter::EmitFunctionBodyStart() {
   bool FirstVReg = true;
   for (unsigned Idx = 0, IdxE = MRI->getNumVirtRegs(); Idx != IdxE; ++Idx) {
     unsigned VReg = TargetRegisterInfo::index2VirtReg(Idx);
-    if (!MRI->use_empty(VReg)) {
+    // FIXME: Don't skip dead virtual registers for now: that would require
+    //        remapping all locals' numbers.
+    //if (!MRI->use_empty(VReg)) {
       if (FirstVReg) {
         OS << (First ? "" : "\n") << "\t.local ";
         First = false;
       }
       OS << (FirstVReg ? "" : ", ") << getRegTypeName(VReg);
       FirstVReg = false;
-    }
+    //}
   }
 
   if (!First)
diff --git a/test/CodeGen/WebAssembly/dead-vreg.ll b/test/CodeGen/WebAssembly/dead-vreg.ll
new file mode 100644 (file)
index 0000000..181a09d
--- /dev/null
@@ -0,0 +1,58 @@
+; RUN: llc < %s -asm-verbose=false | FileCheck %s
+
+; Check that unused vregs don't prevent locals from being numbered wrong.
+;
+; The test currently checks that the dead virtual registers still appear as
+; locals, which isn't what we want long term. Removing them from the list of
+; locals will require remapping the local numbers, and checking that the
+; get_/set_local have the right numbers.
+
+target datalayout = "e-p:32:32-i64:64-n32:64-S128"
+target triple = "wasm32-unknown-unknown"
+
+define void @foo(i32* nocapture %a, i32 %w, i32 %h) {
+; CHECK-LABEL: foo:
+; CHECK-NEXT: .param i32
+; CHECK-NEXT: .param i32
+; CHECK-NEXT: .param i32
+; CHECK-NEXT: .local i32, i32, i32, i32, i32, i32, i32, i32, i32, i32, i32, i32, i32, i32, i32, i32, i32, i32, i32, i32, i32, i32, i32, i32, i32, i32, i32, i32, i32, i32, i32, i32{{$}}
+entry:
+  %cmp.19 = icmp sgt i32 %h, 0
+  br i1 %cmp.19, label %for.cond.1.preheader.lr.ph, label %for.end.7
+
+for.cond.1.preheader.lr.ph:
+  %cmp2.17 = icmp sgt i32 %w, 0
+  br label %for.cond.1.preheader
+
+for.cond.1.preheader:
+  %y.020 = phi i32 [ 0, %for.cond.1.preheader.lr.ph ], [ %inc6, %for.inc.5 ]
+  br i1 %cmp2.17, label %for.body.3.lr.ph, label %for.inc.5
+
+for.body.3.lr.ph:
+  %mul4 = mul nsw i32 %y.020, %w
+  br label %for.body.3
+
+for.body.3:
+  %x.018 = phi i32 [ 0, %for.body.3.lr.ph ], [ %inc, %for.body.3 ]
+  %mul = mul nsw i32 %x.018, %y.020
+  %add = add nsw i32 %x.018, %mul4
+  %arrayidx = getelementptr inbounds i32, i32* %a, i32 %add
+  store i32 %mul, i32* %arrayidx, align 4
+  %inc = add nuw nsw i32 %x.018, 1
+  %exitcond = icmp eq i32 %inc, %w
+  br i1 %exitcond, label %for.inc.5.loopexit, label %for.body.3
+
+for.inc.5.loopexit:
+  br label %for.inc.5
+
+for.inc.5:
+  %inc6 = add nuw nsw i32 %y.020, 1
+  %exitcond22 = icmp eq i32 %inc6, %h
+  br i1 %exitcond22, label %for.end.7.loopexit, label %for.cond.1.preheader
+
+for.end.7.loopexit:
+  br label %for.end.7
+
+for.end.7:
+  ret void
+}