+ ANSI C conversion
This commit is contained in:
parent
0df5d2f50b
commit
75909230c9
403
util/ass/ass00.c
403
util/ass/ass00.c
|
@ -1,5 +1,10 @@
|
||||||
|
#include <string.h>
|
||||||
|
#include <stddef.h>
|
||||||
#include "ass00.h"
|
#include "ass00.h"
|
||||||
#include "assex.h"
|
#include "assex.h"
|
||||||
|
#include "assci.h"
|
||||||
|
#include "asscm.h"
|
||||||
|
#include "assrl.h"
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* (c) copyright 1987 by the Vrije Universiteit, Amsterdam, The Netherlands.
|
* (c) copyright 1987 by the Vrije Universiteit, Amsterdam, The Netherlands.
|
||||||
|
@ -7,17 +12,34 @@
|
||||||
*
|
*
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#ifndef NORCSID
|
char oflag;
|
||||||
static char rcs_id[] = "$Id$" ;
|
static int memflg;
|
||||||
#endif
|
|
||||||
|
/* Forward declarations. */
|
||||||
|
static siz_t* getsizes(char *);
|
||||||
|
static void getcore(void);
|
||||||
|
static void argument(char *);
|
||||||
|
static void flags(char *);
|
||||||
|
static void skipentry(void);
|
||||||
|
static void enmd_pro(void);
|
||||||
|
static void enmd_glo(void);
|
||||||
|
static void archive(void);
|
||||||
|
static void finish_up(void);
|
||||||
|
static void check_def(void);
|
||||||
|
|
||||||
|
static void c_print(void);
|
||||||
|
static void c_dprint(char *, char*);
|
||||||
|
|
||||||
|
/* External definitions */
|
||||||
|
void pass_3(void);
|
||||||
|
void pass_4(void);
|
||||||
|
void pass_5(void);
|
||||||
|
|
||||||
/*
|
/*
|
||||||
** Main routine of EM1-assembler/loader
|
** Main routine of EM1-assembler/loader
|
||||||
*/
|
*/
|
||||||
|
|
||||||
main(argc, argv)
|
int main(int argc, char **argv)
|
||||||
int argc;
|
|
||||||
char **argv;
|
|
||||||
{
|
{
|
||||||
/*
|
/*
|
||||||
* Usage: ass [-[d][p][m][u][U]] [-s(s/m/l/x)] [ [file] [flag] ] ...
|
* Usage: ass [-[d][p][m][u][U]] [-s(s/m/l/x)] [ [file] [flag] ] ...
|
||||||
|
@ -29,10 +51,14 @@ main(argc, argv)
|
||||||
register int argno;
|
register int argno;
|
||||||
|
|
||||||
progname = argv[0];
|
progname = argv[0];
|
||||||
for ( cp=argv[0] ; *cp ; ) if ( *cp++ == '/' ) progname= cp;
|
for (cp = argv[0]; *cp;)
|
||||||
for ( argno=1 ; argno<argc ; argno++ ) {
|
if (*cp++ == '/')
|
||||||
if ( argv[argno][0] == '-' && LC(argv[argno][1]) == 's') {
|
progname = cp;
|
||||||
getsizes(&argv[argno][2]);
|
for (argno = 1; argno < argc; argno++)
|
||||||
|
{
|
||||||
|
if (argv[argno][0] == '-' && LC(argv[argno][1]) == 's')
|
||||||
|
{
|
||||||
|
oursize = getsizes(&argv[argno][2]);
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -48,7 +74,8 @@ main(argc, argv)
|
||||||
exit(nerrors != 0);
|
exit(nerrors != 0);
|
||||||
}
|
}
|
||||||
|
|
||||||
getcore() {
|
static void getcore(void)
|
||||||
|
{
|
||||||
register siz_t *p;
|
register siz_t *p;
|
||||||
siz_t bytes;
|
siz_t bytes;
|
||||||
register unsigned n;
|
register unsigned n;
|
||||||
|
@ -58,125 +85,177 @@ getcore() {
|
||||||
* xglobs[] should be located in front of mglobs[], see upd_reloc()
|
* xglobs[] should be located in front of mglobs[], see upd_reloc()
|
||||||
*/
|
*/
|
||||||
|
|
||||||
p = oursize; n = 0;
|
p = oursize;
|
||||||
|
n = 0;
|
||||||
n += (bytes.n_glab = p->n_glab * (sizeof *xglobs));
|
n += (bytes.n_glab = p->n_glab * (sizeof *xglobs));
|
||||||
n += (bytes.n_mlab = p->n_mlab * (sizeof *mglobs));
|
n += (bytes.n_mlab = p->n_mlab * (sizeof *mglobs));
|
||||||
n += (bytes.n_mproc = p->n_mproc * (sizeof *mprocs));
|
n += (bytes.n_mproc = p->n_mproc * (sizeof *mprocs));
|
||||||
n += (bytes.n_xproc = p->n_xproc * (sizeof *xprocs));
|
n += (bytes.n_xproc = p->n_xproc * (sizeof *xprocs));
|
||||||
n += (bytes.n_proc = p->n_proc * (sizeof *proctab));
|
n += (bytes.n_proc = p->n_proc * (sizeof *proctab));
|
||||||
base = getarea(n);
|
base = getarea(n);
|
||||||
zero(base,n);
|
memset(base, 0, n);
|
||||||
xglobs = gbp_cast base; base += bytes.n_glab;
|
xglobs = gbp_cast base;
|
||||||
mglobs = gbp_cast base; base += bytes.n_mlab;
|
base += bytes.n_glab;
|
||||||
mprocs = prp_cast base; base += bytes.n_mproc;
|
mglobs = gbp_cast base;
|
||||||
xprocs = prp_cast base; base += bytes.n_xproc;
|
base += bytes.n_mlab;
|
||||||
proctab = ptp_cast base; base += bytes.n_proc;
|
mprocs = prp_cast base;
|
||||||
|
base += bytes.n_mproc;
|
||||||
|
xprocs = prp_cast base;
|
||||||
|
base += bytes.n_xproc;
|
||||||
|
proctab = ptp_cast base;
|
||||||
|
base += bytes.n_proc;
|
||||||
}
|
}
|
||||||
|
|
||||||
getsizes(str) char *str; {
|
static siz_t* getsizes(char *str)
|
||||||
|
{
|
||||||
/*
|
/*
|
||||||
* accepts -ss (small), -sm (medium), -sl (large), -sx (extra large)
|
* accepts -ss (small), -sm (medium), -sl (large), -sx (extra large)
|
||||||
*/
|
*/
|
||||||
|
|
||||||
switch(LC(*str)) {
|
switch (LC(*str))
|
||||||
default:error("bad size option %s",str);
|
{
|
||||||
case 's': oursize = &sizes[0]; break;
|
default:
|
||||||
case 'm': oursize = &sizes[1]; break;
|
error("bad size option %s", str);
|
||||||
case 'l': oursize = &sizes[2]; break;
|
case 's':
|
||||||
case 'x': oursize = &sizes[3]; break;
|
return &sizes[0];
|
||||||
|
break;
|
||||||
|
case 'm':
|
||||||
|
return &sizes[1];
|
||||||
|
break;
|
||||||
|
case 'l':
|
||||||
|
return &sizes[2];
|
||||||
|
break;
|
||||||
|
case 'x':
|
||||||
|
return &sizes[3];
|
||||||
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
char oflag;
|
|
||||||
|
|
||||||
argument(arg) char *arg; {
|
|
||||||
register w;
|
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* This routine decides what to do with each argument.
|
* This routine decides what to do with each argument.
|
||||||
* It recognises flags and modules.
|
* It recognises flags and modules.
|
||||||
* Furthermore, it knows a library when it sees it and
|
* Furthermore, it knows a library when it sees it and
|
||||||
* call archive() to split it apart.
|
* call archive() to split it apart.
|
||||||
*/
|
*/
|
||||||
|
static void argument(char *arg)
|
||||||
|
{
|
||||||
|
register int w;
|
||||||
|
|
||||||
if (oflag) {
|
if (oflag)
|
||||||
|
{
|
||||||
eout = arg;
|
eout = arg;
|
||||||
oflag = 0;
|
oflag = 0;
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
if(*arg == '-') {
|
if (*arg == '-')
|
||||||
|
{
|
||||||
flags(arg);
|
flags(arg);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
curfile = arg; /* for error messages etc. */
|
curfile = arg; /* for error messages etc. */
|
||||||
if ((ifile = fopen(arg,"r")) == 0) {
|
if ((ifile = fopen(arg, "r")) == NULL)
|
||||||
|
{
|
||||||
error("can't open %s", arg);
|
error("can't open %s", arg);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
inpoff = 2;
|
inpoff = 2;
|
||||||
if ((w = getu16()) == sp_magic)
|
if ((w = getu16()) == sp_magic)
|
||||||
read_compact();
|
read_compact();
|
||||||
else if (w == ARMAG || w == AALMAG) {
|
else if (w == ARMAG || w == AALMAG)
|
||||||
|
{
|
||||||
archmode = TRUE;
|
archmode = TRUE;
|
||||||
archive();
|
archive();
|
||||||
archmode = FALSE;
|
archmode = FALSE;
|
||||||
} else
|
}
|
||||||
|
else
|
||||||
error("%s: bad format", arg);
|
error("%s: bad format", arg);
|
||||||
if (fclose(ifile) == EOF)
|
if (fclose(ifile) == EOF)
|
||||||
;
|
{
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
** process flag arguments
|
** process flag arguments
|
||||||
*/
|
*/
|
||||||
|
static void flags(char *arg)
|
||||||
static int memflg ;
|
|
||||||
|
|
||||||
flags(arg)
|
|
||||||
char *arg;
|
|
||||||
{
|
{
|
||||||
register char *argp;
|
register char *argp;
|
||||||
register on;
|
register int on;
|
||||||
|
|
||||||
argp = arg;
|
argp = arg;
|
||||||
while (*++argp)
|
while (*++argp)
|
||||||
{
|
{
|
||||||
switch (LC(*argp))
|
switch (LC(*argp))
|
||||||
{
|
{
|
||||||
case 'd': d_flag++;break;
|
case 'd':
|
||||||
case 'r': r_flag++;break;
|
d_flag++;
|
||||||
case 's': return ; /* s-flag is already scanned */
|
break;
|
||||||
|
case 'r':
|
||||||
|
r_flag++;
|
||||||
|
break;
|
||||||
|
case 's':
|
||||||
|
return; /* s-flag is already scanned */
|
||||||
#ifdef MEMUSE
|
#ifdef MEMUSE
|
||||||
case 'm': memflg++ ; break ;
|
case 'm':
|
||||||
|
memflg++;
|
||||||
|
break;
|
||||||
#endif
|
#endif
|
||||||
case 'p': ++procflag;break;
|
case 'p':
|
||||||
|
++procflag;
|
||||||
|
break;
|
||||||
#ifdef DUMP
|
#ifdef DUMP
|
||||||
case 'u': ++c_flag;break;
|
case 'u':
|
||||||
|
++c_flag;
|
||||||
|
break;
|
||||||
#endif
|
#endif
|
||||||
case 'o': ++oflag; break;
|
case 'o':
|
||||||
case 'w': ++wflag; break;
|
++oflag;
|
||||||
|
break;
|
||||||
|
case 'w':
|
||||||
|
++wflag;
|
||||||
|
break;
|
||||||
#ifdef JOHAN
|
#ifdef JOHAN
|
||||||
case 'j': ++jflag; break;
|
case 'j':
|
||||||
|
++jflag;
|
||||||
|
break;
|
||||||
#endif
|
#endif
|
||||||
case 'U': ++Uflag; break;
|
case 'U':
|
||||||
|
++Uflag;
|
||||||
|
break;
|
||||||
case '-':
|
case '-':
|
||||||
case '+':
|
case '+':
|
||||||
on = (*argp == '+');
|
on = (*argp == '+');
|
||||||
while (*++argp) switch(LC(*argp)) {
|
while (*++argp)
|
||||||
case 't': if (on) intflags |= 01;
|
switch (LC(*argp))
|
||||||
else intflags &= ~01;
|
{
|
||||||
|
case 't':
|
||||||
|
if (on)
|
||||||
|
intflags |= 01;
|
||||||
|
else
|
||||||
|
intflags &= ~01;
|
||||||
break;
|
break;
|
||||||
case 'p': if (on) intflags |= 02;
|
case 'p':
|
||||||
else intflags &= ~02;
|
if (on)
|
||||||
|
intflags |= 02;
|
||||||
|
else
|
||||||
|
intflags &= ~02;
|
||||||
break;
|
break;
|
||||||
case 'f': if (on) intflags |= 04;
|
case 'f':
|
||||||
else intflags &= ~04;
|
if (on)
|
||||||
|
intflags |= 04;
|
||||||
|
else
|
||||||
|
intflags &= ~04;
|
||||||
break;
|
break;
|
||||||
case 'c': if (on) intflags |= 010;
|
case 'c':
|
||||||
else intflags &= ~010;
|
if (on)
|
||||||
case 'e': if (on) intflags |= 040;
|
intflags |= 010;
|
||||||
else intflags &= ~040;
|
else
|
||||||
|
intflags &= ~010;
|
||||||
|
case 'e':
|
||||||
|
if (on)
|
||||||
|
intflags |= 040;
|
||||||
|
else
|
||||||
|
intflags &= ~040;
|
||||||
break;
|
break;
|
||||||
default:
|
default:
|
||||||
error("bad interpreter option %s", argp);
|
error("bad interpreter option %s", argp);
|
||||||
|
@ -190,22 +269,32 @@ flags(arg)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
do_proc() {
|
void do_proc(void)
|
||||||
|
{
|
||||||
/* One procedure has been read and will be processed.
|
/* One procedure has been read and will be processed.
|
||||||
*
|
*
|
||||||
* NOTE: The numbers of the passes, 1 3 4 and 5, are a remainder
|
* NOTE: The numbers of the passes, 1 3 4 and 5, are a remainder
|
||||||
* of ancient times.
|
* of ancient times.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
dump(1); if ( memflg>2 )memuse();
|
dump(1);
|
||||||
pass_3(); dump(3);
|
if (memflg > 2)
|
||||||
pass_4(); dump(4);
|
memuse();
|
||||||
pass_5(); if ( memflg>2 ) memuse() ;
|
pass_3();
|
||||||
endproc(); if ( memflg>1 ) memuse() ;
|
dump(3);
|
||||||
|
pass_4();
|
||||||
|
dump(4);
|
||||||
|
pass_5();
|
||||||
|
if (memflg > 2)
|
||||||
|
memuse();
|
||||||
|
endproc();
|
||||||
|
if (memflg > 1)
|
||||||
|
memuse();
|
||||||
}
|
}
|
||||||
|
|
||||||
archive() {
|
static void archive(void)
|
||||||
register i;
|
{
|
||||||
|
register int i;
|
||||||
register char *p;
|
register char *p;
|
||||||
|
|
||||||
/*
|
/*
|
||||||
|
@ -219,21 +308,26 @@ archive() {
|
||||||
* This is the only reason.
|
* This is the only reason.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
for(;;) {
|
for (;;)
|
||||||
if (unresolved == 0) { /* no use for this library anymore */
|
{
|
||||||
|
if (unresolved == 0)
|
||||||
|
{ /* no use for this library anymore */
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
p = chp_cast &archhdr;
|
p = chp_cast &archhdr;
|
||||||
if ((i = fgetc(ifile))==EOF ) {
|
if ((i = fgetc(ifile)) == EOF)
|
||||||
|
{
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
*p++ = i;
|
*p++ = i;
|
||||||
for (i = 1; i < sizeof archhdr.ar_name; i++)
|
for (i = 1; i < sizeof archhdr.ar_name; i++)
|
||||||
*p++ = get8();
|
*p++ = get8();
|
||||||
for (i=0;i<8;i++) get8();
|
for (i = 0; i < 8; i++)
|
||||||
|
get8();
|
||||||
archhdr.ar_size = ((long) get16() << 16);
|
archhdr.ar_size = ((long) get16() << 16);
|
||||||
archhdr.ar_size += getu16();
|
archhdr.ar_size += getu16();
|
||||||
inpoff = 0; libeof = archhdr.ar_size;
|
inpoff = 0;
|
||||||
|
libeof = archhdr.ar_size;
|
||||||
/*
|
/*
|
||||||
* UNIX archiveheader is read now, now process the contents
|
* UNIX archiveheader is read now, now process the contents
|
||||||
* of it. Note that recursive archives are not implemented.
|
* of it. Note that recursive archives are not implemented.
|
||||||
|
@ -241,16 +335,19 @@ archive() {
|
||||||
* The variable libeof is used by get8() to check
|
* The variable libeof is used by get8() to check
|
||||||
* whether or not we try to pass the library-boundary.
|
* whether or not we try to pass the library-boundary.
|
||||||
*/
|
*/
|
||||||
if ( getu16() == sp_magic ) {
|
if (getu16() == sp_magic)
|
||||||
|
{
|
||||||
read_compact();
|
read_compact();
|
||||||
} else
|
}
|
||||||
|
else
|
||||||
error("bad archive entry");
|
error("bad archive entry");
|
||||||
skipentry();
|
skipentry();
|
||||||
libeof = 0;
|
libeof = 0;
|
||||||
} /* up to the next entry */
|
} /* up to the next entry */
|
||||||
}
|
}
|
||||||
|
|
||||||
skipentry() {
|
static void skipentry(void)
|
||||||
|
{
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* for some reason the rest of this library entry needs to be
|
* for some reason the rest of this library entry needs to be
|
||||||
|
@ -263,7 +360,8 @@ skipentry() {
|
||||||
;
|
;
|
||||||
}
|
}
|
||||||
|
|
||||||
init_vars() {
|
void init_vars(void)
|
||||||
|
{
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* A small collection of variables is initialized.
|
* A small collection of variables is initialized.
|
||||||
|
@ -273,33 +371,28 @@ init_vars() {
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
init_files() {
|
void init_files(void)
|
||||||
|
{
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* The temporary files on which text and data are kept
|
* The temporary files on which text and data are kept
|
||||||
* during assembly are set up here.
|
* during assembly are set up here.
|
||||||
*/
|
*/
|
||||||
#ifdef CPM
|
|
||||||
unlink("????????.$$$");
|
|
||||||
tfile=fopen("TFILE.$$$", "w");
|
|
||||||
dfile=fopen("DFILE.$$$", "w");
|
|
||||||
rtfile=fopen("RTFILE.$$$", "w");
|
|
||||||
rdfile=fopen("RDFILE.$$$", "w");
|
|
||||||
#else
|
|
||||||
/*
|
/*
|
||||||
* The function tmpfil() returns a file-descriptor
|
* The function tmpfil() returns a file-descriptor
|
||||||
* of a file that is valid for reading and writing.
|
* of a file that is valid for reading and writing.
|
||||||
* It has the nice property of generating truly unique names.
|
* It has the nice property of generating truly unique names.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
tfile=fdopen(tmpfil(),"w") ;
|
tfile = fopen(tmpfil(), "w+");
|
||||||
dfile=fdopen(tmpfil(),"w") ;
|
dfile = fopen(tmpfil(), "w+");
|
||||||
rtfile=fdopen(tmpfil(),"w") ;
|
rtfile = fopen(tmpfil(), "w+");
|
||||||
rdfile=fdopen(tmpfil(),"w") ;
|
rdfile = fopen(tmpfil(), "w+");
|
||||||
#endif
|
|
||||||
}
|
}
|
||||||
|
|
||||||
initproc() {
|
void initproc(void)
|
||||||
|
{
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Called at the start of assembly of every procedure.
|
* Called at the start of assembly of every procedure.
|
||||||
|
@ -313,31 +406,38 @@ initproc() {
|
||||||
pstate.s_curpro = prp_cast 0;
|
pstate.s_curpro = prp_cast 0;
|
||||||
pstate.s_fline = lnp_cast 0;
|
pstate.s_fline = lnp_cast 0;
|
||||||
pstate.s_fdata = l_data;
|
pstate.s_fdata = l_data;
|
||||||
pstate.s_locl = (locl_t (*)[])
|
pstate.s_locl = (locl_t (*)[]) getarea(
|
||||||
getarea(LOCLABSIZE * sizeof ((*(pstate.s_locl))[0]));
|
LOCLABSIZE * sizeof((*(pstate.s_locl))[0]));
|
||||||
zero(chp_cast pstate.s_locl,
|
memset(chp_cast pstate.s_locl, 0,
|
||||||
LOCLABSIZE * (unsigned) sizeof((*(pstate.s_locl))[0]));
|
LOCLABSIZE * (unsigned) sizeof((*(pstate.s_locl))[0]));
|
||||||
if ( memflg>2 ) memuse() ;
|
if (memflg > 2)
|
||||||
|
memuse();
|
||||||
}
|
}
|
||||||
|
|
||||||
endproc() {
|
void endproc(void)
|
||||||
|
{
|
||||||
/* Throw the contents of the line and local label table away */
|
/* Throw the contents of the line and local label table away */
|
||||||
register line_t *lnp1;
|
register line_t *lnp1;
|
||||||
register locl_t *lbhead, *lbp, *lbp_next;
|
register locl_t *lbhead, *lbp, *lbp_next;
|
||||||
register kind ;
|
register int kind;
|
||||||
register stat_t *prevstate;
|
register stat_t *prevstate;
|
||||||
|
|
||||||
while ( lnp1= pstate.s_fline ) {
|
while ((lnp1 = pstate.s_fline) != NULL)
|
||||||
|
{
|
||||||
pstate.s_fline = lnp1->l_next;
|
pstate.s_fline = lnp1->l_next;
|
||||||
kind = lnp1->type1;
|
kind = lnp1->type1;
|
||||||
if ( kind>VALLOW ) kind=VALLOW ;
|
if (kind > VALLOW)
|
||||||
|
kind = VALLOW;
|
||||||
freearea((area_t) lnp1, (unsigned) linesize[kind]);
|
freearea((area_t) lnp1, (unsigned) linesize[kind]);
|
||||||
}
|
}
|
||||||
prevstate = pstate.s_prevstat;
|
prevstate = pstate.s_prevstat;
|
||||||
if ( prevstate!= pst_cast 0 ) {
|
if (prevstate != pst_cast 0)
|
||||||
for ( lbhead= *pstate.s_locl;
|
{
|
||||||
lbhead<&(*pstate.s_locl)[LOCLABSIZE] ; lbhead++ ) {
|
for (lbhead = *pstate.s_locl; lbhead < &(*pstate.s_locl)[LOCLABSIZE];
|
||||||
for ( lbp=lbhead->l_chain; lbp!= lbp_cast 0; lbp= lbp_next ) {
|
lbhead++)
|
||||||
|
{
|
||||||
|
for (lbp = lbhead->l_chain; lbp != lbp_cast 0; lbp = lbp_next)
|
||||||
|
{
|
||||||
lbp_next = lbp->l_chain;
|
lbp_next = lbp->l_chain;
|
||||||
freearea((area_t) lbp, (unsigned) sizeof *lbp);
|
freearea((area_t) lbp, (unsigned) sizeof *lbp);
|
||||||
}
|
}
|
||||||
|
@ -349,7 +449,8 @@ endproc() {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
init_module() {
|
void init_module(void)
|
||||||
|
{
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Called at the start of every module.
|
* Called at the start of every module.
|
||||||
|
@ -360,7 +461,8 @@ init_module() {
|
||||||
mod_sizes = 0;
|
mod_sizes = 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
end_module() {
|
void end_module(void)
|
||||||
|
{
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Finish a module.
|
* Finish a module.
|
||||||
|
@ -373,10 +475,12 @@ end_module() {
|
||||||
dump(100);
|
dump(100);
|
||||||
enmd_pro();
|
enmd_pro();
|
||||||
enmd_glo();
|
enmd_glo();
|
||||||
if ( memflg ) memuse() ;
|
if (memflg)
|
||||||
|
memuse();
|
||||||
}
|
}
|
||||||
|
|
||||||
enmd_pro() {
|
static void enmd_pro(void)
|
||||||
|
{
|
||||||
register proc_t *p, *limit;
|
register proc_t *p, *limit;
|
||||||
|
|
||||||
/*
|
/*
|
||||||
|
@ -385,25 +489,28 @@ enmd_pro() {
|
||||||
*/
|
*/
|
||||||
|
|
||||||
limit = &mprocs[oursize->n_mproc];
|
limit = &mprocs[oursize->n_mproc];
|
||||||
for (p=mprocs; p<limit; p++) {
|
for (p = mprocs; p < limit; p++)
|
||||||
|
{
|
||||||
if (p->p_name == 0)
|
if (p->p_name == 0)
|
||||||
continue;
|
continue;
|
||||||
if ((p->p_status & DEF) == 0)
|
if ((p->p_status & DEF) == 0)
|
||||||
error("undefined local procedure '%s'", p->p_name);
|
error("undefined local procedure '%s'", p->p_name);
|
||||||
}
|
}
|
||||||
zero(chp_cast mprocs,(limit-mprocs)* (unsigned)sizeof *mprocs);
|
memset(chp_cast mprocs, 0, (limit - mprocs) * (unsigned ) sizeof *mprocs);
|
||||||
|
|
||||||
/* Clobber all flags indicating that external procedures
|
/* Clobber all flags indicating that external procedures
|
||||||
* were used in this module.
|
* were used in this module.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
limit = &xprocs[oursize->n_xproc];
|
limit = &xprocs[oursize->n_xproc];
|
||||||
for (p=xprocs; p<limit; p++) {
|
for (p = xprocs; p < limit; p++)
|
||||||
|
{
|
||||||
p->p_status &= ~EXT;
|
p->p_status &= ~EXT;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
enmd_glo() {
|
static void enmd_glo(void)
|
||||||
|
{
|
||||||
register glob_t *mg, *xg, *limit;
|
register glob_t *mg, *xg, *limit;
|
||||||
|
|
||||||
/*
|
/*
|
||||||
|
@ -420,7 +527,8 @@ enmd_glo() {
|
||||||
*/
|
*/
|
||||||
|
|
||||||
limit = &mglobs[oursize->n_mlab];
|
limit = &mglobs[oursize->n_mlab];
|
||||||
for ( mg = mglobs; mg < limit; mg++) {
|
for (mg = mglobs; mg < limit; mg++)
|
||||||
|
{
|
||||||
if (mg->g_name == 0)
|
if (mg->g_name == 0)
|
||||||
continue;
|
continue;
|
||||||
if ((mg->g_status & (EXT | DEF)) == 0)
|
if ((mg->g_status & (EXT | DEF)) == 0)
|
||||||
|
@ -428,13 +536,15 @@ enmd_glo() {
|
||||||
if ((mg->g_status & EXT) == 0)
|
if ((mg->g_status & EXT) == 0)
|
||||||
continue;
|
continue;
|
||||||
xg = xglolookup(mg->g_name, ENTERING);
|
xg = xglolookup(mg->g_name, ENTERING);
|
||||||
switch(xg->g_status&(EXT|DEF)) {
|
switch (xg->g_status & (EXT | DEF))
|
||||||
|
{
|
||||||
case 0: /* new symbol */
|
case 0: /* new symbol */
|
||||||
if ((mg->g_status & DEF) == 0)
|
if ((mg->g_status & DEF) == 0)
|
||||||
++unresolved;
|
++unresolved;
|
||||||
break;
|
break;
|
||||||
case EXT: /* already used but not defined */
|
case EXT: /* already used but not defined */
|
||||||
if(mg->g_status&DEF) {
|
if (mg->g_status & DEF)
|
||||||
|
{
|
||||||
--unresolved;
|
--unresolved;
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
|
@ -446,10 +556,10 @@ enmd_glo() {
|
||||||
mg->g_val.g_gp = xg; /* used by upd_reloc */
|
mg->g_val.g_gp = xg; /* used by upd_reloc */
|
||||||
} /* up to the next symbol */
|
} /* up to the next symbol */
|
||||||
upd_reloc();
|
upd_reloc();
|
||||||
zero(chp_cast mglobs,(limit-mglobs)*(unsigned) sizeof *mglobs);
|
memset(chp_cast mglobs, 0, (limit - mglobs) * (unsigned ) sizeof *mglobs);
|
||||||
}
|
}
|
||||||
|
|
||||||
finish_up()
|
static void finish_up(void)
|
||||||
{
|
{
|
||||||
/*
|
/*
|
||||||
* Almost done. Check for unresolved references,
|
* Almost done. Check for unresolved references,
|
||||||
|
@ -460,41 +570,55 @@ finish_up()
|
||||||
c_print();
|
c_print();
|
||||||
#endif
|
#endif
|
||||||
check_def();
|
check_def();
|
||||||
if ( nerrors==0 ) copyout();
|
if (nerrors == 0)
|
||||||
|
copyout();
|
||||||
}
|
}
|
||||||
|
|
||||||
#ifdef DUMP
|
#ifdef DUMP
|
||||||
c_print() {
|
static void c_print(void)
|
||||||
if ( ! c_flag ) return ;
|
{
|
||||||
|
if (!c_flag)
|
||||||
|
return;
|
||||||
c_dprint("primary", opcnt1);
|
c_dprint("primary", opcnt1);
|
||||||
c_dprint("secondary", opcnt2);
|
c_dprint("secondary", opcnt2);
|
||||||
c_dprint("extra long", opcnt3);
|
c_dprint("extra long", opcnt3);
|
||||||
}
|
}
|
||||||
|
|
||||||
c_dprint(str,cnt) char *str,*cnt ; {
|
static void c_dprint(char *str, char* cnt)
|
||||||
|
{
|
||||||
register int first, curr;
|
register int first, curr;
|
||||||
printf("unused %s opcodes\n", str);
|
printf("unused %s opcodes\n", str);
|
||||||
for ( first= -1 , curr=0 ; curr<=256 ; curr++ ) {
|
for (first = -1, curr = 0; curr <= 256; curr++)
|
||||||
if ( curr==256 || cnt[curr] ) {
|
{
|
||||||
if ( first!= -1 ) {
|
if (curr == 256 || cnt[curr])
|
||||||
if ( first+1 == curr ) {
|
{
|
||||||
|
if (first != -1)
|
||||||
|
{
|
||||||
|
if (first + 1 == curr)
|
||||||
|
{
|
||||||
printf("%3d\n", first);
|
printf("%3d\n", first);
|
||||||
} else {
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
printf("%3d..%3d\n", first, curr - 1);
|
printf("%3d..%3d\n", first, curr - 1);
|
||||||
}
|
}
|
||||||
first = -1;
|
first = -1;
|
||||||
}
|
}
|
||||||
} else {
|
}
|
||||||
if ( first== -1 ) first=curr ;
|
else
|
||||||
|
{
|
||||||
|
if (first == -1)
|
||||||
|
first = curr;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
check_def() {
|
static void check_def(void)
|
||||||
|
{
|
||||||
register proc_t *p;
|
register proc_t *p;
|
||||||
register glob_t *g;
|
register glob_t *g;
|
||||||
register count;
|
register int count;
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Check for unresolved references.
|
* Check for unresolved references.
|
||||||
|
@ -504,7 +628,8 @@ check_def() {
|
||||||
* Every use of the symbols concerned is undefined.
|
* Every use of the symbols concerned is undefined.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
if (unresolved) {
|
if (unresolved)
|
||||||
|
{
|
||||||
printf("Unresolved references\n Procedures:\n");
|
printf("Unresolved references\n Procedures:\n");
|
||||||
count = oursize->n_xproc;
|
count = oursize->n_xproc;
|
||||||
for (p = xprocs; count--; p++)
|
for (p = xprocs; count--; p++)
|
||||||
|
@ -515,14 +640,16 @@ check_def() {
|
||||||
for (g = xglobs; count--; g++)
|
for (g = xglobs; count--; g++)
|
||||||
if (g->g_name && (g->g_status & DEF) == 0)
|
if (g->g_name && (g->g_status & DEF) == 0)
|
||||||
printf(" %s\n", glostring(g));
|
printf(" %s\n", glostring(g));
|
||||||
if (! Uflag) nerrors++;
|
if (!Uflag)
|
||||||
|
nerrors++;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
ertrap() { /* trap routine to drain input in case of compile errors */
|
void ertrap(void)
|
||||||
|
{ /* trap routine to drain input in case of compile errors */
|
||||||
|
|
||||||
if (fileno(ifile)== 0)
|
if (ifile == stdin)
|
||||||
while (fgetc(ifile) != EOF)
|
while (fgetc(ifile) != EOF)
|
||||||
;
|
;
|
||||||
exit(1);
|
exit(EXIT_FAILURE);
|
||||||
}
|
}
|
||||||
|
|
|
@ -4,15 +4,12 @@
|
||||||
*/
|
*/
|
||||||
#include <stdlib.h>
|
#include <stdlib.h>
|
||||||
#include <stdio.h>
|
#include <stdio.h>
|
||||||
#include <unistd.h>
|
|
||||||
#include <sys/types.h>
|
#include <sys/types.h>
|
||||||
#include <sys/stat.h>
|
#include "em_spec.h"
|
||||||
#include <fcntl.h>
|
#include "as_spec.h"
|
||||||
#include <em_spec.h>
|
#include "em_flag.h"
|
||||||
#include <as_spec.h>
|
#include "arch.h"
|
||||||
#include <em_flag.h>
|
#include "local.h"
|
||||||
#include <arch.h>
|
|
||||||
#include <local.h>
|
|
||||||
|
|
||||||
#define RCS_ASS "$Id$"
|
#define RCS_ASS "$Id$"
|
||||||
|
|
||||||
|
|
262
util/ass/ass30.c
262
util/ass/ass30.c
|
@ -4,25 +4,29 @@
|
||||||
*
|
*
|
||||||
*/
|
*/
|
||||||
|
|
||||||
|
#include <stddef.h>
|
||||||
#include "ass00.h"
|
#include "ass00.h"
|
||||||
#include "assex.h"
|
#include "assex.h"
|
||||||
|
#include "assci.h"
|
||||||
|
#include "asscm.h"
|
||||||
#include "ip_spec.h"
|
#include "ip_spec.h"
|
||||||
|
|
||||||
#ifndef NORCSID
|
|
||||||
static char rcs_id[] = "$Id$" ;
|
|
||||||
static char rcs_ip[] = RCS_IP ;
|
|
||||||
#endif
|
|
||||||
|
|
||||||
short opt_line; /* max_line_no - # lines removed from end
|
short opt_line; /* max_line_no - # lines removed from end
|
||||||
after perfoming exc's.
|
after perfoming exc's.
|
||||||
Used to estimate the distance in # of
|
Used to estimate the distance in # of
|
||||||
instructions.
|
instructions.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
|
/* Forward declarations. */
|
||||||
|
static int valid(register line_t *);
|
||||||
|
static char *findfit(int, cons_t);
|
||||||
|
static char *findnop(int);
|
||||||
|
|
||||||
/*
|
/*
|
||||||
** Determine the exact instruction length & format where possible, and the
|
** Determine the exact instruction length & format where possible, and the
|
||||||
** the upper and lower limits otherwise. Enter limits in labeltable
|
** the upper and lower limits otherwise. Enter limits in labeltable
|
||||||
*/
|
*/
|
||||||
pass_3()
|
void pass_3(void)
|
||||||
{
|
{
|
||||||
register line_t *lnp, *rev_lnp;
|
register line_t *lnp, *rev_lnp;
|
||||||
line_t *tmp_lnp;
|
line_t *tmp_lnp;
|
||||||
|
@ -30,15 +34,19 @@ pass_3()
|
||||||
int min_l, max_l, min_bytes;
|
int min_l, max_l, min_bytes;
|
||||||
short last_line;
|
short last_line;
|
||||||
short hol_err_line;
|
short hol_err_line;
|
||||||
register insno ;
|
register int insno;
|
||||||
|
|
||||||
pass = 3;
|
pass = 3;
|
||||||
opt_line= line_num ; hol_err_line=0 ;
|
opt_line = line_num;
|
||||||
min_bytes = max_bytes = 0; rev_lnp= lnp_cast 0 ;
|
hol_err_line = 0;
|
||||||
for (lnp = pstate.s_fline ; lnp ; opt_line--, line_num-- ) {
|
min_bytes = max_bytes = 0;
|
||||||
|
rev_lnp = lnp_cast 0;
|
||||||
|
for (lnp = pstate.s_fline; lnp; opt_line--, line_num--)
|
||||||
|
{
|
||||||
pstate.s_fline = lnp;
|
pstate.s_fline = lnp;
|
||||||
insno = ctrunc(lnp->instr_num);
|
insno = ctrunc(lnp->instr_num);
|
||||||
switch( insno ) {
|
switch (insno)
|
||||||
|
{
|
||||||
case sp_fpseu:
|
case sp_fpseu:
|
||||||
last_line = line_num;
|
last_line = line_num;
|
||||||
line_num = lnp->ad.ad_ln.ln_first;
|
line_num = lnp->ad.ad_ln.ln_first;
|
||||||
|
@ -52,55 +60,91 @@ pass_3()
|
||||||
lbp->l_max = max_bytes;
|
lbp->l_max = max_bytes;
|
||||||
break;
|
break;
|
||||||
default:
|
default:
|
||||||
if ( lnp->type1==CONST && (em_flag[insno]&EM_PAR)==PAR_G ) {
|
if (lnp->type1 == CONST && (em_flag[insno] & EM_PAR) == PAR_G)
|
||||||
if (holbase != 0) {
|
{
|
||||||
if (lnp->ad.ad_i >= holsize) {
|
if (holbase != 0)
|
||||||
|
{
|
||||||
|
if (lnp->ad.ad_i >= holsize)
|
||||||
|
{
|
||||||
hol_err_line = line_num;
|
hol_err_line = line_num;
|
||||||
}
|
}
|
||||||
lnp->ad.ad_i += holbase;
|
lnp->ad.ad_i += holbase;
|
||||||
}
|
}
|
||||||
} else
|
}
|
||||||
if ( lnp->type1>=VALLOW && (em_flag[insno]&EM_PAR)==PAR_G ) {
|
else if (lnp->type1 >= VALLOW && (em_flag[insno] & EM_PAR) == PAR_G)
|
||||||
if (holbase != 0) {
|
{
|
||||||
|
if (holbase != 0)
|
||||||
|
{
|
||||||
pstate.s_fline = lnp->l_next;
|
pstate.s_fline = lnp->l_next;
|
||||||
newline(CONST);
|
newline(CONST);
|
||||||
pstate.s_fline->instr_num = insno;
|
pstate.s_fline->instr_num = insno;
|
||||||
pstate.s_fline->ad.ad_i =
|
pstate.s_fline->ad.ad_i =
|
||||||
VAL1(lnp->type1) + holbase;
|
VAL1(lnp->type1) + holbase;
|
||||||
freearea((area_t)lnp,
|
freearea((area_t) lnp, (unsigned) linesize[VALLOW]);
|
||||||
(unsigned)linesize[VALLOW]) ;
|
|
||||||
lnp = pstate.s_fline;
|
lnp = pstate.s_fline;
|
||||||
if ( VAL1(lnp->type1) >= holsize) {
|
if ( VAL1(lnp->type1) >= holsize)
|
||||||
|
{
|
||||||
hol_err_line = line_num;
|
hol_err_line = line_num;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if ( !valid(lnp) ) fatal("Invalid operand") ;
|
if (!valid(lnp))
|
||||||
|
fatal("Invalid operand");
|
||||||
|
|
||||||
determine_props(lnp, &min_l, &max_l);
|
determine_props(lnp, &min_l, &max_l);
|
||||||
min_bytes += min_l; max_bytes += max_l;
|
min_bytes += min_l;
|
||||||
|
max_bytes += max_l;
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
tmp_lnp = lnp->l_next;
|
tmp_lnp = lnp->l_next;
|
||||||
lnp->l_next= rev_lnp ; rev_lnp= lnp ;
|
lnp->l_next = rev_lnp;
|
||||||
|
rev_lnp = lnp;
|
||||||
lnp = tmp_lnp;
|
lnp = tmp_lnp;
|
||||||
}
|
}
|
||||||
pstate.s_fline = rev_lnp;
|
pstate.s_fline = rev_lnp;
|
||||||
if ( hol_err_line ) {
|
if (hol_err_line)
|
||||||
|
{
|
||||||
line_num = hol_err_line;
|
line_num = hol_err_line;
|
||||||
werror("address exceeds holsize");
|
werror("address exceeds holsize");
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
int oplength(int flag)
|
||||||
|
{
|
||||||
|
int cnt;
|
||||||
|
|
||||||
|
cnt = 1;
|
||||||
|
if (flag & OPESC)
|
||||||
|
cnt++;
|
||||||
|
switch (flag & OPTYPE)
|
||||||
|
{
|
||||||
|
case OPNO:
|
||||||
|
case OPMINI:
|
||||||
|
break;
|
||||||
|
case OP8:
|
||||||
|
case OPSHORT:
|
||||||
|
cnt++;
|
||||||
|
break;
|
||||||
|
case OP16U:
|
||||||
|
case OP16:
|
||||||
|
cnt += 2;
|
||||||
|
break;
|
||||||
|
case OP32:
|
||||||
|
cnt += 5;
|
||||||
|
break;
|
||||||
|
case OP64:
|
||||||
|
cnt += 9;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
return cnt;
|
||||||
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
** Determine the format that should be used for each instruction,
|
** Determine the format that should be used for each instruction,
|
||||||
** depending on its offsets
|
** depending on its offsets
|
||||||
*/
|
*/
|
||||||
|
|
||||||
determine_props(lnp, min_len, max_len)
|
void determine_props(line_t *lnp, int *min_len, int *max_len)
|
||||||
line_t *lnp;
|
|
||||||
int *min_len, *max_len;
|
|
||||||
{
|
{
|
||||||
cons_t val;
|
cons_t val;
|
||||||
register int insno;
|
register int insno;
|
||||||
|
@ -109,8 +153,10 @@ determine_props(lnp, min_len, max_len)
|
||||||
|
|
||||||
insno = ctrunc(lnp->instr_num);
|
insno = ctrunc(lnp->instr_num);
|
||||||
val = parval(lnp, &defined);
|
val = parval(lnp, &defined);
|
||||||
if ( !defined ) {
|
if (!defined)
|
||||||
switch(em_flag[insno]&EM_PAR) {
|
{
|
||||||
|
switch (em_flag[insno] & EM_PAR)
|
||||||
|
{
|
||||||
case PAR_NO:
|
case PAR_NO:
|
||||||
case PAR_W:
|
case PAR_W:
|
||||||
f_off = findnop(insno);
|
f_off = findnop(insno);
|
||||||
|
@ -128,7 +174,8 @@ determine_props(lnp, min_len, max_len)
|
||||||
case PAR_B:
|
case PAR_B:
|
||||||
f_off = findfit(insno, (cons_t) 0);
|
f_off = findfit(insno, (cons_t) 0);
|
||||||
l_off = findfit(insno, val);
|
l_off = findfit(insno, val);
|
||||||
if ( f_off != l_off ) {
|
if (f_off != l_off)
|
||||||
|
{
|
||||||
*min_len = oplength(*f_off);
|
*min_len = oplength(*f_off);
|
||||||
*max_len = oplength(*l_off);
|
*max_len = oplength(*l_off);
|
||||||
lnp->opoff = NO_OFF;
|
lnp->opoff = NO_OFF;
|
||||||
|
@ -136,24 +183,28 @@ determine_props(lnp, min_len, max_len)
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
} else {
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
f_off = findfit(insno, val);
|
f_off = findfit(insno, val);
|
||||||
}
|
}
|
||||||
lnp->opoff = f_off;
|
lnp->opoff = f_off;
|
||||||
*min_len = *max_len = oplength(*f_off);
|
*min_len = *max_len = oplength(*f_off);
|
||||||
}
|
}
|
||||||
|
|
||||||
char *findfit(instr,val) int instr ; cons_t val ; {
|
static char *findfit(int instr, cons_t val)
|
||||||
|
{
|
||||||
register char *currc, *endc;
|
register char *currc, *endc;
|
||||||
int found, flags, number;
|
int found, flags, number;
|
||||||
char *opc;
|
char *opc;
|
||||||
|
|
||||||
endc = opindex[instr + 1];
|
endc = opindex[instr + 1];
|
||||||
for ( currc=opindex[instr], found=0 ;
|
for (currc = opindex[instr], found = 0; !found && currc < endc; currc++)
|
||||||
!found && currc<endc ; currc++ ) {
|
{
|
||||||
opc = currc;
|
opc = currc;
|
||||||
flags = ctrunc(*currc++);
|
flags = ctrunc(*currc++);
|
||||||
switch ( flags&OPTYPE ) {
|
switch (flags & OPTYPE)
|
||||||
|
{
|
||||||
case OPNO:
|
case OPNO:
|
||||||
continue;
|
continue;
|
||||||
case OPMINI:
|
case OPMINI:
|
||||||
|
@ -162,16 +213,20 @@ char *findfit(instr,val) int instr ; cons_t val ; {
|
||||||
}
|
}
|
||||||
found = opfit(flags, number, val, em_flag[instr] & EM_PAR);
|
found = opfit(flags, number, val, em_flag[instr] & EM_PAR);
|
||||||
}
|
}
|
||||||
if ( !found ) fatal("Cannot find interpreter opcode") ;
|
if (!found)
|
||||||
|
fatal("Cannot find interpreter opcode");
|
||||||
return opc;
|
return opc;
|
||||||
}
|
}
|
||||||
|
|
||||||
char *findnop(instr) int instr ; {
|
static char* findnop(int instr)
|
||||||
|
{
|
||||||
register char *currc, *endc;
|
register char *currc, *endc;
|
||||||
|
|
||||||
endc = opindex[instr + 1];
|
endc = opindex[instr + 1];
|
||||||
for ( currc=opindex[instr] ; currc<endc ; currc++ ) {
|
for (currc = opindex[instr]; currc < endc; currc++)
|
||||||
switch ( ctrunc(*currc)&OPTYPE ) {
|
{
|
||||||
|
switch ( ctrunc(*currc) & OPTYPE)
|
||||||
|
{
|
||||||
case OPNO:
|
case OPNO:
|
||||||
return currc;
|
return currc;
|
||||||
case OPSHORT:
|
case OPSHORT:
|
||||||
|
@ -182,71 +237,62 @@ char *findnop(instr) int instr ; {
|
||||||
}
|
}
|
||||||
fatal("Cannot find interpreter opcode");
|
fatal("Cannot find interpreter opcode");
|
||||||
/* NOTREACHED */
|
/* NOTREACHED */
|
||||||
|
return NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
int opfit(flag,number,val,i_flag)
|
int opfit(int flag, int number, cons_t val, int i_flag)
|
||||||
int i_flag,flag,number ; cons_t val ; {
|
{
|
||||||
/* Number is invalid if flag does not contain MINI or SHORT */
|
/* Number is invalid if flag does not contain MINI or SHORT */
|
||||||
switch ( flag&OPRANGE ) {
|
switch (flag & OPRANGE)
|
||||||
|
{
|
||||||
case OP_POS:
|
case OP_POS:
|
||||||
if ( val<0 ) return 0 ;
|
if (val < 0)
|
||||||
|
return 0;
|
||||||
break;
|
break;
|
||||||
case OP_NEG:
|
case OP_NEG:
|
||||||
if ( val>=0 ) return 0 ;
|
if (val >= 0)
|
||||||
|
return 0;
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
if ( flag&OPWORD ) {
|
if (flag & OPWORD)
|
||||||
if ( val%wordsize ) return 0 ;
|
{
|
||||||
|
if (val % wordsize)
|
||||||
|
return 0;
|
||||||
val /= wordsize;
|
val /= wordsize;
|
||||||
}
|
}
|
||||||
if ( flag&OPNZ ) {
|
if (flag & OPNZ)
|
||||||
if ( val==0 ) return 0 ;
|
{
|
||||||
|
if (val == 0)
|
||||||
|
return 0;
|
||||||
val--;
|
val--;
|
||||||
}
|
}
|
||||||
switch ( flag&OPTYPE ) {
|
switch (flag & OPTYPE)
|
||||||
|
{
|
||||||
case OPMINI:
|
case OPMINI:
|
||||||
if ( val<0 ) val = -1-val ;
|
if (val < 0)
|
||||||
|
val = -1 - val;
|
||||||
return val >= 0 && val < number;
|
return val >= 0 && val < number;
|
||||||
case OPSHORT:
|
case OPSHORT:
|
||||||
if ( val<0 ) val = -1-val ;
|
if (val < 0)
|
||||||
|
val = -1 - val;
|
||||||
return val >= 0 && val < number * 256;
|
return val >= 0 && val < number * 256;
|
||||||
case OP16U:
|
case OP16U:
|
||||||
return val>=0 && val<=65535L &&
|
return val >= 0 && val <= 65535L && (i_flag != PAR_G || val <= maxadr);
|
||||||
( i_flag!=PAR_G || val<=maxadr ) ;
|
|
||||||
case OP16:
|
case OP16:
|
||||||
return val >= -32768 && val <= 32767;
|
return val >= -32768 && val <= 32767;
|
||||||
case OP32:
|
case OP32:
|
||||||
return TRUE;
|
return TRUE;
|
||||||
default:
|
default:
|
||||||
fatal("illegal OPTYPE value");
|
fatal("illegal OPTYPE value");
|
||||||
|
return -1;
|
||||||
/* NOTREACHED */
|
/* NOTREACHED */
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
int oplength(flag) int flag ; {
|
|
||||||
int cnt ;
|
|
||||||
|
|
||||||
cnt=1 ;
|
|
||||||
if ( flag&OPESC ) cnt++ ;
|
|
||||||
switch( flag&OPTYPE ) {
|
|
||||||
case OPNO :
|
|
||||||
case OPMINI : break ;
|
|
||||||
case OP8 :
|
|
||||||
case OPSHORT : cnt++ ; break ;
|
|
||||||
case OP16U:
|
|
||||||
case OP16 : cnt+=2 ; break ;
|
|
||||||
case OP32 : cnt+=5 ; break ;
|
|
||||||
case OP64 : cnt+=9 ; break ;
|
|
||||||
}
|
|
||||||
return cnt ;
|
|
||||||
}
|
|
||||||
|
|
||||||
/*
|
/*
|
||||||
** return estimation of value of parameter
|
** return estimation of value of parameter
|
||||||
*/
|
*/
|
||||||
cons_t parval(lnp,defined)
|
cons_t parval(line_t *lnp, char *defined)
|
||||||
line_t *lnp;
|
|
||||||
char *defined;
|
|
||||||
{
|
{
|
||||||
register int type;
|
register int type;
|
||||||
register locl_t *lbp;
|
register locl_t *lbp;
|
||||||
|
@ -255,8 +301,10 @@ cons_t parval(lnp,defined)
|
||||||
|
|
||||||
*defined = TRUE;
|
*defined = TRUE;
|
||||||
type = lnp->type1;
|
type = lnp->type1;
|
||||||
switch(type) {
|
switch (type)
|
||||||
default: if ( type>=VALLOW && type<=VALHIGH )
|
{
|
||||||
|
default:
|
||||||
|
if (type >= VALLOW && type <= VALHIGH)
|
||||||
return VAL1(type);
|
return VAL1(type);
|
||||||
error("bad type during parval");
|
error("bad type during parval");
|
||||||
break;
|
break;
|
||||||
|
@ -264,27 +312,35 @@ cons_t parval(lnp,defined)
|
||||||
return (lnp->ad.ad_i);
|
return (lnp->ad.ad_i);
|
||||||
case GLOSYM:
|
case GLOSYM:
|
||||||
case GLOOFF:
|
case GLOOFF:
|
||||||
if ( type!=GLOOFF) {
|
if (type != GLOOFF)
|
||||||
|
{
|
||||||
gbp = lnp->ad.ad_gp;
|
gbp = lnp->ad.ad_gp;
|
||||||
offs = 0;
|
offs = 0;
|
||||||
} else {
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
gbp = lnp->ad.ad_df.df_gp;
|
gbp = lnp->ad.ad_df.df_gp;
|
||||||
offs = lnp->ad.ad_df.df_i;
|
offs = lnp->ad.ad_df.df_i;
|
||||||
}
|
}
|
||||||
if (gbp->g_status & DEF)
|
if (gbp->g_status & DEF)
|
||||||
return (gbp->g_val.g_addr + offs);
|
return (gbp->g_val.g_addr + offs);
|
||||||
else {
|
else
|
||||||
|
{
|
||||||
*defined = FALSE;
|
*defined = FALSE;
|
||||||
return offs;
|
return offs;
|
||||||
}
|
}
|
||||||
case LOCSYM:
|
case LOCSYM:
|
||||||
lbp = lnp->ad.ad_lp;
|
lbp = lnp->ad.ad_lp;
|
||||||
switch(pass) {
|
switch (pass)
|
||||||
default:error("bad pass in parval");
|
{
|
||||||
|
default:
|
||||||
|
error("bad pass in parval");
|
||||||
case 3:
|
case 3:
|
||||||
*defined = FALSE;
|
*defined = FALSE;
|
||||||
switch(lbp->l_defined) {
|
switch (lbp->l_defined)
|
||||||
default : fatal("Illegal local label") ;
|
{
|
||||||
|
default:
|
||||||
|
fatal("Illegal local label");
|
||||||
case NO:
|
case NO:
|
||||||
error("Undefined local label");
|
error("Undefined local label");
|
||||||
lbp->l_defined = NOTPRESENT;
|
lbp->l_defined = NOTPRESENT;
|
||||||
|
@ -298,10 +354,12 @@ cons_t parval(lnp,defined)
|
||||||
*/
|
*/
|
||||||
return (lbp->l_min - opt_line - 1) * maxinsl;
|
return (lbp->l_min - opt_line - 1) * maxinsl;
|
||||||
}
|
}
|
||||||
case 4: if(lbp->l_defined == YES)
|
case 4:
|
||||||
|
if (lbp->l_defined == YES)
|
||||||
return (lbp->l_min - prog_size - maxinsl);
|
return (lbp->l_min - prog_size - maxinsl);
|
||||||
return max_bytes - lbp->l_max - prog_size;
|
return max_bytes - lbp->l_max - prog_size;
|
||||||
case 5: if (lbp->l_defined == YES )
|
case 5:
|
||||||
|
if (lbp->l_defined == YES)
|
||||||
return lbp->l_min;
|
return lbp->l_min;
|
||||||
*defined = FALSE;
|
*defined = FALSE;
|
||||||
break;
|
break;
|
||||||
|
@ -315,27 +373,37 @@ cons_t parval(lnp,defined)
|
||||||
}
|
}
|
||||||
return (0);
|
return (0);
|
||||||
}
|
}
|
||||||
int valid(lnp) register line_t *lnp ; {
|
|
||||||
|
static int valid(register line_t *lnp)
|
||||||
|
{
|
||||||
cons_t val;
|
cons_t val;
|
||||||
int type;
|
int type;
|
||||||
|
|
||||||
type = lnp->type1;
|
type = lnp->type1;
|
||||||
if ( type>=VALLOW && type<=VALHIGH ) {
|
if (type >= VALLOW && type <= VALHIGH)
|
||||||
|
{
|
||||||
val = VAL1(type);
|
val = VAL1(type);
|
||||||
type = CONST;
|
type = CONST;
|
||||||
} else if ( type==CONST ) val = lnp->ad.ad_i ;
|
}
|
||||||
switch ( em_flag[ctrunc(lnp->instr_num)]&EM_PAR ) {
|
else if (type == CONST)
|
||||||
|
val = lnp->ad.ad_i;
|
||||||
|
switch (em_flag[ctrunc(lnp->instr_num)] & EM_PAR)
|
||||||
|
{
|
||||||
case PAR_NO:
|
case PAR_NO:
|
||||||
return type == MISSING;
|
return type == MISSING;
|
||||||
case PAR_C:
|
case PAR_C:
|
||||||
if ( type!=CONST ) return FALSE;
|
if (type != CONST)
|
||||||
if ( val>maxint && val<=maxunsig ) {
|
return FALSE;
|
||||||
|
if (val > maxint && val <= maxunsig)
|
||||||
|
{
|
||||||
lnp->ad.ad_i = val - maxunsig - 1;
|
lnp->ad.ad_i = val - maxunsig - 1;
|
||||||
}
|
}
|
||||||
return TRUE;
|
return TRUE;
|
||||||
case PAR_D:
|
case PAR_D:
|
||||||
if ( type!=CONST ) return FALSE;
|
if (type != CONST)
|
||||||
if ( val>maxdint && val<=maxdunsig ) {
|
return FALSE;
|
||||||
|
if (val > maxdint && val <= maxdunsig)
|
||||||
|
{
|
||||||
lnp->ad.ad_i = val - maxdunsig - 1;
|
lnp->ad.ad_i = val - maxdunsig - 1;
|
||||||
}
|
}
|
||||||
return TRUE;
|
return TRUE;
|
||||||
|
@ -347,14 +415,15 @@ int valid(lnp) register line_t *lnp ; {
|
||||||
case PAR_G:
|
case PAR_G:
|
||||||
return type == CONST || type == GLOSYM || type == GLOOFF;
|
return type == CONST || type == GLOSYM || type == GLOOFF;
|
||||||
case PAR_W:
|
case PAR_W:
|
||||||
if ( type==MISSING ) return TRUE ;
|
if (type == MISSING)
|
||||||
|
return TRUE;
|
||||||
case PAR_S:
|
case PAR_S:
|
||||||
return type == CONST && val > 0 && val % wordsize == 0;
|
return type == CONST && val > 0 && val % wordsize == 0;
|
||||||
case PAR_Z:
|
case PAR_Z:
|
||||||
return type == CONST && val >= 0 && val % wordsize == 0;
|
return type == CONST && val >= 0 && val % wordsize == 0;
|
||||||
case PAR_O:
|
case PAR_O:
|
||||||
return type==CONST && val>=0 &&
|
return type == CONST && val >= 0
|
||||||
( val >= wordsize ? val%wordsize : wordsize%val ) == 0 ;
|
&& (val >= wordsize ? val % wordsize : wordsize % val) == 0;
|
||||||
case PAR_P:
|
case PAR_P:
|
||||||
return type == PROCNAME;
|
return type == PROCNAME;
|
||||||
case PAR_B:
|
case PAR_B:
|
||||||
|
@ -363,6 +432,7 @@ int valid(lnp) register line_t *lnp ; {
|
||||||
return type == CONST && val >= 0 && val <= 3;
|
return type == CONST && val >= 0 && val <= 3;
|
||||||
default:
|
default:
|
||||||
fatal("Unknown parameter type");
|
fatal("Unknown parameter type");
|
||||||
|
return -1;
|
||||||
/* NOTREACHED */
|
/* NOTREACHED */
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -7,15 +7,13 @@
|
||||||
#include "ass00.h"
|
#include "ass00.h"
|
||||||
#include "assex.h"
|
#include "assex.h"
|
||||||
|
|
||||||
#ifndef NORCSID
|
|
||||||
static char rcs_id[] = "$Id$" ;
|
|
||||||
#endif
|
|
||||||
|
|
||||||
/*
|
/*
|
||||||
** Make scans to do final assignment of instruction sizes & formats
|
** Make scans to do final assignment of instruction sizes & formats
|
||||||
** to those not already done. assign final values to labels
|
** to those not already done. assign final values to labels
|
||||||
*/
|
*/
|
||||||
pass_4()
|
void pass_4(void)
|
||||||
{
|
{
|
||||||
register line_t *lnp;
|
register line_t *lnp;
|
||||||
register locl_t *lbp;
|
register locl_t *lbp;
|
||||||
|
|
|
@ -6,19 +6,21 @@
|
||||||
|
|
||||||
#include "ass00.h"
|
#include "ass00.h"
|
||||||
#include "assex.h"
|
#include "assex.h"
|
||||||
|
#include "assrl.h"
|
||||||
#include "ip_spec.h"
|
#include "ip_spec.h"
|
||||||
|
|
||||||
#ifndef NORCSID
|
|
||||||
static char rcs_id[] = "$Id$" ;
|
|
||||||
#endif
|
|
||||||
|
|
||||||
/*
|
/*
|
||||||
** Pass 5 of EM1 assembler/loader
|
** Pass 5 of EM1 assembler/loader
|
||||||
** Fix reloc tables
|
** Fix reloc tables
|
||||||
** Write out code
|
** Write out code
|
||||||
*/
|
*/
|
||||||
|
|
||||||
pass_5() {
|
static void patchcase(void);
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
void pass_5(void)
|
||||||
|
{
|
||||||
register line_t *lnp;
|
register line_t *lnp;
|
||||||
cons_t off1;
|
cons_t off1;
|
||||||
char defined ;
|
char defined ;
|
||||||
|
@ -78,14 +80,15 @@ pass_5() {
|
||||||
|
|
||||||
} /* end pass_5 */
|
} /* end pass_5 */
|
||||||
|
|
||||||
genop(startc,value,i_flag) char *startc ; cons_t value ; int i_flag ; {
|
|
||||||
char *currc ;
|
|
||||||
register flag ;
|
|
||||||
char opc ;
|
|
||||||
|
|
||||||
/*
|
/**
|
||||||
* Real code generation.
|
* Real code generation.
|
||||||
*/
|
*/
|
||||||
|
void genop(char *startc,cons_t value,int i_flag)
|
||||||
|
{
|
||||||
|
char *currc ;
|
||||||
|
register int flag ;
|
||||||
|
char opc ;
|
||||||
|
|
||||||
currc= startc ;
|
currc= startc ;
|
||||||
flag = ctrunc(*currc++);
|
flag = ctrunc(*currc++);
|
||||||
|
@ -161,11 +164,12 @@ genop(startc,value,i_flag) char *startc ; cons_t value ; int i_flag ; {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
patchcase() {
|
static void patchcase(void)
|
||||||
|
{
|
||||||
register relc_t *r;
|
register relc_t *r;
|
||||||
register locl_t *k;
|
register locl_t *k;
|
||||||
|
|
||||||
if ( r= pstate.s_fdata ) {
|
if ( (r= pstate.s_fdata) ) {
|
||||||
r= r->r_next ;
|
r= r->r_next ;
|
||||||
} else {
|
} else {
|
||||||
r= f_data ;
|
r= f_data ;
|
||||||
|
|
156
util/ass/ass60.c
156
util/ass/ass60.c
|
@ -8,21 +8,23 @@
|
||||||
#include "assex.h"
|
#include "assex.h"
|
||||||
#include "ip_spec.h"
|
#include "ip_spec.h"
|
||||||
|
|
||||||
#ifndef NORCSID
|
|
||||||
static char rcs_id[] = "$Id$" ;
|
|
||||||
#endif
|
|
||||||
|
|
||||||
#ifdef DUMP
|
#ifdef DUMP
|
||||||
static char *typestr[] =
|
static char *typestr[] =
|
||||||
{ "missing", "const", "procname", "glosym", "locsym", "glosym+off", "pseudo" };
|
{ "missing", "const", "procname", "glosym", "locsym", "glosym+off", "pseudo" };
|
||||||
static char *labstr[] = {"EMPTY","no","yes","seen","notpresent"};
|
static char *labstr[] =
|
||||||
static char formstr[] = { 'm','s','-','1','2','4','8' };
|
{ "EMPTY", "no", "yes", "seen", "notpresent" };
|
||||||
static char *r_data[] = { "null","glob","head","loc","adr" };
|
static char formstr[] =
|
||||||
|
{ 'm', 's', '-', '1', '2', '4', '8' };
|
||||||
|
static char *r_data[] =
|
||||||
|
{ "null", "glob", "head", "loc", "adr" };
|
||||||
|
|
||||||
cons_t nicepr(typ,ap) addr_u *ap; {
|
cons_t nicepr(int typ, addr_u *ap)
|
||||||
|
{
|
||||||
register proc_t *pl;
|
register proc_t *pl;
|
||||||
|
|
||||||
switch (typ) {
|
switch (typ)
|
||||||
|
{
|
||||||
case CONST:
|
case CONST:
|
||||||
return (ap->ad_i);
|
return (ap->ad_i);
|
||||||
case LOCSYM:
|
case LOCSYM:
|
||||||
|
@ -32,37 +34,47 @@ cons_t nicepr(typ,ap) addr_u *ap; {
|
||||||
case GLOSYM:
|
case GLOSYM:
|
||||||
return (ap->ad_gp - mglobs);
|
return (ap->ad_gp - mglobs);
|
||||||
case PROCNAME:
|
case PROCNAME:
|
||||||
pl = ap->ad_pp;;
|
pl = ap->ad_pp;
|
||||||
|
;
|
||||||
if (pl->p_status & EXT)
|
if (pl->p_status & EXT)
|
||||||
return ((pl - xprocs) + 1000);
|
return ((pl - xprocs) + 1000);
|
||||||
else
|
else
|
||||||
return (pl - mprocs);
|
return (pl - mprocs);
|
||||||
default:
|
default:
|
||||||
if ( typ>=VALLOW && typ<=VALHIGH ) return VAL1(typ) ;
|
if (typ >= VALLOW && typ <= VALHIGH)
|
||||||
|
return VAL1(typ);
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
return (0);
|
return (0);
|
||||||
}
|
}
|
||||||
|
|
||||||
char *pflags(flg) int flg ; {
|
char *pflags(int flg)
|
||||||
|
{
|
||||||
static char res[9];
|
static char res[9];
|
||||||
register char *cp;
|
register char *cp;
|
||||||
|
|
||||||
cp = res;
|
cp = res;
|
||||||
if ( flg&OPESC ) *cp++ = 'e' ;
|
if (flg & OPESC)
|
||||||
switch ( flg&OPRANGE ) {
|
*cp++ = 'e';
|
||||||
case OP_NEG : *cp++ = 'N' ; break ;
|
switch (flg & OPRANGE)
|
||||||
case OP_POS : *cp++ = 'P' ; break ;
|
{
|
||||||
|
case OP_NEG:
|
||||||
|
*cp++ = 'N';
|
||||||
|
break;
|
||||||
|
case OP_POS:
|
||||||
|
*cp++ = 'P';
|
||||||
|
break;
|
||||||
}
|
}
|
||||||
if ( flg&OPWORD ) *cp++ = 'w' ;
|
if (flg & OPWORD)
|
||||||
if ( flg&OPNZ ) *cp++ = 'o' ;
|
*cp++ = 'w';
|
||||||
|
if (flg & OPNZ)
|
||||||
|
*cp++ = 'o';
|
||||||
*cp++ = formstr[flg & OPTYPE];
|
*cp++ = formstr[flg & OPTYPE];
|
||||||
*cp++ = 0;
|
*cp++ = 0;
|
||||||
return res;
|
return res;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void dump(int n)
|
||||||
dump(n)
|
|
||||||
{
|
{
|
||||||
register glob_t *gb;
|
register glob_t *gb;
|
||||||
register line_t *ln;
|
register line_t *ln;
|
||||||
|
@ -73,24 +85,29 @@ dump(n)
|
||||||
int insno;
|
int insno;
|
||||||
extern char em_mnem[][4];
|
extern char em_mnem[][4];
|
||||||
|
|
||||||
if (d_flag==0) return;
|
if (d_flag == 0)
|
||||||
if ( (n==0 && d_flag) || (n==4 && d_flag>=2) || (n<100 && d_flag>=3) ) {
|
return;
|
||||||
|
if ((n == 0 && d_flag) || (n == 4 && d_flag >= 2)
|
||||||
|
|| (n < 100 && d_flag >= 3))
|
||||||
|
{
|
||||||
printf("\nEM1-assembler ***** pass %1d complete:\n", n);
|
printf("\nEM1-assembler ***** pass %1d complete:\n", n);
|
||||||
printf("current size %ld\n", prog_size);
|
printf("current size %ld\n", prog_size);
|
||||||
printf(" %9.9s%9.9s%14.14s%8.8s%8.8s\n", "instr_nr",
|
printf(" %9.9s%9.9s%14.14s%8.8s%8.8s\n", "instr_nr", "type1", "addr1",
|
||||||
"type1","addr1","length","format");
|
"length", "format");
|
||||||
for (ln = pstate.s_fline; ln;
|
for (ln = pstate.s_fline; ln;
|
||||||
ln = ln->l_next, n>=3 || n==0 ? i++ : i-- ) {
|
ln = ln->l_next, n >= 3 || n == 0 ? i++ : i--)
|
||||||
|
{
|
||||||
insno = ctrunc(ln->instr_num);
|
insno = ctrunc(ln->instr_num);
|
||||||
if ( insno==sp_fpseu ) {
|
if (insno == sp_fpseu)
|
||||||
|
{
|
||||||
i = ln->ad.ad_ln.ln_first;
|
i = ln->ad.ad_ln.ln_first;
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
printf("%4d ", i);
|
printf("%4d ", i);
|
||||||
switch(insno) {
|
switch (insno)
|
||||||
|
{
|
||||||
default:
|
default:
|
||||||
printf(
|
printf(" %3.3s", em_mnem[insno]);
|
||||||
" %3.3s",em_mnem[insno]) ;
|
|
||||||
break;
|
break;
|
||||||
case sp_ilb1:
|
case sp_ilb1:
|
||||||
printf("l ");
|
printf("l ");
|
||||||
|
@ -103,76 +120,87 @@ if ( (n==0 && d_flag) || (n==4 && d_flag>=2) || (n<100 && d_flag>=3) ) {
|
||||||
typestr[ln->type1 < VALLOW ? ln->type1 : CONST],
|
typestr[ln->type1 < VALLOW ? ln->type1 : CONST],
|
||||||
nicepr(ln->type1, &ln->ad));
|
nicepr(ln->type1, &ln->ad));
|
||||||
if (ln->opoff != NO_OFF)
|
if (ln->opoff != NO_OFF)
|
||||||
printf("%5d %.6s",
|
printf("%5d %.6s", oplength(*(ln->opoff)),
|
||||||
oplength(*(ln->opoff)),pflags(*(ln->opoff)));
|
pflags(*(ln->opoff)));
|
||||||
printf("\n");
|
printf("\n");
|
||||||
}
|
}
|
||||||
printf("\n %8s%8s%8s%8s%8s\n", "labnum", "labid", "minval", "maxval",
|
printf("\n %8s%8s%8s%8s%8s\n", "labnum", "labid", "minval", "maxval",
|
||||||
"defined");
|
"defined");
|
||||||
for ( i = 0, lbhead= *pstate.s_locl ; i<LOCLABSIZE ; lbhead++,i++) {
|
for (i = 0, lbhead = *pstate.s_locl; i < LOCLABSIZE; lbhead++, i++)
|
||||||
if ( lbhead->l_defined!=EMPTY ) printf("%4d\n",i);
|
{
|
||||||
for (lbp= lbhead; lbp != lbp_cast 0; lbp= lbp->l_chain) {
|
if (lbhead->l_defined != EMPTY)
|
||||||
|
printf("%4d\n", i);
|
||||||
|
for (lbp = lbhead; lbp != lbp_cast 0; lbp = lbp->l_chain)
|
||||||
|
{
|
||||||
if (lbp->l_defined != EMPTY)
|
if (lbp->l_defined != EMPTY)
|
||||||
printf(" %8d%8d%8d%8d %-s\n",
|
printf(" %8d%8d%8d%8d %-s\n",
|
||||||
lbp->l_hinum * LOCLABSIZE + i,
|
lbp->l_hinum * LOCLABSIZE + i,
|
||||||
int_cast lbp,lbp->l_min,
|
int_cast lbp, lbp->l_min, lbp->l_max,
|
||||||
lbp->l_max, labstr[lbp->l_defined]);
|
labstr[(unsigned char)lbp->l_defined]);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if ( ( (n==0 || n>=100) && d_flag) || (n<=1 && d_flag>=2) ) {
|
if (((n == 0 || n >= 100) && d_flag) || (n <= 1 && d_flag >= 2))
|
||||||
if ( n==0 || n==100 ) {
|
{
|
||||||
|
if (n == 0 || n == 100)
|
||||||
|
{
|
||||||
printf("File %s", curfile);
|
printf("File %s", curfile);
|
||||||
if ( archmode ) printf("(%.14s)",archhdr.ar_name);
|
if (archmode)
|
||||||
|
printf("(%.14s)", archhdr.ar_name);
|
||||||
printf(" :\n\n");
|
printf(" :\n\n");
|
||||||
}
|
}
|
||||||
printf("Local data labels:\n");
|
printf("Local data labels:\n");
|
||||||
printf(
|
printf("\n\t%8.8s %8.8s %8.8s\n", "g_name", "g_status", "g_addr");
|
||||||
"\n\t%8.8s %8.8s %8.8s\n","g_name","g_status","g_addr");
|
|
||||||
for (gb = mglobs, i = 0; gb < &mglobs[oursize->n_mlab]; gb++, i++)
|
for (gb = mglobs, i = 0; gb < &mglobs[oursize->n_mlab]; gb++, i++)
|
||||||
if (gb->g_name[0] != 0) {
|
if (gb->g_name[0] != 0)
|
||||||
|
{
|
||||||
printf("%5d\t%8.6s", i, gb->g_name);
|
printf("%5d\t%8.6s", i, gb->g_name);
|
||||||
printf(" %8o %8ld\n", gb->g_status, gb->g_val.g_addr);
|
printf(" %8o %8ld\n", gb->g_status, gb->g_val.g_addr);
|
||||||
}
|
}
|
||||||
printf("\n\nGlobal data labels\n");
|
printf("\n\nGlobal data labels\n");
|
||||||
printf("\n\t%8.8s %8.8s %8.8s\n",
|
printf("\n\t%8.8s %8.8s %8.8s\n", "g_name", "g_status", "g_addr");
|
||||||
"g_name","g_status","g_addr");
|
|
||||||
for (gb = xglobs, i = 0; gb < &xglobs[oursize->n_glab]; gb++, i++)
|
for (gb = xglobs, i = 0; gb < &xglobs[oursize->n_glab]; gb++, i++)
|
||||||
if (gb->g_name != 0) {
|
if (gb->g_name != 0)
|
||||||
|
{
|
||||||
printf("%5d\t%8.6s", i, gb->g_name);
|
printf("%5d\t%8.6s", i, gb->g_name);
|
||||||
printf(" %8o %8ld\n", gb->g_status, gb->g_val.g_addr);
|
printf(" %8o %8ld\n", gb->g_status, gb->g_val.g_addr);
|
||||||
}
|
}
|
||||||
printf("\n\nLocal procedures\n");
|
printf("\n\nLocal procedures\n");
|
||||||
printf("\n\t%8.8s%8s%8s\t%8s%8s\n",
|
printf("\n\t%8.8s%8s%8s\t%8s%8s\n", "name", "status", "num", "off",
|
||||||
"name","status","num","off","locals");
|
"locals");
|
||||||
for (pl = mprocs; pl < &mprocs[oursize->n_mproc]; pl++)
|
for (pl = mprocs; pl < &mprocs[oursize->n_mproc]; pl++)
|
||||||
if (pl->p_name) {
|
if (pl->p_name)
|
||||||
printf("%4d\t%-8s%8o%8d",
|
{
|
||||||
pl-mprocs,pl->p_name,pl->p_status,pl->p_num);
|
printf("%4d\t%-8s%8o%8d", pl - mprocs, pl->p_name, pl->p_status,
|
||||||
|
pl->p_num);
|
||||||
if (pl->p_status & DEF)
|
if (pl->p_status & DEF)
|
||||||
printf("\t%8ld%8ld", proctab[pl->p_num].pr_off,
|
printf("\t%8ld%8ld", proctab[pl->p_num].pr_off,
|
||||||
proctab[pl->p_num].pr_loc);
|
proctab[pl->p_num].pr_loc);
|
||||||
printf("\n");
|
printf("\n");
|
||||||
}
|
}
|
||||||
printf("\nGlobal procedures\n");
|
printf("\nGlobal procedures\n");
|
||||||
printf("\n\t%8s%8s%8s\t%8s%8s\n",
|
printf("\n\t%8s%8s%8s\t%8s%8s\n", "name", "status", "num", "off",
|
||||||
"name","status","num","off","locals");
|
"locals");
|
||||||
for (pl = xprocs; pl < &xprocs[oursize->n_xproc]; pl++)
|
for (pl = xprocs; pl < &xprocs[oursize->n_xproc]; pl++)
|
||||||
if (pl->p_name) {
|
if (pl->p_name)
|
||||||
printf("%4d\t%-8s%8o%8d",
|
{
|
||||||
pl-xprocs,pl->p_name,pl->p_status,pl->p_num);
|
printf("%4d\t%-8s%8o%8d", pl - xprocs, pl->p_name, pl->p_status,
|
||||||
|
pl->p_num);
|
||||||
if (pl->p_status & DEF)
|
if (pl->p_status & DEF)
|
||||||
printf("\t%8ld%8ld", proctab[pl->p_num].pr_off,
|
printf("\t%8ld%8ld", proctab[pl->p_num].pr_off,
|
||||||
proctab[pl->p_num].pr_loc);
|
proctab[pl->p_num].pr_loc);
|
||||||
printf("\n");
|
printf("\n");
|
||||||
}
|
}
|
||||||
if ( r_flag ) {
|
if (r_flag)
|
||||||
|
{
|
||||||
register relc_t *rl;
|
register relc_t *rl;
|
||||||
printf("\nData relocation\n");
|
printf("\nData relocation\n");
|
||||||
printf("\n\t%10s %10s %10s\n", "offset", "type", "value");
|
printf("\n\t%10s %10s %10s\n", "offset", "type", "value");
|
||||||
for ( rl=f_data ; rl ; rl= rl->r_next ) {
|
for (rl = f_data; rl; rl = rl->r_next)
|
||||||
|
{
|
||||||
printf("\t%10ld %10s ", rl->r_off, r_data[rl->r_typ]);
|
printf("\t%10ld %10s ", rl->r_off, r_data[rl->r_typ]);
|
||||||
switch(rl->r_typ) {
|
switch (rl->r_typ)
|
||||||
|
{
|
||||||
case RELADR:
|
case RELADR:
|
||||||
case RELHEAD:
|
case RELHEAD:
|
||||||
printf("%10ld\n", rl->r_val.rel_i);
|
printf("%10ld\n", rl->r_val.rel_i);
|
||||||
|
@ -184,21 +212,23 @@ if ( ( (n==0 || n>=100) && d_flag) || (n<=1 && d_flag>=2) ) {
|
||||||
printf("%10d\n", rl->r_val.rel_lp);
|
printf("%10d\n", rl->r_val.rel_lp);
|
||||||
break;
|
break;
|
||||||
case RELNULL:
|
case RELNULL:
|
||||||
printf("\n"); break ;
|
printf("\n");
|
||||||
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
printf("\n\nText relocation\n");
|
printf("\n\nText relocation\n");
|
||||||
printf("\n\t%10s %10s %10s\n", "offset", "flags", "value");
|
printf("\n\t%10s %10s %10s\n", "offset", "flags", "value");
|
||||||
for ( rl=f_text; rl ; rl= rl->r_next ) {
|
for (rl = f_text; rl; rl = rl->r_next)
|
||||||
printf("\t%10ld %10s ",
|
{
|
||||||
rl->r_off,pflags(opchoice[rl->r_typ&~RELMNS])) ;
|
printf("\t%10ld %10s ", rl->r_off,
|
||||||
|
pflags(opchoice[rl->r_typ & ~RELMNS]));
|
||||||
if (rl->r_typ & RELMNS)
|
if (rl->r_typ & RELMNS)
|
||||||
printf("%10ld\n", rl->r_val.rel_i);
|
printf("%10ld\n", rl->r_val.rel_i);
|
||||||
else printf("\n") ;
|
else
|
||||||
|
printf("\n");
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
|
|
|
@ -4,12 +4,11 @@
|
||||||
*
|
*
|
||||||
*/
|
*/
|
||||||
|
|
||||||
|
#include <string.h>
|
||||||
|
#include <stddef.h>
|
||||||
#include "ass00.h"
|
#include "ass00.h"
|
||||||
#include "assex.h"
|
#include "assex.h"
|
||||||
|
#include "asscm.h"
|
||||||
#ifndef NORCSID
|
|
||||||
static char rcs_id[] = "$Id$" ;
|
|
||||||
#endif
|
|
||||||
|
|
||||||
/*
|
/*
|
||||||
** utilities of EM1-assembler/loader
|
** utilities of EM1-assembler/loader
|
||||||
|
@ -17,15 +16,16 @@ static char rcs_id[] = "$Id$" ;
|
||||||
|
|
||||||
static int globstep;
|
static int globstep;
|
||||||
|
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* glohash returns an index in table and leaves a stepsize in globstep
|
* glohash returns an index in table and leaves a stepsize in globstep
|
||||||
*
|
*
|
||||||
*/
|
*/
|
||||||
|
static int glohash(char *aname ,int size)
|
||||||
static int glohash(aname,size) char *aname; {
|
{
|
||||||
register char *p;
|
register char *p;
|
||||||
register i;
|
register int i;
|
||||||
register sum;
|
register int sum;
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Computes a hash-value from a string.
|
* Computes a hash-value from a string.
|
||||||
|
@ -44,17 +44,19 @@ static int glohash(aname,size) char *aname; {
|
||||||
* return index in labeltable
|
* return index in labeltable
|
||||||
*/
|
*/
|
||||||
|
|
||||||
glob_t *glo2lookup(name,status) char *name; {
|
glob_t *glo2lookup(char *name ,int status)
|
||||||
|
{
|
||||||
return(glolookup(name,status,mglobs,oursize->n_mlab));
|
return(glolookup(name,status,mglobs,oursize->n_mlab));
|
||||||
}
|
}
|
||||||
|
|
||||||
glob_t *xglolookup(name,status) char *name; {
|
glob_t *xglolookup(char *name,int status)
|
||||||
|
{
|
||||||
|
|
||||||
return(glolookup(name,status,xglobs,oursize->n_glab));
|
return(glolookup(name,status,xglobs,oursize->n_glab));
|
||||||
}
|
}
|
||||||
|
|
||||||
static void findext(g) glob_t *g ; {
|
static void findext(glob_t *g)
|
||||||
|
{
|
||||||
glob_t *x;
|
glob_t *x;
|
||||||
|
|
||||||
x = xglolookup(g->g_name,ENTERING);
|
x = xglolookup(g->g_name,ENTERING);
|
||||||
|
@ -65,19 +67,10 @@ static void findext(g) glob_t *g ; {
|
||||||
g->g_status |= EXT;
|
g->g_status |= EXT;
|
||||||
}
|
}
|
||||||
|
|
||||||
glob_t *glolookup(name,status,table,size)
|
|
||||||
char *name; /* name */
|
|
||||||
int status; /* kind of lookup */
|
|
||||||
glob_t *table; /* which table to use */
|
|
||||||
int size; /* size for hash */
|
|
||||||
{
|
|
||||||
register glob_t *g;
|
|
||||||
register rem,j;
|
|
||||||
int new;
|
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* lookup global symbol name in specified table.
|
* lookup global symbol name in specified table.
|
||||||
* Various actions are taken depending on status.
|
* Various actions are taken depending on status
|
||||||
|
* parameter.
|
||||||
*
|
*
|
||||||
* DEFINING:
|
* DEFINING:
|
||||||
* Lookup or enter the symbol, check for mult. def.
|
* Lookup or enter the symbol, check for mult. def.
|
||||||
|
@ -92,6 +85,12 @@ int size; /* size for hash */
|
||||||
* ENTERING:
|
* ENTERING:
|
||||||
* Lookup or enter the symbol, don't check
|
* Lookup or enter the symbol, don't check
|
||||||
*/
|
*/
|
||||||
|
glob_t *glolookup(char *name,int status,glob_t *table, int size)
|
||||||
|
{
|
||||||
|
register glob_t *g;
|
||||||
|
register int rem,j;
|
||||||
|
int new;
|
||||||
|
|
||||||
|
|
||||||
rem = glohash(name,size);
|
rem = glohash(name,size);
|
||||||
j = 0; new=0;
|
j = 0; new=0;
|
||||||
|
@ -150,9 +149,18 @@ int size; /* size for hash */
|
||||||
return(g);
|
return(g);
|
||||||
}
|
}
|
||||||
|
|
||||||
locl_t *loclookup(an,status) {
|
/*
|
||||||
|
* lookup local label by number and return the
|
||||||
|
* label definition if found.
|
||||||
|
*
|
||||||
|
* DEFINING:
|
||||||
|
* Lookup or enter the symbol, check for mult. def.
|
||||||
|
*
|
||||||
|
*/
|
||||||
|
locl_t *loclookup(unsigned int an,int status)
|
||||||
|
{
|
||||||
register locl_t *lbp,*l_lbp;
|
register locl_t *lbp,*l_lbp;
|
||||||
register unsigned num;
|
register unsigned int num;
|
||||||
char hinum;
|
char hinum;
|
||||||
|
|
||||||
if ( !pstate.s_locl ) fatal("label outside procedure");
|
if ( !pstate.s_locl ) fatal("label outside procedure");
|
||||||
|
@ -188,10 +196,6 @@ locl_t *loclookup(an,status) {
|
||||||
return(lbp);
|
return(lbp);
|
||||||
}
|
}
|
||||||
|
|
||||||
proc_t *prolookup(name,status) char *name; {
|
|
||||||
register proc_t *p;
|
|
||||||
register pstat;
|
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Look up a procedure name according to status
|
* Look up a procedure name according to status
|
||||||
*
|
*
|
||||||
|
@ -208,6 +212,11 @@ proc_t *prolookup(name,status) char *name; {
|
||||||
* The EXT bit in this table indicates the the name is used
|
* The EXT bit in this table indicates the the name is used
|
||||||
* as external in this module.
|
* as external in this module.
|
||||||
*/
|
*/
|
||||||
|
proc_t *prolookup(char *name,int status)
|
||||||
|
{
|
||||||
|
register proc_t *p= NULL;
|
||||||
|
register int pstat = 0;
|
||||||
|
|
||||||
|
|
||||||
switch(status) {
|
switch(status) {
|
||||||
case PRO_OCC:
|
case PRO_OCC:
|
||||||
|
@ -281,18 +290,15 @@ proc_t *prolookup(name,status) char *name; {
|
||||||
return(enterproc(name,pstat,p));
|
return(enterproc(name,pstat,p));
|
||||||
}
|
}
|
||||||
|
|
||||||
proc_t *searchproc(name,table,size)
|
|
||||||
char *name;
|
|
||||||
proc_t *table;
|
|
||||||
int size;
|
|
||||||
{
|
|
||||||
register proc_t *p;
|
|
||||||
register rem,j;
|
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* return a pointer into table to the place where the procedure
|
* return a pointer into table to the place where the procedure
|
||||||
* name is or should be if in the table.
|
* name is or should be if in the table.
|
||||||
*/
|
*/
|
||||||
|
proc_t *searchproc(char *name,proc_t *table,int size)
|
||||||
|
{
|
||||||
|
register proc_t *p;
|
||||||
|
register int rem,j;
|
||||||
|
|
||||||
|
|
||||||
rem = glohash(name,size);
|
rem = glohash(name,size);
|
||||||
j = 0;
|
j = 0;
|
||||||
|
@ -307,12 +313,6 @@ proc_t *searchproc(name,table,size)
|
||||||
return(p);
|
return(p);
|
||||||
}
|
}
|
||||||
|
|
||||||
proc_t *enterproc(name,status,place)
|
|
||||||
char *name;
|
|
||||||
char status;
|
|
||||||
proc_t *place; {
|
|
||||||
register proc_t *p;
|
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Enter the procedure name into the table at place place.
|
* Enter the procedure name into the table at place place.
|
||||||
* Place had better be computed by searchproc().
|
* Place had better be computed by searchproc().
|
||||||
|
@ -325,6 +325,9 @@ proc_t *place; {
|
||||||
* Two local procedures with the same name in different
|
* Two local procedures with the same name in different
|
||||||
* modules have different numbers.
|
* modules have different numbers.
|
||||||
*/
|
*/
|
||||||
|
proc_t *enterproc(char *name,int status,proc_t *place)
|
||||||
|
{
|
||||||
|
register proc_t *p;
|
||||||
|
|
||||||
p=place;
|
p=place;
|
||||||
p->p_name = (char *) getarea((unsigned) (strlen(name) + 1));
|
p->p_name = (char *) getarea((unsigned) (strlen(name) + 1));
|
||||||
|
|
180
util/ass/ass80.c
180
util/ass/ass80.c
|
@ -6,28 +6,19 @@
|
||||||
|
|
||||||
#include "ass00.h"
|
#include "ass00.h"
|
||||||
#include "assex.h"
|
#include "assex.h"
|
||||||
#include <em_path.h>
|
#include "assrl.h"
|
||||||
|
#include <stddef.h>
|
||||||
|
#include <stdio.h>
|
||||||
#include <stdarg.h>
|
#include <stdarg.h>
|
||||||
|
#include "system.h"
|
||||||
|
|
||||||
#ifndef NORCSID
|
|
||||||
static char rcs_id[] = "$Id$" ;
|
|
||||||
#endif
|
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* this file contains several library routines.
|
* this file contains several library routines.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
zero(area,length) char *area; unsigned length ; {
|
static char filename[L_tmpnam];
|
||||||
register char *p;
|
|
||||||
register n;
|
|
||||||
/*
|
|
||||||
* Clear area of length bytes.
|
|
||||||
*/
|
|
||||||
if ((n=length)==0)
|
|
||||||
return;
|
|
||||||
p = area;
|
|
||||||
do *p++=0; while (--n);
|
|
||||||
}
|
|
||||||
|
|
||||||
/* VARARGS1 */
|
/* VARARGS1 */
|
||||||
static void pr_error(const char* string1, va_list ap) {
|
static void pr_error(const char* string1, va_list ap) {
|
||||||
|
@ -60,7 +51,8 @@ void error(const char* string1, ...)
|
||||||
}
|
}
|
||||||
|
|
||||||
/* VARARGS1 */
|
/* VARARGS1 */
|
||||||
void werror(const char* string1, ...) {
|
void werror(const char* string1, ...)
|
||||||
|
{
|
||||||
va_list ap;
|
va_list ap;
|
||||||
if ( wflag ) return ;
|
if ( wflag ) return ;
|
||||||
|
|
||||||
|
@ -69,57 +61,44 @@ void werror(const char* string1, ...) {
|
||||||
va_end(ap);
|
va_end(ap);
|
||||||
}
|
}
|
||||||
|
|
||||||
fatal(s) char *s; {
|
void fatal(char *s)
|
||||||
|
{
|
||||||
/*
|
/*
|
||||||
* handle fatal errors
|
* handle fatal errors
|
||||||
*/
|
*/
|
||||||
error("Fatal error: %s",s);
|
error("Fatal error: %s",s);
|
||||||
dump(0);
|
dump(0);
|
||||||
exit(-1);
|
exit(EXIT_FAILURE);
|
||||||
}
|
}
|
||||||
|
|
||||||
#ifndef CPM
|
|
||||||
FILE *frewind(f) FILE *f ; {
|
|
||||||
/* Rewind a file open for writing and open it for reading */
|
|
||||||
/* Assumption, file descriptor is r/w */
|
|
||||||
register FILE *tmp ;
|
|
||||||
tmp=fdopen(dup(fileno(f)),"r");
|
|
||||||
fclose(f);
|
|
||||||
rewind(tmp);
|
|
||||||
return tmp ;
|
|
||||||
}
|
|
||||||
#endif
|
|
||||||
|
|
||||||
int xgetc(af) register FILE *af; {
|
|
||||||
|
int xgetc(register FILE *af)
|
||||||
|
{
|
||||||
register int nextc;
|
register int nextc;
|
||||||
/*
|
|
||||||
* read next character; fatal if there isn't one
|
|
||||||
*/
|
|
||||||
nextc=fgetc(af) ;
|
nextc=fgetc(af) ;
|
||||||
if ( feof(af) )
|
if ( feof(af) )
|
||||||
fatal("unexpected end of file");
|
fatal("unexpected end of file");
|
||||||
return nextc ;
|
return nextc ;
|
||||||
}
|
}
|
||||||
|
|
||||||
xputc(c,af) register FILE *af; {
|
void xputc(int c,register FILE *af)
|
||||||
/* output one character and scream if it gives an error */
|
{
|
||||||
fputc(c,af) ;
|
fputc(c,af) ;
|
||||||
if ( ferror(af) ) fatal("write error") ;
|
if ( ferror(af) ) fatal("write error") ;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
putblk(stream,from,amount)
|
void putblk(register FILE *stream,register char *from, register int amount)
|
||||||
register FILE *stream; register char *from ; register int amount ; {
|
{
|
||||||
|
|
||||||
for ( ; amount-- ; from++ ) {
|
for ( ; amount-- ; from++ ) {
|
||||||
fputc(*from,stream) ;
|
fputc(*from,stream) ;
|
||||||
if ( ferror(stream) ) fatal("write error") ;
|
if ( ferror(stream) ) fatal("write error") ;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
int getblk(stream,from,amount)
|
int getblk(register FILE *stream, register char *from, register int amount)
|
||||||
register FILE *stream; register char *from ; register int amount ; {
|
{
|
||||||
|
|
||||||
for ( ; amount-- ; from++ ) {
|
for ( ; amount-- ; from++ ) {
|
||||||
*from = fgetc(stream) ;
|
*from = fgetc(stream) ;
|
||||||
if ( feof(stream) ) return 1 ;
|
if ( feof(stream) ) return 1 ;
|
||||||
|
@ -127,7 +106,8 @@ int getblk(stream,from,amount)
|
||||||
return 0 ;
|
return 0 ;
|
||||||
}
|
}
|
||||||
|
|
||||||
xput16(w,f) FILE *f; {
|
void xput16(int w,FILE *f)
|
||||||
|
{
|
||||||
/*
|
/*
|
||||||
* two times xputc
|
* two times xputc
|
||||||
*/
|
*/
|
||||||
|
@ -135,19 +115,22 @@ xput16(w,f) FILE *f; {
|
||||||
xputc(w>>8,f);
|
xputc(w>>8,f);
|
||||||
}
|
}
|
||||||
|
|
||||||
xputarb(l,w,f) int l ; cons_t w ; FILE *f ; {
|
void xputarb(int l,cons_t w, FILE* f)
|
||||||
|
{
|
||||||
while ( l-- ) {
|
while ( l-- ) {
|
||||||
xputc( int_cast w,f) ;
|
xputc( int_cast w,f) ;
|
||||||
w >>=8 ;
|
w >>=8 ;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
put8(n) {
|
void put8(int n)
|
||||||
|
{
|
||||||
xputc(n,tfile);
|
xputc(n,tfile);
|
||||||
textoff++;
|
textoff++;
|
||||||
}
|
}
|
||||||
|
|
||||||
put16(n) {
|
void put16(int n)
|
||||||
|
{
|
||||||
/*
|
/*
|
||||||
* note reversed order of bytes.
|
* note reversed order of bytes.
|
||||||
* this is done for faster interpretation.
|
* this is done for faster interpretation.
|
||||||
|
@ -157,16 +140,19 @@ put16(n) {
|
||||||
textoff += 2;
|
textoff += 2;
|
||||||
}
|
}
|
||||||
|
|
||||||
put32(n) cons_t n ; {
|
void put32(cons_t n)
|
||||||
|
{
|
||||||
put16( int_cast (n>>16)) ;
|
put16( int_cast (n>>16)) ;
|
||||||
put16( int_cast n) ;
|
put16( int_cast n) ;
|
||||||
}
|
}
|
||||||
|
|
||||||
put64(n) cons_t n ; {
|
void put64(cons_t n)
|
||||||
|
{
|
||||||
fatal("put64 called") ;
|
fatal("put64 called") ;
|
||||||
}
|
}
|
||||||
|
|
||||||
int xget8() {
|
int xget8(void)
|
||||||
|
{
|
||||||
/*
|
/*
|
||||||
* Read one byte from ifile.
|
* Read one byte from ifile.
|
||||||
*/
|
*/
|
||||||
|
@ -176,7 +162,8 @@ int xget8() {
|
||||||
return fgetc(ifile) ;
|
return fgetc(ifile) ;
|
||||||
}
|
}
|
||||||
|
|
||||||
unsigned get8() {
|
unsigned int get8(void)
|
||||||
|
{
|
||||||
register int nextc;
|
register int nextc;
|
||||||
/*
|
/*
|
||||||
* Read one byte from ifile.
|
* Read one byte from ifile.
|
||||||
|
@ -191,16 +178,17 @@ unsigned get8() {
|
||||||
return nextc ;
|
return nextc ;
|
||||||
}
|
}
|
||||||
|
|
||||||
cons_t xgetarb(l,f) int l; FILE *f ; {
|
cons_t xgetarb(int l,FILE *f)
|
||||||
|
{
|
||||||
cons_t val ;
|
cons_t val ;
|
||||||
register int shift ;
|
register int shift ;
|
||||||
int c;
|
int c;
|
||||||
|
|
||||||
shift=0 ; val=0 ;
|
shift=0 ; val=0 ;
|
||||||
while ( l-- ) {
|
while ( l-- ) {
|
||||||
// val += ((cons_t)(c = ctrunc(xgetc(f))))<<shift ;
|
/* val += ((cons_t)(c = ctrunc(xgetc(f))))<<shift ;
|
||||||
// Bug here: shifts with too large shift counts
|
Bug here: shifts with too large shift counts
|
||||||
// get unspecified results. --Ceriel
|
get unspecified results. --Ceriel */
|
||||||
c = ctrunc(xgetc(f));
|
c = ctrunc(xgetc(f));
|
||||||
if (shift < 8 * sizeof(cons_t)) {
|
if (shift < 8 * sizeof(cons_t)) {
|
||||||
val += ((cons_t)c)<<shift ;
|
val += ((cons_t)c)<<shift ;
|
||||||
|
@ -216,7 +204,8 @@ cons_t xgetarb(l,f) int l; FILE *f ; {
|
||||||
return val ;
|
return val ;
|
||||||
}
|
}
|
||||||
|
|
||||||
ext8(b) {
|
void ext8(int b)
|
||||||
|
{
|
||||||
/*
|
/*
|
||||||
* Handle one byte of data.
|
* Handle one byte of data.
|
||||||
*/
|
*/
|
||||||
|
@ -224,55 +213,56 @@ ext8(b) {
|
||||||
xputc(b,dfile);
|
xputc(b,dfile);
|
||||||
}
|
}
|
||||||
|
|
||||||
extword(w) cons_t w ; {
|
void extword(cons_t w)
|
||||||
|
{
|
||||||
/* Assemble the word constant w.
|
/* Assemble the word constant w.
|
||||||
* NOTE: The bytes are written low to high.
|
* NOTE: The bytes are written low to high.
|
||||||
*/
|
*/
|
||||||
register i ;
|
register int i ;
|
||||||
for ( i=wordsize ; i-- ; ) {
|
for ( i=wordsize ; i-- ; ) {
|
||||||
ext8( int_cast w) ;
|
ext8( int_cast w) ;
|
||||||
w >>= 8 ;
|
w >>= 8 ;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
extarb(size,value) int size ; long value ; {
|
void extarb(int size, long value)
|
||||||
|
{
|
||||||
/* Assemble the 'size' constant value.
|
/* Assemble the 'size' constant value.
|
||||||
* The bytes are again written low to high.
|
* The bytes are again written low to high.
|
||||||
*/
|
*/
|
||||||
register i ;
|
register int i ;
|
||||||
for ( i=size ; i-- ; ) {
|
for ( i=size ; i-- ; ) {
|
||||||
ext8( int_cast value ) ;
|
ext8( int_cast value ) ;
|
||||||
value >>=8 ;
|
value >>=8 ;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
extadr(a) cons_t a ; {
|
void extadr(cons_t a)
|
||||||
/* Assemble the word constant a.
|
{
|
||||||
|
/* Assemble the pointer constant a.
|
||||||
* NOTE: The bytes are written low to high.
|
* NOTE: The bytes are written low to high.
|
||||||
*/
|
*/
|
||||||
register i ;
|
register int i ;
|
||||||
for ( i=ptrsize ; i-- ; ) {
|
for ( i=ptrsize ; i-- ; ) {
|
||||||
ext8( int_cast a) ;
|
ext8( int_cast a) ;
|
||||||
a >>= 8 ;
|
a >>= 8 ;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
xputa(a,f) cons_t a ; FILE *f ; {
|
void xputa(cons_t a,FILE* f)
|
||||||
/* Assemble the pointer constant a.
|
{
|
||||||
* NOTE: The bytes are written low to high.
|
|
||||||
*/
|
register int i ;
|
||||||
register i ;
|
|
||||||
for ( i=ptrsize ; i-- ; ) {
|
for ( i=ptrsize ; i-- ; ) {
|
||||||
xputc( int_cast a,f) ;
|
xputc( int_cast a,f) ;
|
||||||
a >>= 8 ;
|
a >>= 8 ;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
cons_t xgeta(f) FILE *f ; {
|
cons_t xgeta(FILE* f)
|
||||||
/* Read the pointer constant a.
|
{
|
||||||
* NOTE: The bytes were written low to high.
|
|
||||||
*/
|
register int i, shift ;
|
||||||
register i, shift ;
|
|
||||||
cons_t val ;
|
cons_t val ;
|
||||||
val = 0 ; shift=0 ;
|
val = 0 ; shift=0 ;
|
||||||
for ( i=ptrsize ; i-- ; ) {
|
for ( i=ptrsize ; i-- ; ) {
|
||||||
|
@ -282,14 +272,16 @@ cons_t xgeta(f) FILE *f ; {
|
||||||
return val ;
|
return val ;
|
||||||
}
|
}
|
||||||
|
|
||||||
int icount(size) {
|
int icount(int size)
|
||||||
|
{
|
||||||
int amount ;
|
int amount ;
|
||||||
amount=(dataoff-lastoff)/size ;
|
amount=(dataoff-lastoff)/size ;
|
||||||
if ( amount>MAXBYTE) fatal("Descriptor overflow");
|
if ( amount>MAXBYTE) fatal("Descriptor overflow");
|
||||||
return amount ;
|
return amount ;
|
||||||
}
|
}
|
||||||
|
|
||||||
set_mode(mode) {
|
void set_mode(int mode)
|
||||||
|
{
|
||||||
|
|
||||||
if (datamode==mode) { /* in right mode already */
|
if (datamode==mode) { /* in right mode already */
|
||||||
switch ( datamode ) {
|
switch ( datamode ) {
|
||||||
|
@ -389,40 +381,12 @@ set_mode(mode) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
#ifndef CPM
|
|
||||||
int tmpfil() {
|
char* tmpfil(void)
|
||||||
register char *fname, *cpname ;
|
{
|
||||||
static char sfname[] = "tmp.00000";
|
if (sys_tmpnam(filename)==NULL)
|
||||||
register fildes,pid;
|
{
|
||||||
static char name[80] = TMP_DIR ;
|
fatal("Cannot create temporary filename.");
|
||||||
int count;
|
|
||||||
/*
|
|
||||||
* This procedure returns a file-descriptor of a temporary
|
|
||||||
* file valid for reading and writing.
|
|
||||||
* After closing the tmpfil-descriptor the file is lost
|
|
||||||
* Calling this routine frees the program from generating uniqe names.
|
|
||||||
*/
|
|
||||||
fname = sfname+4;
|
|
||||||
count = 10;
|
|
||||||
pid = getpid();
|
|
||||||
while (pid!=0) {
|
|
||||||
*fname++ = (pid&07) + '0';
|
|
||||||
pid >>= 3;
|
|
||||||
}
|
}
|
||||||
*fname = 0;
|
return filename;
|
||||||
for ( fname=name ; *fname ; fname++ ) ;
|
|
||||||
cpname=sfname ;
|
|
||||||
while ( *fname++ = *cpname++ ) ;
|
|
||||||
do {
|
|
||||||
fname = name;
|
|
||||||
if ((fildes = creat(fname, 0600)) < 0)
|
|
||||||
if ((fildes = creat(fname=sfname, 0600)) < 0)
|
|
||||||
return(-1);
|
|
||||||
if (close(fildes) < 0)
|
|
||||||
;
|
|
||||||
} while((fildes = open(fname, 2)) < 0 && count--);
|
|
||||||
if (unlink(fname) < 0)
|
|
||||||
;
|
|
||||||
return(fildes);
|
|
||||||
}
|
}
|
||||||
#endif
|
|
||||||
|
|
739
util/ass/assci.c
739
util/ass/assci.c
File diff suppressed because it is too large
Load diff
20
util/ass/assci.h
Normal file
20
util/ass/assci.h
Normal file
|
@ -0,0 +1,20 @@
|
||||||
|
/* Copyright (c) 2019 ACK Project.
|
||||||
|
* See the copyright notice in the ACK home directory,
|
||||||
|
* in the file "Copyright".
|
||||||
|
*
|
||||||
|
* Created on: 2019-03-12
|
||||||
|
*
|
||||||
|
*/
|
||||||
|
#ifndef ASSCI_H_
|
||||||
|
#define ASSCI_H_
|
||||||
|
|
||||||
|
|
||||||
|
/*
|
||||||
|
* read module in compact EM1 code and fill in the table in memory
|
||||||
|
* with all the specified data as a linked list.
|
||||||
|
*/
|
||||||
|
void read_compact(void);
|
||||||
|
void newline(int type);
|
||||||
|
void align(int size);
|
||||||
|
|
||||||
|
#endif /* ASSCI_H_ */
|
|
@ -19,31 +19,31 @@
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#include "ass00.h"
|
#include "ass00.h"
|
||||||
|
#include "assex.h"
|
||||||
#ifndef NORCSID
|
#include "asscm.h"
|
||||||
static char rcs_id[] = "$Id$" ;
|
|
||||||
#endif
|
|
||||||
|
|
||||||
#ifdef MEMUSE
|
#ifdef MEMUSE
|
||||||
static unsigned m_used = 0;
|
static unsigned m_used = 0;
|
||||||
static unsigned m_free = 0;
|
static unsigned m_free = 0;
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
struct freeblock {
|
struct freeblock
|
||||||
|
{
|
||||||
struct freeblock *f_next;
|
struct freeblock *f_next;
|
||||||
unsigned f_size;
|
unsigned f_size;
|
||||||
};
|
};
|
||||||
|
|
||||||
static struct freeblock freexx[2] = {
|
static struct freeblock freexx[2] =
|
||||||
|
{
|
||||||
{ freexx, 0 },
|
{ freexx, 0 },
|
||||||
{ freexx+1, 0 }
|
{ freexx + 1, 0 } };
|
||||||
} ;
|
|
||||||
|
|
||||||
#define freehead freexx[1]
|
#define freehead freexx[1]
|
||||||
|
|
||||||
#define CHUNK 2048 /* Smallest chunk to be gotten from UNIX */
|
#define CHUNK 2048 /* Smallest chunk to be gotten from UNIX */
|
||||||
|
|
||||||
area_t getarea(size) unsigned size ; {
|
area_t getarea(unsigned int size)
|
||||||
|
{
|
||||||
register struct freeblock *c_ptr, *l_ptr;
|
register struct freeblock *c_ptr, *l_ptr;
|
||||||
register char *ptr;
|
register char *ptr;
|
||||||
unsigned rqsize;
|
unsigned rqsize;
|
||||||
|
@ -53,26 +53,32 @@ area_t getarea(size) unsigned size ; {
|
||||||
m_used += size;
|
m_used += size;
|
||||||
m_free -= size;
|
m_free -= size;
|
||||||
#endif
|
#endif
|
||||||
for(;;) {
|
for (;;)
|
||||||
|
{
|
||||||
for (l_ptr = &freehead, c_ptr= freehead.f_next;
|
for (l_ptr = &freehead, c_ptr= freehead.f_next;
|
||||||
c_ptr!= &freehead ; c_ptr = c_ptr->f_next ) {
|
c_ptr!= &freehead; c_ptr = c_ptr->f_next )
|
||||||
if ( size==c_ptr->f_size ) {
|
{
|
||||||
|
if ( size==c_ptr->f_size )
|
||||||
|
{
|
||||||
l_ptr->f_next= c_ptr->f_next;
|
l_ptr->f_next= c_ptr->f_next;
|
||||||
return (area_t) c_ptr;
|
return (area_t) c_ptr;
|
||||||
}
|
}
|
||||||
if ( size+sizeof freehead <= c_ptr->f_size ) {
|
if ( size+sizeof freehead <= c_ptr->f_size )
|
||||||
|
{
|
||||||
c_ptr->f_size -= size;
|
c_ptr->f_size -= size;
|
||||||
return (area_t) ((char *) c_ptr + c_ptr->f_size);
|
return (area_t) ((char *) c_ptr + c_ptr->f_size);
|
||||||
}
|
}
|
||||||
l_ptr = c_ptr;
|
l_ptr = c_ptr;
|
||||||
}
|
}
|
||||||
rqsize = size<CHUNK ? CHUNK : size;
|
rqsize = size<CHUNK ? CHUNK : size;
|
||||||
for(;;){
|
for(;;)
|
||||||
|
{
|
||||||
ptr = malloc( rqsize );
|
ptr = malloc( rqsize );
|
||||||
if ( ptr ) break; /* request succesfull */
|
if ( ptr ) break; /* request succesfull */
|
||||||
rqsize /= 2;
|
rqsize /= 2;
|
||||||
rqsize -= rqsize%sizeof (int);
|
rqsize -= rqsize%sizeof (int);
|
||||||
if ( rqsize < sizeof freehead ) {
|
if ( rqsize < sizeof freehead )
|
||||||
|
{
|
||||||
fatal("Out of memory");
|
fatal("Out of memory");
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -84,7 +90,8 @@ area_t getarea(size) unsigned size ; {
|
||||||
/* NOTREACHED */
|
/* NOTREACHED */
|
||||||
}
|
}
|
||||||
|
|
||||||
freearea(ptr,size) register area_t ptr ; unsigned size ; {
|
void freearea(register area_t ptr, unsigned int size)
|
||||||
|
{
|
||||||
register struct freeblock *c_ptr, *l_ptr;
|
register struct freeblock *c_ptr, *l_ptr;
|
||||||
|
|
||||||
size = ((size + (sizeof(int) - 1)) / sizeof(int)) * sizeof(int);
|
size = ((size + (sizeof(int) - 1)) / sizeof(int)) * sizeof(int);
|
||||||
|
@ -93,7 +100,8 @@ freearea(ptr,size) register area_t ptr ; unsigned size ; {
|
||||||
m_used -= size;
|
m_used -= size;
|
||||||
#endif
|
#endif
|
||||||
for (l_ptr = &freehead, c_ptr=freehead.f_next;
|
for (l_ptr = &freehead, c_ptr=freehead.f_next;
|
||||||
c_ptr!= &freehead ; c_ptr= c_ptr->f_next ) {
|
c_ptr!= &freehead; c_ptr= c_ptr->f_next )
|
||||||
|
{
|
||||||
if ( (area_t)c_ptr>ptr ) break;
|
if ( (area_t)c_ptr>ptr ) break;
|
||||||
l_ptr= c_ptr;
|
l_ptr= c_ptr;
|
||||||
}
|
}
|
||||||
|
@ -101,15 +109,21 @@ freearea(ptr,size) register area_t ptr ; unsigned size ; {
|
||||||
/* Beware they may both point to freehead */
|
/* Beware they may both point to freehead */
|
||||||
|
|
||||||
#ifdef MEMUSE
|
#ifdef MEMUSE
|
||||||
if ( ((char *)l_ptr)+l_ptr->f_size> (char *)ptr && (char *)l_ptr<=(char *)ptr )
|
if (((char *) l_ptr) + l_ptr->f_size > (char *) ptr
|
||||||
|
&& (char *) l_ptr <= (char *) ptr)
|
||||||
fatal("Double freed");
|
fatal("Double freed");
|
||||||
if ( ((char *)ptr)+size > (char *)c_ptr && (char *)ptr<=(char *)c_ptr )
|
if (((char *) ptr) + size > (char *) c_ptr
|
||||||
|
&& (char *) ptr <= (char *) c_ptr)
|
||||||
fatal("Frreed double");
|
fatal("Frreed double");
|
||||||
#endif
|
#endif
|
||||||
/* Is the block before this one adjacent ? */
|
/* Is the block before this one adjacent ? */
|
||||||
if ( ((char *)l_ptr) + l_ptr->f_size == (char *) ptr ) {
|
if (((char *) l_ptr) + l_ptr->f_size == (char *) ptr)
|
||||||
l_ptr->f_size += size ; /* yes */
|
{
|
||||||
} else {
|
l_ptr->f_size += size;
|
||||||
|
/* yes */
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
/* No, create an entry */
|
/* No, create an entry */
|
||||||
((struct freeblock *) ptr)->f_next = c_ptr;
|
((struct freeblock *) ptr)->f_next = c_ptr;
|
||||||
((struct freeblock *) ptr)->f_size = size;
|
((struct freeblock *) ptr)->f_size = size;
|
||||||
|
@ -117,7 +131,8 @@ freearea(ptr,size) register area_t ptr ; unsigned size ; {
|
||||||
l_ptr = (struct freeblock *) ptr;
|
l_ptr = (struct freeblock *) ptr;
|
||||||
}
|
}
|
||||||
/* Are the two entries adjacent ? */
|
/* Are the two entries adjacent ? */
|
||||||
if ( (char *)l_ptr + l_ptr->f_size == (char *) c_ptr ) {
|
if ((char *) l_ptr + l_ptr->f_size == (char *) c_ptr)
|
||||||
|
{
|
||||||
/* the two entries are adjacent */
|
/* the two entries are adjacent */
|
||||||
l_ptr->f_next = c_ptr->f_next;
|
l_ptr->f_next = c_ptr->f_next;
|
||||||
l_ptr->f_size += c_ptr->f_size;
|
l_ptr->f_size += c_ptr->f_size;
|
||||||
|
@ -125,7 +140,8 @@ freearea(ptr,size) register area_t ptr ; unsigned size ; {
|
||||||
}
|
}
|
||||||
|
|
||||||
#ifdef MEMUSE
|
#ifdef MEMUSE
|
||||||
memuse() {
|
void memuse(void)
|
||||||
|
{
|
||||||
printf("Free %7u, Used %7u, Total %7u\n", m_free, m_used, m_free + m_used);
|
printf("Free %7u, Used %7u, Total %7u\n", m_free, m_used, m_free + m_used);
|
||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
|
|
22
util/ass/asscm.h
Normal file
22
util/ass/asscm.h
Normal file
|
@ -0,0 +1,22 @@
|
||||||
|
/* Copyright (c) 2019 ACK Project.
|
||||||
|
* See the copyright notice in the ACK home directory,
|
||||||
|
* in the file "Copyright".
|
||||||
|
*
|
||||||
|
* Created on: 2019-03-12
|
||||||
|
*
|
||||||
|
*/
|
||||||
|
#ifndef ASSCM_H_
|
||||||
|
#define ASSCM_H_
|
||||||
|
|
||||||
|
/* Allocates an area of "size" bytes in memory
|
||||||
|
* and returns a pointer to this area.
|
||||||
|
*/
|
||||||
|
area_t getarea(unsigned int size);
|
||||||
|
/* Frees an area of memory of "size" bytes. */
|
||||||
|
void freearea(register area_t ptr, unsigned int size);
|
||||||
|
|
||||||
|
#ifdef MEMUSE
|
||||||
|
void memuse(void);
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#endif /* ASSCM_H_ */
|
|
@ -5,11 +5,6 @@
|
||||||
#include "ass00.h"
|
#include "ass00.h"
|
||||||
#include "assex.h"
|
#include "assex.h"
|
||||||
|
|
||||||
#ifndef NORCSID
|
|
||||||
static char rcs_id[] = "$Id$" ;
|
|
||||||
static char rcs_ass[]= RCS_ASS ;
|
|
||||||
static char rcs_ex[] = RCS_EX ;
|
|
||||||
#endif
|
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* global data
|
* global data
|
||||||
|
|
145
util/ass/assex.h
145
util/ass/assex.h
|
@ -6,7 +6,7 @@
|
||||||
* global data
|
* global data
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#define RCS_EX "$Id$"
|
#include <stdio.h>
|
||||||
|
|
||||||
extern int wordsize;
|
extern int wordsize;
|
||||||
extern int ptrsize;
|
extern int ptrsize;
|
||||||
|
@ -122,31 +122,126 @@ extern char *opindex[] ;
|
||||||
extern char opchoice[] ;
|
extern char opchoice[] ;
|
||||||
extern int maxinsl ;
|
extern int maxinsl ;
|
||||||
|
|
||||||
/*
|
/* Generate temporary filename. Fatal error in case of error. */
|
||||||
* types of value returning routines
|
extern char *tmpfil(void);
|
||||||
|
|
||||||
|
|
||||||
|
/* Read next byte from "af" file, fatal error if there isn't one. */
|
||||||
|
extern int xgetc(register FILE *af);
|
||||||
|
/* Read a value of length "l" bytes from file "f",
|
||||||
|
* fatal error if cannot be read.
|
||||||
*/
|
*/
|
||||||
#ifndef CPM
|
extern cons_t xgetarb(int l,FILE *f);
|
||||||
extern int tmpfil();
|
/* Read the pointer constant a from file "f".
|
||||||
extern FILE *frewind();
|
* NOTE: The bytes were written low to high (little-endian).
|
||||||
#endif
|
*/
|
||||||
extern int xgetc();
|
extern cons_t xgeta(FILE* f);
|
||||||
extern unsigned get8();
|
|
||||||
extern int get16();
|
|
||||||
extern cons_t get32();
|
|
||||||
extern cons_t xgeta();
|
/* Output one byte into file "af" and fatal error if it gives an error */
|
||||||
extern cons_t parval();
|
extern void xputc(int c,register FILE *af);
|
||||||
extern cons_t valsize();
|
/* Output a 16-bit value into file "f" in little-endian, fatal error if it gives an error. */
|
||||||
extern cons_t xgetarb();
|
extern void xput16(int w,FILE *f);
|
||||||
|
/* Output a value of "l" bytes into file "f" and fatal error if it gives an error. */
|
||||||
|
extern void xputarb(int l,cons_t w, FILE* f);
|
||||||
|
/* Assemble the pointer constant a into file "f".
|
||||||
|
* NOTE: The bytes are written low to high (little-endian).
|
||||||
|
*/
|
||||||
|
extern void xputa(cons_t a,FILE* f);
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
/* Write a byte value into the code temporary file. */
|
||||||
|
extern void put8(int n);
|
||||||
|
/* Write a 16-bit value into the code temporary file. */
|
||||||
|
extern void put16(int n);
|
||||||
|
/* Write a 32-bit value into the code temporary file. */
|
||||||
|
extern void put32(cons_t n);
|
||||||
|
/* Write a 64-bit value into the code temporary file. */
|
||||||
|
extern void put64(cons_t n);
|
||||||
|
|
||||||
|
|
||||||
|
/* Read a byte from the input file, return EOF upon error of EOF */
|
||||||
|
extern int xget8(void);
|
||||||
|
/* Read a byte from the input file, fatal error upon error or EOF. */
|
||||||
|
extern unsigned int get8(void);
|
||||||
|
/* Read a signed 16-bit value from the input file. Raise
|
||||||
|
* a fatal error upon error or end of stream.
|
||||||
|
*/
|
||||||
|
extern int get16(void);
|
||||||
|
/* Read an unsigned 16-bit value from the input file. Raise
|
||||||
|
* a fatal error upon error or end of stream.
|
||||||
|
*/
|
||||||
|
extern int getu16(void);
|
||||||
|
/* Read a 32-bit value from the input file. Raise
|
||||||
|
* a fatal error upon error or end of stream.
|
||||||
|
*/
|
||||||
|
extern cons_t get32(void);
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
/* Write a byte to the data file. */
|
||||||
|
extern void ext8(int b);
|
||||||
|
/* Write a 16-bit value to the data file.
|
||||||
|
* The value is written from low to high (little-endian)
|
||||||
|
*/
|
||||||
|
extern void extword(cons_t w);
|
||||||
|
/* Write "value" of "size" bytes to the data file. The bytes
|
||||||
|
* are written low to high.
|
||||||
|
*/
|
||||||
|
extern void extarb(int size, long value);
|
||||||
|
/* Write pointer "a". The bytes are
|
||||||
|
* written from low to high to the data file.
|
||||||
|
*/
|
||||||
|
extern void extadr(cons_t a);
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
/* Returns the opcode length in bytes */
|
||||||
|
extern int oplength(int);
|
||||||
|
extern void genop(char *,cons_t,int );
|
||||||
|
|
||||||
|
extern void putblk(register FILE *stream,register char *from, register int amount);
|
||||||
|
extern int getblk(register FILE *stream, register char *from, register int amount);
|
||||||
|
|
||||||
|
|
||||||
|
extern void set_mode(int mode);
|
||||||
|
|
||||||
|
/* Dump current information to screen if dump flag is enabled. */
|
||||||
|
void dump(int n);
|
||||||
|
|
||||||
|
/*
|
||||||
extern char *findnop();
|
extern char *findnop();
|
||||||
extern char *findfit();
|
extern char *findfit();
|
||||||
extern glob_t *glolookup();
|
|
||||||
extern glob_t *glo2lookup();
|
*/
|
||||||
extern glob_t *xglolookup();
|
extern glob_t *glolookup(char *name,int status,glob_t *table, int size);
|
||||||
extern locl_t *loclookup();
|
extern proc_t *searchproc(char *name,proc_t *table,int size);
|
||||||
extern proc_t *prolookup();
|
extern glob_t *glo2lookup(char *name ,int status);
|
||||||
extern proc_t *enterproc();
|
extern glob_t *xglolookup(char *name,int status);
|
||||||
extern proc_t *searchproc();
|
extern proc_t *prolookup(char *name,int status);
|
||||||
extern relc_t *text_reloc();
|
extern locl_t *loclookup(unsigned int an,int status);
|
||||||
extern relc_t *data_reloc();
|
extern proc_t *enterproc(char *name,int status,proc_t *place);
|
||||||
extern area_t getarea();
|
extern cons_t parval(line_t *lnp,char *defined);
|
||||||
|
|
||||||
|
|
||||||
|
extern void determine_props(line_t *lnp, int *min_len, int *max_len);
|
||||||
|
extern int opfit(int flag,int number,cons_t val,int i_flag);
|
||||||
|
|
||||||
|
extern void initproc(void);
|
||||||
|
extern void endproc(void);
|
||||||
|
extern void init_files(void);
|
||||||
|
extern void init_module(void);
|
||||||
|
extern void end_module(void);
|
||||||
|
extern void do_proc(void);
|
||||||
|
extern void ertrap(void);
|
||||||
|
extern void init_vars(void);
|
||||||
|
|
||||||
|
extern void error(const char* string1, ...);
|
||||||
|
extern void werror(const char* string1, ...);
|
||||||
|
extern void fatal(char *s);
|
||||||
|
|
||||||
|
|
||||||
|
|
184
util/ass/assrl.c
184
util/ass/assrl.c
|
@ -4,12 +4,13 @@
|
||||||
*
|
*
|
||||||
*/
|
*/
|
||||||
|
|
||||||
|
#include <stdio.h>
|
||||||
#include "ass00.h"
|
#include "ass00.h"
|
||||||
#include "assex.h"
|
#include "assex.h"
|
||||||
|
#include "asscm.h"
|
||||||
|
#include "assrl.h"
|
||||||
|
|
||||||
|
|
||||||
#ifndef NORCSID
|
|
||||||
static char rcs_id[] = "$Id$" ;
|
|
||||||
#endif
|
|
||||||
|
|
||||||
#define COPYFINAL 1
|
#define COPYFINAL 1
|
||||||
#define COPYTEMP 0
|
#define COPYTEMP 0
|
||||||
|
@ -18,10 +19,12 @@ static char rcs_id[] = "$Id$" ;
|
||||||
* collection of routines to deal with relocation business
|
* collection of routines to deal with relocation business
|
||||||
*/
|
*/
|
||||||
|
|
||||||
void dataprocess();
|
|
||||||
void textprocess();
|
static void dataprocess(FILE *, FILE *);
|
||||||
relc_t *
|
static void textprocess(FILE *, FILE *);
|
||||||
text_reloc(glosym,off,typ) glob_t *glosym; FOFFSET off ; int typ ; {
|
|
||||||
|
relc_t * text_reloc(glob_t *glosym, FOFFSET off, int typ)
|
||||||
|
{
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* prepare the relocation that has to be done at text-offset off
|
* prepare the relocation that has to be done at text-offset off
|
||||||
|
@ -36,9 +39,12 @@ text_reloc(glosym,off,typ) glob_t *glosym; FOFFSET off ; int typ ; {
|
||||||
register relc_t *nxtextreloc;
|
register relc_t *nxtextreloc;
|
||||||
|
|
||||||
nxtextreloc = rlp_cast getarea(sizeof *nxtextreloc);
|
nxtextreloc = rlp_cast getarea(sizeof *nxtextreloc);
|
||||||
if ( !f_text ) {
|
if (!f_text)
|
||||||
|
{
|
||||||
f_text = nxtextreloc;
|
f_text = nxtextreloc;
|
||||||
} else {
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
l_text->r_next = nxtextreloc;
|
l_text->r_next = nxtextreloc;
|
||||||
}
|
}
|
||||||
nxtextreloc->r_next = rlp_cast 0;
|
nxtextreloc->r_next = rlp_cast 0;
|
||||||
|
@ -49,8 +55,8 @@ text_reloc(glosym,off,typ) glob_t *glosym; FOFFSET off ; int typ ; {
|
||||||
return (nxtextreloc);
|
return (nxtextreloc);
|
||||||
}
|
}
|
||||||
|
|
||||||
relc_t *
|
relc_t * data_reloc(char *arg ,FOFFSET off, int typ)
|
||||||
data_reloc(arg,off,typ) char *arg ; FOFFSET off ; int typ ; {
|
{
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Same as above.
|
* Same as above.
|
||||||
|
@ -59,9 +65,12 @@ data_reloc(arg,off,typ) char *arg ; FOFFSET off ; int typ ; {
|
||||||
register relc_t *nxdatareloc;
|
register relc_t *nxdatareloc;
|
||||||
|
|
||||||
nxdatareloc = rlp_cast getarea(sizeof *nxdatareloc);
|
nxdatareloc = rlp_cast getarea(sizeof *nxdatareloc);
|
||||||
if ( !f_data ) {
|
if (!f_data)
|
||||||
|
{
|
||||||
f_data = nxdatareloc;
|
f_data = nxdatareloc;
|
||||||
} else {
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
l_data->r_next = nxdatareloc;
|
l_data->r_next = nxdatareloc;
|
||||||
}
|
}
|
||||||
nxdatareloc->r_next = rlp_cast 0;
|
nxdatareloc->r_next = rlp_cast 0;
|
||||||
|
@ -72,8 +81,9 @@ data_reloc(arg,off,typ) char *arg ; FOFFSET off ; int typ ; {
|
||||||
return (nxdatareloc);
|
return (nxdatareloc);
|
||||||
}
|
}
|
||||||
|
|
||||||
copyout() {
|
void copyout(void)
|
||||||
register i;
|
{
|
||||||
|
register int i;
|
||||||
int remtext;
|
int remtext;
|
||||||
|
|
||||||
/*
|
/*
|
||||||
|
@ -114,17 +124,15 @@ copyout() {
|
||||||
*/
|
*/
|
||||||
|
|
||||||
remtext = textbytes % wordsize;
|
remtext = textbytes % wordsize;
|
||||||
if ( remtext != 0 ) remtext = wordsize-remtext ;
|
if (remtext != 0)
|
||||||
|
remtext = wordsize - remtext;
|
||||||
|
|
||||||
if ((ifile = fopen(eout, "w")) == 0)
|
if ((ifile = fopen(eout, "w")) == 0)
|
||||||
fatal("can't create e.out");
|
fatal("can't create e.out");
|
||||||
#ifdef CPM
|
|
||||||
fclose(tfile); tfile=fopen("TFILE.$$$", "r");
|
rewind(tfile);
|
||||||
fclose(dfile); dfile=fopen("DFILE.$$$", "r");
|
rewind(dfile);
|
||||||
#else
|
|
||||||
tfile=frewind(tfile);
|
|
||||||
dfile=frewind(dfile);
|
|
||||||
#endif
|
|
||||||
xput16(as_magic, ifile);
|
xput16(as_magic, ifile);
|
||||||
xput16(intflags, ifile);
|
xput16(intflags, ifile);
|
||||||
xput16(unresolved, ifile);
|
xput16(unresolved, ifile);
|
||||||
|
@ -136,99 +144,110 @@ copyout() {
|
||||||
xputa(textbytes + remtext, ifile);
|
xputa(textbytes + remtext, ifile);
|
||||||
xputa((cons_t) datablocks, ifile);
|
xputa((cons_t) datablocks, ifile);
|
||||||
xputa((cons_t) procnum, ifile);
|
xputa((cons_t) procnum, ifile);
|
||||||
xputa((cons_t)searchproc(MAIN,xprocs,oursize->n_xproc)->p_num,
|
xputa((cons_t) searchproc(MAIN, xprocs, oursize->n_xproc)->p_num, ifile);
|
||||||
ifile);
|
|
||||||
xputa((cons_t) sourcelines, ifile);
|
xputa((cons_t) sourcelines, ifile);
|
||||||
xputa((cons_t) databytes, ifile);
|
xputa((cons_t) databytes, ifile);
|
||||||
xputa((cons_t) 0, ifile);
|
xputa((cons_t) 0, ifile);
|
||||||
xputa((cons_t) 0, ifile);
|
xputa((cons_t) 0, ifile);
|
||||||
|
|
||||||
textprocess(tfile, ifile);
|
textprocess(tfile, ifile);
|
||||||
while ( remtext-- ) xputc(0,ifile) ;
|
while (remtext--)
|
||||||
|
xputc(0, ifile);
|
||||||
|
|
||||||
dataprocess(dfile, ifile);
|
dataprocess(dfile, ifile);
|
||||||
for (i=0;i<procnum;i++) {
|
for (i = 0; i < procnum; i++)
|
||||||
|
{
|
||||||
xputarb(ptrsize, proctab[i].pr_loc, ifile);
|
xputarb(ptrsize, proctab[i].pr_loc, ifile);
|
||||||
xputarb(ptrsize, proctab[i].pr_off, ifile);
|
xputarb(ptrsize, proctab[i].pr_off, ifile);
|
||||||
}
|
}
|
||||||
if ( fclose(ifile)==EOF ) ;
|
if (fclose(ifile) == EOF)
|
||||||
|
;
|
||||||
}
|
}
|
||||||
|
|
||||||
void dataprocess(f1,f2) FILE *f1,*f2; {
|
static void dataprocess(FILE *f1, FILE *outf)
|
||||||
|
{
|
||||||
relc_t datareloc;
|
relc_t datareloc;
|
||||||
FOFFSET i;
|
FOFFSET i;
|
||||||
register ieof ;
|
register int ieof;
|
||||||
|
|
||||||
#ifdef CPM
|
rewind(rdfile);
|
||||||
fclose(rdfile); rdfile=fopen("RDFILE.$$$", "r");
|
|
||||||
#else
|
|
||||||
rdfile=frewind(rdfile) ;
|
|
||||||
#endif
|
|
||||||
ieof = getblk(rdfile, (char *) (&datareloc.r_off),
|
ieof = getblk(rdfile, (char *) (&datareloc.r_off),
|
||||||
sizeof datareloc - sizeof datareloc.r_next);
|
sizeof datareloc - sizeof datareloc.r_next);
|
||||||
for (i=0 ; i<dataoff && !ieof ; i++) {
|
for (i = 0; i < dataoff && !ieof; i++)
|
||||||
if (i==datareloc.r_off) {
|
{
|
||||||
switch(datareloc.r_typ) {
|
if (i == datareloc.r_off)
|
||||||
|
{
|
||||||
|
switch (datareloc.r_typ)
|
||||||
|
{
|
||||||
case RELADR:
|
case RELADR:
|
||||||
xputa(xgeta(f1)+datareloc.r_val.rel_i,f2) ;
|
xputa(xgeta(f1) + datareloc.r_val.rel_i, outf);
|
||||||
i += ptrsize - 1;
|
i += ptrsize - 1;
|
||||||
break;
|
break;
|
||||||
case RELGLO:
|
case RELGLO:
|
||||||
if (datareloc.r_val.rel_gp->g_status&DEF) {
|
if (datareloc.r_val.rel_gp->g_status & DEF)
|
||||||
xputa(xgeta(f1)+
|
{
|
||||||
datareloc.r_val.rel_gp->g_val.g_addr,
|
xputa(xgeta(f1) + datareloc.r_val.rel_gp->g_val.g_addr, outf);
|
||||||
f2);
|
|
||||||
i += ptrsize - 1;
|
i += ptrsize - 1;
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
if (unresolved == 0)
|
if (unresolved == 0)
|
||||||
fatal("Definition botch");
|
fatal("Definition botch");
|
||||||
case RELHEAD:
|
case RELHEAD:
|
||||||
xputc((int)(xgetc(f1)+datareloc.r_val.rel_i),
|
xputc((int) (xgetc(f1) + datareloc.r_val.rel_i), outf);
|
||||||
f2);
|
|
||||||
break;
|
break;
|
||||||
default:
|
default:
|
||||||
fatal("Bad r_typ in dataprocess");
|
fatal("Bad r_typ in dataprocess");
|
||||||
}
|
}
|
||||||
ieof = getblk(rdfile, (char *) (&datareloc.r_off),
|
ieof = getblk(rdfile, (char *) (&datareloc.r_off),
|
||||||
sizeof datareloc - sizeof datareloc.r_next);
|
sizeof datareloc - sizeof datareloc.r_next);
|
||||||
} else
|
|
||||||
xputc(xgetc(f1),f2);
|
|
||||||
}
|
}
|
||||||
for ( ; i<dataoff ; i++ ) xputc(xgetc(f1),f2) ;
|
else
|
||||||
|
xputc(xgetc(f1), outf);
|
||||||
|
}
|
||||||
|
for (; i < dataoff; i++)
|
||||||
|
xputc(xgetc(f1), outf);
|
||||||
if (!ieof && !getblk(rdfile, (char *) &datareloc, 1))
|
if (!ieof && !getblk(rdfile, (char *) &datareloc, 1))
|
||||||
fatal("data relocation botch");
|
fatal("data relocation botch");
|
||||||
}
|
}
|
||||||
|
|
||||||
void textprocess(f1,f2) FILE *f1,*f2; {
|
static void textprocess(FILE *f1, FILE *outf)
|
||||||
|
{
|
||||||
relc_t textreloc;
|
relc_t textreloc;
|
||||||
cons_t n;
|
cons_t n;
|
||||||
FOFFSET i;
|
FOFFSET i;
|
||||||
FILE *otfile;
|
FILE *otfile;
|
||||||
int insl ; register int ieof ;
|
int insl;
|
||||||
|
register int ieof;
|
||||||
char *op_curr;
|
char *op_curr;
|
||||||
register FOFFSET keep;
|
register FOFFSET keep;
|
||||||
|
|
||||||
#ifdef CPM
|
rewind(rtfile);
|
||||||
fclose(rtfile); rtfile=fopen("RTFILE.$$$", "r");
|
keep = textoff;
|
||||||
#else
|
textoff = 0;
|
||||||
rtfile=frewind(rtfile) ;
|
otfile = tfile;
|
||||||
#endif
|
tfile = outf;
|
||||||
keep = textoff ; textoff=0 ; otfile=tfile ; tfile=f2 ;
|
|
||||||
/* This redirects the output of genop */
|
/* This redirects the output of genop */
|
||||||
ieof = getblk(rtfile, (char *) (&textreloc.r_off),
|
ieof = getblk(rtfile, (char *) (&textreloc.r_off),
|
||||||
sizeof textreloc - sizeof textreloc.r_next);
|
sizeof textreloc - sizeof textreloc.r_next);
|
||||||
for(i=0;i<keep && !ieof ;i++) {
|
for (i = 0; i < keep && !ieof; i++)
|
||||||
if( i == textreloc.r_off ) {
|
{
|
||||||
if (textreloc.r_typ&RELMNS) {
|
if (i == textreloc.r_off)
|
||||||
|
{
|
||||||
|
if (textreloc.r_typ & RELMNS)
|
||||||
|
{
|
||||||
n = textreloc.r_val.rel_i;
|
n = textreloc.r_val.rel_i;
|
||||||
} else {
|
}
|
||||||
if (textreloc.r_val.rel_gp->g_status&DEF) {
|
else
|
||||||
|
{
|
||||||
|
if (textreloc.r_val.rel_gp->g_status & DEF)
|
||||||
|
{
|
||||||
n = textreloc.r_val.rel_gp->g_val.g_addr;
|
n = textreloc.r_val.rel_gp->g_val.g_addr;
|
||||||
} else {
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
if (unresolved == 0)
|
if (unresolved == 0)
|
||||||
fatal("Definition botch");
|
fatal("Definition botch");
|
||||||
xputc(xgetc(f1),f2) ;
|
xputc(xgetc(f1), outf);
|
||||||
ieof = getblk(rtfile, (char *) (&textreloc.r_off),
|
ieof = getblk(rtfile, (char *) (&textreloc.r_off),
|
||||||
sizeof textreloc - sizeof textreloc.r_next);
|
sizeof textreloc - sizeof textreloc.r_next);
|
||||||
continue;
|
continue;
|
||||||
|
@ -240,18 +259,22 @@ void textprocess(f1,f2) FILE *f1,*f2; {
|
||||||
i += insl - 1;
|
i += insl - 1;
|
||||||
ieof = getblk(rtfile, (char *) (&textreloc.r_off),
|
ieof = getblk(rtfile, (char *) (&textreloc.r_off),
|
||||||
sizeof textreloc - sizeof textreloc.r_next);
|
sizeof textreloc - sizeof textreloc.r_next);
|
||||||
} else {
|
}
|
||||||
xputc(xgetc(f1),f2) ;
|
else
|
||||||
|
{
|
||||||
|
xputc(xgetc(f1), outf);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
for ( ; i<keep ; i++ ) xputc(xgetc(f1),f2) ;
|
for (; i < keep; i++)
|
||||||
|
xputc(xgetc(f1), outf);
|
||||||
if (!ieof && !getblk(rtfile, (char *) &textreloc, 1))
|
if (!ieof && !getblk(rtfile, (char *) &textreloc, 1))
|
||||||
fatal("text relocation botch");
|
fatal("text relocation botch");
|
||||||
textoff = keep;
|
textoff = keep;
|
||||||
tfile = otfile;
|
tfile = otfile;
|
||||||
}
|
}
|
||||||
|
|
||||||
upd_reloc() {
|
void upd_reloc(void)
|
||||||
|
{
|
||||||
register relc_t *p;
|
register relc_t *p;
|
||||||
register glob_t *gbp;
|
register glob_t *gbp;
|
||||||
|
|
||||||
|
@ -264,28 +287,37 @@ upd_reloc() {
|
||||||
* see also getcore()
|
* see also getcore()
|
||||||
*/
|
*/
|
||||||
|
|
||||||
while ( p= f_text ) {
|
while ( (p = f_text) != NULL)
|
||||||
|
{
|
||||||
gbp = p->r_val.rel_gp;
|
gbp = p->r_val.rel_gp;
|
||||||
if( gbp->g_status&DEF ) {
|
if (gbp->g_status & DEF)
|
||||||
|
{
|
||||||
p->r_typ |= RELMNS;
|
p->r_typ |= RELMNS;
|
||||||
p->r_val.rel_i = gbp->g_val.g_addr;
|
p->r_val.rel_i = gbp->g_val.g_addr;
|
||||||
} else
|
}
|
||||||
|
else
|
||||||
p->r_val.rel_gp = gbp->g_val.g_gp;
|
p->r_val.rel_gp = gbp->g_val.g_gp;
|
||||||
putblk(rtfile, (char *) (&(p->r_off)), sizeof *p - sizeof p);
|
putblk(rtfile, (char *) (&(p->r_off)), sizeof *p - sizeof p);
|
||||||
f_text= p->r_next ; freearea( (area_t) p , sizeof *p ) ;
|
f_text = p->r_next;
|
||||||
|
freearea((area_t) p, sizeof *p);
|
||||||
}
|
}
|
||||||
|
|
||||||
while( p= f_data ) {
|
while ( (p = f_data) != NULL)
|
||||||
if (p->r_typ == RELGLO) {
|
{
|
||||||
|
if (p->r_typ == RELGLO)
|
||||||
|
{
|
||||||
gbp = p->r_val.rel_gp;
|
gbp = p->r_val.rel_gp;
|
||||||
if(gbp->g_status&DEF) {
|
if (gbp->g_status & DEF)
|
||||||
|
{
|
||||||
p->r_typ = RELADR;
|
p->r_typ = RELADR;
|
||||||
p->r_val.rel_i = gbp->g_val.g_addr;
|
p->r_val.rel_i = gbp->g_val.g_addr;
|
||||||
} else
|
}
|
||||||
|
else
|
||||||
p->r_val.rel_gp = gbp->g_val.g_gp;
|
p->r_val.rel_gp = gbp->g_val.g_gp;
|
||||||
}
|
}
|
||||||
putblk(rdfile, (char *) (&(p->r_off)), sizeof *p - sizeof p);
|
putblk(rdfile, (char *) (&(p->r_off)), sizeof *p - sizeof p);
|
||||||
f_data= p->r_next ; freearea( (area_t) p , sizeof *p ) ;
|
f_data = p->r_next;
|
||||||
|
freearea((area_t) p, sizeof *p);
|
||||||
}
|
}
|
||||||
l_data = rlp_cast 0;
|
l_data = rlp_cast 0;
|
||||||
}
|
}
|
||||||
|
|
21
util/ass/assrl.h
Normal file
21
util/ass/assrl.h
Normal file
|
@ -0,0 +1,21 @@
|
||||||
|
/* Copyright (c) 2019 ACK Project.
|
||||||
|
* See the copyright notice in the ACK home directory,
|
||||||
|
* in the file "Copyright".
|
||||||
|
*
|
||||||
|
* Created on: 2019-03-13
|
||||||
|
*
|
||||||
|
*/
|
||||||
|
#ifndef ASSRL_H_
|
||||||
|
#define ASSRL_H_
|
||||||
|
|
||||||
|
/* Generates an e.out file from the the temporary code file "tfile" and
|
||||||
|
* data temporary "dfile" file. Output the data to "ifile".
|
||||||
|
*/
|
||||||
|
void copyout(void);
|
||||||
|
/* Update the relocation entries and place them into "rtfile" and "rdfile". */
|
||||||
|
void upd_reloc(void);
|
||||||
|
|
||||||
|
relc_t * data_reloc(char *arg ,FOFFSET off, int typ);
|
||||||
|
relc_t * text_reloc(glob_t *glosym, FOFFSET off, int typ);
|
||||||
|
|
||||||
|
#endif /* ASSRL_H_ */
|
|
@ -36,7 +36,7 @@ cprogram {
|
||||||
"modules/src/em_data+lib",
|
"modules/src/em_data+lib",
|
||||||
--"modules/src/data+lib",
|
--"modules/src/data+lib",
|
||||||
--"modules/src/object+lib",
|
--"modules/src/object+lib",
|
||||||
--"modules/src/system+lib",
|
"modules/src/system+lib",
|
||||||
"./ass*.h",
|
"./ass*.h",
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -64,7 +64,7 @@ produced code the only messages to expect are "Out of memory"
|
||||||
or of the
|
or of the
|
||||||
form: Overflow in XXXX. The latter can usually be cured by giving
|
form: Overflow in XXXX. The latter can usually be cured by giving
|
||||||
a -sx flag,
|
a -sx flag,
|
||||||
the former means the program is too big, dimishing
|
the former means the program is too big, diminishing
|
||||||
the size of very large procedures can sometimes help.
|
the size of very large procedures can sometimes help.
|
||||||
The most likely errors, however, are unresolved references,
|
The most likely errors, however, are unresolved references,
|
||||||
probably caused by the omission of a library argument.
|
probably caused by the omission of a library argument.
|
||||||
|
|
|
@ -6,13 +6,12 @@
|
||||||
|
|
||||||
#include "ip_spec.h"
|
#include "ip_spec.h"
|
||||||
#include <stdio.h>
|
#include <stdio.h>
|
||||||
|
#include <stdlib.h>
|
||||||
|
#include <stdarg.h>
|
||||||
|
#include <string.h>
|
||||||
#include <em_spec.h>
|
#include <em_spec.h>
|
||||||
#include <em_flag.h>
|
#include <em_flag.h>
|
||||||
|
|
||||||
#ifndef NORCSID
|
|
||||||
static char rcs_id[] = "$Id$" ;
|
|
||||||
#endif
|
|
||||||
|
|
||||||
/* This program reads the human readable interpreter specification
|
/* This program reads the human readable interpreter specification
|
||||||
and produces a efficient machine representation that can be
|
and produces a efficient machine representation that can be
|
||||||
translated by a C-compiler.
|
translated by a C-compiler.
|
||||||
|
@ -35,64 +34,100 @@ char esca[] = "escape" ;
|
||||||
|
|
||||||
extern char em_flag[];
|
extern char em_flag[];
|
||||||
|
|
||||||
main(argc,argv) char **argv ; {
|
|
||||||
if ( argc>1 ) {
|
/* Forward declarations */
|
||||||
if ( freopen(argv[1],"r",stdin)==NULL) {
|
static int readchar(void);
|
||||||
|
static void pushback(int);
|
||||||
|
static void readin(void);
|
||||||
|
static char *ident(void);
|
||||||
|
static int getmnem(char *);
|
||||||
|
static void writeout(void);
|
||||||
|
static void checkall(void);
|
||||||
|
static void chkc(int, int, int);
|
||||||
|
static void ckop(int, int, int, int);
|
||||||
|
static int oplength(struct opform *);
|
||||||
|
static void check(int);
|
||||||
|
static int decflag(char *);
|
||||||
|
int compare(const void *, const void *);
|
||||||
|
|
||||||
|
static void error(char *format, ...);
|
||||||
|
static void mess(char *format, ...);
|
||||||
|
static void fatal(char *format, ...);
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
int main(int argc, char **argv)
|
||||||
|
{
|
||||||
|
if (argc > 1)
|
||||||
|
{
|
||||||
|
if (freopen(argv[1], "r", stdin) == NULL)
|
||||||
|
{
|
||||||
fatal("Cannot open %s", argv[1]);
|
fatal("Cannot open %s", argv[1]);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if ( argc>2 ) {
|
if (argc > 2)
|
||||||
if ( freopen(argv[2],"w",stdout)==NULL) {
|
{
|
||||||
|
if (freopen(argv[2], "w", stdout) == NULL)
|
||||||
|
{
|
||||||
fatal("Cannot create %s", argv[2]);
|
fatal("Cannot create %s", argv[2]);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if ( argc>3 ) {
|
if (argc > 3)
|
||||||
|
{
|
||||||
fatal("%s [ file [ file ] ]", argv[0]);
|
fatal("%s [ file [ file ] ]", argv[0]);
|
||||||
}
|
}
|
||||||
atend = 0;
|
atend = 0;
|
||||||
readin();
|
readin();
|
||||||
atend = 1;
|
atend = 1;
|
||||||
checkall();
|
checkall();
|
||||||
if ( nerror==0 ) {
|
if (nerror == 0)
|
||||||
|
{
|
||||||
writeout();
|
writeout();
|
||||||
}
|
}
|
||||||
exit(nerror);
|
exit(nerror);
|
||||||
}
|
}
|
||||||
|
|
||||||
readin() {
|
static void readin(void)
|
||||||
|
{
|
||||||
register struct opform *nextform;
|
register struct opform *nextform;
|
||||||
char *ident();
|
|
||||||
char *firstid;
|
char *firstid;
|
||||||
register maxl ;
|
register int maxl;
|
||||||
|
|
||||||
maxl = 0;
|
maxl = 0;
|
||||||
for ( nextform=intable ;
|
for (nextform = intable; !feof(stdin) && nextform < &intable[NOTAB];)
|
||||||
!feof(stdin) && nextform<&intable[NOTAB] ; ) {
|
{
|
||||||
firstid = ident();
|
firstid = ident();
|
||||||
if ( *firstid=='\n' || feof(stdin) ) continue ;
|
if (*firstid == '\n' || feof(stdin))
|
||||||
|
continue;
|
||||||
lastform = nextform;
|
lastform = nextform;
|
||||||
nextform->i_opcode = getmnem(firstid);
|
nextform->i_opcode = getmnem(firstid);
|
||||||
nextform->i_flag = decflag(ident());
|
nextform->i_flag = decflag(ident());
|
||||||
switch ( nextform->i_flag&OPTYPE ) {
|
switch (nextform->i_flag & OPTYPE)
|
||||||
|
{
|
||||||
case OPMINI:
|
case OPMINI:
|
||||||
case OPSHORT:
|
case OPSHORT:
|
||||||
nextform->i_num = atoi(ident());
|
nextform->i_num = atoi(ident());
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
nextform->i_low = atoi(ident());
|
nextform->i_low = atoi(ident());
|
||||||
if ( *ident()!='\n' ) {
|
if (*ident() != '\n')
|
||||||
|
{
|
||||||
int c;
|
int c;
|
||||||
error("End of line expected");
|
error("End of line expected");
|
||||||
while ( (c=readchar())!='\n' && c!=EOF ) ;
|
while ((c = readchar()) != '\n' && c != EOF)
|
||||||
|
;
|
||||||
}
|
}
|
||||||
if ( oplength(nextform)>maxl ) maxl=oplength(nextform) ;
|
if (oplength(nextform) > maxl)
|
||||||
|
maxl = oplength(nextform);
|
||||||
nextform++;
|
nextform++;
|
||||||
}
|
}
|
||||||
if ( !feof(stdin) ) fatal("Internal table too small") ;
|
if (!feof(stdin))
|
||||||
|
fatal("Internal table too small");
|
||||||
maxinsl = maxl;
|
maxinsl = maxl;
|
||||||
}
|
}
|
||||||
|
|
||||||
char *ident() {
|
static char *ident(void)
|
||||||
|
{
|
||||||
/* skip spaces and tabs, anything up to space,tab or eof is
|
/* skip spaces and tabs, anything up to space,tab or eof is
|
||||||
a identifier.
|
a identifier.
|
||||||
Anything from # to end-of-line is an end-of-line.
|
Anything from # to end-of-line is an end-of-line.
|
||||||
|
@ -103,63 +138,96 @@ char *ident() {
|
||||||
register int c;
|
register int c;
|
||||||
register char *cc;
|
register char *cc;
|
||||||
|
|
||||||
do {
|
do
|
||||||
|
{
|
||||||
c = readchar();
|
c = readchar();
|
||||||
} while (c == ' ' || c == '\t');
|
} while (c == ' ' || c == '\t');
|
||||||
for ( cc=array ; cc<&array[(sizeof array) - 1] ; cc++ ) {
|
for (cc = array; cc < &array[(sizeof array) - 1]; cc++)
|
||||||
if ( c=='#' ) {
|
{
|
||||||
do {
|
if (c == '#')
|
||||||
|
{
|
||||||
|
do
|
||||||
|
{
|
||||||
c = readchar();
|
c = readchar();
|
||||||
} while (c != '\n' && c != EOF);
|
} while (c != '\n' && c != EOF);
|
||||||
}
|
}
|
||||||
*cc = c;
|
*cc = c;
|
||||||
if ( c=='\n' && cc==array ) break ;
|
if (c == '\n' && cc == array)
|
||||||
|
break;
|
||||||
c = readchar();
|
c = readchar();
|
||||||
if ( c=='\n' ) {
|
if (c == '\n')
|
||||||
|
{
|
||||||
pushback(c);
|
pushback(c);
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
if ( c==' ' || c=='\t' || c==EOF ) break ;
|
if (c == ' ' || c == '\t' || c == EOF)
|
||||||
|
break;
|
||||||
}
|
}
|
||||||
*++cc = 0;
|
*++cc = 0;
|
||||||
return array;
|
return array;
|
||||||
}
|
}
|
||||||
|
|
||||||
int getmnem(str) char *str ; {
|
static int getmnem(char *str)
|
||||||
|
{
|
||||||
char (*ptr)[4];
|
char (*ptr)[4];
|
||||||
|
|
||||||
for ( ptr = em_mnem ; *ptr<= &em_mnem[sp_lmnem-sp_fmnem][0] ; ptr++ ) {
|
for (ptr = em_mnem; *ptr <= &em_mnem[sp_lmnem - sp_fmnem][0]; ptr++)
|
||||||
if ( strcmp(*ptr,str)==0 ) return (ptr-em_mnem) ;
|
{
|
||||||
|
if (strcmp(*ptr, str) == 0)
|
||||||
|
return (ptr - em_mnem);
|
||||||
}
|
}
|
||||||
error("Illegal mnemonic");
|
error("Illegal mnemonic");
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
error(str,a1,a2,a3,a4,a5,a6) /* VARARGS1 */ char *str ; {
|
/* VARARGS1 */
|
||||||
if ( !atend ) fprintf(stderr,"line %d: ",line) ;
|
static void error(char *format, ...)
|
||||||
fprintf(stderr,str,a1,a2,a3,a4,a5,a6) ;
|
{
|
||||||
|
va_list argptr;
|
||||||
|
if (!atend)
|
||||||
|
fprintf(stderr, "line %d: ", line);
|
||||||
|
va_start(argptr, format);
|
||||||
|
vfprintf(stderr, format, argptr);
|
||||||
|
va_end(argptr);
|
||||||
fprintf(stderr, "\n");
|
fprintf(stderr, "\n");
|
||||||
nerror++;
|
nerror++;
|
||||||
}
|
}
|
||||||
|
|
||||||
mess(str,a1,a2,a3,a4,a5,a6) /* VARARGS1 */ char *str ; {
|
/* VARARGS1 */
|
||||||
if ( !atend ) fprintf(stderr,"line %d: ",line) ;
|
static void mess(char *format, ...)
|
||||||
fprintf(stderr,str,a1,a2,a3,a4,a5,a6) ;
|
{
|
||||||
|
va_list argptr;
|
||||||
|
if (!atend)
|
||||||
|
fprintf(stderr, "line %d: ", line);
|
||||||
|
va_start(argptr, format);
|
||||||
|
vfprintf(stderr, format, argptr);
|
||||||
|
va_end(argptr);
|
||||||
fprintf(stderr, "\n");
|
fprintf(stderr, "\n");
|
||||||
}
|
}
|
||||||
|
|
||||||
fatal(str,a1,a2,a3,a4,a5,a6) /* VARARGS1 */ char *str ; {
|
/* VARARGS1 */
|
||||||
error(str,a1,a2,a3,a4,a5,a6) ;
|
static void fatal(char *format, ...)
|
||||||
exit(1) ;
|
{
|
||||||
|
va_list argptr;
|
||||||
|
if (!atend)
|
||||||
|
fprintf(stderr, "line %d: ", line);
|
||||||
|
va_start(argptr, format);
|
||||||
|
vfprintf(stderr, format, argptr);
|
||||||
|
va_end(argptr);
|
||||||
|
fprintf(stderr, "\n");
|
||||||
|
exit(EXIT_FAILURE);
|
||||||
}
|
}
|
||||||
|
|
||||||
#define ILLGL -1
|
#define ILLGL -1
|
||||||
|
|
||||||
check(val) int val ; {
|
static void check(int val)
|
||||||
if ( val!=ILLGL ) error("Illegal flag combination") ;
|
{
|
||||||
|
if (val != ILLGL)
|
||||||
|
error("Illegal flag combination");
|
||||||
}
|
}
|
||||||
|
|
||||||
int decflag(str) char *str ; {
|
static int decflag(char *str)
|
||||||
|
{
|
||||||
int type;
|
int type;
|
||||||
int escape;
|
int escape;
|
||||||
int range;
|
int range;
|
||||||
|
@ -167,83 +235,128 @@ int decflag(str) char *str ; {
|
||||||
int notzero;
|
int notzero;
|
||||||
|
|
||||||
type = escape = range = wordm = notzero = ILLGL;
|
type = escape = range = wordm = notzero = ILLGL;
|
||||||
while ( *str ) switch ( *str++ ) {
|
while (*str)
|
||||||
|
switch (*str++)
|
||||||
|
{
|
||||||
case 'm':
|
case 'm':
|
||||||
check(type) ; type=OPMINI ; break ;
|
check(type);
|
||||||
|
type = OPMINI;
|
||||||
|
break;
|
||||||
case 's':
|
case 's':
|
||||||
check(type) ; type=OPSHORT ; break ;
|
check(type);
|
||||||
|
type = OPSHORT;
|
||||||
|
break;
|
||||||
case '-':
|
case '-':
|
||||||
check(type) ; type=OPNO ; break ;
|
check(type);
|
||||||
|
type = OPNO;
|
||||||
|
break;
|
||||||
case '1':
|
case '1':
|
||||||
check(type) ; type=OP8 ; break ;
|
check(type);
|
||||||
|
type = OP8;
|
||||||
|
break;
|
||||||
case '2':
|
case '2':
|
||||||
check(type) ; type=OP16 ; break ;
|
check(type);
|
||||||
|
type = OP16;
|
||||||
|
break;
|
||||||
case '4':
|
case '4':
|
||||||
check(type) ; type=OP32 ; break ;
|
check(type);
|
||||||
|
type = OP32;
|
||||||
|
break;
|
||||||
case '8':
|
case '8':
|
||||||
check(type) ; type=OP64 ; break ;
|
check(type);
|
||||||
|
type = OP64;
|
||||||
|
break;
|
||||||
case 'u':
|
case 'u':
|
||||||
check(type) ; type=OP16U ; break ;
|
check(type);
|
||||||
|
type = OP16U;
|
||||||
|
break;
|
||||||
case 'e':
|
case 'e':
|
||||||
check(escape) ; escape=0 ; break ;
|
check(escape);
|
||||||
|
escape = 0;
|
||||||
|
break;
|
||||||
case 'N':
|
case 'N':
|
||||||
check(range) ; range= 2 ; break ;
|
check(range);
|
||||||
|
range = 2;
|
||||||
|
break;
|
||||||
case 'P':
|
case 'P':
|
||||||
check(range) ; range= 1 ; break ;
|
check(range);
|
||||||
|
range = 1;
|
||||||
|
break;
|
||||||
case 'w':
|
case 'w':
|
||||||
check(wordm) ; wordm=0 ; break ;
|
check(wordm);
|
||||||
|
wordm = 0;
|
||||||
|
break;
|
||||||
case 'o':
|
case 'o':
|
||||||
check(notzero) ; notzero=0 ; break ;
|
check(notzero);
|
||||||
|
notzero = 0;
|
||||||
|
break;
|
||||||
default:
|
default:
|
||||||
error("Unknown flag");
|
error("Unknown flag");
|
||||||
}
|
}
|
||||||
if ( type==ILLGL ) error("Type must be specified") ;
|
if (type == ILLGL)
|
||||||
switch ( type ) {
|
error("Type must be specified");
|
||||||
|
switch (type)
|
||||||
|
{
|
||||||
case OP64:
|
case OP64:
|
||||||
case OP32:
|
case OP32:
|
||||||
if ( escape!=ILLGL ) error("Conflicting escapes") ;
|
if (escape != ILLGL)
|
||||||
|
error("Conflicting escapes");
|
||||||
escape = ILLGL;
|
escape = ILLGL;
|
||||||
case OP16:
|
case OP16:
|
||||||
case OP16U:
|
case OP16U:
|
||||||
case OP8:
|
case OP8:
|
||||||
case OPSHORT:
|
case OPSHORT:
|
||||||
case OPNO:
|
case OPNO:
|
||||||
if ( notzero!=ILLGL ) mess("Improbable OPNZ") ;
|
if (notzero != ILLGL)
|
||||||
if ( type==OPNO && range!=ILLGL ) {
|
mess("Improbable OPNZ");
|
||||||
|
if (type == OPNO && range != ILLGL)
|
||||||
|
{
|
||||||
mess("No operand in range");
|
mess("No operand in range");
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if ( escape!=ILLGL ) type|=OPESC ;
|
if (escape != ILLGL)
|
||||||
if ( wordm!=ILLGL ) type|=OPWORD ;
|
type |= OPESC;
|
||||||
switch ( range) {
|
if (wordm != ILLGL)
|
||||||
case ILLGL : type|=OP_BOTH ;
|
type |= OPWORD;
|
||||||
|
switch (range)
|
||||||
|
{
|
||||||
|
case ILLGL:
|
||||||
|
type |= OP_BOTH;
|
||||||
if (type == OPMINI || type == OPSHORT)
|
if (type == OPMINI || type == OPSHORT)
|
||||||
error("Minies and shorties must have P or N");
|
error("Minies and shorties must have P or N");
|
||||||
break;
|
break;
|
||||||
case 1 : type|=OP_POS ; break ;
|
case 1:
|
||||||
case 2 : type|=OP_NEG ; break ;
|
type |= OP_POS;
|
||||||
|
break;
|
||||||
|
case 2:
|
||||||
|
type |= OP_NEG;
|
||||||
|
break;
|
||||||
}
|
}
|
||||||
if ( notzero!=ILLGL ) type|=OPNZ ;
|
if (notzero != ILLGL)
|
||||||
|
type |= OPNZ;
|
||||||
return type;
|
return type;
|
||||||
}
|
}
|
||||||
|
|
||||||
writeout() {
|
static void writeout(void)
|
||||||
|
{
|
||||||
register struct opform *next;
|
register struct opform *next;
|
||||||
int elem[sp_lmnem - sp_fmnem + 1 + 1];
|
int elem[sp_lmnem - sp_fmnem + 1 + 1];
|
||||||
/* for each op points to first of descr. */
|
/* for each op points to first of descr. */
|
||||||
register int i, currop;
|
register int i, currop;
|
||||||
int nch;
|
int nch;
|
||||||
int compare() ;
|
|
||||||
|
|
||||||
qsort(intable, (lastform - intable) + 1, sizeof intable[0], compare);
|
qsort(intable, (lastform - intable) + 1, sizeof intable[0], compare);
|
||||||
|
|
||||||
printf("int\tmaxinsl\t= %d ;\n", maxinsl);
|
printf("int\tmaxinsl\t= %d ;\n", maxinsl);
|
||||||
currop= -1 ; nch=0 ;
|
currop = -1;
|
||||||
|
nch = 0;
|
||||||
printf("char opchoice[] = {\n");
|
printf("char opchoice[] = {\n");
|
||||||
for (next=intable ; next<=lastform ; next++ ) {
|
for (next = intable; next <= lastform; next++)
|
||||||
if ( (next->i_opcode&0377)!=currop ) {
|
{
|
||||||
for ( currop++ ;
|
if ((next->i_opcode & 0377) != currop)
|
||||||
currop<(next->i_opcode&0377) ; currop++ ) {
|
{
|
||||||
|
for (currop++; currop < (next->i_opcode & 0377); currop++)
|
||||||
|
{
|
||||||
elem[currop] = nch;
|
elem[currop] = nch;
|
||||||
error("Missing opcode %s", em_mnem[currop]);
|
error("Missing opcode %s", em_mnem[currop]);
|
||||||
}
|
}
|
||||||
|
@ -251,46 +364,67 @@ writeout() {
|
||||||
}
|
}
|
||||||
printf("%d, %d,", next->i_flag & 0377, next->i_low & 0377);
|
printf("%d, %d,", next->i_flag & 0377, next->i_low & 0377);
|
||||||
nch += 2;
|
nch += 2;
|
||||||
switch ( next->i_flag&OPTYPE ) {
|
switch (next->i_flag & OPTYPE)
|
||||||
|
{
|
||||||
case OPMINI:
|
case OPMINI:
|
||||||
case OPSHORT:
|
case OPSHORT:
|
||||||
printf("%d,",next->i_num&0377) ; nch++ ;
|
printf("%d,", next->i_num & 0377);
|
||||||
|
nch++;
|
||||||
}
|
}
|
||||||
printf("\n");
|
printf("\n");
|
||||||
}
|
}
|
||||||
for ( currop++ ; currop<=sp_lmnem-sp_fmnem ; currop++ ) {
|
for (currop++; currop <= sp_lmnem - sp_fmnem; currop++)
|
||||||
|
{
|
||||||
elem[currop] = nch;
|
elem[currop] = nch;
|
||||||
error("Missing opcode %s", em_mnem[currop]);
|
error("Missing opcode %s", em_mnem[currop]);
|
||||||
}
|
}
|
||||||
elem[sp_lmnem - sp_fmnem + 1] = nch;
|
elem[sp_lmnem - sp_fmnem + 1] = nch;
|
||||||
printf("0 } ;\n\nchar *opindex[] = {\n");
|
printf("0 } ;\n\nchar *opindex[] = {\n");
|
||||||
for ( i=0 ; i<=sp_lmnem-sp_fmnem+1 ; i++ ) {
|
for (i = 0; i <= sp_lmnem - sp_fmnem + 1; i++)
|
||||||
|
{
|
||||||
printf(" &opchoice[%d], /* %d = %s */\n", elem[i], i, em_mnem[i]);
|
printf(" &opchoice[%d], /* %d = %s */\n", elem[i], i, em_mnem[i]);
|
||||||
}
|
}
|
||||||
printf("} ;\n");
|
printf("} ;\n");
|
||||||
}
|
}
|
||||||
|
|
||||||
int compare(a,b) struct opform *a,*b ; {
|
int compare(const void *a1, const void *b1)
|
||||||
if ( a->i_opcode!=b->i_opcode ) {
|
{
|
||||||
|
struct opform *a = (struct opform *)(a1);
|
||||||
|
struct opform *b = (struct opform *)(b1);
|
||||||
|
|
||||||
|
if (a->i_opcode != b->i_opcode)
|
||||||
|
{
|
||||||
return (a->i_opcode & 0377) - (b->i_opcode & 0377);
|
return (a->i_opcode & 0377) - (b->i_opcode & 0377);
|
||||||
}
|
}
|
||||||
return oplength(a) - oplength(b);
|
return oplength(a) - oplength(b);
|
||||||
}
|
}
|
||||||
|
|
||||||
int oplength(a) struct opform *a ; {
|
static int oplength(struct opform *a)
|
||||||
|
{
|
||||||
int cnt;
|
int cnt;
|
||||||
|
|
||||||
cnt = 1;
|
cnt = 1;
|
||||||
if ( a->i_flag&OPESC ) cnt++ ;
|
if (a->i_flag & OPESC)
|
||||||
switch( a->i_flag&OPTYPE ) {
|
cnt++;
|
||||||
|
switch (a->i_flag & OPTYPE)
|
||||||
|
{
|
||||||
case OPNO:
|
case OPNO:
|
||||||
case OPMINI : break ;
|
case OPMINI:
|
||||||
|
break;
|
||||||
case OP8:
|
case OP8:
|
||||||
case OPSHORT : cnt++ ; break ;
|
case OPSHORT:
|
||||||
|
cnt++;
|
||||||
|
break;
|
||||||
case OP16U:
|
case OP16U:
|
||||||
case OP16 : cnt+=2 ; break ;
|
case OP16:
|
||||||
case OP32 : cnt+=5 ; break ;
|
cnt += 2;
|
||||||
case OP64 : cnt+=9 ; break ;
|
break;
|
||||||
|
case OP32:
|
||||||
|
cnt += 5;
|
||||||
|
break;
|
||||||
|
case OP64:
|
||||||
|
cnt += 9;
|
||||||
|
break;
|
||||||
}
|
}
|
||||||
return cnt;
|
return cnt;
|
||||||
}
|
}
|
||||||
|
@ -306,31 +440,40 @@ int ecodes[256],codes[256],lcodes[256] ;
|
||||||
|
|
||||||
char negc[NMNEM], zc[NMNEM], posc[NMNEM];
|
char negc[NMNEM], zc[NMNEM], posc[NMNEM];
|
||||||
|
|
||||||
checkall() {
|
static void checkall(void)
|
||||||
register i,flag ;
|
{
|
||||||
|
register int i, flag;
|
||||||
register struct opform *next;
|
register struct opform *next;
|
||||||
int opc, low;
|
int opc, low;
|
||||||
|
|
||||||
for ( i=0 ; i<NMNEM ; i++ ) negc[i]=zc[i]=posc[i]=0 ;
|
for (i = 0; i < NMNEM; i++)
|
||||||
for ( i=0 ; i<256 ; i++ ) lcodes[i]= codes[i]= ecodes[i]= -1 ;
|
negc[i] = zc[i] = posc[i] = 0;
|
||||||
|
for (i = 0; i < 256; i++)
|
||||||
|
lcodes[i] = codes[i] = ecodes[i] = -1;
|
||||||
codes[254] = codes[255] = ESCAP;
|
codes[254] = codes[255] = ESCAP;
|
||||||
|
|
||||||
atend=0 ; line=0 ;
|
atend = 0;
|
||||||
for ( next=intable ; next<=lastform ; next++ ) {
|
line = 0;
|
||||||
|
for (next = intable; next <= lastform; next++)
|
||||||
|
{
|
||||||
line++;
|
line++;
|
||||||
flag = next->i_flag & 0377;
|
flag = next->i_flag & 0377;
|
||||||
opc = next->i_opcode & 0377;
|
opc = next->i_opcode & 0377;
|
||||||
low = next->i_low & 0377;
|
low = next->i_low & 0377;
|
||||||
chkc(flag, low, opc);
|
chkc(flag, low, opc);
|
||||||
switch(flag&OPTYPE) {
|
switch (flag & OPTYPE)
|
||||||
case OPNO : zc[opc]++ ; break ;
|
{
|
||||||
|
case OPNO:
|
||||||
|
zc[opc]++;
|
||||||
|
break;
|
||||||
case OPMINI:
|
case OPMINI:
|
||||||
case OPSHORT:
|
case OPSHORT:
|
||||||
for ( i=1 ; i<((next->i_num)&0377) ; i++ ) {
|
for (i = 1; i < ((next->i_num) & 0377); i++)
|
||||||
|
{
|
||||||
chkc(flag, low + i, opc);
|
chkc(flag, low + i, opc);
|
||||||
}
|
}
|
||||||
if ( !(em_flag[opc]&PAR_G) &&
|
if (!(em_flag[opc] & PAR_G) && (flag & OPRANGE) == OP_BOTH)
|
||||||
(flag&OPRANGE)==OP_BOTH) {
|
{
|
||||||
mess("Mini's and shorties should have P or N");
|
mess("Mini's and shorties should have P or N");
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
|
@ -353,11 +496,15 @@ checkall() {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
atend = 1;
|
atend = 1;
|
||||||
for ( i=0 ; i<256 ; i++ ) if ( codes[i]== -1 ) {
|
for (i = 0; i < 256; i++)
|
||||||
|
if (codes[i] == -1)
|
||||||
|
{
|
||||||
mess("interpreter opcode %d not used", i);
|
mess("interpreter opcode %d not used", i);
|
||||||
}
|
}
|
||||||
for ( opc=0 ; opc<NMNEM ; opc++ ) {
|
for (opc = 0; opc < NMNEM; opc++)
|
||||||
switch(em_flag[opc]&EM_PAR) {
|
{
|
||||||
|
switch (em_flag[opc] & EM_PAR)
|
||||||
|
{
|
||||||
case PAR_NO:
|
case PAR_NO:
|
||||||
ckop(opc, MUST, FORB, FORB);
|
ckop(opc, MUST, FORB, FORB);
|
||||||
break;
|
break;
|
||||||
|
@ -391,56 +538,75 @@ checkall() {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
chkc(flag,icode,emc) {
|
static void chkc(int flag, int icode, int emc)
|
||||||
if ( flag&OPESC ) {
|
{
|
||||||
if ( ecodes[icode]!=-1 ) {
|
if (flag & OPESC)
|
||||||
mess("Escaped opcode %d used by %s and %s",
|
{
|
||||||
icode,ename(emc),ename(ecodes[icode])) ;
|
if (ecodes[icode] != -1)
|
||||||
|
{
|
||||||
|
mess("Escaped opcode %d used by %s and %s", icode, ename(emc),
|
||||||
|
ename(ecodes[icode]));
|
||||||
}
|
}
|
||||||
ecodes[icode] = emc;
|
ecodes[icode] = emc;
|
||||||
} else switch ( flag&OPTYPE ) {
|
}
|
||||||
|
else
|
||||||
|
switch (flag & OPTYPE)
|
||||||
|
{
|
||||||
default:
|
default:
|
||||||
if ( codes[icode]!=-1 ) {
|
if (codes[icode] != -1)
|
||||||
mess("Opcode %d used by %s and %s",
|
{
|
||||||
icode,ename(emc),ename(codes[icode])) ;
|
mess("Opcode %d used by %s and %s", icode, ename(emc),
|
||||||
|
ename(codes[icode]));
|
||||||
}
|
}
|
||||||
codes[icode] = emc;
|
codes[icode] = emc;
|
||||||
break;
|
break;
|
||||||
case OP32:
|
case OP32:
|
||||||
case OP64:
|
case OP64:
|
||||||
if ( lcodes[icode]!=-1 ) {
|
if (lcodes[icode] != -1)
|
||||||
mess("Long opcode %d used by %s and %s",
|
{
|
||||||
icode,ename(emc),ename(codes[icode])) ;
|
mess("Long opcode %d used by %s and %s", icode, ename(emc),
|
||||||
|
ename(codes[icode]));
|
||||||
}
|
}
|
||||||
lcodes[icode] = emc;
|
lcodes[icode] = emc;
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
ckop(emc,zf,pf,nf) {
|
static void ckop(int emc, int zf, int pf, int nf)
|
||||||
if ( zc[emc]>1 ) mess("More then one OPNO for %s",ename(emc)) ;
|
{
|
||||||
if ( posc[emc]>1 ) mess("More then one OP16(pos) for %s",ename(emc)) ;
|
if (zc[emc] > 1)
|
||||||
if ( negc[emc]>1 ) mess("More then one OP16(neg) for %s",ename(emc)) ;
|
mess("More then one OPNO for %s", ename(emc));
|
||||||
switch(zf) {
|
if (posc[emc] > 1)
|
||||||
|
mess("More then one OP16(pos) for %s", ename(emc));
|
||||||
|
if (negc[emc] > 1)
|
||||||
|
mess("More then one OP16(neg) for %s", ename(emc));
|
||||||
|
switch (zf)
|
||||||
|
{
|
||||||
case MUST:
|
case MUST:
|
||||||
if ( zc[emc]==0 ) mess("No OPNO for %s",ename(emc)) ;
|
if (zc[emc] == 0)
|
||||||
|
mess("No OPNO for %s", ename(emc));
|
||||||
break;
|
break;
|
||||||
case FORB:
|
case FORB:
|
||||||
if ( zc[emc]==1 ) mess("Forbidden OPNO for %s",ename(emc)) ;
|
if (zc[emc] == 1)
|
||||||
|
mess("Forbidden OPNO for %s", ename(emc));
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
switch(pf) {
|
switch (pf)
|
||||||
|
{
|
||||||
case MUST:
|
case MUST:
|
||||||
if ( posc[emc]==0 ) mess("No OP16(pos) for %s",ename(emc)) ;
|
if (posc[emc] == 0)
|
||||||
|
mess("No OP16(pos) for %s", ename(emc));
|
||||||
break;
|
break;
|
||||||
case FORB:
|
case FORB:
|
||||||
if (posc[emc] == 1)
|
if (posc[emc] == 1)
|
||||||
mess("Forbidden OP16(pos) for %s", ename(emc));
|
mess("Forbidden OP16(pos) for %s", ename(emc));
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
switch(nf) {
|
switch (nf)
|
||||||
|
{
|
||||||
case MUST:
|
case MUST:
|
||||||
if ( negc[emc]==0 ) mess("No OP16(neg) for %s",ename(emc)) ;
|
if (negc[emc] == 0)
|
||||||
|
mess("No OP16(neg) for %s", ename(emc));
|
||||||
break;
|
break;
|
||||||
case FORB:
|
case FORB:
|
||||||
if (negc[emc] == 1)
|
if (negc[emc] == 1)
|
||||||
|
@ -452,25 +618,34 @@ ckop(emc,zf,pf,nf) {
|
||||||
static int pushchar;
|
static int pushchar;
|
||||||
static int pushf;
|
static int pushf;
|
||||||
|
|
||||||
int readchar() {
|
static int readchar(void)
|
||||||
|
{
|
||||||
int c;
|
int c;
|
||||||
|
|
||||||
if ( pushf ) {
|
if (pushf)
|
||||||
|
{
|
||||||
pushf = 0;
|
pushf = 0;
|
||||||
c = pushchar;
|
c = pushchar;
|
||||||
} else {
|
}
|
||||||
if ( feof(stdin) ) return EOF ;
|
else
|
||||||
|
{
|
||||||
|
if (feof(stdin))
|
||||||
|
return EOF;
|
||||||
c = getc(stdin);
|
c = getc(stdin);
|
||||||
}
|
}
|
||||||
if ( c=='\n' ) line++ ;
|
if (c == '\n')
|
||||||
|
line++;
|
||||||
return c;
|
return c;
|
||||||
}
|
}
|
||||||
|
|
||||||
pushback(c) {
|
static void pushback(int c)
|
||||||
if ( pushf ) {
|
{
|
||||||
|
if (pushf)
|
||||||
|
{
|
||||||
fatal("Double pushback");
|
fatal("Double pushback");
|
||||||
}
|
}
|
||||||
pushf++;
|
pushf++;
|
||||||
pushchar = c;
|
pushchar = c;
|
||||||
if ( c=='\n' ) line-- ;
|
if (c == '\n')
|
||||||
|
line--;
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in a new issue