Commit e3e043be authored by Martin Möhrmann's avatar Martin Möhrmann

cmd/compile: improve typechecking of OSLICEHEADER nodes

Create a new node for OSLICEHEADER nodes to ensure typechecks are applied.
Add nil checks for OSLICEHEADER type and pointer parameters
for better error messages when these are not set.
Improve formatting of OSLICEHEADER nodes in compiler error messages.

Change-Id: Idea8f41bb4beb636f0e1fc381ff8d79b1d44fbae
Reviewed-on: https://go-review.googlesource.com/c/146997
Run-TryBot: Martin Möhrmann <moehrmann@google.com>
TryBot-Result: Gobot Gobot <gobot@golang.org>
Reviewed-by: 's avatarJosh Bleecher Snyder <josharian@gmail.com>
parent c5aea7a4
......@@ -1114,6 +1114,7 @@ var opprec = []int{
OSLICEARR: 8,
OSLICE3: 8,
OSLICE3ARR: 8,
OSLICEHEADER: 8,
ODOTINTER: 8,
ODOTMETH: 8,
ODOTPTR: 8,
......@@ -1393,6 +1394,12 @@ func (n *Node) exprfmt(s fmt.State, prec int, mode fmtMode) {
}
fmt.Fprint(s, "]")
case OSLICEHEADER:
if n.List.Len() != 2 {
Fatalf("bad OSLICEHEADER list length %d", n.List.Len())
}
mode.Fprintf(s, "sliceheader{%v,%v,%v}", n.Left, n.List.First(), n.List.Second())
case OCOPY, OCOMPLEX:
mode.Fprintf(s, "%#v(%v, %v)", n.Op, n.Left, n.Right)
......
......@@ -1160,11 +1160,15 @@ func typecheck1(n *Node, top int) (res *Node) {
ok |= Erv
t := n.Type
if t == nil {
Fatalf("no type specified for OSLICEHEADER")
}
if !t.IsSlice() {
Fatalf("invalid type %v for OSLICEHEADER", n.Type)
}
if !n.Left.Type.IsUnsafePtr() {
if n.Left == nil || n.Left.Type == nil || !n.Left.Type.IsUnsafePtr() {
Fatalf("need unsafe.Pointer for OSLICEHEADER")
}
......
......@@ -1351,14 +1351,17 @@ opswitch:
argtype = types.Types[TINT]
}
m := nod(OSLICEHEADER, nil, nil)
m.Type = t
fn := syslook(fnname)
n.Left = mkcall1(fn, types.Types[TUNSAFEPTR], init, typename(t.Elem()), conv(len, argtype), conv(cap, argtype))
n.Left.SetNonNil(true)
n.List.Set2(conv(len, types.Types[TINT]), conv(cap, types.Types[TINT]))
n.Op = OSLICEHEADER
n.Type = t
n = typecheck(n, Erv)
n = walkexpr(n, init)
m.Left = mkcall1(fn, types.Types[TUNSAFEPTR], init, typename(t.Elem()), conv(len, argtype), conv(cap, argtype))
m.Left.SetNonNil(true)
m.List.Set2(conv(len, types.Types[TINT]), conv(cap, types.Types[TINT]))
m = typecheck(m, Erv)
m = walkexpr(m, init)
n = m
}
case ORUNESTR:
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment