Path: seismo!harvard!talcott!panda!sources-request From: sources-request@panda.UUCP Newsgroups: mod.sources Subject: Patches to make MC68000 disassembler work on SUN UNIX Message-ID: <1559@panda.UUCP> Date: 27 Mar 86 21:48:57 GMT Sender: jpn@panda.UUCP Lines: 1954 Approved: jpn@panda.UUCP Mod.sources: Volume 4, Issue 39 Submitted by: seismo!mcvax!daimi!pederch (Peder Chr. N|rgaard) Below follow diffs to the original posting of 'unc' to make it run on SUN Unix, a 4.2BSD Unix for the M68000. The diff set it a small subset of the diff set to the version I work at currently, for reasons to be explained below. It is the smallest possible diff set that makes it possible to compile and run the 'unc' without running headlong into troubles. There are several problems with using the 'unc' on a SUN Unix system; I list the two most severe ones. They both have to do with some assumption made by to program, and not holding on SUN Unix. The problems means that the program is great for disassembling most object files, including the standard libraries, but it cannot in general search for object modules in stripped exe- cutables binaries. 1) SUN Unix (and, I believe, all 4.2bsd ports of unix) uses a new kind of libraries, called 'ranlib's, random libraries. These libraries start with an index of entry points-to-module relations. Therefore the libraries do not have to be sorted with 'lorder' - and they are not! This means that the logic of 'firstfile' in libmtch.c, routine lscan, just doesn't work. As you can imagine, it is not reasonable just to remove that logic and accept a search time of O(size-of-mainfile*count-of- modules); the standard C library of SUN Unix holds almost 300 modules, and it would take days to search it in the brute force way of the distributed 'unc'. This is, however, what the cur- rent program does. The solution is to optimize the search. I have more or less implemented a quite efficient solution, which I am willing to distribute when it is completely tested. I don't send it with this set of diffs, as I don't think this problem has very much to do with SUN Unix; it is a general improvement of the program. 2) SUN Unix library modules are very ingeniously build. They include horrible things like - undefined symbols not referred to in module (to provoke a certain load sequence, I believe) - self-modifying code in the data segment (substi- tution of floating point arithmetic depending on hardware configuration, I think) - data constants in text segment and a lot of other stuff. And these things are present in all programs, provoked by the reference from 'printf' to the floating point code. I have 'solved' the last problem; the diffs to 'iset.c' contain the necessary logic. The other problems can only be solved by relaxing the assumption that everything in the text module is code, until explicitly disproved. I have a lot of ideas on better assumptions, but none which are easy to implement as changes to the program. The diffs follows: They are relative to the original posting, and they are made by program 'diff' on the two directories, [ the diffs were originally standard diff, I converted them to context diff format - patch likes context diffs better if minor changes have been made to the files - moderator ] I have used Larry Walls 'patch' program to verify the diffs, and the result is compilable and runnable apart from the problems described above. Oh, one last thing. I have included a modification of the file 'doc' to put it into the on-line manual format. The SUN Unix system doesn't have whatever nroff macro package are used for that file. Yours Truly Peder Chr. N|rgaard pederch@daimi.UUCP --------------------------------------------------------- diff -c1 ../temp2/alloc.c ./alloc.c *** ../temp2/alloc.c Thu Mar 27 09:47:34 1986 --- ./alloc.c Thu Mar 27 09:48:21 1986 *************** *** 161,164 - seg += TEXT - RTEXT; - /* --- 161,162 ----- /* *************** *** 184,186 res->s_value = pos; ! if (seg == TEXT) { t_entry tent; --- 182,184 ----- res->s_value = pos; ! if (seg == N_TEXT) { t_entry tent; *************** *** 191,193 } ! else if (seg == DATA || seg == BSS) { d_entry dent; --- 189,191 ----- } ! else if (seg == N_DATA || seg == N_BSS) { d_entry dent; *************** *** 216,218 tent.t_lab = inventsymb("TS"); ! tent.t_lab->s_type = TEXT; tent.t_lab->s_value = loc; --- 214,216 ----- tent.t_lab = inventsymb("TS"); ! tent.t_lab->s_type = N_TEXT; tent.t_lab->s_value = loc; *************** *** 273,275 ds = inventsymb("BS"); ! ds->s_type = BSS; } --- 271,273 ----- ds = inventsymb("BS"); ! ds->s_type = N_BSS; } *************** *** 277,279 ds = inventsymb("DS"); ! ds->s_type = DATA; } --- 275,277 ----- ds = inventsymb("DS"); ! ds->s_type = N_DATA; } diff -c1 ../temp2/doc ./doc *** ../temp2/doc Thu Mar 27 09:47:34 1986 --- ./doc Thu Mar 27 09:48:28 1986 *************** *** 1,11 ! .\"/*% nroff -cm -rL72 %|epson|spr -f plain.a -h uncdoc -w ! .nr Hb 7 ! .nr Hs 3 ! .ds HF 3 3 3 3 3 3 3 ! .nr Hu 5 ! .nr Hc 1 ! .SA 1 ! .PH "''A Disassembler''" ! .PF "'Issue %I%'- Page \\\\nP -'%G%'" ! .H 1 "Introduction" This document describes the first release of a disassembler for UNIX --- 1,16 ----- ! .\"unc.1, from John Collins ! .TH UNC 1 "1 November 1985" ! .SH NAME ! unc \- a M68000 disassembler ! .SH SYNOPSIS ! .B /usr/local/unc ! [ \fB\-o\fP \fIfilename\fP ] ! [ \fB\-t\fP \fIprefix\fP ] ! [ \fB\-a\fP ] ! [ \fB\-s\fP ] ! [ \fB\-v\fP ] ! mainfile ! [ lib-or-obj \fB\|.\|.\|.\fP ] ! .SH DESCRIPTION ! .LP This document describes the first release of a disassembler for UNIX *************** *** 13,16 The key features are: ! .AL ! .LI For object files the output can be assembled to generate the same --- 18,21 ----- The key features are: ! .RS ! .PP For object files the output can be assembled to generate the same *************** *** 18,20 input. ! .LI For stripped executable files object modules and libraries may be scanned, --- 23,25 ----- input. ! .PP For stripped executable files object modules and libraries may be scanned, *************** *** 22,24 inserted into the output. ! .LI An option is available to convert most non-global names into local symbols, --- 27,29 ----- inserted into the output. ! .PP An option is available to convert most non-global names into local symbols, *************** *** 25,27 which cuts down the symbols in the generated assembler file. ! .LI The disassembler copes reasonably with modules merged with the --- 30,32 ----- which cuts down the symbols in the generated assembler file. ! .PP The disassembler copes reasonably with modules merged with the *************** *** 31,34 generating a warning message as to the number of modules involved. ! .LE ! .P At present this is available for certain Motorola 68000 ports of UNIX --- 36,39 ----- generating a warning message as to the number of modules involved. ! .RE ! .PP At present this is available for certain Motorola 68000 ports of UNIX *************** *** 35,38 System III and System V. Dependencies on ! .AL a ! .LI Instruction set. --- 40,43 ----- System III and System V. Dependencies on ! .TP ! (1) Instruction set. *************** *** 38,40 Instruction set. ! .LI Object module format. --- 43,46 ----- Instruction set. ! .TP ! (2) Object module format. *************** *** 40,42 Object module format. ! .LI Library module format. --- 46,49 ----- Object module format. ! .TP ! (3) Library module format. *************** *** 42,44 Library module format. ! .LI Assembler output format. --- 49,52 ----- Library module format. ! .TP ! (4) Assembler output format. *************** *** 44,47 Assembler output format. ! .LE ! .P are hopefully sufficiently localised to make the product useful as a --- 52,54 ----- Assembler output format. ! .PP are hopefully sufficiently localised to make the product useful as a *************** *** 48,50 basis for other disassemblers for other versions of UNIX. ! .P The product is thus distributed in source form at present. --- 55,57 ----- basis for other disassemblers for other versions of UNIX. ! .PP The product is thus distributed in source form at present. *************** *** 50,57 The product is thus distributed in source form at present. ! .H 1 "Use" ! The disassembler is run by entering: ! .DS I ! unc mainfile lib1 lib2 ... ! .DE ! .P The first named file is the file to be disassembled, which should be --- 57,59 ----- The product is thus distributed in source form at present. ! .SH USE The first named file is the file to be disassembled, which should be *************** *** 60,62 parenthesis notation, thus: ! .DS I unc '/lib/libc.a(printf.o)' --- 62,64 ----- parenthesis notation, thus: ! .RS unc '/lib/libc.a(printf.o)' *************** *** 62,65 unc '/lib/libc.a(printf.o)' ! .DE ! .P It is usually necessary to escape the arguments in this case to prevent --- 64,66 ----- unc '/lib/libc.a(printf.o)' ! .RE It is usually necessary to escape the arguments in this case to prevent *************** *** 72,74 thus ! .DS I unc '-lc(printf.o)' --- 73,76 ----- thus ! .RS ! .nf unc '-lc(printf.o)' *************** *** 75,78 unc '-lcurses(wmove.o)' ! .DE ! .P As an additional facility, the list of directories searched for --- 77,80 ----- unc '-lcurses(wmove.o)' ! .fi ! .RE As an additional facility, the list of directories searched for *************** *** 83,85 variable, and of course defaults to ! .DS I LDPATH=/lib:/usr/lib --- 85,87 ----- variable, and of course defaults to ! .RS LDPATH=/lib:/usr/lib *************** *** 85,88 LDPATH=/lib:/usr/lib ! .DE ! .P As a further facility, the insertion of --- 87,89 ----- LDPATH=/lib:/usr/lib ! .RE As a further facility, the insertion of *************** *** 96,98 then the command ! .DS I unc -Lcrt0.o --- 97,99 ----- then the command ! .RS unc -Lcrt0.o *************** *** 98,101 unc -Lcrt0.o ! .DE ! .P should have the desired effect. --- 99,101 ----- unc -Lcrt0.o ! .RE should have the desired effect. *************** *** 101,103 should have the desired effect. ! .P Second and subsequent file arguments are only referenced for stripped --- 101,103 ----- should have the desired effect. ! .PP Second and subsequent file arguments are only referenced for stripped *************** *** 106,108 files, thus: ! .DS I unc strippedfile -Lcrt0.o -lcurses -ltermcap '-lm(sqrt.o)' -lc --- 106,108 ----- files, thus: ! .RS unc strippedfile -Lcrt0.o -lcurses -ltermcap '-lm(sqrt.o)' -lc *************** *** 108,111 unc strippedfile -Lcrt0.o -lcurses -ltermcap '-lm(sqrt.o)' -lc ! .DE ! .P It is advisable to make some effort to put the libraries to be searched --- 108,110 ----- unc strippedfile -Lcrt0.o -lcurses -ltermcap '-lm(sqrt.o)' -lc ! .RE It is advisable to make some effort to put the libraries to be searched *************** *** 116,118 is confused by object modules which are very nearly similar. ! .H 1 "Additional options" The following options are available to modify the behaviour of the --- 115,117 ----- is confused by object modules which are very nearly similar. ! .SH OPTIONS The following options are available to modify the behaviour of the *************** *** 119,122 disassembler. ! .VL 15 2 ! .LI "-o file" Causes output to be sent to the specified file instead of the standard --- 118,121 ----- disassembler. ! .TP ! .BI \-o " file" Causes output to be sent to the specified file instead of the standard *************** *** 123,125 output. ! .LI "-t prefix" Causes temporary files to be created with the given prefix. The default --- 122,125 ----- output. ! .TP ! .BI \-t " prefix" Causes temporary files to be created with the given prefix. The default *************** *** 134,136 complete map of the text and data segments is generated. ! .LI "-a" Suppresses the generation of non-global absolute symbols from the --- 134,137 ----- complete map of the text and data segments is generated. ! .TP ! .B \-a Suppresses the generation of non-global absolute symbols from the *************** *** 139,141 producing as nearly identical output as possible to the original source. ! .LI "-s" Causes an additional scan to take place where all possible labels are --- 140,143 ----- producing as nearly identical output as possible to the original source. ! .TP ! .B \-s Causes an additional scan to take place where all possible labels are *************** *** 143,145 ascending order, starting at 1. ! .LI "-v" Causes a blow-by-blow account of activities to be output on the standard --- 145,148 ----- ascending order, starting at 1. ! .TP ! .B \-v Causes a blow-by-blow account of activities to be output on the standard *************** *** 146,149 error. ! .LE ! .H 1 "Diagnostics etc" Truncated or garbled object and library files usually cause processing --- 149,151 ----- error. ! .SH DIAGNOSTICS Truncated or garbled object and library files usually cause processing *************** *** 150,152 to stop with an explanatory message. ! .P The only other kinds of message are some passing warnings concerning --- 152,154 ----- to stop with an explanatory message. ! .PP The only other kinds of message are some passing warnings concerning *************** *** 154,156 or the relocation of overlapping fields. Occasionally a message ! .DS I Library clash: message --- 156,158 ----- or the relocation of overlapping fields. Occasionally a message ! .RS Library clash: message *************** *** 156,159 Library clash: message ! .DE ! .P may appear and processing cease. This message is found where at a late --- 158,160 ----- Library clash: message ! .RE may appear and processing cease. This message is found where at a late *************** *** 163,165 to the program which members to take in which order. ! .H 1 "Future development" In the future it is hoped to devise ways of making the disassembler --- 164,166 ----- to the program which members to take in which order. ! .SH FUTURE DEVELOPMENT In the future it is hoped to devise ways of making the disassembler *************** *** 168,170 after the Common Object Format becomes more standard. ! .P In the long term it would be desirable and useful to enhance the product --- 169,171 ----- after the Common Object Format becomes more standard. ! .PP In the long term it would be desirable and useful to enhance the product *************** *** 172,175 the process are seen as follows: ! .AL ! .LI Better identification of basic blocks in the code. Switch statements are --- 173,176 ----- the process are seen as follows: ! .TP ! (1) Better identification of basic blocks in the code. Switch statements are *************** *** 176,178 a major problem here, as are constant data held in the text segment. ! .LI Marrying of data to the corresponding text. It is in various places hard --- 177,180 ----- a major problem here, as are constant data held in the text segment. ! .TP ! (2) Marrying of data to the corresponding text. It is in various places hard *************** *** 181,183 is part of the problem of identifying basic blocks. ! .LI Compilation of header files to work out structure references within the --- 183,186 ----- is part of the problem of identifying basic blocks. ! .TP ! (3) Compilation of header files to work out structure references within the *************** *** 184,187 text. At this stage some interaction may be needed. ! .LE ! .P Meanwhile the product is one which is a useful tool to the author in its --- 187,189 ----- text. At this stage some interaction may be needed. ! .PP Meanwhile the product is one which is a useful tool to the author in its diff -c1 ../temp2/heur.c ./heur.c *** ../temp2/heur.c Thu Mar 27 09:47:35 1986 --- ./heur.c Thu Mar 27 09:48:39 1986 *************** *** 278,280 ds = inventsymb("BS"); ! ds->s_type = BSS; } --- 278,280 ----- ds = inventsymb("BS"); ! ds->s_type = N_BSS; } *************** *** 282,284 ds = inventsymb("DS"); ! ds->s_type = DATA; } --- 282,284 ----- ds = inventsymb("DS"); ! ds->s_type = N_DATA; } *************** *** 388,390 ! for (pos = 0; pos < endt;) { gette(&mainfile, pos, &tent); --- 388,390 ----- ! for (pos = mainfile.ef_tbase; pos < endt;) { gette(&mainfile, pos, &tent); diff -c1 ../temp2/iset.c ./iset.c *** ../temp2/iset.c Thu Mar 27 09:47:35 1986 --- ./iset.c Thu Mar 27 09:48:46 1986 *************** *** 240,241 } if ((tc & 0xff00) == 0x6000) --- 240,245 ----- } + if ( dest < mainfile.ef_tbase + || dest >= mainfile.ef_tbase+mainfile.ef_tsize + || (dest & 1) != 0 ) + return 0; /* Illegal branch destination */ if ((tc & 0xff00) == 0x6000) *************** *** 247,249 ! te->t_relsymb = textlab(dest, pos); return res; --- 251,256 ----- ! if ( (te->t_relsymb = textlab(dest, pos)) == NULL ) { ! te->t_bchtyp = T_NOBR;/* Branch to a continuation */ ! return 0; ! } return res; *************** *** 257,258 t_entry nextl; --- 264,266 ----- t_entry nextl; + long dest; *************** *** 262,264 if (nextl.t_relsymb == NULL) { ! nextl.t_relsymb = textlab(gettw(&mainfile, pos+2, R_LONG), pos); putte(&mainfile, pos+2, &nextl); --- 270,278 ----- if (nextl.t_relsymb == NULL) { ! dest = gettw(&mainfile, pos + 2, R_LONG ); ! if ( dest < mainfile.ef_tbase ! || dest >= mainfile.ef_tbase+mainfile.ef_tsize ! || (dest & 1) != 0 ) ! return 0; /* Illegal branch destination */ ! if ( ( nextl.t_relsymb = textlab(dest, pos) ) == NULL ) ! return 0; /* Branch to a continuation */ putte(&mainfile, pos+2, &nextl); *************** *** 995,997 te->t_type = T_UNKNOWN; ! te->t_bchtype = T_NOBR; } --- 1009,1011 ----- te->t_type = T_UNKNOWN; ! te->t_bchtyp = T_NOBR; } diff -c1 ../temp2/libmtch.c ./libmtch.c *** ../temp2/libmtch.c Thu Mar 27 09:47:36 1986 --- ./libmtch.c Thu Mar 27 09:48:54 1986 *************** *** 27,28 #include #include --- 27,29 ----- #include + #include #include *************** *** 32,33 long lseek(); --- 33,35 ----- + long atol(); long lseek(); *************** *** 35,38 void rrell2(), markmatch(); ! char *strchr(), *strrchr(), *strncpy(), *strcat(), *strcpy(), *malloc(); ! int matchup(); long findstart(); --- 37,39 ----- void rrell2(), markmatch(); ! char *malloc(); long findstart(); *************** *** 77,79 lfd->lf_offset = lfd->lf_next + sizeof(arbuf); ! lfd->lf_next = (lfd->lf_offset + arbuf.ar_size + 1) & ~1; return lfd->lf_offset; --- 78,80 ----- lfd->lf_offset = lfd->lf_next + sizeof(arbuf); ! lfd->lf_next = (lfd->lf_offset + atol(arbuf.ar_size) + 1) & ~1; return lfd->lf_offset; *************** *** 105,107 extern char *getenv(); ! long magic; struct ar_hdr arhdr; --- 106,108 ----- extern char *getenv(); ! char magic[8]; struct ar_hdr arhdr; *************** *** 109,112 ! if ((bp = strrchr(str, '(')) != NULL && ! (ep = strrchr(str, ')')) != NULL) *ep = *bp = '\0'; --- 110,113 ----- ! if ((bp = rindex(str, '(')) != NULL && ! (ep = rindex(str, ')')) != NULL) *ep = *bp = '\0'; *************** *** 123,125 do { ! pathe = strchr(pathb, ':'); if (*pathb == ':') --- 124,126 ----- do { ! pathe = index(pathb, ':'); if (*pathb == ':') *************** *** 155,158 ! if ((read(fd, (char *) &magic, sizeof(magic)) != sizeof(magic) || ! magic != ARMAG)) { if (ep != NULL) { --- 156,159 ----- ! if (read(fd, magic, sizeof(magic)) != sizeof(magic) || ! strcmp(magic, ARMAG) != 0) { if (ep != NULL) { *************** *** 177,178 if (ep != NULL) { currlib.lf_offset = sizeof(magic) + sizeof(struct ar_hdr); --- 178,181 ----- if (ep != NULL) { + char *cp; + currlib.lf_offset = sizeof(magic) + sizeof(struct ar_hdr); *************** *** 184,186 } ! if (strncmp(bp+1, arhdr.ar_name, sizeof(arhdr.ar_name)) == 0) break; --- 187,192 ----- } ! for ( cp = arhdr.ar_name + sizeof(arhdr.ar_name) - 1; ! *cp == ' '; ! cp -- ) ; ! if (strncmp(bp+1, arhdr.ar_name, cp - arhdr.ar_name + 1) == 0) break; *************** *** 186,188 break; ! currlib.lf_offset += arhdr.ar_size + sizeof(arhdr) + 1; currlib.lf_offset &= ~ 1; --- 192,194 ----- break; ! currlib.lf_offset += atol(arhdr.ar_size) + sizeof(arhdr) + 1; currlib.lf_offset &= ~ 1; *************** *** 211,213 currlib.lf_offset = sizeof(magic) + sizeof(arhdr); ! currlib.lf_next = currlib.lf_offset + arhdr.ar_size + 1; currlib.lf_next &= ~1; --- 217,219 ----- currlib.lf_offset = sizeof(magic) + sizeof(arhdr); ! currlib.lf_next = currlib.lf_offset + atol(arhdr.ar_size) + 1; currlib.lf_next &= ~1; diff -c1 ../temp2/main.c ./main.c *** ../temp2/main.c Thu Mar 27 09:47:36 1986 --- ./main.c Thu Mar 27 09:48:58 1986 *************** *** 26,28 #include ! #include #include --- 26,28 ----- #include ! #include #include *************** *** 28,30 #include - #include #include "unc.h" --- 28,29 ----- #include #include "unc.h" *************** *** 38,40 - int par_entry, par_round; /* 68000 parameters */ int nmods; /* Number of modules it looks like */ --- 37,38 ----- int nmods; /* Number of modules it looks like */ *************** *** 107,109 register char *arg; - struct var vs; --- 105,106 ----- register char *arg; *************** *** 109,114 - uvar(&vs); - par_entry = vs.v_ustart; - par_round = vs.v_txtrnd - 1; - for (;;) { --- 106,107 ----- for (;;) { *************** *** 143,146 ! case 'R': ! case 'N': if (*arg == '\0') { --- 136,138 ----- ! case 't': if (*arg == '\0') { *************** *** 148,150 arg = *++av; ! if (arg == NULL) { bo: (void) fprintf(stderr,"Bad -%c option\n",lt); --- 140,142 ----- arg = *++av; ! if (arg == NULL) { bo: (void) fprintf(stderr,"Bad -%c option\n",lt); *************** *** 151,166 exit(1); ! } ! } ! if (lt == 'R') ! par_entry = ghex(arg); ! else ! par_round = ghex(arg) - 1; ! continue; ! ! case 't': ! if (*arg == '\0') { ! cnt++; ! arg = *++av; ! if (arg == NULL) ! goto bo; } --- 143,145 ----- exit(1); ! } } diff -c1 ../temp2/makefile ./makefile *** ../temp2/makefile Thu Mar 27 09:47:36 1986 --- ./makefile Thu Mar 27 09:49:02 1986 *************** *** 1,2 ! CFLAGS=-v -OB OBJS=alloc.o file.o libmtch.o robj.o iset.o prin.o heur.o main.o --- 1,2 ----- ! CFLAGS=-O OBJS=alloc.o file.o libmtch.o robj.o iset.o prin.o heur.o main.o diff -c1 ../temp2/prin.c ./prin.c *** ../temp2/prin.c Thu Mar 27 09:47:36 1986 --- ./prin.c Thu Mar 27 09:49:08 1986 *************** *** 104,106 gette(fid, tpos, &tstr); ! plabs(tstr.t_lab, TEXT); if (tstr.t_type == T_BEGIN) --- 104,106 ----- gette(fid, tpos, &tstr); ! plabs(tstr.t_lab, N_TEXT); if (tstr.t_type == T_BEGIN) *************** *** 109,112 (void) printf("\t.long\t%s", tstr.t_relsymb->s_name); ! if (tstr.t_relsymb->s_type!=TEXT && ! tstr.t_relsymb->s_type!=DATA) (void) printf("+0x%x", gettw(fid, tpos, R_LONG)); --- 109,112 ----- (void) printf("\t.long\t%s", tstr.t_relsymb->s_name); ! if (tstr.t_relsymb->s_type!=N_TEXT && ! tstr.t_relsymb->s_type!=N_DATA) (void) printf("+0x%x", gettw(fid, tpos, R_LONG)); *************** *** 125,127 gette(fid, tpos, &tstr); ! plabs(tstr.t_lab, TEXT); } --- 125,127 ----- gette(fid, tpos, &tstr); ! plabs(tstr.t_lab, N_TEXT); } *************** *** 150,152 getde(fid, dpos, &dstr); ! plabs(dstr.d_lab, DATA); --- 150,152 ----- getde(fid, dpos, &dstr); ! plabs(dstr.d_lab, N_DATA); *************** *** 270,272 getde(fid, dpos, &dstr); ! plabs(dstr.d_lab, DATA); } --- 270,272 ----- getde(fid, dpos, &dstr); ! plabs(dstr.d_lab, N_DATA); } *************** *** 284,286 getde(fid, bpos, &bstr); ! plabs(bstr.d_lab, BSS); (void) printf("\t.space\t%d\n", bstr.d_lng); --- 284,286 ----- getde(fid, bpos, &bstr); ! plabs(bstr.d_lab, N_BSS); (void) printf("\t.space\t%d\n", bstr.d_lng); *************** *** 290,292 getde(fid, endb, &bstr); ! plabs(bstr.d_lab, BSS); ! } --- 290,293 ----- getde(fid, endb, &bstr); ! plabs(bstr.d_lab, N_BSS); ! } ! diff -c1 ../temp2/robj.c ./robj.c *** ../temp2/robj.c Thu Mar 27 09:47:36 1986 --- ./robj.c Thu Mar 27 09:49:16 1986 *************** *** 47,48 #define DBSIZE 100 --- 47,50 ----- + #define RWORD 1 + #define RLONG 2 #define DBSIZE 100 *************** *** 60,62 t_entry tstr; ! struct bhdr filhdr; register long size; --- 62,64 ----- t_entry tstr; ! struct exec filhdr; register long size; *************** *** 96,98 ! if (filhdr.fmagic != FMAGIC && filhdr.fmagic != NMAGIC) return 0; --- 98,100 ----- ! if ( N_BADMAG( filhdr ) ) return 0; *************** *** 99,102 ! /* ! * Warn user if entry point does not tie up. */ --- 101,109 ----- ! /* I am not at all sure that this setup is correct ! * but my SUN UNIX manual (version 1.2) is VERY unclear ! * about the interpretation of the bases of relocatable ! * files. This, however seems to work for executable ! * binaries (ZMAGIC) and relocatable .o files (OMAGIC). ! * I have not found any NMAGIC files on my system, so ! * it is not likely to work for such ones. */ *************** *** 102,106 */ ! ! if (filhdr.entry != par_entry) ! (void) fprintf(stderr, "Warning: File has -R%X\n", filhdr.entry); --- 109,119 ----- */ ! outf->ef_entry = filhdr.a_entry; ! outf->ef_tbase = ! (filhdr.a_magic==OMAGIC) ? 0 : SEGSIZ; ! outf->ef_dbase = ! (filhdr.a_magic==OMAGIC) ! ? filhdr.a_text ! : (SEGSIZ+((SEGSIZ+filhdr.a_text-1) & ~(SEGSIZ-1))); ! outf->ef_bbase = outf->ef_dbase + filhdr.a_data; ! outf->ef_end = outf->ef_bbase + filhdr.a_bss; *************** *** 106,120 ! outf->ef_entry = filhdr.entry; ! outf->ef_tbase = filhdr.entry; ! outf->ef_dbase = filhdr.tsize + filhdr.entry; ! ! if (filhdr.fmagic == NMAGIC) ! outf->ef_dbase = (outf->ef_dbase + par_round) & (~par_round); ! ! outf->ef_bbase = outf->ef_dbase + filhdr.dsize; ! outf->ef_end = outf->ef_bbase + filhdr.bsize; ! ! outf->ef_tsize = filhdr.tsize; ! outf->ef_dsize = filhdr.dsize; ! outf->ef_bsize = filhdr.bsize; --- 119,123 ----- ! outf->ef_tsize = filhdr.a_text; ! outf->ef_dsize = filhdr.a_data; ! outf->ef_bsize = filhdr.a_bss; *************** *** 120,122 ! (void) lseek(inf, offset + TEXTPOS, 0); --- 123,125 ----- ! (void) lseek(inf, offset + N_TXTOFF(filhdr), 0); *************** *** 154,156 d_entry dstr; ! struct bhdr filhdr; register long size; --- 157,159 ----- d_entry dstr; ! struct exec filhdr; register long size; *************** *** 179,181 ! (void) lseek(inf, offset + DATAPOS, 0); --- 182,184 ----- ! (void) lseek(inf, offset + N_TXTOFF(filhdr) + filhdr.a_text, 0); *************** *** 220,221 { register symbol csym; --- 223,225 ----- { + #define SYMLENGTH 256 register symbol csym; *************** *** 221,224 register symbol csym; ! struct bhdr filhdr; ! struct sym isym; register long size; --- 225,228 ----- register symbol csym; ! struct exec filhdr; ! struct nlist isym; register long size; *************** *** 224,227 register long size; ! register int i, l; ! char inbuf[SYMLENGTH+1]; --- 228,232 ----- register long size; ! unsigned long stroff; ! register int l; ! char inbuf[SYMLENGTH+1], *cp; *************** *** 236,239 ! offset += SYMPOS; ! size = filhdr.ssize; if (size <= 0) --- 241,245 ----- ! offset += N_SYMOFF(filhdr); ! stroff = offset + filhdr.a_syms; ! size = filhdr.a_syms; if (size <= 0) *************** *** 245,247 ! l = size / (sizeof(struct sym) + 4); if (l <= 0) --- 251,253 ----- ! l = size / (sizeof(struct nlist) + 4); if (l <= 0) *************** *** 256,258 ! while (size > sizeof(struct sym)) { (void) lseek(inf, offset, 0); --- 262,264 ----- ! while (size > 0) { (void) lseek(inf, offset, 0); *************** *** 261,274 size -= sizeof(isym); ! l = SYMLENGTH; ! if (l > size) ! l = size; ! if (read(inf, inbuf, l) != l) ! return 0; ! inbuf[l] = '\0'; ! for (i = 0; inbuf[i] != '\0'; i++) ! ; ! size -= i + 1; ! offset += sizeof(isym) + i + 1; ! csym = (*dproc)(lookup(inbuf), isym.stype, isym.svalue, outf); ! if (outf->ef_stcnt >= outf->ef_stmax) reallst(outf); --- 267,281 ----- size -= sizeof(isym); ! offset += sizeof(isym); ! if ( (isym.n_type & N_STAB) != 0x00 ) ! continue;/* Stab entry, not interesting for now */ ! (void) lseek(inf, stroff + isym.n_un.n_strx, 0 ); ! cp = inbuf; ! do { ! if ( read( inf, cp, 1 ) != 1 )/* Read symbol chars 1-by-1 */ ! return 0; ! if ( cp - inbuf >= SYMLENGTH )/* Check against buffer overflow */ ! return 0; ! } while (*cp++ != '\0');/* Terminate on null byte */ ! csym = (*dproc)(lookup(inbuf), isym.n_type, isym.n_value, outf); ! if (outf->ef_stcnt >= outf->ef_stmax) reallst(outf); *************** *** 288,291 { ! struct bhdr filhdr; ! struct reloc crel; t_entry tstr; --- 295,298 ----- { ! struct exec filhdr; ! struct relocation_info crel; t_entry tstr; *************** *** 303,305 return -1; ! if (filhdr.rtsize <= 0 && filhdr.rdsize <= 0) return 0; --- 310,312 ----- return -1; ! if (filhdr.a_trsize <= 0 && filhdr.a_drsize <= 0) return 0; *************** *** 306,308 ! size = filhdr.rtsize; --- 313,315 ----- ! size = filhdr.a_trsize; *************** *** 308,311 ! (void) lseek(inf, RTEXTPOS + offset, 0); ! while (size >= sizeof(struct reloc)) { if (read(inf, (char *)&crel, sizeof(crel)) != sizeof(crel)) --- 315,318 ----- ! (void) lseek(inf, N_TXTOFF(filhdr) + filhdr.a_text + filhdr.a_data + offset, 0); ! while (size >= sizeof(struct relocation_info)) { if (read(inf, (char *)&crel, sizeof(crel)) != sizeof(crel)) *************** *** 313,315 ! pos = crel.rpos + outf->ef_tbase; gette(outf, pos, &tstr); --- 320,322 ----- ! pos = crel.r_address + outf->ef_tbase; gette(outf, pos, &tstr); *************** *** 315,321 gette(outf, pos, &tstr); ! tstr.t_reloc = crel.rsize + 1; /* Fiddle! YUK!!! */ ! tstr.t_rdisp = crel.rdisp; ! tstr.t_rptr = crel.rsegment; ! if (crel.rsegment == REXT) { ! if (crel.rsymbol >= outf->ef_stcnt) return -1; --- 322,326 ----- gette(outf, pos, &tstr); ! tstr.t_reloc = crel.r_length + 1; /* Fiddle! YUK!!! */ ! if (crel.r_extern) { ! if (crel.r_symbolnum >= outf->ef_stcnt) return -1; *************** *** 321,324 return -1; ! tstr.t_relsymb = outf->ef_stvec[crel.rsymbol]; ! tstr.t_reldisp = gettw(outf, pos, (int)crel.rsize+1); } --- 326,329 ----- return -1; ! tstr.t_relsymb = outf->ef_stvec[crel.r_symbolnum]; ! tstr.t_reldisp = gettw(outf, pos, (int)crel.r_length+1); } *************** *** 325,328 else { ! cont = gettw(outf, pos, (int)crel.rsize+1); ! tstr.t_relsymb = getnsymb(outf, crel.rsegment, cont); } --- 330,333 ----- else { ! cont = gettw(outf, pos, (int)crel.r_length+1); ! tstr.t_relsymb = getnsymb(outf, crel.r_symbolnum, cont); } *************** *** 337,339 ! size = filhdr.rdsize; --- 342,344 ----- ! size = filhdr.a_drsize; *************** *** 339,342 ! (void) lseek(inf, RDATAPOS + offset, 0); ! while (size >= sizeof(struct reloc)) { if (read(inf, (char *)&crel, sizeof(crel)) != sizeof(crel)) --- 344,349 ----- ! (void) lseek(inf, ! N_TXTOFF(filhdr) + filhdr.a_text + filhdr.a_data ! + filhdr.a_trsize + offset, 0); ! while (size >= sizeof(struct relocation_info)) { if (read(inf, (char *)&crel, sizeof(crel)) != sizeof(crel)) *************** *** 344,346 ! pos = crel.rpos + outf->ef_dbase; getde(outf, pos, &dstr); --- 351,353 ----- ! pos = crel.r_address + outf->ef_dbase; getde(outf, pos, &dstr); *************** *** 346,349 getde(outf, pos, &dstr); ! dstr.d_reloc = crel.rsize + 1; /* Fiddle! YUK!!! */ ! dstr.d_rptr = crel.rsegment; --- 353,355 ----- getde(outf, pos, &dstr); ! dstr.d_reloc = crel.r_length + 1; /* Fiddle! YUK!!! */ *************** *** 349,352 ! if (crel.rsegment == REXT) { ! if (crel.rsymbol >= outf->ef_stcnt) return -1; --- 355,358 ----- ! if (crel.r_extern) { ! if (crel.r_symbolnum >= outf->ef_stcnt) return -1; *************** *** 352,355 return -1; ! dstr.d_relsymb = outf->ef_stvec[crel.rsymbol]; ! dstr.d_reldisp = getdw(outf, pos, (int)crel.rsize+1); } --- 358,361 ----- return -1; ! dstr.d_relsymb = outf->ef_stvec[crel.r_symbolnum]; ! dstr.d_reldisp = getdw(outf, pos, (int)crel.r_length+1); } *************** *** 356,360 else { ! cont = getdw(outf, pos, (int)crel.rsize+1); ! dstr.d_relsymb = getnsymb(outf, crel.rsegment, cont); ! if (dstr.d_relsymb->s_type == TEXT) { gette(outf, cont, &tstr); --- 362,366 ----- else { ! cont = getdw(outf, pos, (int)crel.r_length+1); ! dstr.d_relsymb = getnsymb(outf, crel.r_symbolnum, cont); ! if (dstr.d_relsymb->s_type == N_TEXT) { gette(outf, cont, &tstr); *************** *** 364,366 } ! switch (crel.rsize) { default: --- 370,372 ----- } ! switch (crel.r_length) { default: *************** *** 403,405 if (!sy->s_newsym) { ! if (type & EXTERN) { (void) fprintf(stderr, "Duplicate symbol %s\n", sy->s_name); --- 409,411 ----- if (!sy->s_newsym) { ! if (type & N_EXT) { (void) fprintf(stderr, "Duplicate symbol %s\n", sy->s_name); *************** *** 418,420 ! case EXTERN|UNDEF: if (val != 0) { --- 424,426 ----- ! case N_EXT|N_UNDF: if (val != 0) { *************** *** 420,422 if (val != 0) { ! sy->s_type = COMM; addit(&comtab, sy); --- 426,428 ----- if (val != 0) { ! sy->s_type = N_COMM; addit(&comtab, sy); *************** *** 428,430 ! case EXTERN|ABS: sy->s_type = N_ABS; --- 434,436 ----- ! case N_EXT|N_ABS: sy->s_type = N_ABS; *************** *** 434,436 ! case ABS: sy->s_type = N_ABS; --- 440,442 ----- ! case N_ABS: sy->s_type = N_ABS; *************** *** 439,442 ! case EXTERN|TEXT: ! case TEXT: sy->s_type = N_TEXT; --- 445,448 ----- ! case N_EXT|N_TEXT: ! case N_TEXT: sy->s_type = N_TEXT; *************** *** 444,446 tstr.t_bdest = 1; ! if (type & EXTERN) { tstr.t_gbdest = 1; --- 450,452 ----- tstr.t_bdest = 1; ! if (type & N_EXT) { tstr.t_gbdest = 1; *************** *** 453,456 ! case BSS: ! case EXTERN|BSS: sy->s_type = N_BSS; --- 459,462 ----- ! case N_BSS: ! case N_EXT|N_BSS: sy->s_type = N_BSS; *************** *** 457,460 goto datrest; ! case DATA: ! case EXTERN|DATA: sy->s_type = N_DATA; --- 463,466 ----- goto datrest; ! case N_DATA: ! case N_EXT|N_DATA: sy->s_type = N_DATA; *************** *** 462,464 getde(fid, val, &dstr); ! if (type & EXTERN) sy->s_glob = 1; --- 468,470 ----- getde(fid, val, &dstr); ! if (type & N_EXT) sy->s_glob = 1; *************** *** 474,475 /* --- 480,482 ----- + /* *************** *** 487,490 { ! struct bhdr filhdr; ! struct reloc crel; t_entry tstr; --- 494,497 ----- { ! struct exec filhdr; ! struct relocation_info crel; t_entry tstr; *************** *** 501,503 return -1; ! if (filhdr.rtsize <= 0 && filhdr.rdsize <= 0) return 0; --- 508,510 ----- return -1; ! if (filhdr.a_trsize <= 0 && filhdr.a_drsize <= 0) return 0; *************** *** 504,506 ! size = filhdr.rtsize; --- 511,513 ----- ! size = filhdr.a_trsize; *************** *** 506,509 ! (void) lseek(inf, RTEXTPOS + offset, 0); ! while (size >= sizeof(struct reloc)) { if (read(inf, (char *)&crel, sizeof(crel)) != sizeof(crel)) --- 513,516 ----- ! (void) lseek(inf, N_TXTOFF(filhdr) + filhdr.a_text + filhdr.a_data + offset, 0); ! while (size >= sizeof(struct relocation_info)) { if (read(inf, (char *)&crel, sizeof(crel)) != sizeof(crel)) *************** *** 511,513 ! pos = crel.rpos + outf->ef_tbase; gette(outf, pos, &tstr); --- 518,520 ----- ! pos = crel.r_address + outf->ef_tbase; gette(outf, pos, &tstr); *************** *** 513,517 gette(outf, pos, &tstr); ! tstr.t_reloc = crel.rsize + 1; /* Fiddle! YUK!!! */ ! tstr.t_rdisp = crel.rdisp; ! tstr.t_rptr = crel.rsegment; tstr.t_isrel = 1; --- 520,522 ----- gette(outf, pos, &tstr); ! tstr.t_reloc = crel.r_length + 1; /* Fiddle! YUK!!! */ tstr.t_isrel = 1; *************** *** 518,520 putte(outf, pos, &tstr); ! if (crel.rsize == RLONG) { gette(outf, pos+2, &tstr); --- 523,525 ----- putte(outf, pos, &tstr); ! if (crel.r_length == RLONG) { gette(outf, pos+2, &tstr); *************** *** 553,555 ! case EXTERN|UNDEF: if (!sy->s_newsym) --- 558,560 ----- ! case N_EXT|N_UNDF: if (!sy->s_newsym) *************** *** 558,560 if (val != 0) { ! sy->s_type = COMM; addit(&dreltab, sy); --- 563,565 ----- if (val != 0) { ! sy->s_type = N_COMM; addit(&dreltab, sy); *************** *** 566,568 ! case EXTERN|ABS: if (!sy->s_newsym) { --- 571,573 ----- ! case N_EXT|N_ABS: if (!sy->s_newsym) { *************** *** 577,579 ! case EXTERN|TEXT: sy->s_type = N_TEXT; --- 582,584 ----- ! case N_EXT|N_TEXT: sy->s_type = N_TEXT; *************** *** 595,597 ! case EXTERN|BSS: if (!sy->s_newsym) --- 600,602 ----- ! case N_EXT|N_BSS: if (!sy->s_newsym) *************** *** 602,604 ! case EXTERN|DATA: if (!sy->s_newsym) --- 607,609 ----- ! case N_EXT|N_DATA: if (!sy->s_newsym) *************** *** 688,691 { ! struct bhdr filhdr; ! struct reloc crel; t_entry mtstr; --- 693,696 ----- { ! struct exec filhdr; ! struct relocation_info crel; t_entry mtstr; *************** *** 705,707 return; ! if (filhdr.rtsize <= 0 && filhdr.rdsize <= 0) return; --- 710,712 ----- return; ! if (filhdr.a_trsize <= 0 && filhdr.a_drsize <= 0) return; *************** *** 708,710 ! size = filhdr.rtsize; --- 713,715 ----- ! size = filhdr.a_trsize; *************** *** 710,713 ! (void) lseek(inf, RTEXTPOS + offset, 0); ! for (; size >= sizeof(struct reloc); size -= sizeof(crel)) { if (read(inf, (char *)&crel, sizeof(crel)) != sizeof(crel)) --- 715,718 ----- ! (void) lseek(inf, N_TXTOFF(filhdr) + filhdr.a_text + filhdr.a_data + offset, 0); ! for (; size >= sizeof(struct relocation_info); size -= sizeof(crel)) { if (read(inf, (char *)&crel, sizeof(crel)) != sizeof(crel)) *************** *** 715,718 ! pos = crel.rpos + outf->ef_tbase; ! mpos = crel.rpos + trelpos; gette(&mainfile, mpos, &mtstr); --- 720,723 ----- ! pos = crel.r_address + outf->ef_tbase; ! mpos = crel.r_address + trelpos; gette(&mainfile, mpos, &mtstr); *************** *** 718,721 gette(&mainfile, mpos, &mtstr); ! lval = gettw(outf, pos, (int)crel.rsize+1); ! mval = gettw(&mainfile, mpos, (int)crel.rsize+1); --- 723,726 ----- gette(&mainfile, mpos, &mtstr); ! lval = gettw(outf, pos, (int)crel.r_length+1); ! mval = gettw(&mainfile, mpos, (int)crel.r_length+1); *************** *** 721,724 ! switch (crel.rsegment) { ! case RTEXT: if (lval + trelpos - outf->ef_tbase != mval) --- 726,730 ----- ! if ( !crel.r_extern ) { ! switch (crel.r_symbolnum) { ! case N_TEXT: if (lval + trelpos - outf->ef_tbase != mval) *************** *** 726,728 continue; ! case RDATA: if (donedrel) { --- 732,734 ----- continue; ! case N_DATA: if (donedrel) { *************** *** 736,738 continue; ! case RBSS: if (donebrel) { --- 742,744 ----- continue; ! case N_BSS: if (donebrel) { *************** *** 746,749 continue; ! case REXT: ! if (crel.rsymbol >= outf->ef_stcnt) lclash("Bad sy no"); --- 752,756 ----- continue; ! } ! } else { ! if (crel.r_symbolnum >= outf->ef_stcnt) lclash("Bad sy no"); *************** *** 749,751 lclash("Bad sy no"); ! csymb = outf->ef_stvec[crel.rsymbol]; if (csymb == NULL) --- 756,758 ----- lclash("Bad sy no"); ! csymb = outf->ef_stvec[crel.r_symbolnum]; if (csymb == NULL) *************** *** 772,774 break; ! case COMM: reassign(csymb, mval - lval); --- 779,781 ----- break; ! case N_COMM: reassign(csymb, mval - lval); *************** *** 778,780 mtstr.t_reldisp = lval; - break; } --- 785,786 ----- mtstr.t_reldisp = lval; } *************** *** 801,803 ! size = filhdr.rdsize; --- 807,809 ----- ! size = filhdr.a_drsize; *************** *** 803,806 ! (void) lseek(inf, RDATAPOS + offset, 0); ! for (; size >= sizeof(struct reloc); size -= sizeof(crel)) { if (read(inf, (char *)&crel, sizeof(crel)) != sizeof(crel)) --- 809,813 ----- ! (void) lseek(inf, N_TXTOFF(filhdr) + filhdr.a_text + filhdr.a_data ! + filhdr.a_trsize + offset, 0); ! for (; size >= sizeof(struct relocation_info); size -= sizeof(crel)) { if (read(inf, (char *)&crel, sizeof(crel)) != sizeof(crel)) *************** *** 808,810 ! if (crel.rsize != RLONG) continue; --- 815,817 ----- ! if (crel.r_length != RLONG) continue; *************** *** 811,814 ! pos = crel.rpos + outf->ef_dbase; ! mpos = crel.rpos + drelpos; getde(&mainfile, mpos, &mdstr); --- 818,821 ----- ! pos = crel.r_address + outf->ef_dbase; ! mpos = crel.r_address + drelpos; getde(&mainfile, mpos, &mdstr); *************** *** 814,819 getde(&mainfile, mpos, &mdstr); ! lval = getdw(outf, pos, (int)crel.rsize+1); ! mval = getdw(&mainfile, mpos, (int)crel.rsize+1); ! switch (crel.rsegment) { ! case RTEXT: if (lval + trelpos - outf->ef_tbase != mval) --- 821,827 ----- getde(&mainfile, mpos, &mdstr); ! lval = getdw(outf, pos, (int)crel.r_length+1); ! mval = getdw(&mainfile, mpos, (int)crel.r_length+1); ! if ( !crel.r_extern ) { ! switch (crel.r_symbolnum) { ! case N_TEXT: if (lval + trelpos - outf->ef_tbase != mval) *************** *** 821,823 continue; ! case RDATA: if (lval + drelpos - outf->ef_dbase != mval) --- 829,831 ----- continue; ! case N_DATA: if (lval + drelpos - outf->ef_dbase != mval) *************** *** 825,827 continue; ! case RBSS: if (donebrel) { --- 833,835 ----- continue; ! case N_BSS: if (donebrel) { *************** *** 835,838 continue; ! case REXT: ! if (crel.rsymbol >= outf->ef_stcnt) lclash("Bad sy no"); --- 843,847 ----- continue; ! } ! } else { ! if (crel.r_symbolnum >= outf->ef_stcnt) lclash("Bad sy no"); *************** *** 838,840 lclash("Bad sy no"); ! csymb = outf->ef_stvec[crel.rsymbol]; if (csymb == NULL) --- 847,849 ----- lclash("Bad sy no"); ! csymb = outf->ef_stvec[crel.r_symbolnum]; if (csymb == NULL) *************** *** 861,863 break; ! case COMM: reassign(csymb, mval - lval); --- 870,872 ----- break; ! case N_COMM: reassign(csymb, mval - lval); *************** *** 867,869 mtstr.t_reldisp = lval; - break; } --- 876,877 ----- mtstr.t_reldisp = lval; } diff -c1 ../temp2/unc.h ./unc.h *** ../temp2/unc.h Thu Mar 27 09:47:36 1986 --- ./unc.h Thu Mar 27 09:49:19 1986 *************** *** 35,37 struct symstr *s_link; /* Next in duplicate labels */ ! unsigned s_type : 3; /* Symbol type */ unsigned s_newsym: 1; /* A new symbol */ --- 35,37 ----- struct symstr *s_link; /* Next in duplicate labels */ ! unsigned s_type : 5; /* Symbol type */ unsigned s_newsym: 1; /* A new symbol */