<div dir="ltr"><div dir="ltr"><div dir="ltr"><div dir="ltr"><div dir="ltr"><div dir="ltr"><div dir="ltr"><div dir="ltr"><div dir="ltr"><div dir="ltr"><div dir="ltr"><div dir="ltr"><div dir="ltr"><div dir="ltr"><div dir="ltr"><div dir="ltr">Hi all,<div><br></div><div>I have been trying to use LLVM's GC infrastructure (Statepoints) and ran into an issue when using exception handling.</div><div>The problem happens when I use an invoke instruction to support exception handling, and try to apply the pass RewriteStatepointsForGC to produce stackmaps.</div>I was able to create a minimal example using the example in the documentation of RewriteStatepointsForGC:</div><div dir="ltr"><br></div></div></div></div></div></div></div><blockquote style="margin:0px 0px 0px 40px;border:none;padding:0px"><span style="font-family:Menlo;color:rgb(0,0,128);font-weight:bold">declare void </span><span style="color:rgb(0,0,0);font-family:Menlo">()* @foo()<br></span><span style="font-family:Menlo;color:rgb(0,0,128);font-weight:bold">declare </span><span style="color:rgb(0,0,0);font-family:Menlo">i8* @__gxx_personality_v0()</span><font color="#000000" face="Menlo"><span style="white-space:pre"><br></span></font><span style="font-family:Menlo;color:rgb(0,0,128);font-weight:bold">define </span><span style="color:rgb(0,0,0);font-family:Menlo">i8 </span><span style="font-family:Menlo;color:rgb(0,0,128);font-weight:bold">addrspace</span><span style="color:rgb(0,0,0);font-family:Menlo">(</span><span style="font-family:Menlo;color:rgb(0,0,255)">1</span><span style="color:rgb(0,0,0);font-family:Menlo">)* @test1(i8 </span><span style="font-family:Menlo;color:rgb(0,0,128);font-weight:bold">addrspace</span><span style="color:rgb(0,0,0);font-family:Menlo">(</span><span style="font-family:Menlo;color:rgb(0,0,255)">1</span><span style="color:rgb(0,0,0);font-family:Menlo">)* %obj)<br></span><span style="font-family:Menlo;color:rgb(0,0,128);font-weight:bold">    gc </span><span style="font-family:Menlo;color:rgb(0,128,0);font-weight:bold">"statepoint-example" </span><span style="font-family:Menlo;color:rgb(0,0,128);font-weight:bold">personality </span><span style="color:rgb(0,0,0);font-family:Menlo">i8* ()* @__gxx_personality_v0 {</span><font color="#000000" face="Menlo"><span style="white-space:pre"><br></span></font><span style="font-weight:bold;color:rgb(0,0,0);font-family:Menlo">blk_entry:<br></span><span style="font-family:Menlo;color:rgb(0,0,128);font-weight:bold">  invoke void </span><span style="color:rgb(0,0,0);font-family:Menlo">()* @foo() </span><span style="font-family:Menlo;color:rgb(0,0,128);font-weight:bold">to </span><span style="color:rgb(0,0,0);font-family:Menlo">label %blk_normal </span><span style="font-family:Menlo;color:rgb(0,0,128);font-weight:bold">unwind </span><span style="color:rgb(0,0,0);font-family:Menlo">label %blk_exc</span><font color="#000000" face="Menlo"><span style="white-space:pre"><br></span></font><span style="font-weight:bold;color:rgb(0,0,0);font-family:Menlo">blk_normal:<br></span><span style="font-family:Menlo;color:rgb(0,0,128);font-weight:bold">  ret </span><span style="color:rgb(0,0,0);font-family:Menlo">i8 </span><span style="font-family:Menlo;color:rgb(0,0,128);font-weight:bold">addrspace</span><span style="color:rgb(0,0,0);font-family:Menlo">(</span><span style="font-family:Menlo;color:rgb(0,0,255)">1</span><span style="color:rgb(0,0,0);font-family:Menlo">)* %obj</span><font color="#000000" face="Menlo"><span style="white-space:pre"><br></span></font><span style="font-weight:bold;color:rgb(0,0,0);font-family:Menlo">blk_exc:<br></span><span style="color:rgb(0,0,0);font-family:Menlo">  %res1 </span><span style="font-family:Menlo;color:rgb(0,0,128);font-weight:bold">= landingpad </span><span style="color:rgb(0,0,0);font-family:Menlo">{ i8*, i32 }<br></span><span style="font-family:Menlo;color:rgb(0,0,128);font-weight:bold">  catch </span><span style="color:rgb(0,0,0);font-family:Menlo">i8* </span><span style="font-family:Menlo;color:rgb(0,0,128);font-weight:bold">null<br></span><span style="font-family:Menlo;color:rgb(0,0,128);font-weight:bold">  ret </span><span style="color:rgb(0,0,0);font-family:Menlo">i8 </span><span style="font-family:Menlo;color:rgb(0,0,128);font-weight:bold">addrspace</span><span style="color:rgb(0,0,0);font-family:Menlo">(</span><span style="font-family:Menlo;color:rgb(0,0,255)">1</span><span style="color:rgb(0,0,0);font-family:Menlo">)* %obj<br></span><span style="color:rgb(0,0,0);font-family:Menlo">}<br><br></span></blockquote><div dir="ltr"><div dir="ltr"><div dir="ltr"><div dir="ltr"><div dir="ltr"><div dir="ltr"><div dir="ltr"><div>The pass is suppose to rewrite the invoke call into a call to <b>llvm.experimental.gc.statepoint</b>, producing a token, and the token can be used in <b>llvm.experimental.gc.relocate</b>, to get the relocated pointer. For a normal call, the IR after the pass should look like:</div></div></div></div></div></div></div></div></div></div></div></div><blockquote style="margin:0px 0px 0px 40px;border:none;padding:0px"><pre style="color:rgb(0,0,0);font-family:Menlo"><pre style="font-family:Menlo"><span style="font-weight:bold">blk_entry:<br></span><span style="font-weight:bold">  </span>%statepoint_token <span style="color:rgb(0,0,128);font-weight:bold">= call </span>token (i64, i32, <span style="color:rgb(0,0,128);font-weight:bold">void </span>()* ()*, i32, i32, ...) @llvm.experimental.gc.statepoint.p0f_p0f_isVoidff(i64 <span style="color:rgb(0,0,255)">2882400000</span>, i32 <span style="color:rgb(0,0,255)">0</span>, <span style="color:rgb(0,0,128);font-weight:bold">void </span>()* ()* @foo, i32 <span style="color:rgb(0,0,255)">0</span>, i32 <span style="color:rgb(0,0,255)">0</span>, i32 <span style="color:rgb(0,0,255)">0</span>, i32 <span style="color:rgb(0,0,255)">0</span>, i8 <span style="color:rgb(0,0,128);font-weight:bold">addrspace</span>(<span style="color:rgb(0,0,255)">1</span>)* %obj)<br>  %obj.relocated <span style="color:rgb(0,0,128);font-weight:bold">= call coldcc </span>i8 <span style="color:rgb(0,0,128);font-weight:bold">addrspace</span>(<span style="color:rgb(0,0,255)">1</span>)* @llvm.experimental.gc.relocate.p1i8(token %statepoint_token, i32 <span style="color:rgb(0,0,255)">7</span>, i32 <span style="color:rgb(0,0,255)">7</span>) <span style="color:rgb(128,128,128);font-style:italic">; (%obj, %obj)<br></span><span style="color:rgb(128,128,128);font-style:italic">  </span><span style="color:rgb(0,0,128);font-weight:bold">br </span>label %blk_normal<br><br><span style="font-weight:bold">blk_normal:                                       </span><span style="color:rgb(128,128,128);font-style:italic">; preds = %blk_entry<br></span><span style="color:rgb(128,128,128);font-style:italic">  </span><span style="color:rgb(0,0,128);font-weight:bold">ret </span>i8 <span style="color:rgb(0,0,128);font-weight:bold">addrspace</span>(<span style="color:rgb(0,0,255)">1</span>)* %obj.relocated</pre></pre></blockquote>However, since I'm using an invoke, I do not have access to the token returned by the call to <b>llvm.experimental.gc.statepoint</b> in <b>blk_exc</b>, making it not possible to relocate <b>%obj</b> when an exception is thrown. When running the pass on the initial example I get:<br><br></div></div></div><blockquote style="margin:0px 0px 0px 40px;border:none;padding:0px"><div><div><div>    Call parameter type does not match function signature!</div></div></div><div><div><div>  %res1 = landingpad { i8*, i32 }</div></div></div><div><div><div>          catch i8* null</div></div></div><div><div><div> token  %obj.relocated = call coldcc i8 addrspace(1)* @llvm.experimental.gc.relocate.p1i8({ i8*, i32 } %res1, i32 7, i32 7) ; (%obj, %obj)</div></div></div><div><div><div>LLVM ERROR: Broken function found, compilation aborted!</div></div></div></blockquote><div dir="ltr"><div dir="ltr"><div dir="ltr"><br>I assume the pass does not consider the invoke scenario, but even then, I would not know how to fix this issue myself, since I cannot access <b>%statepoint_token</b> in the exception block.</div></div></div><div dir="ltr"><div dir="ltr"><div dir="ltr"><div dir="ltr"><div dir="ltr"><div dir="ltr"><div dir="ltr"><div dir="ltr"><div dir="ltr"><div dir="ltr"><div dir="ltr"><div dir="ltr"><div dir="ltr"><div dir="ltr"><div>Is this a known issue? Is there any way to work around it that I might not be seeing?</div><div><br></div><div>Thanks in advance,</div><div><br></div>-- <br><div dir="ltr"><div dir="ltr"><div dir="ltr">Luis Eduardo de Souza Amorim<br></div></div></div></div></div></div></div></div></div></div></div></div></div></div></div></div></div></div></div>