Initial revision
This commit is contained in:
237
modules/src/object/rd.c
Normal file
237
modules/src/object/rd.c
Normal file
@@ -0,0 +1,237 @@
|
||||
#include <out.h>
|
||||
#include "object.h"
|
||||
|
||||
extern long lseek();
|
||||
|
||||
/*
|
||||
* Parts of the output file.
|
||||
*/
|
||||
#define PARTEMIT 0
|
||||
#define PARTRELO 1
|
||||
#define PARTNAME 2
|
||||
#define PARTCHAR 3
|
||||
#ifdef SYMDBUG
|
||||
#define PARTDBUG 4
|
||||
#else
|
||||
#define PARTDBUG 3
|
||||
#define NPARTS (PARTDBUG + 1)
|
||||
|
||||
static long offset[MAXSECT];
|
||||
|
||||
static int outfile;
|
||||
static long outseek[NPARTS];
|
||||
static long currpos;
|
||||
static long rd_base;
|
||||
#define OUTSECT(i) \
|
||||
(outseek[PARTEMIT] = offset[i])
|
||||
#define BEGINSEEK(p, o) \
|
||||
(outseek[(p)] = (o))
|
||||
|
||||
static int sectionnr;
|
||||
|
||||
static
|
||||
OUTREAD(p, b, n)
|
||||
char *b;
|
||||
long n;
|
||||
{
|
||||
register long l = outseek[p];
|
||||
|
||||
if (currpos != l) {
|
||||
lseek(outfile, l, 0);
|
||||
}
|
||||
rd_bytes(outfile, b, n);
|
||||
l += n;
|
||||
currpos = l;
|
||||
outseek[p] = l;
|
||||
}
|
||||
|
||||
/*
|
||||
* Open the output file according to the chosen strategy.
|
||||
*/
|
||||
int
|
||||
rd_open(f)
|
||||
char *f;
|
||||
{
|
||||
|
||||
if ((outfile = open(f, 0)) < 0)
|
||||
return 0;
|
||||
return rd_fdopen(outfile);
|
||||
}
|
||||
|
||||
static int offcnt;
|
||||
|
||||
rd_fdopen(fd)
|
||||
{
|
||||
register int i;
|
||||
|
||||
for (i = 0; i < NPARTS; i++) outseek[i] = 0;
|
||||
offcnt = 0;
|
||||
rd_base = lseek(fd, 0L, 1);
|
||||
if (rd_base < 0) {
|
||||
return 0;
|
||||
}
|
||||
currpos = rd_base;
|
||||
outseek[PARTEMIT] = currpos;
|
||||
outfile = fd;
|
||||
sectionnr = 0;
|
||||
return 1;
|
||||
}
|
||||
|
||||
rd_close()
|
||||
{
|
||||
|
||||
close(outfile);
|
||||
}
|
||||
|
||||
rd_ohead(head)
|
||||
register struct outhead *head;
|
||||
{
|
||||
register long off;
|
||||
|
||||
OUTREAD(PARTEMIT, (char *) head, (long) SZ_HEAD);
|
||||
#if ! (BYTES_REVERSED || WORDS_REVERSED)
|
||||
if (sizeof(struct outhead) != SZ_HEAD)
|
||||
#endif
|
||||
{
|
||||
register char *c = (char *) head + (SZ_HEAD-4);
|
||||
|
||||
head->oh_nchar = get4(c);
|
||||
c -= 4; head->oh_nemit = get4(c);
|
||||
c -= 2; head->oh_nname = uget2(c);
|
||||
c -= 2; head->oh_nrelo = uget2(c);
|
||||
c -= 2; head->oh_nsect = uget2(c);
|
||||
c -= 2; head->oh_flags = uget2(c);
|
||||
c -= 2; head->oh_stamp = uget2(c);
|
||||
c -= 2; head->oh_magic = uget2(c);
|
||||
}
|
||||
off = OFF_RELO(*head) + rd_base;
|
||||
BEGINSEEK(PARTRELO, off);
|
||||
off += (long) head->oh_nrelo * SZ_RELO;
|
||||
BEGINSEEK(PARTNAME, off);
|
||||
off += (long) head->oh_nname * SZ_NAME;
|
||||
BEGINSEEK(PARTCHAR, off);
|
||||
#ifdef SYMDBUG
|
||||
off += head->oh_nchar;
|
||||
BEGINSEEK(PARTDBUG, off);
|
||||
#endif
|
||||
}
|
||||
|
||||
rd_rew_relos(head)
|
||||
register struct outhead *head;
|
||||
{
|
||||
register long off = OFF_RELO(*head) + rd_base;
|
||||
|
||||
BEGINSEEK(PARTRELO, off);
|
||||
}
|
||||
|
||||
rd_sect(sect, cnt)
|
||||
register struct outsect *sect;
|
||||
register unsigned int cnt;
|
||||
{
|
||||
register char *c = (char *) sect + cnt * SZ_SECT;
|
||||
|
||||
OUTREAD(PARTEMIT, (char *) sect, (long)cnt * SZ_SECT);
|
||||
sect += cnt;
|
||||
offcnt += cnt;
|
||||
while (cnt--) {
|
||||
sect--;
|
||||
#if ! (BYTES_REVERSED || WORDS_REVERSED)
|
||||
if (sizeof(struct outsect) != SZ_SECT) {
|
||||
#endif
|
||||
c -= 4; sect->os_lign = get4(c);
|
||||
c -= 4; sect->os_flen = get4(c);
|
||||
c -= 4; sect->os_foff = get4(c);
|
||||
#if ! (BYTES_REVERSED || WORDS_REVERSED)
|
||||
}
|
||||
#endif
|
||||
offset[--offcnt] = sect->os_foff + rd_base;
|
||||
#if ! (BYTES_REVERSED || WORDS_REVERSED)
|
||||
if (sizeof(struct outsect) != SZ_SECT) {
|
||||
#endif
|
||||
c -= 4; sect->os_size = get4(c);
|
||||
c -= 4; sect->os_base = get4(c);
|
||||
#if ! (BYTES_REVERSED || WORDS_REVERSED)
|
||||
}
|
||||
#endif
|
||||
}
|
||||
}
|
||||
|
||||
rd_outsect(s)
|
||||
{
|
||||
OUTSECT(s);
|
||||
sectionnr = s;
|
||||
}
|
||||
|
||||
/*
|
||||
* We don't have to worry about byte order here.
|
||||
*/
|
||||
rd_emit(emit, cnt)
|
||||
char *emit;
|
||||
long cnt;
|
||||
{
|
||||
OUTREAD(PARTEMIT, emit, cnt);
|
||||
offset[sectionnr] += cnt;
|
||||
}
|
||||
|
||||
rd_relo(relo, cnt)
|
||||
register struct outrelo *relo;
|
||||
register unsigned int cnt;
|
||||
{
|
||||
|
||||
OUTREAD(PARTRELO, (char *) relo, (long) cnt * SZ_RELO);
|
||||
#if ! (BYTES_REVERSED || WORDS_REVERSED)
|
||||
if (sizeof(struct outrelo) != SZ_RELO)
|
||||
#endif
|
||||
{
|
||||
register char *c = (char *) relo + (long) cnt * SZ_RELO;
|
||||
|
||||
relo += cnt;
|
||||
while (cnt--) {
|
||||
relo--;
|
||||
c -= 4; relo->or_addr = get4(c);
|
||||
c -= 2; relo->or_nami = uget2(c);
|
||||
relo->or_sect = *--c;
|
||||
relo->or_type = *--c;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
rd_name(name, cnt)
|
||||
register struct outname *name;
|
||||
register unsigned int cnt;
|
||||
{
|
||||
|
||||
OUTREAD(PARTNAME, (char *) name, (long) cnt * SZ_NAME);
|
||||
#if ! (BYTES_REVERSED || WORDS_REVERSED)
|
||||
if (sizeof(struct outname) != SZ_NAME)
|
||||
#endif
|
||||
{
|
||||
register char *c = (char *) name + (long) cnt * SZ_NAME;
|
||||
|
||||
name += cnt;
|
||||
while (cnt--) {
|
||||
name--;
|
||||
c -= 4; name->on_valu = get4(c);
|
||||
c -= 2; name->on_desc = uget2(c);
|
||||
c -= 2; name->on_type = uget2(c);
|
||||
c -= 4; name->on_foff = get4(c);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
rd_string(addr, len)
|
||||
char *addr;
|
||||
long len;
|
||||
{
|
||||
|
||||
OUTREAD(PARTCHAR, addr, len);
|
||||
}
|
||||
|
||||
#ifdef SYMDBUG
|
||||
rd_dbug(buf, size)
|
||||
char *buf;
|
||||
long size;
|
||||
{
|
||||
OUTREAD(PARTDBUG, buf, size);
|
||||
}
|
||||
#endif
|
||||
Reference in New Issue
Block a user