ssa.UnOp: sub/not/xor

This commit is contained in:
visualfc
2024-05-07 09:55:51 +08:00
parent bc7412f6c9
commit 68949c28c8
3 changed files with 114 additions and 17 deletions

View File

@@ -100,13 +100,13 @@ func printuint(v uint64) {
gwrite(buf[i:])
}
// func printint(v int64) {
// if v < 0 {
// printstring("-")
// v = -v
// }
// printuint(uint64(v))
// }
func printint(v int64) {
if v < 0 {
printstring("-")
v = -v
}
printuint(uint64(v))
}
var minhexdigits = 0
@@ -171,4 +171,27 @@ func main() {
printnl()
printhex(0x1234abcf)
printnl()
prinxor(1)
printnl()
prinsub(100)
printnl()
prinusub(1<<64 - 1)
printnl()
prinfsub(100.1)
}
func prinxor(n int64) {
printint(^n)
}
func prinsub(n int64) {
printint(-n)
}
func prinusub(n uint64) {
printuint(-n)
}
func prinfsub(n float64) {
_ = -n
}

View File

@@ -11,8 +11,9 @@ source_filename = "main"
@0 = private unnamed_addr constant [3 x i8] c"%c\00", align 1
@1 = private unnamed_addr constant [5 x i8] c"llgo\00", align 1
@2 = private unnamed_addr constant [17 x i8] c"0123456789abcdef\00", align 1
@3 = private unnamed_addr constant [2 x i8] c"\0A\00", align 1
@4 = private unnamed_addr constant [2 x i8] c" \00", align 1
@3 = private unnamed_addr constant [2 x i8] c"-\00", align 1
@4 = private unnamed_addr constant [2 x i8] c"\0A\00", align 1
@5 = private unnamed_addr constant [2 x i8] c" \00", align 1
define %"github.com/goplus/llgo/internal/runtime.Slice" @main.bytes(%"github.com/goplus/llgo/internal/runtime.String" %0) {
_llgo_0:
@@ -91,6 +92,26 @@ _llgo_0:
call void @main.printnl()
call void @main.printhex(i64 305441743)
call void @main.printnl()
call void @main.prinxor(i64 1)
call void @main.printnl()
call void @main.prinsub(i64 100)
call void @main.printnl()
call void @main.prinusub(i64 -1)
call void @main.printnl()
call void @main.prinfsub(double 1.001000e+02)
ret void
}
define void @main.prinfsub(double %0) {
_llgo_0:
%1 = fneg double %0
ret void
}
define void @main.prinsub(i64 %0) {
_llgo_0:
%1 = sub i64 0, %0
call void @main.printint(i64 %1)
ret void
}
@@ -139,16 +160,33 @@ _llgo_5: ; preds = %_llgo_1
br i1 %21, label %_llgo_2, label %_llgo_4
}
define void @main.printint(i64 %0) {
_llgo_0:
%1 = icmp slt i64 %0, 0
br i1 %1, label %_llgo_1, label %_llgo_2
_llgo_1: ; preds = %_llgo_0
%2 = call %"github.com/goplus/llgo/internal/runtime.String" @"github.com/goplus/llgo/internal/runtime.NewString"(ptr @3, i64 1)
call void @main.printstring(%"github.com/goplus/llgo/internal/runtime.String" %2)
%3 = sub i64 0, %0
br label %_llgo_2
_llgo_2: ; preds = %_llgo_1, %_llgo_0
%4 = phi i64 [ %0, %_llgo_0 ], [ %3, %_llgo_1 ]
call void @main.printuint(i64 %4)
ret void
}
define void @main.printnl() {
_llgo_0:
%0 = call %"github.com/goplus/llgo/internal/runtime.String" @"github.com/goplus/llgo/internal/runtime.NewString"(ptr @3, i64 1)
%0 = call %"github.com/goplus/llgo/internal/runtime.String" @"github.com/goplus/llgo/internal/runtime.NewString"(ptr @4, i64 1)
call void @main.printstring(%"github.com/goplus/llgo/internal/runtime.String" %0)
ret void
}
define void @main.printsp() {
_llgo_0:
%0 = call %"github.com/goplus/llgo/internal/runtime.String" @"github.com/goplus/llgo/internal/runtime.NewString"(ptr @4, i64 1)
%0 = call %"github.com/goplus/llgo/internal/runtime.String" @"github.com/goplus/llgo/internal/runtime.NewString"(ptr @5, i64 1)
call void @main.printstring(%"github.com/goplus/llgo/internal/runtime.String" %0)
ret void
}
@@ -191,6 +229,20 @@ _llgo_4: ; preds = %_llgo_1
br label %_llgo_3
}
define void @main.prinusub(i64 %0) {
_llgo_0:
%1 = sub i64 0, %0
call void @main.printuint(i64 %1)
ret void
}
define void @main.prinxor(i64 %0) {
_llgo_0:
%1 = xor i64 %0, -1
call void @main.printint(i64 %1)
ret void
}
define ptr @main.stringStructOf(ptr %0) {
_llgo_0:
ret ptr %0

View File

@@ -342,16 +342,38 @@ func (b Builder) BinOp(op token.Token, x, y Expr) Expr {
// XOR is bitwise complement.
// SUB is negation.
// NOT is logical negation.
func (b Builder) UnOp(op token.Token, x Expr) Expr {
switch op {
case token.MUL:
return b.Load(x)
}
func (b Builder) UnOp(op token.Token, x Expr) (ret Expr) {
if debugInstr {
log.Printf("UnOp %v, %v\n", op, x.impl)
}
switch op {
case token.MUL:
return b.Load(x)
case token.SUB:
switch t := x.Type.raw.Underlying().(type) {
case *types.Basic:
ret.Type = x.Type
if t.Info()&types.IsInteger != 0 {
ret.impl = b.impl.CreateNeg(x.impl, "")
} else if t.Info()&types.IsFloat != 0 {
ret.impl = b.impl.CreateFNeg(x.impl, "")
} else {
panic("todo")
}
default:
panic("unreachable")
}
case token.NOT:
ret.Type = x.Type
ret.impl = b.impl.CreateNot(x.impl, "")
case token.XOR:
ret.Type = x.Type
ret.impl = b.impl.CreateXor(x.impl, llvm.ConstInt(x.Type.ll, ^uint64(0), false), "")
case token.ARROW:
panic("todo")
}
return
}
// -----------------------------------------------------------------------------