本文整理匯總了Golang中cmd/internal/gc.Node.Type方法的典型用法代碼示例。如果您正苦於以下問題:Golang Node.Type方法的具體用法?Golang Node.Type怎麽用?Golang Node.Type使用的例子?那麽, 這裏精選的方法代碼示例或許可以為您提供幫助。您也可以進一步了解該方法所在類cmd/internal/gc.Node
的用法示例。
在下文中一共展示了Node.Type方法的15個代碼示例,這些例子默認根據受歡迎程度排序。您可以為喜歡或者感覺有用的代碼點讚,您的評價將有助於係統推薦出更棒的Golang代碼示例。
示例1: split64
/*
* n is a 64-bit value. fill in lo and hi to refer to its 32-bit halves.
*/
func split64(n *gc.Node, lo *gc.Node, hi *gc.Node) {
if !gc.Is64(n.Type) {
gc.Fatal("split64 %v", gc.Tconv(n.Type, 0))
}
if nsclean >= len(sclean) {
gc.Fatal("split64 clean")
}
sclean[nsclean].Op = gc.OEMPTY
nsclean++
switch n.Op {
default:
switch n.Op {
default:
var n1 gc.Node
if !dotaddable(n, &n1) {
gc.Igen(n, &n1, nil)
sclean[nsclean-1] = n1
}
n = &n1
case gc.ONAME:
if n.Class == gc.PPARAMREF {
var n1 gc.Node
gc.Cgen(n.Heapaddr, &n1)
sclean[nsclean-1] = n1
n = &n1
}
// nothing
case gc.OINDREG:
break
}
*lo = *n
*hi = *n
lo.Type = gc.Types[gc.TUINT32]
if n.Type.Etype == gc.TINT64 {
hi.Type = gc.Types[gc.TINT32]
} else {
hi.Type = gc.Types[gc.TUINT32]
}
hi.Xoffset += 4
case gc.OLITERAL:
var n1 gc.Node
gc.Convconst(&n1, n.Type, &n.Val)
i := gc.Mpgetfix(n1.Val.U.Xval)
gc.Nodconst(lo, gc.Types[gc.TUINT32], int64(uint32(i)))
i >>= 32
if n.Type.Etype == gc.TINT64 {
gc.Nodconst(hi, gc.Types[gc.TINT32], int64(int32(i)))
} else {
gc.Nodconst(hi, gc.Types[gc.TUINT32], int64(uint32(i)))
}
}
}
示例2: cgen_aret
/*
* call to n has already been generated.
* generate:
* res = &return value from call.
*/
func cgen_aret(n *gc.Node, res *gc.Node) {
t := n.Left.Type
if gc.Isptr[t.Etype] {
t = t.Type
}
var flist gc.Iter
fp := gc.Structfirst(&flist, gc.Getoutarg(t))
if fp == nil {
gc.Fatal("cgen_aret: nil")
}
var nod1 gc.Node
nod1.Op = gc.OINDREG
nod1.Val.U.Reg = ppc64.REGSP
nod1.Addable = 1
nod1.Xoffset = fp.Width + int64(gc.Widthptr) // +widthptr: saved lr at 0(SP)
nod1.Type = fp.Type
if res.Op != gc.OREGISTER {
var nod2 gc.Node
regalloc(&nod2, gc.Types[gc.Tptr], res)
agen(&nod1, &nod2)
gins(ppc64.AMOVD, &nod2, res)
regfree(&nod2)
} else {
agen(&nod1, res)
}
}
示例3: restx
func restx(x *gc.Node, oldx *gc.Node) {
if oldx.Op != 0 {
x.Type = gc.Types[gc.TINT64]
reg[x.Reg] = uint8(oldx.Ostk)
gmove(oldx, x)
gc.Regfree(oldx)
}
}
示例4: savex
/*
* register dr is one of the special ones (AX, CX, DI, SI, etc.).
* we need to use it. if it is already allocated as a temporary
* (r > 1; can only happen if a routine like sgen passed a
* special as cgen's res and then cgen used regalloc to reuse
* it as its own temporary), then move it for now to another
* register. caller must call restx to move it back.
* the move is not necessary if dr == res, because res is
* known to be dead.
*/
func savex(dr int, x *gc.Node, oldx *gc.Node, res *gc.Node, t *gc.Type) {
r := int(reg[dr])
// save current ax and dx if they are live
// and not the destination
*oldx = gc.Node{}
gc.Nodreg(x, t, dr)
if r > 1 && !gc.Samereg(x, res) {
gc.Regalloc(oldx, gc.Types[gc.TINT64], nil)
x.Type = gc.Types[gc.TINT64]
gmove(x, oldx)
x.Type = t
oldx.Ostk = int32(r) // squirrel away old r value
reg[dr] = 1
}
}
示例5: restx
func restx(x *gc.Node, oldx *gc.Node) {
gc.Regfree(x)
if oldx.Op != 0 {
x.Type = gc.Types[gc.TINT32]
gmove(oldx, x)
}
}
示例6: cgen_call
/*
* generate function call;
* proc=0 normal call
* proc=1 goroutine run in new proc
* proc=2 defer call save away stack
*/
func cgen_call(n *gc.Node, proc int) {
if n == nil {
return
}
var afun gc.Node
if n.Left.Ullman >= gc.UINF {
// if name involves a fn call
// precompute the address of the fn
gc.Tempname(&afun, gc.Types[gc.Tptr])
cgen(n.Left, &afun)
}
gc.Genlist(n.List) // assign the args
t := n.Left.Type
// call tempname pointer
if n.Left.Ullman >= gc.UINF {
var nod gc.Node
regalloc(&nod, gc.Types[gc.Tptr], nil)
gc.Cgen_as(&nod, &afun)
nod.Type = t
ginscall(&nod, proc)
regfree(&nod)
return
}
// call pointer
if n.Left.Op != gc.ONAME || n.Left.Class != gc.PFUNC {
var nod gc.Node
regalloc(&nod, gc.Types[gc.Tptr], nil)
gc.Cgen_as(&nod, n.Left)
nod.Type = t
ginscall(&nod, proc)
regfree(&nod)
return
}
// call direct
n.Left.Method = 1
ginscall(n.Left, proc)
}
示例7: dotaddable
func dotaddable(n *gc.Node, n1 *gc.Node) bool {
if n.Op != gc.ODOT {
return false
}
var oary [10]int64
var nn *gc.Node
o := gc.Dotoffset(n, oary[:], &nn)
if nn != nil && nn.Addable && o == 1 && oary[0] >= 0 {
*n1 = *nn
n1.Type = n.Type
n1.Xoffset += oary[0]
return true
}
return false
}
示例8: cgen_callret
/*
* call to n has already been generated.
* generate:
* res = return value from call.
*/
func cgen_callret(n *gc.Node, res *gc.Node) {
t := n.Left.Type
if t.Etype == gc.TPTR32 || t.Etype == gc.TPTR64 {
t = t.Type
}
var flist gc.Iter
fp := gc.Structfirst(&flist, gc.Getoutarg(t))
if fp == nil {
gc.Fatal("cgen_callret: nil")
}
var nod gc.Node
nod.Op = gc.OINDREG
nod.Val.U.Reg = x86.REG_SP
nod.Addable = 1
nod.Xoffset = fp.Width
nod.Type = fp.Type
gc.Cgen_as(res, &nod)
}
示例9: cgen_shift
/*
* generate shift according to op, one of:
* res = nl << nr
* res = nl >> nr
*/
func cgen_shift(op int, bounded bool, nl *gc.Node, nr *gc.Node, res *gc.Node) {
a := optoas(op, nl.Type)
if nr.Op == gc.OLITERAL {
var n1 gc.Node
gc.Regalloc(&n1, nl.Type, res)
gc.Cgen(nl, &n1)
sc := uint64(gc.Mpgetfix(nr.Val.U.Xval))
if sc >= uint64(nl.Type.Width*8) {
// large shift gets 2 shifts by width-1
var n3 gc.Node
gc.Nodconst(&n3, gc.Types[gc.TUINT32], nl.Type.Width*8-1)
gins(a, &n3, &n1)
gins(a, &n3, &n1)
} else {
gins(a, nr, &n1)
}
gmove(&n1, res)
gc.Regfree(&n1)
return
}
if nl.Ullman >= gc.UINF {
var n4 gc.Node
gc.Tempname(&n4, nl.Type)
gc.Cgen(nl, &n4)
nl = &n4
}
if nr.Ullman >= gc.UINF {
var n5 gc.Node
gc.Tempname(&n5, nr.Type)
gc.Cgen(nr, &n5)
nr = &n5
}
rcx := int(reg[x86.REG_CX])
var n1 gc.Node
gc.Nodreg(&n1, gc.Types[gc.TUINT32], x86.REG_CX)
// Allow either uint32 or uint64 as shift type,
// to avoid unnecessary conversion from uint32 to uint64
// just to do the comparison.
tcount := gc.Types[gc.Simtype[nr.Type.Etype]]
if tcount.Etype < gc.TUINT32 {
tcount = gc.Types[gc.TUINT32]
}
gc.Regalloc(&n1, nr.Type, &n1) // to hold the shift type in CX
var n3 gc.Node
gc.Regalloc(&n3, tcount, &n1) // to clear high bits of CX
var cx gc.Node
gc.Nodreg(&cx, gc.Types[gc.TUINT64], x86.REG_CX)
var oldcx gc.Node
if rcx > 0 && !gc.Samereg(&cx, res) {
gc.Regalloc(&oldcx, gc.Types[gc.TUINT64], nil)
gmove(&cx, &oldcx)
}
cx.Type = tcount
var n2 gc.Node
if gc.Samereg(&cx, res) {
gc.Regalloc(&n2, nl.Type, nil)
} else {
gc.Regalloc(&n2, nl.Type, res)
}
if nl.Ullman >= nr.Ullman {
gc.Cgen(nl, &n2)
gc.Cgen(nr, &n1)
gmove(&n1, &n3)
} else {
gc.Cgen(nr, &n1)
gmove(&n1, &n3)
gc.Cgen(nl, &n2)
}
gc.Regfree(&n3)
// test and fix up large shifts
if !bounded {
gc.Nodconst(&n3, tcount, nl.Type.Width*8)
gins(optoas(gc.OCMP, tcount), &n1, &n3)
p1 := gc.Gbranch(optoas(gc.OLT, tcount), nil, +1)
if op == gc.ORSH && gc.Issigned[nl.Type.Etype] {
gc.Nodconst(&n3, gc.Types[gc.TUINT32], nl.Type.Width*8-1)
gins(a, &n3, &n2)
} else {
gc.Nodconst(&n3, nl.Type, 0)
gmove(&n3, &n2)
}
//.........這裏部分代碼省略.........
示例10: stackcopy
func stackcopy(n, ns *gc.Node, osrc, odst, w int64) {
var noddi gc.Node
gc.Nodreg(&noddi, gc.Types[gc.Tptr], x86.REG_DI)
var nodsi gc.Node
gc.Nodreg(&nodsi, gc.Types[gc.Tptr], x86.REG_SI)
var nodl gc.Node
var nodr gc.Node
if n.Ullman >= ns.Ullman {
gc.Agenr(n, &nodr, &nodsi)
if ns.Op == gc.ONAME {
gc.Gvardef(ns)
}
gc.Agenr(ns, &nodl, &noddi)
} else {
if ns.Op == gc.ONAME {
gc.Gvardef(ns)
}
gc.Agenr(ns, &nodl, &noddi)
gc.Agenr(n, &nodr, &nodsi)
}
if nodl.Val.U.Reg != x86.REG_DI {
gmove(&nodl, &noddi)
}
if nodr.Val.U.Reg != x86.REG_SI {
gmove(&nodr, &nodsi)
}
gc.Regfree(&nodl)
gc.Regfree(&nodr)
c := w % 8 // bytes
q := w / 8 // quads
var oldcx gc.Node
var cx gc.Node
savex(x86.REG_CX, &cx, &oldcx, nil, gc.Types[gc.TINT64])
// if we are copying forward on the stack and
// the src and dst overlap, then reverse direction
if osrc < odst && odst < osrc+w {
// reverse direction
gins(x86.ASTD, nil, nil) // set direction flag
if c > 0 {
gconreg(addptr, w-1, x86.REG_SI)
gconreg(addptr, w-1, x86.REG_DI)
gconreg(movptr, c, x86.REG_CX)
gins(x86.AREP, nil, nil) // repeat
gins(x86.AMOVSB, nil, nil) // MOVB *(SI)-,*(DI)-
}
if q > 0 {
if c > 0 {
gconreg(addptr, -7, x86.REG_SI)
gconreg(addptr, -7, x86.REG_DI)
} else {
gconreg(addptr, w-8, x86.REG_SI)
gconreg(addptr, w-8, x86.REG_DI)
}
gconreg(movptr, q, x86.REG_CX)
gins(x86.AREP, nil, nil) // repeat
gins(x86.AMOVSQ, nil, nil) // MOVQ *(SI)-,*(DI)-
}
// we leave with the flag clear
gins(x86.ACLD, nil, nil)
} else {
// normal direction
if q > 128 || (gc.Nacl && q >= 4) {
gconreg(movptr, q, x86.REG_CX)
gins(x86.AREP, nil, nil) // repeat
gins(x86.AMOVSQ, nil, nil) // MOVQ *(SI)+,*(DI)+
} else if q >= 4 {
p := gins(obj.ADUFFCOPY, nil, nil)
p.To.Type = obj.TYPE_ADDR
p.To.Sym = gc.Linksym(gc.Pkglookup("duffcopy", gc.Runtimepkg))
// 14 and 128 = magic constants: see ../../runtime/asm_amd64.s
p.To.Offset = 14 * (128 - q)
} else if !gc.Nacl && c == 0 {
// We don't need the MOVSQ side-effect of updating SI and DI,
// and issuing a sequence of MOVQs directly is faster.
nodsi.Op = gc.OINDREG
noddi.Op = gc.OINDREG
for q > 0 {
gmove(&nodsi, &cx) // MOVQ x+(SI),CX
gmove(&cx, &noddi) // MOVQ CX,x+(DI)
nodsi.Xoffset += 8
noddi.Xoffset += 8
q--
}
} else {
for q > 0 {
gins(x86.AMOVSQ, nil, nil) // MOVQ *(SI)+,*(DI)+
q--
}
}
//.........這裏部分代碼省略.........
示例11: agenr
/*
* allocate a register (reusing res if possible) and generate
* a = &n
* The caller must call regfree(a).
* The generated code checks that the result is not nil.
*/
func agenr(n *gc.Node, a *gc.Node, res *gc.Node) {
if gc.Debug['g'] != 0 {
gc.Dump("agenr-n", n)
}
nl := n.Left
nr := n.Right
switch n.Op {
case gc.ODOT,
gc.ODOTPTR,
gc.OCALLFUNC,
gc.OCALLMETH,
gc.OCALLINTER:
var n1 gc.Node
igen(n, &n1, res)
regalloc(a, gc.Types[gc.Tptr], &n1)
agen(&n1, a)
regfree(&n1)
case gc.OIND:
cgenr(n.Left, a, res)
gc.Cgen_checknil(a)
case gc.OINDEX:
var p2 *obj.Prog // to be patched to panicindex.
w := uint32(n.Type.Width)
//bounded = debug['B'] || n->bounded;
var n3 gc.Node
var n1 gc.Node
if nr.Addable != 0 {
var tmp gc.Node
if !gc.Isconst(nr, gc.CTINT) {
gc.Tempname(&tmp, gc.Types[gc.TINT64])
}
if !gc.Isconst(nl, gc.CTSTR) {
agenr(nl, &n3, res)
}
if !gc.Isconst(nr, gc.CTINT) {
cgen(nr, &tmp)
regalloc(&n1, tmp.Type, nil)
gmove(&tmp, &n1)
}
} else if nl.Addable != 0 {
if !gc.Isconst(nr, gc.CTINT) {
var tmp gc.Node
gc.Tempname(&tmp, gc.Types[gc.TINT64])
cgen(nr, &tmp)
regalloc(&n1, tmp.Type, nil)
gmove(&tmp, &n1)
}
if !gc.Isconst(nl, gc.CTSTR) {
agenr(nl, &n3, res)
}
} else {
var tmp gc.Node
gc.Tempname(&tmp, gc.Types[gc.TINT64])
cgen(nr, &tmp)
nr = &tmp
if !gc.Isconst(nl, gc.CTSTR) {
agenr(nl, &n3, res)
}
regalloc(&n1, tmp.Type, nil)
gins(optoas(gc.OAS, tmp.Type), &tmp, &n1)
}
// &a is in &n3 (allocated in res)
// i is in &n1 (if not constant)
// w is width
// constant index
if gc.Isconst(nr, gc.CTINT) {
if gc.Isconst(nl, gc.CTSTR) {
gc.Fatal("constant string constant index")
}
v := uint64(gc.Mpgetfix(nr.Val.U.Xval))
if gc.Isslice(nl.Type) || nl.Type.Etype == gc.TSTRING {
if gc.Debug['B'] == 0 && !n.Bounded {
n1 = n3
n1.Op = gc.OINDREG
n1.Type = gc.Types[gc.Tptr]
n1.Xoffset = int64(gc.Array_nel)
var n4 gc.Node
regalloc(&n4, n1.Type, nil)
gmove(&n1, &n4)
ginscon2(optoas(gc.OCMP, gc.Types[gc.TUINT64]), &n4, int64(v))
regfree(&n4)
p1 := gc.Gbranch(optoas(gc.OGT, gc.Types[gc.TUINT64]), nil, +1)
ginscall(gc.Panicindex, 0)
gc.Patch(p1, gc.Pc)
}
//.........這裏部分代碼省略.........
示例12: cgen
/*
* generate:
* res = n;
* simplifies and calls gmove.
*/
func cgen(n *gc.Node, res *gc.Node) {
//print("cgen %N(%d) -> %N(%d)\n", n, n->addable, res, res->addable);
if gc.Debug['g'] != 0 {
gc.Dump("\ncgen-n", n)
gc.Dump("cgen-res", res)
}
if n == nil || n.Type == nil {
return
}
if res == nil || res.Type == nil {
gc.Fatal("cgen: res nil")
}
for n.Op == gc.OCONVNOP {
n = n.Left
}
switch n.Op {
case gc.OSLICE,
gc.OSLICEARR,
gc.OSLICESTR,
gc.OSLICE3,
gc.OSLICE3ARR:
if res.Op != gc.ONAME || res.Addable == 0 {
var n1 gc.Node
gc.Tempname(&n1, n.Type)
gc.Cgen_slice(n, &n1)
cgen(&n1, res)
} else {
gc.Cgen_slice(n, res)
}
return
case gc.OEFACE:
if res.Op != gc.ONAME || res.Addable == 0 {
var n1 gc.Node
gc.Tempname(&n1, n.Type)
gc.Cgen_eface(n, &n1)
cgen(&n1, res)
} else {
gc.Cgen_eface(n, res)
}
return
}
if n.Ullman >= gc.UINF {
if n.Op == gc.OINDREG {
gc.Fatal("cgen: this is going to misscompile")
}
if res.Ullman >= gc.UINF {
var n1 gc.Node
gc.Tempname(&n1, n.Type)
cgen(n, &n1)
cgen(&n1, res)
return
}
}
if gc.Isfat(n.Type) {
if n.Type.Width < 0 {
gc.Fatal("forgot to compute width for %v", gc.Tconv(n.Type, 0))
}
sgen(n, res, n.Type.Width)
return
}
if res.Addable == 0 {
if n.Ullman > res.Ullman {
var n1 gc.Node
regalloc(&n1, n.Type, res)
cgen(n, &n1)
if n1.Ullman > res.Ullman {
gc.Dump("n1", &n1)
gc.Dump("res", res)
gc.Fatal("loop in cgen")
}
cgen(&n1, res)
regfree(&n1)
return
}
var f int
if res.Ullman >= gc.UINF {
goto gen
}
if gc.Complexop(n, res) {
gc.Complexgen(n, res)
return
}
f = 1 // gen thru register
//.........這裏部分代碼省略.........
示例13: componentgen
/*
* copy a composite value by moving its individual components.
* Slices, strings and interfaces are supported.
* Small structs or arrays with elements of basic type are
* also supported.
* nr is N when assigning a zero value.
* return 1 if can do, 0 if can't.
*/
func componentgen(nr *gc.Node, nl *gc.Node) bool {
var nodl gc.Node
var nodr gc.Node
freel := 0
freer := 0
switch nl.Type.Etype {
default:
goto no
case gc.TARRAY:
t := nl.Type
// Slices are ok.
if gc.Isslice(t) {
break
}
// Small arrays are ok.
if t.Bound > 0 && t.Bound <= 3 && !gc.Isfat(t.Type) {
break
}
goto no
// Small structs with non-fat types are ok.
// Zero-sized structs are treated separately elsewhere.
case gc.TSTRUCT:
fldcount := int64(0)
for t := nl.Type.Type; t != nil; t = t.Down {
if gc.Isfat(t.Type) {
goto no
}
if t.Etype != gc.TFIELD {
gc.Fatal("componentgen: not a TFIELD: %v", gc.Tconv(t, obj.FmtLong))
}
fldcount++
}
if fldcount == 0 || fldcount > 4 {
goto no
}
case gc.TSTRING,
gc.TINTER:
break
}
nodl = *nl
if !cadable(nl) {
if nr != nil && !cadable(nr) {
goto no
}
igen(nl, &nodl, nil)
freel = 1
}
if nr != nil {
nodr = *nr
if !cadable(nr) {
igen(nr, &nodr, nil)
freer = 1
}
} else {
// When zeroing, prepare a register containing zero.
var tmp gc.Node
gc.Nodconst(&tmp, nl.Type, 0)
regalloc(&nodr, gc.Types[gc.TUINT], nil)
gmove(&tmp, &nodr)
freer = 1
}
// nl and nr are 'cadable' which basically means they are names (variables) now.
// If they are the same variable, don't generate any code, because the
// VARDEF we generate will mark the old value as dead incorrectly.
// (And also the assignments are useless.)
if nr != nil && nl.Op == gc.ONAME && nr.Op == gc.ONAME && nl == nr {
goto yes
}
switch nl.Type.Etype {
// componentgen for arrays.
case gc.TARRAY:
if nl.Op == gc.ONAME {
gc.Gvardef(nl)
}
t := nl.Type
if !gc.Isslice(t) {
nodl.Type = t.Type
//.........這裏部分代碼省略.........
示例14: bgen
/*
* generate:
* if(n == true) goto to;
*/
func bgen(n *gc.Node, true_ bool, likely int, to *obj.Prog) {
if gc.Debug['g'] != 0 {
gc.Dump("\nbgen", n)
}
if n == nil {
n = gc.Nodbool(true)
}
if n.Ninit != nil {
gc.Genlist(n.Ninit)
}
if n.Type == nil {
gc.Convlit(&n, gc.Types[gc.TBOOL])
if n.Type == nil {
return
}
}
et := int(n.Type.Etype)
if et != gc.TBOOL {
gc.Yyerror("cgen: bad type %v for %v", gc.Tconv(n.Type, 0), gc.Oconv(int(n.Op), 0))
gc.Patch(gins(obj.AEND, nil, nil), to)
return
}
var nr *gc.Node
for n.Op == gc.OCONVNOP {
n = n.Left
if n.Ninit != nil {
gc.Genlist(n.Ninit)
}
}
var nl *gc.Node
switch n.Op {
default:
var n1 gc.Node
regalloc(&n1, n.Type, nil)
cgen(n, &n1)
var n2 gc.Node
gc.Nodconst(&n2, n.Type, 0)
gins(optoas(gc.OCMP, n.Type), &n1, &n2)
a := ppc64.ABNE
if !true_ {
a = ppc64.ABEQ
}
gc.Patch(gc.Gbranch(a, n.Type, likely), to)
regfree(&n1)
return
// need to ask if it is bool?
case gc.OLITERAL:
if !true_ == (n.Val.U.Bval == 0) {
gc.Patch(gc.Gbranch(ppc64.ABR, nil, likely), to)
}
return
case gc.OANDAND,
gc.OOROR:
if (n.Op == gc.OANDAND) == true_ {
p1 := gc.Gbranch(obj.AJMP, nil, 0)
p2 := gc.Gbranch(obj.AJMP, nil, 0)
gc.Patch(p1, gc.Pc)
bgen(n.Left, !true_, -likely, p2)
bgen(n.Right, !true_, -likely, p2)
p1 = gc.Gbranch(obj.AJMP, nil, 0)
gc.Patch(p1, to)
gc.Patch(p2, gc.Pc)
} else {
bgen(n.Left, true_, likely, to)
bgen(n.Right, true_, likely, to)
}
return
case gc.OEQ,
gc.ONE,
gc.OLT,
gc.OGT,
gc.OLE,
gc.OGE:
nr = n.Right
if nr == nil || nr.Type == nil {
return
}
fallthrough
case gc.ONOT: // unary
nl = n.Left
if nl == nil || nl.Type == nil {
return
}
//.........這裏部分代碼省略.........
示例15: anyregalloc
func anyregalloc() bool {
var j int
for i := x86.REG_AX; i <= x86.REG_DI; i++ {
if reg[i] == 0 {
goto ok
}
for j = 0; j < len(resvd); j++ {
if resvd[j] == i {
goto ok
}
}
return true
ok:
}
for i := x86.REG_X0; i <= x86.REG_X7; i++ {
if reg[i] != 0 {
return true
}
}
return false
}
/*
* allocate register of type t, leave in n.
* if o != N, o is desired fixed register.
* caller must regfree(n).
*/
func regalloc(n *gc.Node, t *gc.Type, o *gc.Node) {
if t == nil {
gc.Fatal("regalloc: t nil")
}
et := int(gc.Simtype[t.Etype])
var i int
switch et {
case gc.TINT64,
gc.TUINT64:
gc.Fatal("regalloc64")
case gc.TINT8,
gc.TUINT8,
gc.TINT16,
gc.TUINT16,
gc.TINT32,
gc.TUINT32,
gc.TPTR32,
gc.TPTR64,
gc.TBOOL:
if o != nil && o.Op == gc.OREGISTER {
i = int(o.Val.U.Reg)
if i >= x86.REG_AX && i <= x86.REG_DI {
goto out
}
}
for i = x86.REG_AX; i <= x86.REG_DI; i++ {
if reg[i] == 0 {
goto out
}
}
fmt.Printf("registers allocated at\n")
for i := x86.REG_AX; i <= x86.REG_DI; i++ {
fmt.Printf("\t%v\t%#x\n", obj.Rconv(i), regpc[i])
}
gc.Fatal("out of fixed registers")
goto err
case gc.TFLOAT32,
gc.TFLOAT64:
if gc.Use_sse == 0 {
i = x86.REG_F0
goto out
}
if o != nil && o.Op == gc.OREGISTER {
i = int(o.Val.U.Reg)
if i >= x86.REG_X0 && i <= x86.REG_X7 {
goto out
}
}
for i = x86.REG_X0; i <= x86.REG_X7; i++ {
if reg[i] == 0 {
goto out
}
}
fmt.Printf("registers allocated at\n")
for i := x86.REG_X0; i <= x86.REG_X7; i++ {
fmt.Printf("\t%v\t%#x\n", obj.Rconv(i), regpc[i])
}
gc.Fatal("out of floating registers")
}
gc.Yyerror("regalloc: unknown type %v", gc.Tconv(t, 0))
err:
gc.Nodreg(n, t, 0)
//.........這裏部分代碼省略.........