summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorYuri Zaporogets <yuriz@users.sourceforge.net>2004-09-15 06:54:34 +0000
committerYuri Zaporogets <yuriz@users.sourceforge.net>2004-09-15 06:54:34 +0000
commite0c059ab4e1e5d471372aa42caa57573de912655 (patch)
treef496dd3cd93c4ec4126ab9dd327474a589ac9ae1
parent7549d149982c8c89991485d5ef359d22a3416a1f (diff)
downloadnasm-e0c059ab4e1e5d471372aa42caa57573de912655.tar.gz
outrdf2.c now uses the same definitions of RDOFF2 format that RDOFF utils.
Export/import/common label size is increased from 33 to 64. Fixed the bug that caused wrong behavior of rdfgetheaderrec() if label length was 32. Changed error codes from numeric values to symbolic constants. Moved some routines from rdfdump.c to rdoff.c. They will be utilized also by rdfdisasm, which is being developed.
-rw-r--r--output/outrdf2.c432
-rw-r--r--rdoff/Makefile.in4
-rw-r--r--rdoff/Mkfiles/Makefile.dj4
-rw-r--r--rdoff/Mkfiles/Makefile.emx4
-rw-r--r--rdoff/Mkfiles/Makefile.unx4
-rw-r--r--rdoff/README2
-rw-r--r--rdoff/collectn.c46
-rw-r--r--rdoff/collectn.h10
-rw-r--r--rdoff/doc/rdoff.texi4
-rw-r--r--rdoff/hash.c1
-rw-r--r--rdoff/ldrdf.c113
-rw-r--r--rdoff/rdf2bin.c5
-rw-r--r--rdoff/rdf2ihx.c9
-rw-r--r--rdoff/rdfdump.c473
-rw-r--r--rdoff/rdfload.c31
-rw-r--r--rdoff/rdfload.h2
-rw-r--r--rdoff/rdlib.c5
-rw-r--r--rdoff/rdlib.h6
-rw-r--r--rdoff/rdoff.c455
-rw-r--r--rdoff/rdoff.h166
-rw-r--r--rdoff/rdx.c11
-rw-r--r--rdoff/segtab.h1
22 files changed, 905 insertions, 883 deletions
diff --git a/output/outrdf2.c b/output/outrdf2.c
index 931f872c..6c7a1027 100644
--- a/output/outrdf2.c
+++ b/output/outrdf2.c
@@ -1,10 +1,9 @@
-/* outrdf2.c output routines for the Netwide Assembler to produce
- * RDOFF version 2 format object files (which are intended
- * mainly for use in proprietary projects, as the code to
- * load and execute them is very simple). They will also be
- * used for device drivers and possibly some executable files
- * in the MOSCOW operating system. See Rdoff.txt for
- * details.
+/*
+ * outrdf2.c output routines for the Netwide Assembler to produce
+ * RDOFF version 2 format object files, which is used as a
+ * main binary format in the RadiOS (http://radios.sf.net).
+ * Originally Julian planned to use it in his MOSCOW
+ * operating system.
*
* The Netwide Assembler is copyright (C) 1996-1998 Simon Tatham and
* Julian Hall. All rights reserved. The software is
@@ -23,19 +22,15 @@
#include "outform.h"
/* VERBOSE_WARNINGS: define this to add some extra warnings... */
-#define VERBOSE_WARNINGS
+#define VERBOSE_WARNINGS
#ifdef OF_RDF2
-#define RDF_MAXSEGS 64 /* maximum number of segments - user configurable */
-
-typedef unsigned short int16;
-typedef unsigned char byte;
-
-static const char *RDOFF2Id = "RDOFF2"; /* written to start of RDOFF files */
+#include "rdoff/rdoff.h"
+/* This signature is written to start of RDOFF files */
+static const char *RDOFF2Id = RDOFF2_SIGNATURE;
-/* the records that can be found in the RDOFF header */
/* Note that whenever a segment is referred to in the RDOFF file, its number
* is always half of the segment number that NASM uses to refer to it; this
@@ -44,86 +39,16 @@ static const char *RDOFF2Id = "RDOFF2"; /* written to start of RDOFF files */
* allows up to 65533 external labels to be defined; otherwise it would be
* 32764. */
-#define RDFREC_RELOC 1
-#define RDFREC_IMPORT 2
-#define RDFREC_GLOBAL 3
-#define RDFREC_DLL 4
-#define RDFREC_BSS 5
-#define RDFREC_SEGRELOC 6
-#define RDFREC_FARIMPORT 7
-#define RDFREC_MODNAME 8
-#define RDFREC_COMMON 10
-#define RDFREC_GENERIC 0
-
-
-struct RelocRec {
- byte type; /* must be 1, or 6 for segment base ref */
- byte reclen; /* set to 8 */
- byte segment; /* only 0 for code, or 1 for data supported,
- * but add 64 for relative refs (ie do not require
- * reloc @ loadtime, only linkage) */
- long offset; /* from start of segment in which reference is loc'd */
- byte length; /* 1 2 or 4 bytes */
- int16 refseg; /* segment to which reference refers to */
-};
-
-struct ImportRec {
- byte type; /* must be 2, or 7 for FAR import */
- byte reclen; /* equals 3+label length */
- byte flags; /* SYM_* flags (see below) */
- int16 segment; /* segment number allocated to the label for reloc
- * records - label is assumed to be at offset zero
- * in this segment, so linker must fix up with offset
- * of segment and of offset within segment */
- char label[33]; /* zero terminated... should be written to file until
- * the zero, but not after it - max len = 32 chars */
-};
-
-struct ExportRec {
- byte type; /* must be 3 */
- byte reclen; /* equals 7+label length */
- byte flags; /* SYM_* flags (see below) */
- byte segment; /* segment referred to (0/1) */
- long offset; /* offset within segment */
- char label[33]; /* zero terminated as above. max len = 32 chars */
-};
-
-struct BSSRec {
- byte type; /* must be 5 */
- byte reclen; /* equals 4 */
- long amount; /* number of bytes BSS to reserve */
-};
-
-struct DLLModRec {
- byte type; /* 4 for DLLRec, 8 for ModRec */
- byte reclen; /* 1+lib name length for DLLRec, 1+mod name length */
- char name[128]; /* library to link at load time or module name */
-};
-
-struct CommonRec {
- byte type; /* must be 10 */
- byte reclen; /* equals 9+label length */
- int16 segment; /* segment number */
- long size; /* size of common variable */
- int16 align; /* alignment (power of two) */
- char label[33]; /* zero terminated as above. max len = 32 chars */
-};
-
-/* Flags for ExportRec */
-#define SYM_DATA 1
-#define SYM_FUNCTION 2
-#define SYM_GLOBAL 4
-#define SYM_IMPORT 8
-
#define COUNT_SEGTYPES 9
static char * segmenttypes[COUNT_SEGTYPES] = {
- "null", "text", "code", "data", "comment", "lcomment", "pcomment",
- "symdebug", "linedebug"
+ "null", "text", "code", "data",
+ "comment", "lcomment", "pcomment",
+ "symdebug", "linedebug"
};
static int segmenttypenumbers[COUNT_SEGTYPES] = {
- 0, 1, 1, 2, 3, 4, 5, 6, 7
+ 0, 1, 1, 2, 3, 4, 5, 6, 7
};
/* code for managing buffers needed to separate code and data into individual
@@ -147,11 +72,11 @@ static FILE *ofile;
static efunc error;
static struct seginfo {
- char *segname;
- int segnumber;
- int16 segtype;
- int16 segreserved;
- long seglength;
+ char *segname;
+ int segnumber;
+ uint16 segtype;
+ uint16 segreserved;
+ long seglength;
} segments[RDF_MAXSEGS];
static int nsegments;
@@ -290,11 +215,15 @@ static long rdf2_section_names(char *name, int pass, int *bits)
return i;
}
+
+/*
+ * Write relocation record
+ */
static void write_reloc_rec(struct RelocRec *r)
{
char buf[4],*b;
- if (r->refseg != (int16)NO_SEG && (r->refseg & 1)) /* segment base ref */
+ if (r->refseg != (uint16)NO_SEG && (r->refseg & 1)) /* segment base ref */
r->type = RDFREC_SEGRELOC;
r->refseg >>= 1; /* adjust segment nos to RDF rather than NASM */
@@ -310,37 +239,45 @@ static void write_reloc_rec(struct RelocRec *r)
headerlength += r->reclen + 2;
}
+
+/*
+ * Write export record
+ */
static void write_export_rec(struct ExportRec *r)
{
- char buf[4], *b;
+ char buf[4], *b;
- r->segment >>= 1;
+ r->segment >>= 1;
- saa_wbytes(header,&r->type,1);
- saa_wbytes(header,&r->reclen,1);
- saa_wbytes(header,&r->flags,1);
- saa_wbytes(header,&r->segment,1);
- b = buf; WRITELONG(b,r->offset);
- saa_wbytes(header,buf,4);
- saa_wbytes(header,r->label,strlen(r->label) + 1);
- headerlength += r->reclen + 2;
+ saa_wbytes(header, &r->type, 1);
+ saa_wbytes(header, &r->reclen, 1);
+ saa_wbytes(header, &r->flags, 1);
+ saa_wbytes(header, &r->segment, 1);
+ b = buf; WRITELONG(b, r->offset);
+ saa_wbytes(header, buf, 4);
+ saa_wbytes(header, r->label, strlen(r->label) + 1);
+ headerlength += r->reclen + 2;
}
static void write_import_rec(struct ImportRec *r)
{
- char buf[4], *b;
+ char buf[4], *b;
- r->segment >>= 1;
+ r->segment >>= 1;
- saa_wbytes(header,&r->type,1);
- saa_wbytes(header,&r->reclen,1);
- saa_wbytes(header,&r->flags,1);
- b = buf; WRITESHORT(b,r->segment);
- saa_wbytes(header,buf,2);
- saa_wbytes(header,r->label,strlen(r->label) + 1);
- headerlength += r->reclen + 2;
+ saa_wbytes(header, &r->type, 1);
+ saa_wbytes(header, &r->reclen, 1);
+ saa_wbytes(header, &r->flags, 1);
+ b = buf; WRITESHORT(b,r->segment);
+ saa_wbytes(header, buf, 2);
+ saa_wbytes(header, r->label, strlen(r->label) + 1);
+ headerlength += r->reclen + 2;
}
+
+/*
+ * Write BSS record
+ */
static void write_bss_rec(struct BSSRec *r)
{
char buf[4], *b;
@@ -353,139 +290,160 @@ static void write_bss_rec(struct BSSRec *r)
}
/*
- * Write common variable record.
+ * Write common variable record
*/
static void write_common_rec(struct CommonRec *r)
{
- char buf[4], *b;
+ char buf[4], *b;
- r->segment >>= 1;
+ r->segment >>= 1;
- saa_wbytes(header,&r->type,1);
- saa_wbytes(header,&r->reclen,1);
- b = buf; WRITESHORT(b,r->segment);
- saa_wbytes(header,buf,2);
- b = buf; WRITELONG(b,r->size);
- saa_wbytes(header,buf,4);
- b = buf; WRITESHORT(b,r->align);
- saa_wbytes(header,buf,2);
- saa_wbytes(header,r->label,strlen(r->label) + 1);
- headerlength += r->reclen + 2;
+ saa_wbytes(header, &r->type, 1);
+ saa_wbytes(header, &r->reclen, 1);
+ b = buf; WRITESHORT(b,r->segment);
+ saa_wbytes(header, buf, 2);
+ b = buf; WRITELONG(b, r->size);
+ saa_wbytes(header,buf,4);
+ b = buf; WRITESHORT(b, r->align);
+ saa_wbytes(header, buf, 2);
+ saa_wbytes(header, r->label, strlen(r->label) + 1);
+ headerlength += r->reclen + 2;
+}
+
+/*
+ * Write library record
+ */
+static void write_dll_rec(struct DLLRec *r)
+{
+ saa_wbytes(header,&r->type,1);
+ saa_wbytes(header,&r->reclen,1);
+ saa_wbytes(header, r->libname, strlen(r->libname) + 1);
+ headerlength += r->reclen + 2;
}
+
/*
- * Write library record. Also used for module name records.
+ * Write module name record
*/
-static void write_dllmod_rec(struct DLLModRec *r)
+static void write_modname_rec(struct ModRec *r)
{
saa_wbytes(header,&r->type,1);
saa_wbytes(header,&r->reclen,1);
- saa_wbytes(header,r->name,strlen(r->name) + 1);
+ saa_wbytes(header, r->modname, strlen(r->modname) + 1);
headerlength += r->reclen + 2;
}
+
+/*
+ * Handle export, import and common records.
+ */
static void rdf2_deflabel(char *name, long segment, long offset,
int is_global, char *special)
{
- struct ExportRec r;
- struct ImportRec ri;
- struct CommonRec ci;
- static int farsym = 0;
- static int i;
- byte symflags = 0;
-
- if (is_global == 2) {
- /* Common variable */
- ci.type = RDFREC_COMMON;
- ci.size = offset;
- ci.segment = segment;
- strncpy(ci.label, name, 32);
- ci.label[32] = 0;
- ci.reclen = 9 + strlen(ci.label);
- ci.align = 0;
+ struct ExportRec r;
+ struct ImportRec ri;
+ struct CommonRec ci;
+ static int farsym = 0;
+ static int i;
+ byte symflags = 0;
+ int len;
+
+ /* Check if the label length is OK */
+ if ((len = strlen(name)) >= EXIM_LABEL_MAX) {
+ error(ERR_NONFATAL, "label size exceeds %d bytes", EXIM_LABEL_MAX);
+ return;
+ }
+ if (!len) {
+ error(ERR_NONFATAL, "zero-length label");
+ return;
+ }
+
+ if (is_global == 2) {
+ /* Common variable */
+ ci.type = RDFREC_COMMON;
+ ci.size = offset;
+ ci.segment = segment;
+ strcpy(ci.label, name);
+ ci.reclen = 9 + len;
+ ci.align = 0;
- /*
- * Check the special text to see if it's a valid number and power
- * of two; if so, store it as the alignment for the common variable.
- */
- if (special) {
- int err;
- ci.align = readnum(special, &err);
- if (err) error(ERR_NONFATAL, "alignment constraint `%s' is not a"
- " valid number", special);
- else if ( (ci.align | (ci.align-1)) != 2*ci.align - 1)
- error(ERR_NONFATAL, "alignment constraint `%s' is not a"
- " power of two", special);
- }
- write_common_rec(&ci);
- }
+ /*
+ * Check the special text to see if it's a valid number and power
+ * of two; if so, store it as the alignment for the common variable.
+ */
+ if (special) {
+ int err;
+ ci.align = readnum(special, &err);
+ if (err)
+ error(ERR_NONFATAL, "alignment constraint `%s' is not a"
+ " valid number", special);
+ else if ( (ci.align | (ci.align-1)) != 2*ci.align - 1)
+ error(ERR_NONFATAL, "alignment constraint `%s' is not a"
+ " power of two", special);
+ }
+ write_common_rec(&ci);
+ }
- /* We don't care about local labels or fix-up hints */
- if (is_global != 1) return;
+ /* We don't care about local labels or fix-up hints */
+ if (is_global != 1) return;
- if (special) {
- while(*special == ' ' || *special == '\t') special++;
+ if (special) {
+ while(*special == ' ' || *special == '\t') special++;
- if (!nasm_strnicmp(special, "export", 6)) {
- special += 6;
- symflags |= SYM_GLOBAL;
- }
- else if (!nasm_strnicmp(special, "import", 6)) {
- special += 6;
- symflags |= SYM_IMPORT;
+ if (!nasm_strnicmp(special, "export", 6)) {
+ special += 6;
+ symflags |= SYM_GLOBAL;
+ } else if (!nasm_strnicmp(special, "import", 6)) {
+ special += 6;
+ symflags |= SYM_IMPORT;
+ }
+
+ if (*special) {
+ while (isspace(*special)) special++;
+ if (!nasm_stricmp(special, "far")) {
+ farsym = 1;
+ } else if (!nasm_stricmp(special, "near")) {
+ farsym = 0;
+ } else if (!nasm_stricmp(special, "proc") ||
+ !nasm_stricmp(special, "function")) {
+ symflags |= SYM_FUNCTION;
+ } else if (!nasm_stricmp(special, "data") ||
+ !nasm_stricmp(special, "object")) {
+ symflags |= SYM_DATA;
+ } else
+ error(ERR_NONFATAL, "unrecognised symbol type `%s'", special);
+ }
}
- if (*special) {
- while(isspace(*special)) special++;
- if (!nasm_stricmp(special, "far")) {
- farsym = 1;
- }
- else if (!nasm_stricmp(special, "near")) {
- farsym = 0;
- }
- else if (!nasm_stricmp(special, "proc") ||
- !nasm_stricmp(special, "function")) {
- symflags |= SYM_FUNCTION;
- }
- else if (!nasm_stricmp(special, "data") ||
- !nasm_stricmp(special, "object")) {
- symflags |= SYM_DATA;
- }
- else
- error(ERR_NONFATAL, "unrecognised symbol type `%s'", special);
- }
- }
+ if (name[0] == '.' && name[1] == '.' && name[2] != '@') {
+ error (ERR_NONFATAL, "unrecognised special symbol `%s'", name);
+ return;
+ }
- if (name[0] == '.' && name[1] == '.' && name[2] != '@') {
- error (ERR_NONFATAL, "unrecognised special symbol `%s'", name);
- return;
- }
+ for (i = 0; i < nsegments; i++) {
+ if (segments[i].segnumber == segment>>1) break;
+ }
- for (i = 0; i < nsegments; i++) {
- if (segments[i].segnumber == segment>>1) break;
- }
- if (i >= nsegments) { /* EXTERN declaration */
- ri.type = farsym ? RDFREC_FARIMPORT : RDFREC_IMPORT;
- if (symflags & SYM_GLOBAL)
- error(ERR_NONFATAL, "symbol type conflict - EXTERN cannot be EXPORT");
- ri.flags = symflags;
- ri.segment = segment;
- strncpy(ri.label,name,32);
- ri.label[32] = 0;
- ri.reclen = 4 + strlen(ri.label);
- write_import_rec(&ri);
- } else if (is_global) {
- r.type = RDFREC_GLOBAL;
- if (symflags & SYM_IMPORT)
- error(ERR_NONFATAL, "symbol type conflict - GLOBAL cannot be IMPORT");
- r.flags = symflags;
- r.segment = segment;
- r.offset = offset;
- strncpy(r.label,name,32);
- r.label[32] = 0;
- r.reclen = 7 + strlen(r.label);
- write_export_rec(&r);
- }
+ if (i >= nsegments) { /* EXTERN declaration */
+ ri.type = farsym ? RDFREC_FARIMPORT : RDFREC_IMPORT;
+ if (symflags & SYM_GLOBAL)
+ error(ERR_NONFATAL, "symbol type conflict - EXTERN cannot be EXPORT");
+ ri.flags = symflags;
+ ri.segment = segment;
+ strcpy(ri.label, name);
+ ri.reclen = 4 + len;
+ write_import_rec(&ri);
+ } else if (is_global) {
+ r.type = RDFREC_GLOBAL; /* GLOBAL declaration */
+ if (symflags & SYM_IMPORT)
+ error(ERR_NONFATAL, "symbol type conflict - GLOBAL cannot be IMPORT");
+ r.flags = symflags;
+ r.segment = segment;
+ r.offset = offset;
+ strcpy(r.label, name);
+ r.reclen = 7 + len;
+ write_export_rec(&r);
+ }
}
static void membufwrite(int segment, const void * data, int bytes)
@@ -681,8 +639,7 @@ static void rdf2_cleanup (int debuginfo) {
/* generate the output file... */
fwrite(RDOFF2Id,6,1,ofile); /* file type magic number */
- if (bsslength != 0) /* reserve BSS */
- {
+ if (bsslength != 0) { /* reserve BSS */
bs.type = RDFREC_BSS;
bs.amount = bsslength;
bs.reclen = 4;
@@ -730,25 +687,38 @@ static long rdf2_segbase (long segment) {
return segment;
}
-static int rdf2_directive (char *directive, char *value, int pass) {
- struct DLLModRec r;
+
+/*
+ * Handle RDOFF2 specific directives
+ */
+static int rdf2_directive (char *directive, char *value, int pass)
+{
+ int n;
+
+ /* Check if the name length is OK */
+ if ((n = strlen(value)) >= MODLIB_NAME_MAX) {
+ error(ERR_NONFATAL, "name size exceeds %d bytes", MODLIB_NAME_MAX);
+ return 0;
+ }
if (! strcmp(directive, "library")) {
if (pass == 1) {
+ struct DLLRec r;
r.type = RDFREC_DLL;
- r.reclen=strlen(value)+1;
- strcpy(r.name, value);
- write_dllmod_rec(&r);
+ r.reclen = n+1;
+ strcpy(r.libname, value);
+ write_dll_rec(&r);
}
return 1;
}
if (! strcmp(directive, "module")) {
if (pass == 1) {
+ struct ModRec r;
r.type = RDFREC_MODNAME;
- r.reclen=strlen(value)+1;
- strcpy(r.name, value);
- write_dllmod_rec(&r);
+ r.reclen = n+1;
+ strcpy(r.modname, value);
+ write_modname_rec(&r);
}
return 1;
}
diff --git a/rdoff/Makefile.in b/rdoff/Makefile.in
index 8ac3242b..f2e14f4d 100644
--- a/rdoff/Makefile.in
+++ b/rdoff/Makefile.in
@@ -42,8 +42,8 @@ PROGRAMS = rdfdump$(X) ldrdf$(X) rdx$(X) rdflib$(X) \
all: $(PROGRAMS)
-rdfdump$(X): rdfdump.$(O)
- $(CC) $(LDFLAGS) -o rdfdump$(X) rdfdump.$(O)
+rdfdump$(X): rdfdump.$(O) rdoff.$(O)
+ $(CC) $(LDFLAGS) -o rdfdump$(X) rdfdump.$(O) rdoff.$(O)
ldrdf$(X): ldrdf.$(O) $(LDRDFLIBS)
$(CC) $(LDFLAGS) -o ldrdf$(X) ldrdf.$(O) $(LDRDFLIBS)
rdx$(X): rdx.$(O) $(RDXLIBS)
diff --git a/rdoff/Mkfiles/Makefile.dj b/rdoff/Mkfiles/Makefile.dj
index 20997395..163d278f 100644
--- a/rdoff/Mkfiles/Makefile.dj
+++ b/rdoff/Mkfiles/Makefile.dj
@@ -33,8 +33,8 @@ RDXLIBS = rdoff.o rdfload.o symtab.o hash.o collectn.o
all: rdfdump ldrdf rdx rdflib rdf2bin rdf2com
-rdfdump: rdfdump.o
- $(CC) -o rdfdump rdfdump.o
+rdfdump: rdfdump.o rdoff.o
+ $(CC) -o rdfdump rdfdump.o rdoff.o
ldrdf: ldrdf.o $(LDRDFLIBS)
$(CC) -o ldrdf ldrdf.o $(LDRDFLIBS)
diff --git a/rdoff/Mkfiles/Makefile.emx b/rdoff/Mkfiles/Makefile.emx
index fbaa934c..9a28745d 100644
--- a/rdoff/Mkfiles/Makefile.emx
+++ b/rdoff/Mkfiles/Makefile.emx
@@ -33,8 +33,8 @@ RDXLIBS = rdoff.o rdfload.o symtab.o collectn.o hash.o
all: rdfdump ldrdf rdx rdflib rdf2bin
-rdfdump: rdfdump.o
- $(CC) $(LDFLAGS) -o rdfdump rdfdump.o $(LIBS)
+rdfdump: rdfdump.o rdoff.o
+ $(CC) $(LDFLAGS) -o rdfdump rdfdump.o rdoff.o $(LIBS)
ldrdf: ldrdf.o $(LDRDFLIBS)
$(CC) $(LDFLAGS) -o ldrdf ldrdf.o $(LDRDFLIBS) $(LIBS)
rdx: rdx.o $(RDXLIBS)
diff --git a/rdoff/Mkfiles/Makefile.unx b/rdoff/Mkfiles/Makefile.unx
index 89d439f8..1bf9b969 100644
--- a/rdoff/Mkfiles/Makefile.unx
+++ b/rdoff/Mkfiles/Makefile.unx
@@ -33,8 +33,8 @@ RDXLIBS = rdoff.o rdfload.o symtab.o hash.o collectn.o
all: rdfdump ldrdf rdx rdflib rdf2bin rdf2com
-rdfdump: rdfdump.o
- $(CC) -o rdfdump rdfdump.o
+rdfdump: rdfdump.o rdoff.o
+ $(CC) -o rdfdump rdfdump.o rdoff.o
ldrdf: ldrdf.o $(LDRDFLIBS)
$(CC) -o ldrdf ldrdf.o $(LDRDFLIBS)
diff --git a/rdoff/README b/rdoff/README
index 4962b89c..a5a6fd1b 100644
--- a/rdoff/README
+++ b/rdoff/README
@@ -181,5 +181,5 @@ file for a comment containing the word 'TODO'. A brief list is given here:
MAINTAINERS
===========
-Yuri Zaporogets <yuriz@ukr.net> - primary maintainer
+Yuri Zaporogets <yuriz@users.sf.net> - primary maintainer
Julian Hall <jules@dsf.org.uk> - original designer and author
diff --git a/rdoff/collectn.c b/rdoff/collectn.c
index c265c95f..71dc10e7 100644
--- a/rdoff/collectn.c
+++ b/rdoff/collectn.c
@@ -1,4 +1,5 @@
-/* collectn.c Implements variable length pointer arrays [collections]
+/*
+ * collectn.c - implements variable length pointer arrays [collections].
*
* This file is public domain.
*/
@@ -8,33 +9,36 @@
void collection_init(Collection * c)
{
- int i;
+ int i;
- for (i = 0; i < 32; i++) c->p[i] = NULL;
- c->next = NULL;
+ for (i = 0; i < 32; i++)
+ c->p[i] = NULL;
+ c->next = NULL;
}
-void ** colln(Collection * c, int index)
+void **colln(Collection * c, int index)
{
- while (index >= 32) {
- index -= 32;
- if (c->next == NULL) {
- c->next = malloc(sizeof(Collection));
- collection_init(c->next);
+ while (index >= 32) {
+ index -= 32;
+ if (c->next == NULL) {
+ c->next = malloc(sizeof(Collection));
+ collection_init(c->next);
+ }
+ c = c->next;
}
- c = c->next;
- }
- return &(c->p[index]);
+ return &(c->p[index]);
}
-void collection_reset(Collection *c)
+void collection_reset(Collection * c)
{
- int i;
- if (c->next) {
- collection_reset(c->next);
- free(c->next);
- }
+ int i;
- c->next = NULL;
- for (i = 0; i < 32; i++) c->p[i] = NULL;
+ if (c->next) {
+ collection_reset(c->next);
+ free(c->next);
+ }
+
+ c->next = NULL;
+ for (i = 0; i < 32; i++)
+ c->p[i] = NULL;
}
diff --git a/rdoff/collectn.h b/rdoff/collectn.h
index 2dc786eb..dc4f7ccd 100644
--- a/rdoff/collectn.h
+++ b/rdoff/collectn.h
@@ -1,17 +1,18 @@
-/* collectn.h Header file for 'collection' abstract data type
+/*
+ * collectn.h - header file for 'collection' abstract data type.
*
* This file is public domain, and does not come under the NASM license.
* It, along with 'collectn.c' implements what is basically a variable
- * length array (of pointers)
+ * length array (of pointers).
*/
#ifndef _COLLECTN_H
#define _COLLECTN_H
typedef struct tagCollection {
- void *p[32]; /* array of pointers to objects */
+ void *p[32]; /* array of pointers to objects */
- struct tagCollection *next;
+ struct tagCollection *next;
} Collection;
void collection_init(Collection * c);
@@ -19,4 +20,3 @@ void ** colln(Collection * c, int index);
void collection_reset(Collection * c);
#endif
-
diff --git a/rdoff/doc/rdoff.texi b/rdoff/doc/rdoff.texi
index c958cc3f..44312875 100644
--- a/rdoff/doc/rdoff.texi
+++ b/rdoff/doc/rdoff.texi
@@ -12,8 +12,8 @@
@end titlepage
@ifinfo
-Copyright @copyright{} 2002-2003 Netwide Assembler Project.
-Written by Yuri Zaporogets @email{yuriz@@ukr.net}
+Copyright @copyright{} 2002-2004 Netwide Assembler Project.
+Written by Yuri Zaporogets @email{yuriz@@users.sf.net}
Based on various sources and notes written by Julian Hall @email{jules@@dsf.org.uk}
Distributed under GNU documentation license.
@end ifinfo
diff --git a/rdoff/hash.c b/rdoff/hash.c
index c22d182a..7f28f12b 100644
--- a/rdoff/hash.c
+++ b/rdoff/hash.c
@@ -92,4 +92,3 @@ hash (const char *name)
return (hashval);
}
-
diff --git a/rdoff/ldrdf.c b/rdoff/ldrdf.c
index f31ca7a3..22e077e6 100644
--- a/rdoff/ldrdf.c
+++ b/rdoff/ldrdf.c
@@ -2,7 +2,7 @@
* ldrdf.c - RDOFF Object File linker/loader main program.
*
* Copyright (c) 1996,99 Julian Hall. All rights reserved.
- * Copyright (c) 2000-2003 RET & COM Research.
+ * Improvements and fixes (c) 1999-2004 RET & COM Research.
*
* This file is distributed under the terms and conditions of the
* GNU Lesser Public License (LGPL), version 2.1.
@@ -28,6 +28,8 @@
#include <stdlib.h>
#include <string.h>
+#define RDOFF_UTILS
+
#include "rdoff.h"
#include "symtab.h"
#include "collectn.h"
@@ -36,7 +38,6 @@
#define LDRDF_VERSION "1.07"
-#define RDF_MAXSEGS 64
/* #define STINGY_MEMORY */
/* =======================================================================
@@ -70,8 +71,8 @@ struct modulenode {
*/
void processmodule(const char * filename, struct modulenode * mod);
-int allocnewseg(int16 type,int16 reserved);
-int findsegment(int16 type,int16 reserved);
+int allocnewseg(uint16 type,uint16 reserved);
+int findsegment(uint16 type,uint16 reserved);
void symtab_add(const char * symbol, int segment, long offset);
int symtab_get(const char * symbol, int * segment, long * offset);
@@ -219,8 +220,7 @@ void processmodule(const char * filename, struct modulenode * mod)
long bssamount = 0;
int bss_was_referenced = 0;
- for (seg = 0; seg < mod->f.nsegs; seg++)
- {
+ for (seg = 0; seg < mod->f.nsegs; seg++) {
/*
* get the segment configuration for this type from the segment
* table. getsegconfig() is a macro, defined in ldsegs.h.
@@ -418,7 +418,7 @@ int lookformodule(const char *name)
* a segment of the type requested, and if one isn't found allocates a
* new one.
*/
-int allocnewseg(int16 type,int16 reserved)
+int allocnewseg(uint16 type,uint16 reserved)
{
outputseg[nsegs].type = type;
outputseg[nsegs].number = nsegs;
@@ -430,7 +430,7 @@ int allocnewseg(int16 type,int16 reserved)
return nsegs++;
}
-int findsegment(int16 type,int16 reserved)
+int findsegment(uint16 type,uint16 reserved)
{
int i;
@@ -463,8 +463,7 @@ void symtab_add(const char * symbol, int segment, long offset)
symtabEnt * ste;
ste = symtabFind(symtab, symbol);
- if (ste)
- {
+ if (ste) {
if (ste->segment >= 0) {
/*
* symbol previously defined
@@ -516,9 +515,7 @@ int symtab_get(const char * symbol, int * segment, long * offset)
*segment = -1;
*offset = 0;
return 0;
- }
- else
- {
+ } else {
*segment = ste->segment;
*offset = ste->offset;
return 1;
@@ -539,16 +536,13 @@ void add_library(const char * name)
errorcount++;
return;
}
- if (! libraries)
- {
+ if (!libraries) {
lastlib = libraries = malloc(sizeof(*libraries));
if (! libraries) {
fprintf(stderr, "ldrdf: out of memory\n");
exit(1);
}
- }
- else
- {
+ } else {
lastlib->next = malloc(sizeof(*libraries));
if (!lastlib->next) {
fprintf(stderr, "ldrdf: out of memory\n");
@@ -588,13 +582,11 @@ int search_libraries()
cur = libraries;
- while (cur)
- {
+ while (cur) {
if (options.verbose > 2)
printf("scanning library `%s', pass %d...\n", cur->name, pass);
- for (i = 0; rdl_openmodule(cur, i, &f) == 0; i++)
- {
+ for (i = 0; rdl_openmodule(cur, i, &f) == 0; i++) {
if (pass == 2 && lookformodule(f.name)) continue;
if (options.verbose > 3)
@@ -613,8 +605,7 @@ int search_libraries()
keepfile = 0;
- while ((hr = rdfgetheaderrec (&f)))
- {
+ while ((hr = rdfgetheaderrec (&f))) {
/* We're only interested in exports, so skip others */
if (hr->type != RDFREC_GLOBAL) continue;
@@ -744,8 +735,7 @@ void write_output(const char * filename)
* under 16 bit DOS, but that would be a slower way of doing this.
* And you could always use DJGPP...
*/
- for (i = 0; i < nsegs; i++)
- {
+ for (i = 0; i < nsegs; i++) {
outputseg[i].data=NULL;
if(!outputseg[i].length) continue;
outputseg[i].data = malloc(outputseg[i].length);
@@ -764,21 +754,18 @@ void write_output(const char * filename)
/*
* Step through the modules, performing required actions on each one
*/
- for (cur = modules; cur; cur=cur->next)
- {
+ for (cur = modules; cur; cur=cur->next) {
/*
* Read the actual segment contents into the correct places in
* the newly allocated segments
*/
- for (i = 0; i < cur->f.nsegs; i++)
- {
+ for (i = 0; i < cur->f.nsegs; i++) {
int dest = cur->seginfo[i].dest_seg;
if (dest == -1) continue;
if (rdfloadseg(&cur->f, i,
- outputseg[dest].data + cur->seginfo[i].reloc))
- {
+ outputseg[dest].data + cur->seginfo[i].reloc)) {
rdfperror("ldrdf", cur->name);
exit(1);
}
@@ -797,8 +784,7 @@ void write_output(const char * filename)
if (cur->f.header_loc)
rdfheaderrewind(&cur->f);
else
- if (rdfloadseg(&cur->f, RDOFF_HEADER, header))
- {
+ if (rdfloadseg(&cur->f, RDOFF_HEADER, header)) {
rdfperror("ldrdf", cur->name);
exit(1);
}
@@ -808,18 +794,16 @@ void write_output(const char * filename)
* table for the segments in this module.
*/
init_seglocations(&segs);
- for (i = 0; i < cur->f.nsegs; i++)
- {
+ for (i = 0; i < cur->f.nsegs; i++) {
add_seglocation(&segs, cur->f.seg[i].number,
cur->seginfo[i].dest_seg, cur->seginfo[i].reloc);
}
/*
* and the BSS segment (doh!)
*/
- add_seglocation (&segs, 2, 2, cur->bss_reloc);
+ add_seglocation(&segs, 2, 2, cur->bss_reloc);
- while ((hr = rdfgetheaderrec(&cur->f)))
- {
+ while ((hr = rdfgetheaderrec(&cur->f))) {
switch(hr->type) {
case RDFREC_RELOC: /* relocation record - need to do a fixup */
/*
@@ -834,21 +818,18 @@ void write_output(const char * filename)
* case we have to first subtract the amount we've relocated
* the containing segment by.
*/
-
- if (!get_seglocation(&segs, hr->r.refseg, &seg, &offset))
- {
+ if (!get_seglocation(&segs, hr->r.refseg, &seg, &offset)) {
fprintf(stderr, "%s: reloc to undefined segment %04x\n",
cur->name, (int) hr->r.refseg);
errorcount++;
break;
}
- isrelative = (hr->r.segment & 64) == 64;
- hr->r.segment &= 63;
+ isrelative = (hr->r.segment & RDOFF_RELATIVEMASK) == RDOFF_RELATIVEMASK;
+ hr->r.segment &= (RDOFF_RELATIVEMASK-1);
if (hr->r.segment == 2 ||
- (localseg = rdffindsegment(&cur->f, hr->r.segment)) == -1)
- {
+ (localseg = rdffindsegment(&cur->f, hr->r.segment)) == -1) {
fprintf(stderr, "%s: reloc from %s segment (%d)\n",
cur->name,
hr->r.segment == 2 ? "BSS" : "unknown",
@@ -857,8 +838,8 @@ void write_output(const char * filename)
break;
}
- if (hr->r.length != 1 && hr->r.length != 2 && hr->r.length!=4)
- {
+ if (hr->r.length != 1 && hr->r.length != 2 &&
+ hr->r.length != 4 ) {
fprintf(stderr, "%s: nonstandard length reloc "
"(%d bytes)\n", cur->name, hr->r.length);
errorcount++;
@@ -883,10 +864,10 @@ void write_output(const char * filename)
* Then add 'offset' onto the value at data.
*/
- if (isrelative) offset -= cur->seginfo[localseg].reloc;
- switch (hr->r.length)
- {
- case 1:
+ if (isrelative)
+ offset -= cur->seginfo[localseg].reloc;
+ switch (hr->r.length) {
+ case 1:
offset += *data;
if (offset < -127 || offset > 128)
fprintf(error_file, "warning: relocation out of range "
@@ -894,7 +875,7 @@ void write_output(const char * filename)
(int)hr->r.segment, hr->r.offset);
*data = (char) offset;
break;
- case 2:
+ case 2:
offset += * (short *)data;
if (offset < -32767 || offset > 32768)
fprintf(error_file, "warning: relocation out of range "
@@ -902,7 +883,7 @@ void write_output(const char * filename)
(int)hr->r.segment, hr->r.offset);
* (short *)data = (short) offset;
break;
- case 4:
+ case 4:
* (long *)data += offset;
/* we can't easily detect overflow on this one */
break;
@@ -915,13 +896,12 @@ void write_output(const char * filename)
* Otherwise, we need to output a new relocation record
* with the references updated segment and offset...
*/
- if (! isrelative || cur->seginfo[localseg].dest_seg != seg)
- {
+ if (!isrelative || cur->seginfo[localseg].dest_seg != seg) {
hr->r.segment = cur->seginfo[localseg].dest_seg;
hr->r.offset += cur->seginfo[localseg].reloc;
hr->r.refseg = seg;
if (isrelative)
- hr->r.segment += 64;
+ hr->r.segment += RDOFF_RELATIVEMASK;
rdfaddheader(rdfheader, hr);
}
break;
@@ -1045,8 +1025,7 @@ void write_output(const char * filename)
hr->r.segment = cur->seginfo[localseg].dest_seg;
hr->r.offset += cur->seginfo[localseg].reloc;
- if (!get_seglocation(&segs, hr->r.refseg, &seg, &offset))
- {
+ if (!get_seglocation(&segs, hr->r.refseg, &seg, &offset)) {
fprintf(stderr, "%s: segment fixup to undefined "
"segment %04x\n", cur->name, (int)hr->r.refseg);
errorcount++;
@@ -1085,8 +1064,7 @@ void write_output(const char * filename)
/*
* Write the header
*/
- for (i = 0; i < nsegs; i++)
- {
+ for (i = 0; i < nsegs; i++) {
if (i == 2) continue;
rdfaddsegment (rdfheader, outputseg[i].length);
}
@@ -1098,9 +1076,8 @@ void write_output(const char * filename)
* Step through the segments, one at a time, writing out into
* the output file
*/
- for (i = 0; i < nsegs; i++)
- {
- int16 s;
+ for (i = 0; i < nsegs; i++) {
+ uint16 s;
long l;
if (i == 2) continue;
@@ -1154,14 +1131,13 @@ int main(int argc, char ** argv)
error_file = stderr;
- argc --, argv ++;
+ argc--, argv++;
if (argc == 0) usage();
- while (argc && *argv && **argv == '-' && argv[0][1] != 'l')
- {
+ while (argc && *argv && **argv == '-' && argv[0][1] != 'l') {
switch(argv[0][1]) {
case 'r':
printf("ldrdf (linker for RDF files) version " LDRDF_VERSION "\n");
- printf( _RDOFF_H "\n");
+ printf("RDOFF2 revision %s\n", RDOFF2_REVISION);
exit(0);
case 'v':
if (argv[0][2] == '=') {
@@ -1318,3 +1294,4 @@ int main(int argc, char ** argv)
if (errorcount > 0) exit(1);
return 0;
}
+
diff --git a/rdoff/rdf2bin.c b/rdoff/rdf2bin.c
index 938b4a92..aee6afb2 100644
--- a/rdoff/rdf2bin.c
+++ b/rdoff/rdf2bin.c
@@ -1,11 +1,12 @@
-/* rdf2bin: convert an RDOFF object file to flat binary */
+/*
+ * rdf2bin.c - convert an RDOFF object file to flat binary
+ */
#include <stdlib.h>
#include <stdio.h>
#include <string.h>
#include "rdfload.h"
-#include "rdoff.h"
#include "nasmlib.h"
long origin = 0;
diff --git a/rdoff/rdf2ihx.c b/rdoff/rdf2ihx.c
index ed915370..43e5c720 100644
--- a/rdoff/rdf2ihx.c
+++ b/rdoff/rdf2ihx.c
@@ -1,12 +1,14 @@
-/* rdf2ihx: convert an RDOFF object file to Intel Hex format. This is based
- on rdf2bin. Note that this program only writes 16-bit HEX. */
+/*
+ * rdf2ihx.c - convert an RDOFF object file to Intel Hex format.
+ * This is based on rdf2bin.
+ * Note that this program only writes 16-bit HEX.
+ */
#include <stdlib.h>
#include <stdio.h>
#include <string.h>
#include "rdfload.h"
-#include "rdoff.h"
#include "nasmlib.h"
#include "symtab.h"
@@ -186,4 +188,3 @@ int main(int argc, char **argv)
fclose(of);
return 0;
}
-
diff --git a/rdoff/rdfdump.c b/rdoff/rdfdump.c
index 09f2d801..626fd2a1 100644
--- a/rdoff/rdfdump.c
+++ b/rdoff/rdfdump.c
@@ -6,74 +6,52 @@
#include <stdlib.h>
#include <string.h>
-#include "rdoff.h"
-
-FILE *infile;
-
-/* Translate from little endian to local representation */
-long translatelong(long in)
-{
- long r;
- unsigned char *i;
-
- i = (unsigned char *)&in;
- r = i[3];
- r = (r << 8) + i[2];
- r = (r << 8) + i[1];
- r = (r << 8) + *i;
+#define RDOFF_UTILS
- return r;
-}
-
-int16 translateshort(int16 in)
-{
- int r;
- unsigned char *i;
+#include "rdoff.h"
- i = (unsigned char *)&in;
- r = (i[1] << 8) + *i;
+#define PROGRAM_VERSION "2.3"
- return r;
-}
+FILE *infile;
void print_header(long length, int rdf_version)
{
- char buf[129],t,l,s,flags;
+ char buf[129], t, l, s, flags;
unsigned char reclen;
- long o,ll;
- int16 rs;
+ long o, ll;
+ uint16 rs;
while (length > 0) {
- fread(&t,1,1,infile);
+ fread(&t, 1, 1, infile);
if (rdf_version >= 2) {
- fread(&reclen,1,1,infile);
+ fread(&reclen, 1, 1, infile);
}
- switch(t) {
- case RDFREC_GENERIC: /* generic record */
- printf(" generic record (length=%d)\n", (int)reclen);
+ switch (t) {
+ case RDFREC_GENERIC: /* generic record */
+ printf(" generic record (length=%d)\n", (int) reclen);
fseek(infile, reclen, SEEK_CUR);
break;
-
- case RDFREC_RELOC: /* relocation record */
- case RDFREC_SEGRELOC: /* segment relocation */
- fread(&s,1,1,infile);
- fread(&o,4,1,infile);
- fread(&l,1,1,infile);
- fread(&rs,2,1,infile);
+
+ case RDFREC_RELOC: /* relocation record */
+ case RDFREC_SEGRELOC: /* segment relocation */
+ fread(&s, 1, 1, infile);
+ fread(&o, 4, 1, infile);
+ fread(&l, 1, 1, infile);
+ fread(&rs, 2, 1, infile);
printf(" %s: location (%04x:%08lx), length %d, "
- "referred seg %04x\n", t == 1 ? "relocation" : "seg relocation",
- (int)s,translatelong(o),(int)l,
- translateshort(rs));
- if (rdf_version >= 2 && reclen != 8)
+ "referred seg %04x\n", t == 1 ? "relocation" : "seg relocation",
+ (int) s, translatelong(o), (int) l, translateshort(rs));
+ if (rdf_version >= 2 && reclen != 8)
printf(" warning: reclen != 8\n");
- if (rdf_version == 1) length -= 9;
+ if (rdf_version == 1)
+ length -= 9;
if (rdf_version == 1 && t == 6)
printf(" warning: seg relocation not supported in RDOFF1\n");
- break;
-
- case RDFREC_IMPORT: /* import record */
- case RDFREC_FARIMPORT: /* import far symbol */
- fread(&flags, 1, 1, infile);
+ break;
+
+ case RDFREC_IMPORT: /* import record */
+ case RDFREC_FARIMPORT: /* import far symbol */
+ fread(&flags, 1, 1, infile);
fread(&rs, 2, 1, infile);
ll = 0;
@@ -82,22 +60,25 @@ void print_header(long length, int rdf_version)
fread(&buf[ll], 1, 1, infile);
} while (buf[ll++]);
} else {
- for (;ll < reclen - 3; ll++)
+ for (; ll < reclen - 3; ll++)
fread(&buf[ll], 1, 1, infile);
- }
+ }
if (t == 7)
printf("far ");
printf((flags & SYM_IMPORT) ? " import" : " extern");
- if (flags & SYM_FUNCTION) printf(" proc");
- if (flags & SYM_DATA) printf(" data");
+ if (flags & SYM_FUNCTION)
+ printf(" proc");
+ if (flags & SYM_DATA)
+ printf(" data");
printf(": segment %04x = %s\n", translateshort(rs), buf);
- if (rdf_version == 1) length -= ll + 3;
+ if (rdf_version == 1)
+ length -= ll + 3;
if (rdf_version == 1 && t == 7)
- printf (" warning: far import not supported in RDOFF1\n");
- break;
-
- case RDFREC_GLOBAL: /* export record */
+ printf(" warning: far import not supported in RDOFF1\n");
+ break;
+
+ case RDFREC_GLOBAL: /* export record */
fread(&flags, 1, 1, infile);
fread(&s, 1, 1, infile);
fread(&o, 4, 1, infile);
@@ -105,228 +86,218 @@ void print_header(long length, int rdf_version)
if (rdf_version == 1) {
do {
- fread(&buf[ll], 1, 1, infile);
+ fread(&buf[ll], 1, 1, infile);
} while (buf[ll++]);
} else {
- for (; ll < reclen - 6; ll ++)
- fread(&buf[ll], 1, 1, infile);
- }
- printf((flags & SYM_GLOBAL) ? " export" : " public");
- if (flags & SYM_FUNCTION) printf(" proc");
- if (flags & SYM_DATA) printf(" data");
- printf(": (%04x:%08lx) = %s\n", (int)s, translatelong(o), buf);
- if (rdf_version == 1) length -= ll + 6;
+ for (; ll < reclen - 6; ll++)
+ fread(&buf[ll], 1, 1, infile);
+ }
+ printf((flags & SYM_GLOBAL) ? " export" : " public");
+ if (flags & SYM_FUNCTION)
+ printf(" proc");
+ if (flags & SYM_DATA)
+ printf(" data");
+ printf(": (%04x:%08lx) = %s\n", (int) s, translatelong(o), buf);
+ if (rdf_version == 1)
+ length -= ll + 6;
break;
-
- case RDFREC_DLL: /* DLL and Module records */
+
+ case RDFREC_DLL: /* DLL and Module records */
case RDFREC_MODNAME:
ll = 0;
if (rdf_version == 1) {
do {
- fread(&buf[ll],1,1,infile);
+ fread(&buf[ll], 1, 1, infile);
} while (buf[ll++]);
} else {
for (; ll < reclen; ll++)
fread(&buf[ll], 1, 1, infile);
- }
- if (t==4) printf(" dll: %s\n",buf);
- else printf(" module: %s\n",buf);
+ }
+ if (t == 4)
+ printf(" dll: %s\n", buf);
+ else
+ printf(" module: %s\n", buf);
if (rdf_version == 1)
length -= ll + 1;
- break;
-
- case RDFREC_BSS: /* BSS reservation */
- fread(&ll,4,1,infile);
- printf(" bss reservation: %08lx bytes\n",translatelong(ll));
- if (rdf_version == 1) length -= 5;
+ break;
+
+ case RDFREC_BSS: /* BSS reservation */
+ fread(&ll, 4, 1, infile);
+ printf(" bss reservation: %08lx bytes\n", translatelong(ll));
+ if (rdf_version == 1)
+ length -= 5;
if (rdf_version > 1 && reclen != 4)
printf(" warning: reclen != 4\n");
break;
-
- case RDFREC_COMMON: {
+
+ case RDFREC_COMMON: {
unsigned short seg, align;
unsigned long size;
-
+
fread(&seg, 2, 1, infile);
fread(&size, 4, 1, infile);
fread(&align, 2, 1, infile);
for (ll = 0; ll < reclen - 8; ll++)
- fread(buf+ll, 1, 1, infile);
+ fread(buf + ll, 1, 1, infile);
printf(" common: segment %04x = %s, %ld:%d\n", translateshort(seg),
buf, translatelong(size), translateshort(align));
- break;
+ break;
}
default:
- printf(" unrecognized record (type %d", (int)t);
+ printf(" unrecognized record (type %d", (int) t);
if (rdf_version > 1) {
- printf(", length %d",(int)reclen);
- fseek(infile,reclen,SEEK_CUR);
- } else length --;
- printf(")\n");
+ printf(", length %d", (int) reclen);
+ fseek(infile, reclen, SEEK_CUR);
+ } else
+ length--;
+ printf(")\n");
}
- if (rdf_version != 1) length -= 2 + reclen;
+ if (rdf_version != 1)
+ length -= 2 + reclen;
}
}
-char * knowntypes[8] = {"NULL", "text", "data", "object comment",
- "linked comment", "loader comment",
- "symbolic debug", "line number debug"};
-
-char * translatesegmenttype(int16 type) {
- if (type < 8) return knowntypes[type];
- if (type < 0x0020) return "reserved";
- if (type < 0x1000) return "reserved - moscow";
- if (type < 0x8000) return "reserved - system dependant";
- if (type < 0xFFFF) return "reserved - other";
- if (type == 0xFFFF) return "invalid type code";
- return "type code out of range";
-}
-
-int main(int argc,char **argv) {
- char id[7];
- long l;
- int16 s;
- int verbose = 0;
- long offset;
- int foundnullsegment = 0;
- int version;
- long segmentcontentlength = 0;
- int nsegments = 0;
- long headerlength = 0;
- long objectlength = 0;
-
- puts("RDOFF Dump utility v2.2\n"\
- "Copyright (c) 1996,99 Julian R Hall\n"
- "Copyright (c) 2000-2002 RET & COM Research.");
-
- if (argc < 2) {
- fputs("Usage: rdfdump [-v] <filename>\n",stderr);
- exit(1);
- }
-
- if (! strcmp (argv[1], "-v") )
- {
- verbose = 1;
- if (argc < 3)
- {
- fputs("required parameter missing\n",stderr);
- exit(1);
+int main(int argc, char **argv)
+{
+ char id[7];
+ long l;
+ uint16 s;
+ int verbose = 0;
+ long offset;
+ int foundnullsegment = 0;
+ int version;
+ long segmentcontentlength = 0;
+ int nsegments = 0;
+ long headerlength = 0;
+ long objectlength = 0;
+
+ printf("RDOFF dump utility, version %s\n", PROGRAM_VERSION);
+ printf("RDOFF2 revision %s\n", RDOFF2_REVISION);
+ puts("Copyright (c) 1996,99 Julian R Hall\n"
+ "Improvements and fixes (c) 2002-2004 RET & COM Research.");
+
+ if (argc < 2) {
+ fputs("Usage: rdfdump [-v] <filename>\n", stderr);
+ exit(1);
+ }
+
+ if (!strcmp(argv[1], "-v")) {
+ verbose = 1;
+ if (argc < 3) {
+ fputs("required parameter missing\n", stderr);
+ exit(1);
+ }
+ argv++;
+ }
+
+ infile = fopen(argv[1], "rb");
+ if (!infile) {
+ fprintf(stderr, "rdfdump: Could not open %s\n", argv[1]);
+ exit(1);
+ }
+
+ fread(id, 6, 1, infile);
+ if (strncmp(id, "RDOFF", 5)) {
+ fputs("rdfdump: File does not contain valid RDOFF header\n", stderr);
+ exit(1);
+ }
+
+ printf("File %s: RDOFF version %c\n\n", argv[1], id[5]);
+ if (id[5] < '1' || id[5] > '2') {
+ fprintf(stderr, "rdfdump: unknown RDOFF version '%c'\n", id[5]);
+ exit(1);
+ }
+ version = id[5] - '0';
+
+ if (version > 1) {
+ fread(&l, 4, 1, infile);
+ objectlength = translatelong(l);
+ printf("Object content size: %ld bytes\n", objectlength);
+ }
+
+ fread(&l, 4, 1, infile);
+ headerlength = translatelong(l);
+ printf("Header (%ld bytes):\n", headerlength);
+ print_header(headerlength, version);
+
+ if (version == 1) {
+ fread(&l, 4, 1, infile);
+ l = translatelong(l);
+ printf("\nText segment length = %ld bytes\n", l);
+ offset = 0;
+ while (l--) {
+ fread(id, 1, 1, infile);
+ if (verbose) {
+ if (offset % 16 == 0)
+ printf("\n%08lx ", offset);
+ printf(" %02x", (int) (unsigned char) id[0]);
+ offset++;
+ }
+ }
+ if (verbose)
+ printf("\n\n");
+
+ fread(&l, 4, 1, infile);
+ l = translatelong(l);
+ printf("Data segment length = %ld bytes\n", l);
+
+ if (verbose) {
+ offset = 0;
+ while (l--) {
+ fread(id, 1, 1, infile);
+ if (offset % 16 == 0)
+ printf("\n%08lx ", offset);
+ printf(" %02x", (int) (unsigned char) id[0]);
+ offset++;
+ }
+ printf("\n");
+ }
+ } else {
+ do {
+ fread(&s, 2, 1, infile);
+ s = translateshort(s);
+ if (!s) {
+ printf("\nNULL segment\n");
+ foundnullsegment = 1;
+ break;
+ }
+ printf("\nSegment:\n Type = %04X (%s)\n", (int) s, translatesegmenttype(s));
+ nsegments++;
+
+ fread(&s, 2, 1, infile);
+ printf(" Number = %04X\n", (int) translateshort(s));
+ fread(&s, 2, 1, infile);
+ printf(" Resrvd = %04X\n", (int) translateshort(s));
+ fread(&l, 4, 1, infile);
+ l = translatelong(l);
+ printf(" Length = %ld bytes\n", l);
+ segmentcontentlength += l;
+
+ offset = 0;
+ while (l--) {
+ fread(id, 1, 1, infile);
+ if (verbose) {
+ if (offset % 16 == 0)
+ printf("\n%08lx ", offset);
+ printf(" %02x", (int) (unsigned char) id[0]);
+ offset++;
+ }
+ }
+ if (verbose)
+ printf("\n");
+ } while (!feof(infile));
+ if (!foundnullsegment)
+ printf("\nWarning: unexpected end of file - " "NULL segment not found\n");
+
+ printf("\nTotal number of segments: %d\n", nsegments);
+ printf("Total segment content length: %ld bytes\n", segmentcontentlength);
+
+ /* calculate what the total object content length should have been */
+ l = segmentcontentlength + 10 * (nsegments + 1) + headerlength + 4;
+ if (l != objectlength)
+ printf("Warning: actual object length (%ld) != " "stored object length (%ld)\n", l, objectlength);
}
- argv++;
- }
-
- infile = fopen(argv[1],"rb");
- if (! infile) {
- fprintf(stderr,"rdfdump: Could not open %s\n",argv[1]);
- exit(1);
- }
-
- fread(id,6,1,infile);
- if (strncmp(id,"RDOFF",5)) {
- fputs("rdfdump: File does not contain valid RDOFF header\n",stderr);
- exit(1);
- }
-
- printf("File %s: RDOFF version %c\n\n",argv[1],id[5]);
- if (id[5] < '1' || id[5] > '2') {
- fprintf(stderr,"rdfdump: unknown RDOFF version '%c'\n",id[5]);
- exit(1);
- }
- version = id[5] - '0';
-
- if (version > 1) {
- fread(&l, 4, 1, infile);
- objectlength = translatelong(l);
- printf("Object content size: %ld bytes\n", objectlength);
- }
-
- fread(&l,4,1,infile);
- headerlength = translatelong(l);
- printf("Header (%ld bytes):\n",headerlength);
- print_header(headerlength, version);
-
- if (version == 1) {
- fread(&l,4,1,infile);
- l = translatelong(l);
- printf("\nText segment length = %ld bytes\n",l);
- offset = 0;
- while(l--) {
- fread(id,1,1,infile);
- if (verbose) {
- if (offset % 16 == 0)
- printf("\n%08lx ", offset);
- printf(" %02x",(int) (unsigned char)id[0]);
- offset++;
- }
- }
- if (verbose) printf("\n\n");
-
- fread(&l,4,1,infile);
- l = translatelong(l);
- printf("Data segment length = %ld bytes\n",l);
-
- if (verbose)
- {
- offset = 0;
- while (l--) {
- fread(id,1,1,infile);
- if (offset % 16 == 0)
- printf("\n%08lx ", offset);
- printf(" %02x",(int) (unsigned char) id[0]);
- offset++;
- }
- printf("\n");
- }
- }
- else
- {
- do {
- fread(&s,2,1,infile);
- s = translateshort(s);
- if (!s) {
- printf("\nNULL segment\n");
- foundnullsegment = 1;
- break;
- }
- printf("\nSegment:\n Type = %04X (%s)\n",(int)s,
- translatesegmenttype(s));
- nsegments++;
-
- fread(&s,2,1,infile);
- printf(" Number = %04X\n",(int)translateshort(s));
- fread(&s,2,1,infile);
- printf(" Resrvd = %04X\n",(int)translateshort(s));
- fread(&l,4,1,infile);
- l = translatelong(l);
- printf(" Length = %ld bytes\n",l);
- segmentcontentlength += l;
-
- offset = 0;
- while(l--) {
- fread(id,1,1,infile);
- if (verbose) {
- if (offset % 16 == 0)
- printf("\n%08lx ", offset);
- printf(" %02x",(int) (unsigned char)id[0]);
- offset++;
- }
- }
- if (verbose) printf("\n");
- } while (!feof(infile));
- if (! foundnullsegment)
- printf("\nWarning: unexpected end of file - "
- "NULL segment not found\n");
-
- printf("\nTotal number of segments: %d\n", nsegments);
- printf("Total segment content length: %ld bytes\n",segmentcontentlength);
-
- /* calculate what the total object content length should have been */
- l = segmentcontentlength + 10 * (nsegments+1) + headerlength + 4;
- if (l != objectlength)
- printf("Warning: actual object length (%ld) != "
- "stored object length (%ld)\n", l, objectlength);
- }
- fclose(infile);
- return 0;
+ fclose(infile);
+ return 0;
}
diff --git a/rdoff/rdfload.c b/rdoff/rdfload.c
index 8fb6ca3a..2f8bf6b1 100644
--- a/rdoff/rdfload.c
+++ b/rdoff/rdfload.c
@@ -23,7 +23,6 @@
#include "rdfload.h"
#include "symtab.h"
-#include "rdoff.h"
#include "collectn.h"
extern int rdf_errno;
@@ -36,17 +35,15 @@ rdfmodule * rdfload(const char *filename)
rdfheaderrec *r;
f = malloc(sizeof(rdfmodule));
- if (f == NULL)
- {
- rdf_errno = 6; /* out of memory */
+ if (f == NULL) {
+ rdf_errno = RDF_ERR_NOMEM;
return NULL;
}
f->symtab = symtabNew();
- if (!f->symtab)
- {
+ if (!f->symtab) {
free(f);
- rdf_errno = 6;
+ rdf_errno = RDF_ERR_NOMEM;
return NULL;
}
@@ -63,7 +60,7 @@ rdfmodule * rdfload(const char *filename)
hdr = malloc (f->f.header_len);
if (! f->t || ! f->d || !hdr) {
- rdf_errno = 6;
+ rdf_errno = RDF_ERR_NOMEM;
rdfclose(&f->f);
if (f->t) free(f->t);
if (f->d) free(f->d);
@@ -87,20 +84,18 @@ rdfmodule * rdfload(const char *filename)
/* Allocate BSS segment; step through header and count BSS records */
- while ( ( r = rdfgetheaderrec (&f->f) ) )
- {
+ while ((r = rdfgetheaderrec(&f->f))) {
if (r->type == 5)
bsslength += r->b.amount;
}
f->b = malloc ( bsslength );
- if (bsslength && (!f->b))
- {
+ if (bsslength && (!f->b)) {
free(f->t);
free(f->d);
free(f);
free(hdr);
- rdf_errno = 6;
+ rdf_errno = RDF_ERR_NOMEM;
return NULL;
}
@@ -121,13 +116,11 @@ int rdf_relocate(rdfmodule * m)
long rel;
unsigned char * seg;
- rdfheaderrewind ( & m->f );
+ rdfheaderrewind (&m->f);
collection_init(&imports);
- while ( (r = rdfgetheaderrec ( & m->f ) ) )
- {
- switch (r->type)
- {
+ while ((r = rdfgetheaderrec(&m->f))) {
+ switch (r->type) {
case 1: /* Relocation record */
/* calculate relocation factor */
@@ -154,7 +147,7 @@ int rdf_relocate(rdfmodule * m)
seg[r->r.offset] += (char) rel;
break;
case 2:
- *(int16 *)(seg + r->r.offset) += (int16) rel;
+ *(uint16 *)(seg + r->r.offset) += (uint16) rel;
break;
case 4:
*(long *)(seg + r->r.offset) += rel;
diff --git a/rdoff/rdfload.h b/rdoff/rdfload.h
index 5e264b93..3889a4e1 100644
--- a/rdoff/rdfload.h
+++ b/rdoff/rdfload.h
@@ -12,6 +12,8 @@
#ifndef _RDFLOAD_H
#define _RDFLOAD_H
+#define RDOFF_UTILS
+
#include "rdoff.h"
typedef struct RDFModuleStruct {
diff --git a/rdoff/rdlib.c b/rdoff/rdlib.c
index f511c1c7..97f682f3 100644
--- a/rdoff/rdlib.c
+++ b/rdoff/rdlib.c
@@ -6,6 +6,8 @@
#include <stdlib.h>
#include <string.h>
+#define RDOFF_UTILS
+
#include "rdoff.h"
#include "rdlib.h"
#include "rdlar.h"
@@ -264,6 +266,3 @@ void rdl_perror(const char *apname, const char *filename)
else
fprintf(stderr,"%s:%s:%s\n",apname,filename,rdl_errors[rdl_error]);
}
-
-
-
diff --git a/rdoff/rdlib.h b/rdoff/rdlib.h
index 28c6ee73..62550248 100644
--- a/rdoff/rdlib.h
+++ b/rdoff/rdlib.h
@@ -1,4 +1,6 @@
-/* rdlib.h Functions for manipulating librarys of RDOFF object files */
+/*
+ * rdlib.h Functions for manipulating libraries of RDOFF object files.
+ */
struct librarynode {
@@ -23,5 +25,3 @@ int rdl_searchlib (struct librarynode * lib,
int rdl_openmodule (struct librarynode * lib, int module, rdffile * f);
void rdl_perror(const char *apname, const char *filename);
-
-
diff --git a/rdoff/rdoff.c b/rdoff/rdoff.c
index 504d8420..bfdb9cc1 100644
--- a/rdoff/rdoff.c
+++ b/rdoff/rdoff.c
@@ -19,6 +19,9 @@
#include <stdlib.h>
#include <string.h>
#include <errno.h>
+
+#define RDOFF_UTILS
+
#include "rdoff.h"
#define newstr(str) strcpy(malloc(strlen(str) + 1),str)
@@ -53,7 +56,7 @@ memorybuffer * newmembuf()
void membufwrite(memorybuffer *const b, void *data, int bytes)
{
- int16 w;
+ uint16 w;
long l;
if (b->next) { /* memory buffer full - use next buffer */
@@ -85,7 +88,7 @@ void membufwrite(memorybuffer *const b, void *data, int bytes)
break;
case -2:
- w = * (int16 *) data ;
+ w = * (uint16 *) data ;
b->buffer[b->length++] = w & 0xFF;
w >>= 8 ;
b->buffer[b->length++] = w & 0xFF;
@@ -146,9 +149,9 @@ long translatelong(long in)
return r;
}
-int16 translateshort(int16 in)
+uint16 translateshort(uint16 in)
{
- int16 r;
+ uint16 r;
unsigned char * i;
i = (unsigned char *)&in;
@@ -157,15 +160,48 @@ int16 translateshort(int16 in)
return r;
}
-const char *RDOFFId = "RDOFF2"; /* written to the start of RDOFF files */
+/* Segment types */
+static char *knownsegtypes[8] = {
+ "NULL", "text", "data", "object comment",
+ "linked comment", "loader comment",
+ "symbolic debug", "line number debug"
+};
+
+/* Get a textual string describing the segment type */
+char *translatesegmenttype(uint16 type)
+{
+ if (type < 8)
+ return knownsegtypes[type];
+ if (type < 0x0020)
+ return "reserved";
+ if (type < 0x1000)
+ return "reserved - Moscow";
+ if (type < 0x8000)
+ return "reserved - system dependant";
+ if (type < 0xFFFF)
+ return "reserved - other";
+ if (type == 0xFFFF)
+ return "invalid type code";
+ return "type code out of range";
+}
+
+/* This signature is written to the start of RDOFF files */
+const char *RDOFFId = RDOFF2_SIGNATURE;
+/* Error messages. Must correspond to the codes defined in rdoff.h */
const char *rdf_errors[11] = {
- "no error occurred","could not open file","invalid file format",
- "error reading file","unknown error","header not read",
- "out of memory", "RDOFF v1 not supported",
- "unknown extended header record",
- "header record of known type but unknown length",
- "no such segment"};
+ /* 0 */ "no error occurred",
+ /* 1 */ "could not open file",
+ /* 2 */ "invalid file format",
+ /* 3 */ "error reading file",
+ /* 4 */ "unknown error",
+ /* 5 */ "header not read",
+ /* 6 */ "out of memory",
+ /* 7 */ "RDOFF v1 not supported",
+ /* 8 */ "unknown extended header record",
+ /* 9 */ "header record of known type but unknown length",
+ /* 10 */ "no such segment"
+};
int rdf_errno = 0;
@@ -178,119 +214,120 @@ int rdfopen(rdffile *f, const char *name)
FILE * fp;
fp = fopen(name,"rb");
- if (!fp) return rdf_errno = 1; /* error 1: file open error */
+ if (!fp)
+ return rdf_errno = RDF_ERR_OPEN;
return rdfopenhere(f,fp,NULL,name);
}
int rdfopenhere(rdffile *f, FILE *fp, int *refcount, const char *name)
{
- char buf[8];
- long initpos;
- long l;
- int16 s;
-
- if (translatelong(0x01020304) != 0x01020304)
- { /* fix this to be portable! */
- fputs("*** this program requires a little endian machine\n",stderr);
- fprintf(stderr,"01020304h = %08lxh\n",translatelong(0x01020304));
- exit(3);
- }
-
- f->fp = fp;
- initpos = ftell(fp);
-
- fread(buf,6,1,f->fp); /* read header */
- buf[6] = 0;
-
- if (strcmp(buf,RDOFFId)) {
- fclose(f->fp);
- if (!strcmp(buf,"RDOFF1"))
- return rdf_errno = 7; /* error 7: RDOFF 1 not supported */
- return rdf_errno = 2; /* error 2: invalid file format */
- }
-
- if (fread(&l,1,4,f->fp) != 4 ||
- fread(&f->header_len,1,4,f->fp) != 4) {
- fclose(f->fp);
- return rdf_errno = 3; /* error 3: file read error */
- }
-
- f->header_ofs = ftell(f->fp);
- f->eof_offset = f->header_ofs + translatelong(l) - 4;
-
- if (fseek(f->fp,f->header_len,SEEK_CUR)) {
- fclose(f->fp);
- return rdf_errno = 2; /* seek past end of file...? */
- }
-
- if (fread(&s,1,2,f->fp) != 2) {
- fclose(f->fp);
- return rdf_errno = 3;
- }
-
- f->nsegs = 0;
-
- while (s != 0)
- {
- f->seg[f->nsegs].type = s;
- if (fread(&f->seg[f->nsegs].number,1,2,f->fp) != 2 ||
- fread(&f->seg[f->nsegs].reserved,1,2,f->fp) != 2 ||
- fread(&f->seg[f->nsegs].length,1,4,f->fp) != 4)
- {
- fclose(f->fp);
- return rdf_errno = 3;
- }
-
- f->seg[f->nsegs].offset = ftell(f->fp);
- if (fseek(f->fp,f->seg[f->nsegs].length,SEEK_CUR)) {
- fclose(f->fp);
- return rdf_errno = 2;
- }
- f->nsegs++;
-
- if (fread(&s,1,2,f->fp) != 2) {
- fclose(f->fp);
- return rdf_errno = 3;
- }
- }
-
- if (f->eof_offset != ftell(f->fp) + 8) /* +8 = skip null segment header */
- {
- fprintf(stderr, "warning: eof_offset [%ld] and actual eof offset "
+ char buf[8];
+ long initpos;
+ long l;
+ uint16 s;
+
+ if (translatelong(0x01020304) != 0x01020304) {
+ /* fix this to be portable! */
+ fputs("*** this program requires a little endian machine\n",stderr);
+ fprintf(stderr,"01020304h = %08lxh\n",translatelong(0x01020304));
+ exit(3);
+ }
+
+ f->fp = fp;
+ initpos = ftell(fp);
+
+ fread(buf,6,1,f->fp); /* read header */
+ buf[6] = 0;
+
+ if (strcmp(buf,RDOFFId)) {
+ fclose(f->fp);
+ if (!strcmp(buf,"RDOFF1"))
+ return rdf_errno = RDF_ERR_VER;
+ return rdf_errno = RDF_ERR_FORMAT;
+ }
+
+ if (fread(&l,1,4,f->fp) != 4 || fread(&f->header_len,1,4,f->fp) != 4) {
+ fclose(f->fp);
+ return rdf_errno = RDF_ERR_READ;
+ }
+
+ f->header_ofs = ftell(f->fp);
+ f->eof_offset = f->header_ofs + translatelong(l) - 4;
+
+ if (fseek(f->fp,f->header_len,SEEK_CUR)) {
+ fclose(f->fp);
+ return rdf_errno = RDF_ERR_FORMAT; /* seek past end of file...? */
+ }
+
+ if (fread(&s,1,2,f->fp) != 2) {
+ fclose(f->fp);
+ return rdf_errno = RDF_ERR_READ;
+ }
+
+ f->nsegs = 0;
+
+ while (s != 0) {
+ f->seg[f->nsegs].type = s;
+ if (fread(&f->seg[f->nsegs].number,1,2,f->fp) != 2 ||
+ fread(&f->seg[f->nsegs].reserved,1,2,f->fp) != 2 ||
+ fread(&f->seg[f->nsegs].length,1,4,f->fp) != 4) {
+ fclose(f->fp);
+ return rdf_errno = RDF_ERR_READ;
+ }
+
+ f->seg[f->nsegs].offset = ftell(f->fp);
+ if (fseek(f->fp,f->seg[f->nsegs].length,SEEK_CUR)) {
+ fclose(f->fp);
+ return rdf_errno = RDF_ERR_FORMAT;
+ }
+ f->nsegs++;
+
+ if (fread(&s,1,2,f->fp) != 2) {
+ fclose(f->fp);
+ return rdf_errno = RDF_ERR_READ;
+ }
+ }
+
+ if (f->eof_offset != ftell(f->fp) + 8) { /* +8 = skip null segment header */
+ fprintf(stderr, "warning: eof_offset [%ld] and actual eof offset "
"[%ld] don't match\n", f->eof_offset, ftell(f->fp) + 8);
- }
- fseek(f->fp,initpos,SEEK_SET);
- f->header_loc = NULL;
-
- f->name = newstr(name);
- f->refcount = refcount;
- if (refcount) (*refcount)++;
- return 0;
+ }
+ fseek(f->fp,initpos,SEEK_SET);
+ f->header_loc = NULL;
+
+ f->name = newstr(name);
+ f->refcount = refcount;
+ if (refcount) (*refcount)++;
+ return RDF_OK;
}
int rdfclose(rdffile *f)
{
- if (! f->refcount || ! --(*f->refcount))
- {
- fclose(f->fp);
- f->fp = NULL;
- }
+ if (! f->refcount || ! --(*f->refcount)) {
+ fclose(f->fp);
+ f->fp = NULL;
+ }
free(f->name);
return 0;
}
-void rdfperror(const char *app,const char *name)
+/*
+ * Print the message for last error (from rdf_errno)
+ */
+void rdfperror(const char *app, const char *name)
{
- fprintf(stderr,"%s:%s: %s\n",app,name,rdf_errors[rdf_errno]);
- if (rdf_errno == 1 || rdf_errno == 3)
- {
- perror(app);
- }
-
+ fprintf(stderr,"%s:%s: %s\n",app,name,rdf_errors[rdf_errno]);
+ if (rdf_errno == RDF_ERR_OPEN || rdf_errno == RDF_ERR_READ) {
+ perror(app);
+ }
}
+/*
+ * Find the segment by its number.
+ * Returns segment array index, or -1 if segment with such number was not found.
+ */
int rdffindsegment(rdffile * f, int segno)
{
int i;
@@ -299,36 +336,37 @@ int rdffindsegment(rdffile * f, int segno)
return -1;
}
+/*
+ * Load the segment. Returns status.
+ */
int rdfloadseg(rdffile *f,int segment,void *buffer)
{
- long fpos;
- long slen;
-
- switch(segment) {
- case RDOFF_HEADER:
- fpos = f->header_ofs;
- slen = f->header_len;
- f->header_loc = (byte *)buffer;
- f->header_fp = 0;
- break;
- default:
- if (segment < f->nsegs) {
- fpos = f->seg[segment].offset;
- slen = f->seg[segment].length;
- f->seg[segment].data = (byte *)buffer;
- }
- else {
- return rdf_errno = 10; /* no such segment */
- }
- }
-
- if (fseek(f->fp,fpos,SEEK_SET))
- return rdf_errno = 4;
+ long fpos, slen;
+
+ switch(segment) {
+ case RDOFF_HEADER:
+ fpos = f->header_ofs;
+ slen = f->header_len;
+ f->header_loc = (byte *)buffer;
+ f->header_fp = 0;
+ break;
+ default:
+ if (segment < f->nsegs) {
+ fpos = f->seg[segment].offset;
+ slen = f->seg[segment].length;
+ f->seg[segment].data = (byte *)buffer;
+ } else {
+ return rdf_errno = RDF_ERR_SEGMENT;
+ }
+ }
+
+ if (fseek(f->fp,fpos,SEEK_SET))
+ return rdf_errno = RDF_ERR_UNKNOWN;
- if (fread(buffer,1,slen,f->fp) != slen)
- return rdf_errno = 3;
+ if (fread(buffer,1,slen,f->fp) != slen)
+ return rdf_errno = RDF_ERR_READ;
- return 0;
+ return RDF_OK;
}
/* Macros for reading integers from header in memory */
@@ -347,86 +385,93 @@ int rdfloadseg(rdffile *f,int segment,void *buffer)
#define RS(str,max) { for(i=0;i<max;i++){\
RI8(str[i]); if (!str[i]) break;} str[i]=0; }
+/*
+ * Read a header record.
+ * Returns the address of record, or NULL in case of error.
+ */
rdfheaderrec *rdfgetheaderrec(rdffile *f)
{
- static rdfheaderrec r;
- int i;
-
- if (!f->header_loc) {
- rdf_errno = 5;
- return NULL;
- }
-
- if (f->header_fp >= f->header_len) return 0;
-
- RI8(r.type);
- RI8(r.g.reclen);
-
- switch(r.type) {
- case RDFREC_RELOC: /* Relocation record */
- case RDFREC_SEGRELOC:
- if (r.r.reclen != 8) {
- rdf_errno = 9;
- return NULL;
- }
- RI8(r.r.segment);
- RI32(r.r.offset);
- RI8(r.r.length);
- RI16(r.r.refseg);
- break;
-
- case RDFREC_IMPORT: /* Imported symbol record */
- case RDFREC_FARIMPORT:
- RI8(r.i.flags);
- RI16(r.i.segment);
- RS(r.i.label,32);
- break;
-
- case RDFREC_GLOBAL: /* Exported symbol record */
- RI8(r.e.flags);
- RI8(r.e.segment);
- RI32(r.e.offset);
- RS(r.e.label,32);
- break;
-
- case RDFREC_DLL: /* DLL record */
- RS(r.d.libname,127);
- break;
-
- case RDFREC_BSS: /* BSS reservation record */
- if (r.r.reclen != 4) {
- rdf_errno = 9;
- return NULL;
- }
- RI32(r.b.amount);
- break;
-
- case RDFREC_MODNAME: /* Module name record */
- RS(r.m.modname,127);
- break;
-
- case RDFREC_COMMON: /* Common variable */
- RI16(r.c.segment);
- RI32(r.c.size);
- RI16(r.c.align);
- RS(r.c.label,32);
- break;
+ static rdfheaderrec r;
+ int i;
+
+ if (!f->header_loc) {
+ rdf_errno = RDF_ERR_HEADER;
+ return NULL;
+ }
+
+ if (f->header_fp >= f->header_len) return 0;
+
+ RI8(r.type);
+ RI8(r.g.reclen);
+
+ switch(r.type) {
+ case RDFREC_RELOC: /* Relocation record */
+ case RDFREC_SEGRELOC:
+ if (r.r.reclen != 8) {
+ rdf_errno = RDF_ERR_RECLEN;
+ return NULL;
+ }
+ RI8(r.r.segment);
+ RI32(r.r.offset);
+ RI8(r.r.length);
+ RI16(r.r.refseg);
+ break;
+
+ case RDFREC_IMPORT: /* Imported symbol record */
+ case RDFREC_FARIMPORT:
+ RI8(r.i.flags);
+ RI16(r.i.segment);
+ RS(r.i.label, EXIM_LABEL_MAX);
+ break;
+
+ case RDFREC_GLOBAL: /* Exported symbol record */
+ RI8(r.e.flags);
+ RI8(r.e.segment);
+ RI32(r.e.offset);
+ RS(r.e.label, EXIM_LABEL_MAX);
+ break;
+
+ case RDFREC_DLL: /* DLL record */
+ RS(r.d.libname, MODLIB_NAME_MAX);
+ break;
+
+ case RDFREC_BSS: /* BSS reservation record */
+ if (r.r.reclen != 4) {
+ rdf_errno = RDF_ERR_RECLEN;
+ return NULL;
+ }
+ RI32(r.b.amount);
+ break;
+
+ case RDFREC_MODNAME: /* Module name record */
+ RS(r.m.modname, MODLIB_NAME_MAX);
+ break;
+
+ case RDFREC_COMMON: /* Common variable */
+ RI16(r.c.segment);
+ RI32(r.c.size);
+ RI16(r.c.align);
+ RS(r.c.label, EXIM_LABEL_MAX);
+ break;
- default:
+ default:
#ifdef STRICT_ERRORS
- rdf_errno = 8; /* unknown header record */
- return NULL;
+ rdf_errno = RDF_ERR_RECTYPE; /* unknown header record */
+ return NULL;
#else
- for (i = 0; i < r.g.reclen; i++)
- RI8(r.g.data[i]);
+ for (i = 0; i < r.g.reclen; i++)
+ RI8(r.g.data[i]);
#endif
- }
- return &r;
+ }
+ return &r;
}
-
+
+/*
+ * Rewind to the beginning of the file
+ */
void rdfheaderrewind(rdffile *f)
{
- f->header_fp = 0;
+ f->header_fp = 0;
}
@@ -450,8 +495,7 @@ int rdfaddheader(rdf_headerbuf * h, rdfheaderrec * r)
membufwrite(h->buf,&r->type,1);
membufwrite(h->buf,&r->g.reclen,1);
- switch (r->type)
- {
+ switch (r->type) {
case RDFREC_GENERIC: /* generic */
membufwrite(h->buf, &r->g.data, r->g.reclen);
break;
@@ -491,7 +535,7 @@ int rdfaddheader(rdf_headerbuf * h, rdfheaderrec * r)
default:
#ifdef STRICT_ERRORS
- return (rdf_errno = 8);
+ return rdf_errno = RDF_ERR_RECTYPE;
#else
for (i = 0; i < r->g.reclen; i++)
membufwrite(h->buf, r->g.data[i], 1);
@@ -530,4 +574,3 @@ void rdfdoneheader(rdf_headerbuf * h)
freemembuf(h->buf);
free(h);
}
-
diff --git a/rdoff/rdoff.h b/rdoff/rdoff.h
index c6957dce..dd431263 100644
--- a/rdoff/rdoff.h
+++ b/rdoff/rdoff.h
@@ -1,4 +1,5 @@
-/* rdoff.h RDOFF Object File manipulation routines header file
+/*
+ * rdoff.h RDOFF Object File manipulation routines header file
*
* The Netwide Assembler is copyright (C) 1996 Simon Tatham and
* Julian Hall. All rights reserved. The software is
@@ -11,17 +12,37 @@
*/
#ifndef _RDOFF_H
-#define _RDOFF_H "RDOFF2 support routines v0.3"
+#define _RDOFF_H
-/* Some systems don't define this automatically */
-extern char *strdup(const char *);
+/*
+ * RDOFF definitions. They are used by RDOFF utilities and by NASM's
+ * 'outrdf2.c' output module.
+ */
-typedef unsigned short int16;
+/* Type definitions */
+typedef unsigned long uint32;
+typedef unsigned short uint16;
typedef unsigned char byte;
+typedef unsigned int bool;
+
+/* RDOFF format revision (currently used only when printing the version) */
+#define RDOFF2_REVISION "0.6.1"
+
+/* RDOFF2 file signature */
+#define RDOFF2_SIGNATURE "RDOFF2"
+
+/* Maximum size of an import/export label (including trailing zero) */
+#define EXIM_LABEL_MAX 64
-#define RDF_MAXSEGS 64
+/* Maximum size of library or module name (including trailing zero) */
+#define MODLIB_NAME_MAX 128
-/* the records that can be found in the RDOFF header */
+/* Maximum number of segments that we can handle in one file */
+#define RDF_MAXSEGS 64
+
+
+/* Record types that may present the RDOFF header */
+#define RDFREC_GENERIC 0
#define RDFREC_RELOC 1
#define RDFREC_IMPORT 2
#define RDFREC_GLOBAL 3
@@ -31,8 +52,21 @@ typedef unsigned char byte;
#define RDFREC_FARIMPORT 7
#define RDFREC_MODNAME 8
#define RDFREC_COMMON 10
-#define RDFREC_GENERIC 0
+
+/*
+ * Generic record - contains the type and length field, plus a 128 byte
+ * char array 'data'
+ */
+struct GenericRec {
+ byte type;
+ byte reclen;
+ char data[128];
+};
+
+/*
+ * Relocation record
+ */
struct RelocRec {
byte type; /* must be 1 */
byte reclen; /* content length */
@@ -41,55 +75,73 @@ struct RelocRec {
reloc @ loadtime, only linkage) */
long offset; /* from start of segment in which reference is loc'd */
byte length; /* 1 2 or 4 bytes */
- int16 refseg; /* segment to which reference refers to */
+ uint16 refseg; /* segment to which reference refers to */
};
+/*
+ * Extern/import record
+ */
struct ImportRec {
byte type; /* must be 2 */
byte reclen; /* content length */
byte flags; /* SYM_* flags (see below) */
- int16 segment; /* segment number allocated to the label for reloc
+ uint16 segment; /* segment number allocated to the label for reloc
records - label is assumed to be at offset zero
in this segment, so linker must fix up with offset
of segment and of offset within segment */
- char label[33]; /* zero terminated... should be written to file until
- the zero, but not after it - max len = 32 chars */
+ char label[EXIM_LABEL_MAX]; /* zero terminated, should be written to file
+ until the zero, but not after it */
};
+/*
+ * Public/export record
+ */
struct ExportRec {
byte type; /* must be 3 */
byte reclen; /* content length */
byte flags; /* SYM_* flags (see below) */
byte segment; /* segment referred to (0/1/2) */
long offset; /* offset within segment */
- char label[33]; /* zero terminated as above. max len = 32 chars */
+ char label[EXIM_LABEL_MAX]; /* zero terminated as in import */
};
+/*
+ * DLL record
+ */
struct DLLRec {
byte type; /* must be 4 */
byte reclen; /* content length */
- char libname[128]; /* name of library to link with at load time */
+ char libname[MODLIB_NAME_MAX]; /* name of library to link with at load time */
};
+/*
+ * BSS record
+ */
struct BSSRec {
byte type; /* must be 5 */
- byte reclen; /* content length */
+ byte reclen; /* content length */
long amount; /* number of bytes BSS to reserve */
};
+/*
+ * Module name record
+ */
struct ModRec {
byte type; /* must be 8 */
byte reclen; /* content length */
- char modname[128]; /* module name */
+ char modname[MODLIB_NAME_MAX]; /* module name */
};
+/*
+ * Common variable record
+ */
struct CommonRec {
byte type; /* must be 10 */
byte reclen; /* equals 7+label length */
- int16 segment; /* segment number */
+ uint16 segment; /* segment number */
long size; /* size of common variable */
- int16 align; /* alignment (power of two) */
- char label[33]; /* zero terminated as above. max len = 32 chars */
+ uint16 align; /* alignment (power of two) */
+ char label[EXIM_LABEL_MAX]; /* zero terminated as in import */
};
/* Flags for ExportRec */
@@ -98,15 +150,13 @@ struct CommonRec {
#define SYM_GLOBAL 4
#define SYM_IMPORT 8
-/*
- * GenericRec - contains the type and length field, plus a 128 byte
- * char array 'data'
- */
-struct GenericRec {
- byte type;
- byte reclen;
- char data[128];
-};
+
+/*** The following part is used only by the utilities *************************/
+
+#ifdef RDOFF_UTILS
+
+/* Some systems don't define this automatically */
+extern char *strdup(const char *);
typedef union RDFHeaderRec {
char type; /* invariant throughout all below */
@@ -122,9 +172,9 @@ typedef union RDFHeaderRec {
struct SegmentHeaderRec {
/* information from file */
- int16 type;
- int16 number;
- int16 reserved;
+ uint16 type;
+ uint16 number;
+ uint16 reserved;
long length;
/* information built up here */
@@ -133,30 +183,30 @@ struct SegmentHeaderRec {
};
typedef struct RDFFileInfo {
- FILE *fp; /* file descriptor; must be open to use this struct */
- int rdoff_ver; /* should be 1; any higher => not guaranteed to work */
- long header_len;
- long header_ofs;
+ FILE *fp; /* file descriptor; must be open to use this struct */
+ int rdoff_ver; /* should be 1; any higher => not guaranteed to work */
+ long header_len;
+ long header_ofs;
- byte *header_loc; /* keep location of header */
- long header_fp; /* current location within header for reading */
+ byte *header_loc; /* keep location of header */
+ long header_fp; /* current location within header for reading */
- struct SegmentHeaderRec seg[RDF_MAXSEGS];
- int nsegs;
+ struct SegmentHeaderRec seg[RDF_MAXSEGS];
+ int nsegs;
- long eof_offset; /* offset of the first byte beyond the end of this
+ long eof_offset; /* offset of the first byte beyond the end of this
module */
- char *name; /* name of module in libraries */
- int *refcount; /* pointer to reference count on file, or NULL */
+ char *name; /* name of module in libraries */
+ int *refcount; /* pointer to reference count on file, or NULL */
} rdffile;
#define BUF_BLOCK_LEN 4088 /* selected to match page size (4096)
* on 80x86 machines for efficiency */
typedef struct memorybuffer {
- int length;
- byte buffer[BUF_BLOCK_LEN];
- struct memorybuffer *next;
+ int length;
+ byte buffer[BUF_BLOCK_LEN];
+ struct memorybuffer *next;
} memorybuffer;
typedef struct {
@@ -166,9 +216,9 @@ typedef struct {
} rdf_headerbuf;
/* segments used by RDOFF, understood by rdoffloadseg */
-#define RDOFF_CODE 0
-#define RDOFF_DATA 1
-#define RDOFF_HEADER -1
+#define RDOFF_CODE 0
+#define RDOFF_DATA 1
+#define RDOFF_HEADER -1
/* mask for 'segment' in relocation records to find if relative relocation */
#define RDOFF_RELATIVEMASK 64
/* mask to find actual segment value in relocation records */
@@ -176,9 +226,25 @@ typedef struct {
extern int rdf_errno;
+/* rdf_errno can hold these error codes */
+enum {
+ /* 0 */ RDF_OK,
+ /* 1 */ RDF_ERR_OPEN,
+ /* 2 */ RDF_ERR_FORMAT,
+ /* 3 */ RDF_ERR_READ,
+ /* 4 */ RDF_ERR_UNKNOWN,
+ /* 5 */ RDF_ERR_HEADER,
+ /* 6 */ RDF_ERR_NOMEM,
+ /* 7 */ RDF_ERR_VER,
+ /* 8 */ RDF_ERR_RECTYPE,
+ /* 9 */ RDF_ERR_RECLEN,
+ /* 10 */ RDF_ERR_SEGMENT
+};
+
/* utility functions */
-int16 translateshort(int16 in);
long translatelong(long in);
+uint16 translateshort(uint16 in);
+char *translatesegmenttype(uint16 type);
/* RDOFF file manipulation functions */
int rdfopen(rdffile *f,const char *name);
@@ -203,4 +269,6 @@ int rdfaddsegment(rdf_headerbuf *h, long seglength);
int rdfwriteheader(FILE *fp,rdf_headerbuf *h);
void rdfdoneheader(rdf_headerbuf *h);
+#endif /* RDOFF_UTILS */
+
#endif /* _RDOFF_H */
diff --git a/rdoff/rdx.c b/rdoff/rdx.c
index 5a3058db..778b29fa 100644
--- a/rdoff/rdx.c
+++ b/rdoff/rdx.c
@@ -16,7 +16,6 @@
#include <stdlib.h>
#include "rdfload.h"
-#include "rdoff.h"
#include "symtab.h"
typedef int (*main_fn) (int,char**); /* Main function prototype */
@@ -27,16 +26,14 @@ int main(int argc, char **argv)
main_fn code;
symtabEnt * s;
- if (argc < 2)
- {
+ if (argc < 2) {
puts("usage: rdx <rdoff-executable> [params]\n");
exit(255);
}
m = rdfload(argv[1]);
- if (! m)
- {
+ if (! m) {
rdfperror("rdx",argv[1]);
exit(255);
}
@@ -46,8 +43,7 @@ int main(int argc, char **argv)
in other cases... */
s = symtabFind(m->symtab, "_main");
- if (! s)
- {
+ if (! s) {
fprintf(stderr,"rdx: could not find symbol '_main' in '%s'\n",argv[1]);
exit(255);
}
@@ -58,4 +54,3 @@ int main(int argc, char **argv)
return code(argc,argv); /* execute */
}
-
diff --git a/rdoff/segtab.h b/rdoff/segtab.h
index b5d96fa1..7e8e1937 100644
--- a/rdoff/segtab.h
+++ b/rdoff/segtab.h
@@ -4,4 +4,3 @@ void init_seglocations(segtab * r);
void add_seglocation(segtab * r, int localseg, int destseg, long offset);
int get_seglocation(segtab * r, int localseg, int * destseg, long * offset);
void done_seglocations(segtab * r);
-