mirror of
https://github.com/golang/go
synced 2024-11-14 07:20:22 -07:00
move various bits of code around
and delete some dead code. no actual changes here. R=ken OCL=32764 CL=32764
This commit is contained in:
parent
d169dcee3b
commit
aa347c4a0d
@ -15,28 +15,30 @@ YFILES=\
|
|||||||
go.y\
|
go.y\
|
||||||
|
|
||||||
OFILES=\
|
OFILES=\
|
||||||
reflect.$O\
|
align.$O\
|
||||||
y.tab.$O\
|
bits.$O\
|
||||||
lex.$O\
|
builtin.$O\
|
||||||
subr.$O\
|
compat.$O\
|
||||||
dcl.$O\
|
|
||||||
sinit.$O\
|
|
||||||
export.$O\
|
|
||||||
walk.$O\
|
|
||||||
swt.$O\
|
|
||||||
const.$O\
|
const.$O\
|
||||||
|
dcl.$O\
|
||||||
|
export.$O\
|
||||||
|
gen.$O\
|
||||||
|
init.$O\
|
||||||
|
lex.$O\
|
||||||
mparith1.$O\
|
mparith1.$O\
|
||||||
mparith2.$O\
|
mparith2.$O\
|
||||||
mparith3.$O\
|
mparith3.$O\
|
||||||
builtin.$O\
|
|
||||||
compat.$O\
|
|
||||||
bits.$O\
|
|
||||||
align.$O\
|
|
||||||
gen.$O\
|
|
||||||
obj.$O\
|
obj.$O\
|
||||||
print.$O\
|
print.$O\
|
||||||
typecheck.$O\
|
reflect.$O\
|
||||||
select.$O\
|
select.$O\
|
||||||
|
sinit.$O\
|
||||||
|
subr.$O\
|
||||||
|
swt.$O\
|
||||||
|
typecheck.$O\
|
||||||
|
unsafe.$O\
|
||||||
|
walk.$O\
|
||||||
|
y.tab.$O\
|
||||||
|
|
||||||
$(LIB): $(OFILES)
|
$(LIB): $(OFILES)
|
||||||
ar rsc $(LIB) $(OFILES)
|
ar rsc $(LIB) $(OFILES)
|
||||||
|
2028
src/cmd/gc/dcl.c
2028
src/cmd/gc/dcl.c
File diff suppressed because it is too large
Load Diff
@ -601,8 +601,6 @@ EXTERN char namebuf[NSYMB];
|
|||||||
EXTERN char lexbuf[NSYMB];
|
EXTERN char lexbuf[NSYMB];
|
||||||
EXTERN char debug[256];
|
EXTERN char debug[256];
|
||||||
EXTERN Sym* hash[NHASH];
|
EXTERN Sym* hash[NHASH];
|
||||||
EXTERN Sym* dclstack;
|
|
||||||
EXTERN Sym* b0stack;
|
|
||||||
EXTERN Sym* pkgmyname; // my name for package
|
EXTERN Sym* pkgmyname; // my name for package
|
||||||
EXTERN Sym* pkgimportname; // package name from imported package
|
EXTERN Sym* pkgimportname; // package name from imported package
|
||||||
EXTERN int tptr; // either TPTR32 or TPTR64
|
EXTERN int tptr; // either TPTR32 or TPTR64
|
||||||
@ -814,7 +812,6 @@ void argtype(Node*, Type*);
|
|||||||
int eqargs(Type*, Type*);
|
int eqargs(Type*, Type*);
|
||||||
uint32 typehash(Type*, int, int);
|
uint32 typehash(Type*, int, int);
|
||||||
void frame(int);
|
void frame(int);
|
||||||
Node* dobad(void);
|
|
||||||
Node* nodintconst(int64);
|
Node* nodintconst(int64);
|
||||||
void nodconst(Node*, Type*, int64);
|
void nodconst(Node*, Type*, int64);
|
||||||
Node* nodnil(void);
|
Node* nodnil(void);
|
||||||
@ -921,7 +918,6 @@ Type* newtype(Sym*);
|
|||||||
Type* oldtype(Sym*);
|
Type* oldtype(Sym*);
|
||||||
void fninit(NodeList*);
|
void fninit(NodeList*);
|
||||||
Node* nametodcl(Node*, Type*);
|
Node* nametodcl(Node*, Type*);
|
||||||
Node* anondcl(Type*);
|
|
||||||
NodeList* checkarglist(NodeList*);
|
NodeList* checkarglist(NodeList*);
|
||||||
void checkwidth(Type*);
|
void checkwidth(Type*);
|
||||||
void defercheckwidth(void);
|
void defercheckwidth(void);
|
||||||
|
@ -1137,7 +1137,6 @@ fndcl:
|
|||||||
{
|
{
|
||||||
Node *n;
|
Node *n;
|
||||||
|
|
||||||
b0stack = dclstack; // mark base for fn literals
|
|
||||||
$$ = nod(ODCLFUNC, N, N);
|
$$ = nod(ODCLFUNC, N, N);
|
||||||
$$->nname = $1;
|
$$->nname = $1;
|
||||||
if($3 == nil && $5 == nil)
|
if($3 == nil && $5 == nil)
|
||||||
@ -1159,7 +1158,6 @@ fndcl:
|
|||||||
rcvr = N;
|
rcvr = N;
|
||||||
}
|
}
|
||||||
|
|
||||||
b0stack = dclstack; // mark base for fn literals
|
|
||||||
$$ = nod(ODCLFUNC, N, N);
|
$$ = nod(ODCLFUNC, N, N);
|
||||||
$$->nname = $4;
|
$$->nname = $4;
|
||||||
$$->nname = methodname($4, rcvr->type);
|
$$->nname = methodname($4, rcvr->type);
|
||||||
|
193
src/cmd/gc/init.c
Normal file
193
src/cmd/gc/init.c
Normal file
@ -0,0 +1,193 @@
|
|||||||
|
// Copyright 2009 The Go Authors. All rights reserved.
|
||||||
|
// Use of this source code is governed by a BSD-style
|
||||||
|
// license that can be found in the LICENSE file.
|
||||||
|
|
||||||
|
#include "go.h"
|
||||||
|
|
||||||
|
/*
|
||||||
|
* a function named init is a special case.
|
||||||
|
* it is called by the initialization before
|
||||||
|
* main is run. to make it unique within a
|
||||||
|
* package and also uncallable, the name,
|
||||||
|
* normally "pkg.init", is altered to "pkg.init·filename".
|
||||||
|
*/
|
||||||
|
Node*
|
||||||
|
renameinit(Node *n)
|
||||||
|
{
|
||||||
|
Sym *s;
|
||||||
|
|
||||||
|
s = n->sym;
|
||||||
|
if(s == S)
|
||||||
|
return n;
|
||||||
|
if(strcmp(s->name, "init") != 0)
|
||||||
|
return n;
|
||||||
|
|
||||||
|
snprint(namebuf, sizeof(namebuf), "init·%s", filename);
|
||||||
|
s = lookup(namebuf);
|
||||||
|
return newname(s);
|
||||||
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
* hand-craft the following initialization code
|
||||||
|
* var initdone·<file> uint8 (1)
|
||||||
|
* func Init·<file>() (2)
|
||||||
|
* if initdone·<file> { (3)
|
||||||
|
* if initdone·<file> == 2 (4)
|
||||||
|
* return
|
||||||
|
* throw(); (5)
|
||||||
|
* }
|
||||||
|
* initdone.<file>++; (6)
|
||||||
|
* // over all matching imported symbols
|
||||||
|
* <pkg>.init·<file>() (7)
|
||||||
|
* { <init stmts> } (8)
|
||||||
|
* init·<file>() // if any (9)
|
||||||
|
* initdone.<file>++; (10)
|
||||||
|
* return (11)
|
||||||
|
* }
|
||||||
|
*/
|
||||||
|
int
|
||||||
|
anyinit(NodeList *n)
|
||||||
|
{
|
||||||
|
uint32 h;
|
||||||
|
Sym *s;
|
||||||
|
|
||||||
|
// are there any init statements
|
||||||
|
if(n != nil)
|
||||||
|
return 1;
|
||||||
|
|
||||||
|
// is this main
|
||||||
|
if(strcmp(package, "main") == 0)
|
||||||
|
return 1;
|
||||||
|
|
||||||
|
// is there an explicit init function
|
||||||
|
snprint(namebuf, sizeof(namebuf), "init·%s", filename);
|
||||||
|
s = lookup(namebuf);
|
||||||
|
if(s->def != N)
|
||||||
|
return 1;
|
||||||
|
|
||||||
|
// are there any imported init functions
|
||||||
|
for(h=0; h<NHASH; h++)
|
||||||
|
for(s = hash[h]; s != S; s = s->link) {
|
||||||
|
if(s->name[0] != 'I' || strncmp(s->name, "Init·", 6) != 0)
|
||||||
|
continue;
|
||||||
|
if(s->def == N)
|
||||||
|
continue;
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
// then none
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
fninit(NodeList *n)
|
||||||
|
{
|
||||||
|
Node *gatevar;
|
||||||
|
Node *a, *b, *fn;
|
||||||
|
NodeList *r;
|
||||||
|
uint32 h;
|
||||||
|
Sym *s, *initsym;
|
||||||
|
|
||||||
|
if(strcmp(package, "PACKAGE") == 0) {
|
||||||
|
// sys.go or unsafe.go during compiler build
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
if(!anyinit(n))
|
||||||
|
return;
|
||||||
|
|
||||||
|
r = nil;
|
||||||
|
|
||||||
|
// (1)
|
||||||
|
snprint(namebuf, sizeof(namebuf), "initdone·%s", filename);
|
||||||
|
gatevar = newname(lookup(namebuf));
|
||||||
|
addvar(gatevar, types[TUINT8], PEXTERN);
|
||||||
|
|
||||||
|
// (2)
|
||||||
|
|
||||||
|
maxarg = 0;
|
||||||
|
stksize = initstksize;
|
||||||
|
|
||||||
|
snprint(namebuf, sizeof(namebuf), "Init·%s", filename);
|
||||||
|
|
||||||
|
// this is a botch since we need a known name to
|
||||||
|
// call the top level init function out of rt0
|
||||||
|
if(strcmp(package, "main") == 0)
|
||||||
|
snprint(namebuf, sizeof(namebuf), "init");
|
||||||
|
|
||||||
|
fn = nod(ODCLFUNC, N, N);
|
||||||
|
initsym = lookup(namebuf);
|
||||||
|
fn->nname = newname(initsym);
|
||||||
|
fn->type = functype(N, nil, nil);
|
||||||
|
funchdr(fn);
|
||||||
|
|
||||||
|
// (3)
|
||||||
|
a = nod(OIF, N, N);
|
||||||
|
a->ntest = nod(ONE, gatevar, nodintconst(0));
|
||||||
|
r = list(r, a);
|
||||||
|
|
||||||
|
// (4)
|
||||||
|
b = nod(OIF, N, N);
|
||||||
|
b->ntest = nod(OEQ, gatevar, nodintconst(2));
|
||||||
|
b->nbody = list1(nod(ORETURN, N, N));
|
||||||
|
a->nbody = list1(b);
|
||||||
|
|
||||||
|
// (5)
|
||||||
|
b = syslook("throwinit", 0);
|
||||||
|
b = nod(OCALL, b, N);
|
||||||
|
a->nbody = list(a->nbody, b);
|
||||||
|
|
||||||
|
// (6)
|
||||||
|
a = nod(OASOP, gatevar, nodintconst(1));
|
||||||
|
a->etype = OADD;
|
||||||
|
r = list(r, a);
|
||||||
|
|
||||||
|
// (7)
|
||||||
|
for(h=0; h<NHASH; h++)
|
||||||
|
for(s = hash[h]; s != S; s = s->link) {
|
||||||
|
if(s->name[0] != 'I' || strncmp(s->name, "Init·", 6) != 0)
|
||||||
|
continue;
|
||||||
|
if(s->def == N)
|
||||||
|
continue;
|
||||||
|
if(s == initsym)
|
||||||
|
continue;
|
||||||
|
|
||||||
|
// could check that it is fn of no args/returns
|
||||||
|
a = nod(OCALL, s->def, N);
|
||||||
|
r = list(r, a);
|
||||||
|
}
|
||||||
|
|
||||||
|
// (8)
|
||||||
|
r = concat(r, initfix(n));
|
||||||
|
|
||||||
|
// (9)
|
||||||
|
// could check that it is fn of no args/returns
|
||||||
|
snprint(namebuf, sizeof(namebuf), "init·%s", filename);
|
||||||
|
s = lookup(namebuf);
|
||||||
|
if(s->def != N) {
|
||||||
|
a = nod(OCALL, s->def, N);
|
||||||
|
r = list(r, a);
|
||||||
|
}
|
||||||
|
|
||||||
|
// (10)
|
||||||
|
a = nod(OASOP, gatevar, nodintconst(1));
|
||||||
|
a->etype = OADD;
|
||||||
|
r = list(r, a);
|
||||||
|
|
||||||
|
// (11)
|
||||||
|
a = nod(ORETURN, N, N);
|
||||||
|
r = list(r, a);
|
||||||
|
|
||||||
|
exportsym(fn->nname->sym);
|
||||||
|
|
||||||
|
fn->nbody = r;
|
||||||
|
//dump("b", fn);
|
||||||
|
//dump("r", fn->nbody);
|
||||||
|
|
||||||
|
popdcl();
|
||||||
|
initflag = 1; // flag for loader static initialization
|
||||||
|
compile(fn);
|
||||||
|
initflag = 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
@ -393,10 +393,11 @@ typ(int et)
|
|||||||
return t;
|
return t;
|
||||||
}
|
}
|
||||||
|
|
||||||
Node*
|
|
||||||
dobad(void)
|
Type*
|
||||||
|
sortinter(Type *t)
|
||||||
{
|
{
|
||||||
return nod(OBAD, N, N);
|
return t;
|
||||||
}
|
}
|
||||||
|
|
||||||
Node*
|
Node*
|
||||||
@ -2636,23 +2637,25 @@ NodeList*
|
|||||||
structargs(Type **tl, int mustname)
|
structargs(Type **tl, int mustname)
|
||||||
{
|
{
|
||||||
Iter savet;
|
Iter savet;
|
||||||
Node *a;
|
Node *a, *n;
|
||||||
NodeList *args;
|
NodeList *args;
|
||||||
Type *t;
|
Type *t;
|
||||||
char nam[100];
|
char buf[100];
|
||||||
int n;
|
int gen;
|
||||||
|
|
||||||
args = nil;
|
args = nil;
|
||||||
n = 0;
|
gen = 0;
|
||||||
for(t = structfirst(&savet, tl); t != T; t = structnext(&savet)) {
|
for(t = structfirst(&savet, tl); t != T; t = structnext(&savet)) {
|
||||||
|
n = N;
|
||||||
if(t->sym)
|
if(t->sym)
|
||||||
a = nametodcl(newname(t->sym), t->type);
|
n = newname(t->sym);
|
||||||
else if(mustname) {
|
else if(mustname) {
|
||||||
// have to give it a name so we can refer to it in trampoline
|
// have to give it a name so we can refer to it in trampoline
|
||||||
snprint(nam, sizeof nam, ".anon%d", n++);
|
snprint(buf, sizeof buf, ".anon%d", gen++);
|
||||||
a = nametodcl(newname(lookup(nam)), t->type);
|
n = newname(lookup(buf));
|
||||||
} else
|
}
|
||||||
a = anondcl(t->type);
|
a = nod(ODCLFIELD, n, N);
|
||||||
|
a->type = t->type;
|
||||||
args = list(args, a);
|
args = list(args, a);
|
||||||
}
|
}
|
||||||
return args;
|
return args;
|
||||||
@ -2694,7 +2697,8 @@ genwrapper(Type *rcvr, Type *method, Sym *newnam)
|
|||||||
dclcontext = PEXTERN;
|
dclcontext = PEXTERN;
|
||||||
markdcl();
|
markdcl();
|
||||||
|
|
||||||
this = nametodcl(newname(lookup(".this")), rcvr);
|
this = nod(ODCLFIELD, newname(lookup(".this")), N);
|
||||||
|
this->type = rcvr;
|
||||||
in = structargs(getinarg(method->type), 1);
|
in = structargs(getinarg(method->type), 1);
|
||||||
out = structargs(getoutarg(method->type), 0);
|
out = structargs(getoutarg(method->type), 0);
|
||||||
|
|
||||||
@ -2982,6 +2986,9 @@ liststmt(NodeList *l)
|
|||||||
return n;
|
return n;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
* return nelem of list
|
||||||
|
*/
|
||||||
int
|
int
|
||||||
count(NodeList *l)
|
count(NodeList *l)
|
||||||
{
|
{
|
||||||
@ -2992,3 +2999,96 @@ count(NodeList *l)
|
|||||||
n++;
|
n++;
|
||||||
return n;
|
return n;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
* return nelem of list
|
||||||
|
*/
|
||||||
|
int
|
||||||
|
structcount(Type *t)
|
||||||
|
{
|
||||||
|
int v;
|
||||||
|
Iter s;
|
||||||
|
|
||||||
|
v = 0;
|
||||||
|
for(t = structfirst(&s, &t); t != T; t = structnext(&s))
|
||||||
|
v++;
|
||||||
|
return v;
|
||||||
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
* when a type's width should be known, we call checkwidth
|
||||||
|
* to compute it. during a declaration like
|
||||||
|
*
|
||||||
|
* type T *struct { next T }
|
||||||
|
*
|
||||||
|
* it is necessary to defer the calculation of the struct width
|
||||||
|
* until after T has been initialized to be a pointer to that struct.
|
||||||
|
* similarly, during import processing structs may be used
|
||||||
|
* before their definition. in those situations, calling
|
||||||
|
* defercheckwidth() stops width calculations until
|
||||||
|
* resumecheckwidth() is called, at which point all the
|
||||||
|
* checkwidths that were deferred are executed.
|
||||||
|
* sometimes it is okay to
|
||||||
|
*/
|
||||||
|
typedef struct TypeList TypeList;
|
||||||
|
struct TypeList {
|
||||||
|
Type *t;
|
||||||
|
TypeList *next;
|
||||||
|
};
|
||||||
|
|
||||||
|
static TypeList *tlfree;
|
||||||
|
static TypeList *tlq;
|
||||||
|
static int defercalc;
|
||||||
|
|
||||||
|
void
|
||||||
|
checkwidth(Type *t)
|
||||||
|
{
|
||||||
|
TypeList *l;
|
||||||
|
|
||||||
|
// function arg structs should not be checked
|
||||||
|
// outside of the enclosing function.
|
||||||
|
if(t->funarg)
|
||||||
|
fatal("checkwidth %T", t);
|
||||||
|
|
||||||
|
if(!defercalc) {
|
||||||
|
dowidth(t);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
l = tlfree;
|
||||||
|
if(l != nil)
|
||||||
|
tlfree = l->next;
|
||||||
|
else
|
||||||
|
l = mal(sizeof *l);
|
||||||
|
|
||||||
|
l->t = t;
|
||||||
|
l->next = tlq;
|
||||||
|
tlq = l;
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
defercheckwidth(void)
|
||||||
|
{
|
||||||
|
// we get out of sync on syntax errors, so don't be pedantic.
|
||||||
|
// if(defercalc)
|
||||||
|
// fatal("defercheckwidth");
|
||||||
|
defercalc = 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
resumecheckwidth(void)
|
||||||
|
{
|
||||||
|
TypeList *l;
|
||||||
|
|
||||||
|
if(!defercalc)
|
||||||
|
fatal("restartcheckwidth");
|
||||||
|
defercalc = 0;
|
||||||
|
|
||||||
|
for(l = tlq; l != nil; l = tlq) {
|
||||||
|
dowidth(l->t);
|
||||||
|
tlq = l->next;
|
||||||
|
l->next = tlfree;
|
||||||
|
tlfree = l;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
87
src/cmd/gc/unsafe.c
Normal file
87
src/cmd/gc/unsafe.c
Normal file
@ -0,0 +1,87 @@
|
|||||||
|
// Copyright 2009 The Go Authors. All rights reserved.
|
||||||
|
// Use of this source code is governed by a BSD-style
|
||||||
|
// license that can be found in the LICENSE file.
|
||||||
|
|
||||||
|
#include "go.h"
|
||||||
|
|
||||||
|
/*
|
||||||
|
* look for
|
||||||
|
* unsafe.Sizeof
|
||||||
|
* unsafe.Offsetof
|
||||||
|
* rewrite with a constant
|
||||||
|
*/
|
||||||
|
Node*
|
||||||
|
unsafenmagic(Node *fn, NodeList *args)
|
||||||
|
{
|
||||||
|
Node *r, *n;
|
||||||
|
Sym *s;
|
||||||
|
Type *t, *tr;
|
||||||
|
long v;
|
||||||
|
Val val;
|
||||||
|
|
||||||
|
if(fn == N || fn->op != ONAME || (s = fn->sym) == S)
|
||||||
|
goto no;
|
||||||
|
if(strcmp(s->package, "unsafe") != 0)
|
||||||
|
goto no;
|
||||||
|
|
||||||
|
if(args == nil) {
|
||||||
|
yyerror("missing argument for %S", s);
|
||||||
|
goto no;
|
||||||
|
}
|
||||||
|
r = args->n;
|
||||||
|
|
||||||
|
n = nod(OLITERAL, N, N);
|
||||||
|
if(strcmp(s->name, "Sizeof") == 0) {
|
||||||
|
typecheck(&r, Erv);
|
||||||
|
tr = r->type;
|
||||||
|
if(r->op == OLITERAL && r->val.ctype == CTSTR)
|
||||||
|
tr = types[TSTRING];
|
||||||
|
if(tr == T)
|
||||||
|
goto no;
|
||||||
|
v = tr->width;
|
||||||
|
goto yes;
|
||||||
|
}
|
||||||
|
if(strcmp(s->name, "Offsetof") == 0) {
|
||||||
|
if(r->op != ODOT && r->op != ODOTPTR)
|
||||||
|
goto no;
|
||||||
|
typecheck(&r, Erv);
|
||||||
|
v = r->xoffset;
|
||||||
|
goto yes;
|
||||||
|
}
|
||||||
|
if(strcmp(s->name, "Alignof") == 0) {
|
||||||
|
typecheck(&r, Erv);
|
||||||
|
tr = r->type;
|
||||||
|
if(r->op == OLITERAL && r->val.ctype == CTSTR)
|
||||||
|
tr = types[TSTRING];
|
||||||
|
if(tr == T)
|
||||||
|
goto no;
|
||||||
|
|
||||||
|
// make struct { byte; T; }
|
||||||
|
t = typ(TSTRUCT);
|
||||||
|
t->type = typ(TFIELD);
|
||||||
|
t->type->type = types[TUINT8];
|
||||||
|
t->type->down = typ(TFIELD);
|
||||||
|
t->type->down->type = tr;
|
||||||
|
// compute struct widths
|
||||||
|
dowidth(t);
|
||||||
|
|
||||||
|
// the offset of T is its required alignment
|
||||||
|
v = t->type->down->width;
|
||||||
|
goto yes;
|
||||||
|
}
|
||||||
|
|
||||||
|
no:
|
||||||
|
return N;
|
||||||
|
|
||||||
|
yes:
|
||||||
|
if(args->next != nil)
|
||||||
|
yyerror("extra arguments for %S", s);
|
||||||
|
// any side effects disappear; ignore init
|
||||||
|
val.ctype = CTINT;
|
||||||
|
val.u.xval = mal(sizeof(*n->val.u.xval));
|
||||||
|
mpmovecfix(val.u.xval, v);
|
||||||
|
n = nod(OLITERAL, N, N);
|
||||||
|
n->val = val;
|
||||||
|
n->type = types[TINT];
|
||||||
|
return n;
|
||||||
|
}
|
Loading…
Reference in New Issue
Block a user