compiler: fix phi nodes for type asserts
Type asserts insert more basic block, causing phi node values to be invalid. Fix this by remembering the outgoing LLVM basic block.
Этот коммит содержится в:
родитель
57661a3c76
коммит
9cd7c7f0ba
1 изменённых файлов: 3 добавлений и 0 удалений
|
@ -63,6 +63,7 @@ type Frame struct {
|
||||||
params map[*ssa.Parameter]int // arguments to the function
|
params map[*ssa.Parameter]int // arguments to the function
|
||||||
locals map[ssa.Value]llvm.Value // local variables
|
locals map[ssa.Value]llvm.Value // local variables
|
||||||
blocks map[*ssa.BasicBlock]llvm.BasicBlock
|
blocks map[*ssa.BasicBlock]llvm.BasicBlock
|
||||||
|
currentBlock *ssa.BasicBlock
|
||||||
phis []Phi
|
phis []Phi
|
||||||
blocking bool
|
blocking bool
|
||||||
taskHandle llvm.Value
|
taskHandle llvm.Value
|
||||||
|
@ -1316,6 +1317,7 @@ func (c *Compiler) parseFunc(frame *Frame) error {
|
||||||
fmt.Printf("%s:\n", block.Comment)
|
fmt.Printf("%s:\n", block.Comment)
|
||||||
}
|
}
|
||||||
c.builder.SetInsertPointAtEnd(frame.blocks[block])
|
c.builder.SetInsertPointAtEnd(frame.blocks[block])
|
||||||
|
frame.currentBlock = block
|
||||||
for _, instr := range block.Instrs {
|
for _, instr := range block.Instrs {
|
||||||
if c.dumpSSA {
|
if c.dumpSSA {
|
||||||
if val, ok := instr.(ssa.Value); ok && val.Name() != "" {
|
if val, ok := instr.(ssa.Value); ok && val.Name() != "" {
|
||||||
|
@ -2369,6 +2371,7 @@ func (c *Compiler) parseExpr(frame *Frame, expr ssa.Value) (llvm.Value, error) {
|
||||||
prevBlock := c.builder.GetInsertBlock()
|
prevBlock := c.builder.GetInsertBlock()
|
||||||
okBlock := c.ctx.AddBasicBlock(frame.fn.llvmFn, "typeassert.ok")
|
okBlock := c.ctx.AddBasicBlock(frame.fn.llvmFn, "typeassert.ok")
|
||||||
nextBlock := c.ctx.AddBasicBlock(frame.fn.llvmFn, "typeassert.next")
|
nextBlock := c.ctx.AddBasicBlock(frame.fn.llvmFn, "typeassert.next")
|
||||||
|
frame.blocks[frame.currentBlock] = nextBlock // adjust outgoing block for phi nodes
|
||||||
c.builder.CreateCondBr(commaOk, okBlock, nextBlock)
|
c.builder.CreateCondBr(commaOk, okBlock, nextBlock)
|
||||||
|
|
||||||
// Retrieve the value from the interface if the type assert was
|
// Retrieve the value from the interface if the type assert was
|
||||||
|
|
Загрузка…
Создание таблицы
Сослаться в новой задаче