diff options
Diffstat (limited to 'src/cmd/gc')
-rw-r--r-- | src/cmd/gc/dcl.c | 16 | ||||
-rw-r--r-- | src/cmd/gc/export.c | 53 | ||||
-rw-r--r-- | src/cmd/gc/go.h | 5 | ||||
-rw-r--r-- | src/cmd/gc/go.y | 20 |
4 files changed, 78 insertions, 16 deletions
diff --git a/src/cmd/gc/dcl.c b/src/cmd/gc/dcl.c index ef1ddbc71..ca76bd712 100644 --- a/src/cmd/gc/dcl.c +++ b/src/cmd/gc/dcl.c @@ -35,8 +35,8 @@ dodclvar(Node *n, Type *t) t = typ(TFORW); addvar(n, t, dclcontext); - if(exportadj) - exportsym(n->sym); + if(dcladj) + dcladj(n->sym); } void @@ -49,8 +49,8 @@ dodclconst(Node *n, Node *e) dodclconst(n, e); addconst(n, e, dclcontext); - if(exportadj) - exportsym(n->sym); + if(dcladj) + dcladj(n->sym); } /* @@ -79,8 +79,8 @@ dodcltype(Type *n) found: n->sym->local = 1; - if(exportadj) - exportsym(n->sym); + if(dcladj) + dcladj(n->sym); return n; } @@ -226,7 +226,7 @@ Node* methodname(Node *n, Type *t) { Sym *s; - + s = methodsym(n->sym, t); if(s == S) return n; @@ -1191,7 +1191,7 @@ embedded(Sym *s) { Node *n; char *name; - + // Names sometimes have disambiguation junk // appended after a center dot. Discard it when // making the name for the embedded struct field. diff --git a/src/cmd/gc/export.c b/src/cmd/gc/export.c index 3498aa3df..41d3fc414 100644 --- a/src/cmd/gc/export.c +++ b/src/cmd/gc/export.c @@ -28,13 +28,30 @@ exportsym(Sym *s) { if(s == S) return; - if(s->export != 0) + if(s->export != 0) { + if(s->export != 1) + yyerror("export/package mismatch: %S", s); return; + } s->export = 1; addexportsym(s); } +void +packagesym(Sym *s) +{ + if(s == S) + return; + if(s->export != 0) { + if(s->export != 2) + yyerror("export/package mismatch: %S", s); + return; + } + s->export = 2; + + addexportsym(s); +} void dumpprereq(Type *t) @@ -67,8 +84,10 @@ dumpexportconst(Sym *s) dumpprereq(t); Bprint(bout, "\t"); - if(s->export != 0) + if(s->export == 1) Bprint(bout, "export "); + else if(s->export == 2) + Bprint(bout, "package "); Bprint(bout, "const %lS ", s); if(t != T) Bprint(bout, "%#T ", t); @@ -110,8 +129,10 @@ dumpexportvar(Sym *s) dumpprereq(t); Bprint(bout, "\t"); - if(s->export != 0) + if(s->export == 1) Bprint(bout, "export "); + else if(s->export == 2) + Bprint(bout, "package "); if(t->etype == TFUNC) Bprint(bout, "func "); else @@ -124,8 +145,10 @@ dumpexporttype(Sym *s) { dumpprereq(s->otype); Bprint(bout, "\t"); - if(s->export != 0) + if(s->export == 1) Bprint(bout, "export "); + else if(s->export == 2) + Bprint(bout, "package "); switch (s->otype->etype) { case TFORW: case TFORWSTRUCT: @@ -290,12 +313,21 @@ pkgtype(char *name, char *pkg) return s->otype; } +static int +mypackage(Node *ss) +{ + return strcmp(ss->psym->name, package) == 0; +} + void importconst(int export, Node *ss, Type *t, Val *v) { Node *n; Sym *s; + if(export == 2 && !mypackage(ss)) + return; + n = nod(OLITERAL, N, N); n->val = *v; n->type = t; @@ -307,6 +339,7 @@ importconst(int export, Node *ss, Type *t, Val *v) } dodclconst(newname(s), n); + s->export = export; if(debug['e']) print("import const %S\n", s); @@ -317,6 +350,9 @@ importvar(int export, Node *ss, Type *t) { Sym *s; + if(export == 2 && !mypackage(ss)) + return; + s = importsym(ss, LNAME); if(s->oname != N) { if(eqtype(t, s->oname->type, 0)) @@ -326,6 +362,7 @@ importvar(int export, Node *ss, Type *t) } checkwidth(t); addvar(newname(s), t, PEXTERN); + s->export = export; if(debug['e']) print("import var %S %lT\n", s, t); @@ -352,6 +389,14 @@ importtype(int export, Node *ss, Type *t) s->otype->sym = s; checkwidth(s->otype); + // If type name should not be visible to importers, + // hide it by setting the lexical type to name. + // This will make references in the ordinary program + // (but not the import sections) look at s->oname, + // which is nil, as for an undefined name. + if(export == 0 || (export == 2 && !mypackage(ss))) + s->lexical = LNAME; + if(debug['e']) print("import type %S %lT\n", s, t); } diff --git a/src/cmd/gc/go.h b/src/cmd/gc/go.h index c76adf692..cc842bc94 100644 --- a/src/cmd/gc/go.h +++ b/src/cmd/gc/go.h @@ -41,7 +41,7 @@ enum ASTRING, APTR, AINTER, - + BADWIDTH = -1000000000 }; @@ -438,7 +438,7 @@ EXTERN Sym* pkgimportname; // package name from imported package EXTERN int tptr; // either TPTR32 or TPTR64 extern char* sysimport; EXTERN char* filename; // name to uniqify names -EXTERN int exportadj; // declaration is being exported +EXTERN void (*dcladj)(Sym*); // declaration is being exported/packaged EXTERN Type* types[NTYPE]; EXTERN uchar simtype[NTYPE]; @@ -710,6 +710,7 @@ Node* embedded(Sym*); */ void renamepkg(Node*); void exportsym(Sym*); +void packagesym(Sym*); void dumpe(Sym*); void dumpexport(void); void dumpexporttype(Sym*); diff --git a/src/cmd/gc/go.y b/src/cmd/gc/go.y index 861f4fb29..077231810 100644 --- a/src/cmd/gc/go.y +++ b/src/cmd/gc/go.y @@ -193,10 +193,16 @@ xdcl: { $$ = N; } -| LEXPORT { exportadj = 1; stksize = initstksize; } common_dcl +| LEXPORT { dcladj = exportsym; stksize = initstksize; } common_dcl { $$ = $3; - exportadj = 0; + dcladj = 0; + initstksize = stksize; + } +| LPACKAGE { dcladj = packagesym; stksize = initstksize; } common_dcl + { + $$ = $3; + dcladj = 0; initstksize = stksize; } | LEXPORT '(' export_list_r ')' @@ -209,6 +215,12 @@ xdcl: exportsym($2->nname->sym); $$ = N; } +| LPACKAGE xfndcl + { + if($2 != N && $2->nname != N) + packagesym($2->nname->sym); + $$ = N; + } | ';' { $$ = N; @@ -1773,6 +1785,10 @@ oexport: { $$ = 1; } +| LPACKAGE + { + $$ = 2; + } oliteral: { |