Implement shifting with a differently-sized integer

Этот коммит содержится в:
Ayke van Laethem 2018-08-22 04:35:25 +02:00
родитель 337e48270b
коммит 8fb9cd4e23
Не найден ключ, соответствующий данной подписи
Идентификатор ключа GPG: E97FF5335DFDFDED

Просмотреть файл

@ -1530,6 +1530,15 @@ func (c *Compiler) parseBinOp(frame *Frame, binop *ssa.BinOp) (llvm.Value, error
return c.builder.CreateOr(x, y, ""), nil return c.builder.CreateOr(x, y, ""), nil
case token.XOR: // ^ case token.XOR: // ^
return c.builder.CreateXor(x, y, ""), nil return c.builder.CreateXor(x, y, ""), nil
case token.SHL, token.SHR:
sizeX := c.targetData.TypeAllocSize(x.Type())
sizeY := c.targetData.TypeAllocSize(y.Type())
if sizeX > sizeY {
// x and y must have equal sizes, make Y bigger in this case.
// y is unsigned, this has been checked by the Go type checker.
y = c.builder.CreateZExt(y, x.Type(), "")
}
switch binop.Op {
case token.SHL: // << case token.SHL: // <<
return c.builder.CreateShl(x, y, ""), nil return c.builder.CreateShl(x, y, ""), nil
case token.SHR: // >> case token.SHR: // >>
@ -1538,6 +1547,9 @@ func (c *Compiler) parseBinOp(frame *Frame, binop *ssa.BinOp) (llvm.Value, error
} else { } else {
return c.builder.CreateLShr(x, y, ""), nil return c.builder.CreateLShr(x, y, ""), nil
} }
default:
panic("unreachable")
}
case token.AND_NOT: // &^ case token.AND_NOT: // &^
// Go specific. Calculate "and not" with x & (~y) // Go specific. Calculate "and not" with x & (~y)
inv := c.builder.CreateNot(y, "") // ~y inv := c.builder.CreateNot(y, "") // ~y