69
69
static void loadpkgdata(char*, char*, char*, int);
70
static void loaddynimport(char*, char*, char*, int);
71
static void loaddynexport(char*, char*, char*, int);
70
static void loadcgo(char*, char*, char*, int);
72
71
static int parsemethod(char**, char*, char**);
73
72
static int parsepkgdata(char*, char*, char**, char*, char**, char**, char**);
78
75
ldpkg(Biobuf *f, char *pkg, int64 len, char *filename, int whence)
178
175
loadpkgdata(filename, pkg, p0, p1 - p0);
180
// look for dynimport section
181
p0 = strstr(p1, "\n$$ // dynimport");
183
p0 = strchr(p0+1, '\n');
185
fprint(2, "%s: found $$ // dynimport but no newline in %s\n", argv0, filename);
190
p1 = strstr(p0, "\n$$");
192
p1 = strstr(p0, "\n!\n");
194
fprint(2, "%s: cannot find end of // dynimport section in %s\n", argv0, filename);
199
loaddynimport(filename, pkg, p0 + 1, p1 - (p0+1));
202
// look for dynexp section
203
p0 = strstr(p1, "\n$$ // dynexport");
205
p0 = strchr(p0+1, '\n');
207
fprint(2, "%s: found $$ // dynexporg but no newline in %s\n", argv0, filename);
212
p1 = strstr(p0, "\n$$");
214
p1 = strstr(p0, "\n!\n");
216
fprint(2, "%s: cannot find end of // dynexporg section in %s\n", argv0, filename);
221
loaddynexport(filename, pkg, p0 + 1, p1 - (p0+1));
177
// look for cgo section
178
p0 = strstr(p1, "\n$$ // cgo");
180
p0 = strchr(p0+1, '\n');
182
fprint(2, "%s: found $$ // cgo but no newline in %s\n", argv0, filename);
187
p1 = strstr(p0, "\n$$");
189
p1 = strstr(p0, "\n!\n");
191
fprint(2, "%s: cannot find end of // cgo section in %s\n", argv0, filename);
196
loadcgo(filename, pkg, p0 + 1, p1 - (p0+1));
431
loaddynimport(char *file, char *pkg, char *p, int n)
412
loadcgo(char *file, char *pkg, char *p, int n)
433
char *pend, *next, *name, *def, *p0, *lib, *q;
414
char *pend, *next, *p0, *q;
415
char *f[10], *local, *remote, *lib;
438
422
for(; p<pend; p=next) {
439
423
next = strchr(p, '\n');
445
if(strncmp(p, "dynimport ", 10) != 0)
449
p = strchr(name, ' ');
455
p = strchr(def, ' ');
462
// successful parse: now can edit the line
463
*strchr(name, ' ') = 0;
464
*strchr(def, ' ') = 0;
467
fprint(2, "%s: %s: cannot use dynamic imports with -d flag\n", argv0, file);
472
if(strcmp(name, "_") == 0 && strcmp(def, "_") == 0) {
473
// allow #pragma dynimport _ _ "foo.so"
474
// to force a link of foo.so.
480
name = expandpkg(name, pkg);
481
q = strchr(def, '@');
486
if(s->type == 0 || s->type == SXREF) {
490
s->type = SDYNIMPORT;
430
p0 = estrdup(p); // save for error message
431
nf = tokenize(p, f, nelem(f));
433
if(strcmp(f[0], "cgo_import_dynamic") == 0) {
446
fprint(2, "%s: %s: cannot use dynamic imports with -d flag\n", argv0, file);
451
if(strcmp(local, "_") == 0 && strcmp(remote, "_") == 0) {
452
// allow #pragma dynimport _ _ "foo.so"
453
// to force a link of foo.so.
459
local = expandpkg(local, pkg);
460
q = strchr(remote, '#');
463
s = lookup(local, 0);
466
if(s->type == 0 || s->type == SXREF || s->type == SHOSTOBJ) {
470
if(s->type != SHOSTOBJ)
471
s->type = SDYNIMPORT;
477
if(strcmp(f[0], "cgo_import_static") == 0) {
481
s = lookup(local, 0);
487
if(strcmp(f[0], "cgo_export_static") == 0 || strcmp(f[0], "cgo_export_dynamic") == 0) {
488
// TODO: Remove once we know Windows is okay.
489
if(strcmp(f[0], "cgo_export_static") == 0 && HEADTYPE == Hwindows)
499
local = expandpkg(local, pkg);
500
s = lookup(local, 0);
502
// export overrides import, for openbsd/cgo.
504
if(s->dynimplib != nil) {
511
if(s->cgoexport == 0) {
514
dynexp = erealloc(dynexp, (ndynexp+32)*sizeof dynexp[0]);
515
dynexp[ndynexp++] = s;
516
} else if(strcmp(s->extname, remote) != 0) {
517
fprint(2, "%s: conflicting cgo_export directives: %s as %s and %s\n", argv0, s->name, s->extname, remote);
521
if(strcmp(f[0], "cgo_export_static") == 0)
522
s->cgoexport |= CgoExportStatic;
524
s->cgoexport |= CgoExportDynamic;
530
if(strcmp(f[0], "cgo_dynamic_linker") == 0) {
534
if(!debug['I']) { // not overridden by command line
535
if(interpreter != nil && strcmp(interpreter, f[1]) != 0) {
536
fprint(2, "%s: conflict dynlinker: %s and %s\n", argv0, interpreter, f[1]);
541
interpreter = estrdup(f[1]);
546
if(strcmp(f[0], "cgo_ldflag") == 0) {
550
ldflag = erealloc(ldflag, (nldflag+32)*sizeof ldflag[0]);
551
ldflag[nldflag++] = estrdup(f[1]);
502
loaddynexport(char *file, char *pkg, char *p, int n)
504
char *pend, *next, *local, *elocal, *remote, *p0;
509
for(; p<pend; p=next) {
510
next = strchr(p, '\n');
516
if(strncmp(p, "dynexport ", 10) != 0)
520
p = strchr(local, ' ');
527
// successful parse: now can edit the line
528
*strchr(local, ' ') = 0;
530
elocal = expandpkg(local, pkg);
532
s = lookup(elocal, 0);
533
if(s->dynimplib != nil) {
534
fprint(2, "%s: symbol is both dynimport and dynexport %s\n", argv0, local);
537
s->dynimpname = remote;
541
dynexp = realloc(dynexp, (ndynexp+32)*sizeof dynexp[0]);
542
dynexp[ndynexp++] = s;
550
fprint(2, "%s: invalid dynexport line: %s\n", argv0, p0);
554
static int markdepth;
567
mark1(Sym *s, Sym *parent)
569
if(s == S || s->reachable)
571
if(strncmp(s->name, "go.weak.", 8) == 0)
574
s->reachparent = parent;
566
Bprint(&bso, "%d marktext %s\n", markdepth, s->name);
567
for(a=s->autom; a; a=a->link)
569
for(p=s->text; p != P; p=p->link) {
596
for(s=markq; s!=S; s=s->queue) {
599
Bprint(&bso, "marktext %s\n", s->name);
600
for(a=s->autom; a; a=a->link)
602
for(p=s->text; p != P; p=p->link) {
603
mark1(p->from.sym, s);
607
for(i=0; i<s->nr; i++)
608
mark1(s->r[i].sym, s);
583
if(s == S || s->reachable)
585
if(strncmp(s->name, "weak.", 5) == 0)
590
for(i=0; i<s->nr; i++)
658
674
Bprint(&bso, "%5.2f deadcode\n", cputime());
660
676
mark(lookup(INITENTRY, 0));
678
mark(lookup(LIBINITENTRY, 0));
661
679
for(i=0; i<nelem(morename); i++)
662
680
mark(lookup(morename[i], 0));
664
682
for(i=0; i<ndynexp; i++)
687
// keep each beginning with 'typelink.' if the symbol it points at is being kept.
688
for(s = allsym; s != S; s = s->allsym) {
689
if(strncmp(s->name, "go.typelink.", 12) == 0)
690
s->reachable = s->nr==1 && s->r[0].sym->reachable;
667
693
// remove dead text but keep file information (z symbols).
690
716
last->next = nil;
692
718
for(s = allsym; s != S; s = s->allsym)
693
if(strncmp(s->name, "weak.", 5) == 0) {
719
if(strncmp(s->name, "go.weak.", 8) == 0) {
694
720
s->special = 1; // do not lay out in data segment
695
721
s->reachable = 1;
725
// record field tracking references
727
for(s = allsym; s != S; s = s->allsym) {
728
if(strncmp(s->name, "go.track.", 9) == 0) {
729
s->special = 1; // do not lay out in data segment
732
fmtprint(&fmt, "%s", s->name+9);
733
for(p=s->reachparent; p; p=p->reachparent)
734
fmtprint(&fmt, "\t%s", p->name);
735
fmtprint(&fmt, "\n");
743
s = lookup(tracksym, 0);
746
addstrdata(tracksym, fmtstrflush(&fmt));
705
754
// resolve weak references only if
706
755
// target symbol will be in binary anyway.
707
756
for(s = allsym; s != S; s = s->allsym) {
708
if(strncmp(s->name, "weak.", 5) == 0) {
709
t = rlookup(s->name+5, s->version);
757
if(strncmp(s->name, "go.weak.", 8) == 0) {
758
t = rlookup(s->name+8, s->version);
710
759
if(t && t->type != 0 && t->reachable) {
711
760
s->value = t->value;
712
761
s->type = t->type;
714
764
s->type = SCONST;