1 2 /* linksyms.c - write binary file for linker */ 3 4 /* Copyright (C) 1994 Bruce Evans */ 5 6 #include "syshead.h" 7 #include "const.h" 8 #include "obj.h" 9 #include "type.h" 10 #undef EXTERN 11 #include "globvar.h" 12 13 FORWARD void linkrefs P((struct modstruct *modptr)); 14 PUBLIC bool_t reloc_output = 0; 15 16 /* link all symbols connected to entry symbols */ 17 linksyms(argreloc_output)18PUBLIC void linksyms(argreloc_output) 19 bool_pt argreloc_output; 20 { 21 char needlink; 22 struct entrylist *elptr; 23 struct modstruct *modptr; 24 struct symstruct *symptr; 25 26 #ifdef REL_OUTPUT 27 reloc_output = argreloc_output; 28 if (argreloc_output) 29 { 30 if (modfirst->modnext != NUL_PTR) 31 fatalerror("relocatable output only works for one input file"); 32 for (modptr = modfirst; modptr != NUL_PTR; modptr = modptr->modnext) 33 modptr->loadflag = TRUE; 34 return; 35 } 36 #endif 37 if ((symptr = findsym("_start")) != NUL_PTR || 38 (symptr = findsym("_main")) != NUL_PTR) 39 entrysym(symptr); 40 do 41 { 42 if ((elptr = entryfirst) == NUL_PTR) 43 fatalerror("no start symbol"); 44 for (modptr = modfirst; modptr != NUL_PTR; modptr = modptr->modnext) 45 modptr->loadflag = FALSE; 46 for (; elptr != NUL_PTR; elptr = elptr->elnext) 47 linkrefs(elptr->elsymptr->modptr); 48 if ((symptr = findsym("start")) != NUL_PTR) 49 linkrefs(symptr->modptr); 50 needlink = FALSE; 51 { 52 struct redlist *prlptr = 0; 53 struct redlist *rlptr; 54 55 for (rlptr = redfirst; rlptr != NUL_PTR; 56 rlptr = (prlptr = rlptr)->rlnext) 57 if (rlptr->rlmodptr->loadflag && 58 rlptr->rlmodptr->class > rlptr->rlsymptr->modptr->class) 59 { 60 rlptr->rlsymptr->modptr = rlptr->rlmodptr; 61 rlptr->rlsymptr->value = rlptr->rlvalue; 62 if (rlptr == redfirst) 63 redfirst = rlptr->rlnext; 64 else 65 prlptr->rlnext = rlptr->rlnext; 66 needlink = TRUE; 67 } 68 } 69 } 70 while (needlink); 71 } 72 linkrefs(modptr)73PRIVATE void linkrefs(modptr) 74 struct modstruct *modptr; 75 { 76 register struct symstruct **symparray; 77 register struct symstruct *symptr; 78 79 modptr->loadflag = TRUE; 80 for (symparray = modptr->symparray; 81 (symptr = *symparray) != NUL_PTR; ++symparray) 82 if (symptr->modptr->loadflag == FALSE) 83 linkrefs(symptr->modptr); 84 } 85 86