use new C_insertpart mechanism, other minor changes

This commit is contained in:
ceriel 1987-07-16 13:27:37 +00:00
parent 2381b2e136
commit 0619d27b8d
19 changed files with 428 additions and 317 deletions

View file

@ -97,7 +97,7 @@
!File: inputtype.h
#undef INP_READ_IN_ONE 1 /* read input file in one */
#define INP_READ_IN_ONE 1 /* read input file in one */
!File: nopp.h

View file

@ -58,7 +58,7 @@ CSRC = main.c idf.c declarator.c decspecs.c struct.c \
tokenname.c LLlex.c LLmessage.c \
input.c domacro.c replace.c init.c options.c \
scan.c skip.c stack.c type.c ch7mon.c label.c eval.c \
switch.c conversion.c \
switch.c conversion.c util.c \
blocks.c dataflow.c Version.c
COBJ = main.o idf.o declarator.o decspecs.o struct.o \
expr.o ch7.o ch7bin.o cstoper.o arith.o \
@ -66,7 +66,7 @@ COBJ = main.o idf.o declarator.o decspecs.o struct.o \
tokenname.o LLlex.o LLmessage.o \
input.o domacro.o replace.o init.o options.o \
scan.o skip.o stack.o type.o ch7mon.o label.o eval.o \
switch.o conversion.o \
switch.o conversion.o util.o \
blocks.o dataflow.o Version.o
# Objects of other generated C files
@ -74,11 +74,11 @@ GCSRC = char.c symbol2str.c next.c
GOBJ = char.o symbol2str.o next.o
STRSRC = code.str declar.str decspecs.str def.str expr.str field.str \
estack.str \
estack.str util.str \
idf.str macro.str stack.str stmt.str struct.str switch.str type.str
# generated source files
GHSTRSRC = code.h declar.h decspecs.h def.h expr.h field.h \
estack.h \
estack.h util.h \
idf.h macro.h stack.h stmt.h struct.h switch.h type.h
GSRC = $(GCSRC) $(GHSTRSRC)
@ -185,6 +185,7 @@ struct.h: make.allocd
switch.h: make.allocd
type.h: make.allocd
estack.h: make.allocd
util.h: make.allocd
depend: Cfiles
sed '/^#AUTOAUTO/,$$d' makefile >makefile.new
@ -441,7 +442,6 @@ error.o: nofloat.h
error.o: nopp.h
error.o: spec_arith.h
error.o: tokenname.h
error.o: use_tmp.h
field.o: Lpars.h
field.o: arith.h
field.o: assert.h
@ -677,6 +677,15 @@ conversion.o: sizes.h
conversion.o: spec_arith.h
conversion.o: target_sizes.h
conversion.o: type.h
util.o: align.h
util.o: atw.h
util.o: nocross.h
util.o: nofloat.h
util.o: sizes.h
util.o: stack.h
util.o: target_sizes.h
util.o: use_tmp.h
util.o: util.h
blocks.o: align.h
blocks.o: arith.h
blocks.o: atw.h

View file

@ -97,7 +97,7 @@
!File: inputtype.h
#undef INP_READ_IN_ONE 1 /* read input file in one */
#define INP_READ_IN_ONE 1 /* read input file in one */
!File: nopp.h

View file

@ -6,6 +6,7 @@
/* B L O C K S T O R I N G A N D L O A D I N G */
#include <em.h>
#include <em_reg.h>
#include "arith.h"
#include "sizes.h"
#include "atw.h"
@ -13,7 +14,8 @@
#ifndef STB
#include "label.h"
#include "stack.h"
extern arith tmp_pointer_var();
extern arith NewLocal();
#define LocalPtrVar() NewLocal(pointer_size, pointer_align, reg_pointer, 0)
#endif STB
/* Because EM does not support the loading and storing of
@ -58,22 +60,20 @@ store_block(sz, al)
C_sti(sz);
else {
#ifndef STB
arith src, dst, src_offs, dst_offs;
arith src, dst;
/* allocate two pointer temporaries */
src = tmp_pointer_var(&src_offs);
dst = tmp_pointer_var(&dst_offs);
src = LocalPtrVar();
dst = LocalPtrVar();
/* load the addresses */
C_lal(dst);
C_sti(pointer_size);
StoreLocal(dst, pointer_size);
C_lor((arith)1); /* push current sp */
C_lal(src);
C_sti(pointer_size);
StoreLocal(src, pointer_size);
copy_loop(sz, src, dst);
C_asp(ATW(sz));
free_tmp_var(dst_offs);
free_tmp_var(src_offs);
FreeLocal(dst);
FreeLocal(src);
#else STB
/* address of destination lies on the stack */
@ -103,21 +103,19 @@ load_block(sz, al)
C_loi(esz);
else {
#ifndef STB
arith src, dst, src_offs, dst_offs;
arith src, dst;
/* allocate two pointer temporaries */
src = tmp_pointer_var(&src_offs);
dst = tmp_pointer_var(&dst_offs);
src = LocalPtrVar();
dst = LocalPtrVar();
C_lal(src);
C_sti(pointer_size);
StoreLocal(src, pointer_size);
C_asp(-esz); /* allocate stack block */
C_lor((arith)1); /* push & of stack block as dst */
C_lal(dst);
C_sti(pointer_size);
StoreLocal(dst, pointer_size);
copy_loop(sz, src, dst);
free_tmp_var(dst_offs);
free_tmp_var(src_offs);
FreeLocal(dst);
FreeLocal(src);
#else STB
C_asp(-(esz - pointer_size)); /* allocate stack block */
C_lor((arith)1); /* push & of stack block as dst */
@ -143,19 +141,15 @@ copy_loop(sz, src, dst)
C_dup(word_size);
C_zle(l_stop);
C_dec();
C_lal(src);
C_loi(pointer_size);
LoadLocal(src, pointer_size);
C_dup(pointer_size);
C_adp((arith)1);
C_lal(src);
C_sti(pointer_size);
StoreLocal(src, pointer_size);
C_loi((arith)1);
C_lal(dst);
C_loi(pointer_size);
LoadLocal(dst, pointer_size);
C_dup(pointer_size);
C_adp((arith)1);
C_lal(dst);
C_sti(pointer_size);
StoreLocal(dst, pointer_size);
C_sti((arith)1);
C_bra(l_cont);
C_df_ilb(l_stop);

View file

@ -86,7 +86,6 @@ ch7mon(oper, expp)
"& on register variable not allowed");
break; /* break case '&' */
}
def->df_register = REG_NONE;
}
(*expp)->ex_type = pointer_to((*expp)->ex_type);
(*expp)->ex_lvalue = 0;

View file

@ -40,6 +40,12 @@ label datlab_count = 1;
int fp_used;
#endif NOFLOAT
#ifdef USE_TMP
static int tmp_id;
static int pro_id;
static char *pro_name;
#endif USE_TMP
extern char options[];
char *symbol2str();
@ -52,16 +58,11 @@ init_code(dst_file)
C_init(word_size, pointer_size); /* initialise EM module */
if (C_open(dst_file) == 0)
fatal("cannot write to %s\n", dst_file);
#ifdef USE_TMP
if (options['N'])
#endif USE_TMP
famous_first_words();
}
famous_first_words()
{
C_magic();
C_ms_emx(word_size, pointer_size);
#ifdef USE_TMP
C_insertpart(tmp_id = C_getid());
#endif USE_TMP
}
static struct string_cst *str_list = 0;
@ -84,11 +85,13 @@ code_string(val, len, dlb)
def_strings(sc)
register struct string_cst *sc;
{
if (sc) {
def_strings(sc->next);
while (sc) {
struct string_cst *sc1 = sc;
C_df_dlb(sc->sc_dlb);
str_cst(sc->sc_value, sc->sc_len);
free_string_cst(sc);
sc = sc->next;
free_string_cst(sc1);
}
}
@ -97,6 +100,12 @@ end_code()
/* end_code() performs the actions to be taken when closing
the output stream.
*/
#ifndef NOFLOAT
if (fp_used) {
/* floating point used */
C_ms_flt();
}
#endif NOFLOAT
def_strings(str_list);
str_list = 0;
C_ms_src((int)(LineNumber - 2), FileName);
@ -104,18 +113,15 @@ end_code()
}
#ifdef USE_TMP
prepend_scopes(dst_file)
char *dst_file;
prepend_scopes()
{
/* prepend_scopes() runs down the list of global idf's
and generates those exa's, exp's, ina's and inp's
that superior hindsight has provided, on the file dst_file.
that superior hindsight has provided.
*/
register struct stack_entry *se = local_level->sl_entry;
if (C_open(dst_file) == 0)
fatal("cannot create %s", dst_file ? dst_file : "stdout");
famous_first_words();
C_beginpart(tmp_id);
while (se != 0) {
register struct idf *id = se->se_idf;
register struct def *df = id->id_def;
@ -124,7 +130,7 @@ prepend_scopes(dst_file)
code_scope(id->id_text, df);
se = se->next;
}
C_close();
C_endpart(tmp_id);
}
#endif USE_TMP
@ -156,8 +162,9 @@ code_scope(text, def)
}
static label return_label;
static char return_expr_occurred;
/* static char return_expr_occurred; */
static struct type *func_tp;
static arith func_size;
static label func_res_label;
static char *last_fn_given = "";
static label file_name_label;
@ -174,12 +181,9 @@ begin_proc(name, def) /* to be called when entering a procedure */
does not fit in the return area
- a fil pseudo instruction
*/
arith size;
register struct type *tp = def->df_type;
#ifdef USE_TMP
if (options['N']) code_scope(name,def);
#else USE_TMP
#ifndef USE_TMP
code_scope(name, def);
#endif USE_TMP
#ifdef DATAFLOW
@ -194,11 +198,16 @@ begin_proc(name, def) /* to be called when entering a procedure */
else
tp = tp->tp_up;
func_tp = tp;
size = ATW(tp->tp_size);
func_size = ATW(tp->tp_size);
#ifndef USE_TMP
C_pro_narg(name);
#else
pro_name = name;
C_insertpart(pro_id = C_getid());
#endif
if (is_struct_or_union(tp->tp_fund)) {
C_df_dlb(func_res_label = data_label());
C_bss_cst(size, (arith)0, 1);
C_bss_cst(func_size, (arith)0, 1);
}
else
func_res_label = 0;
@ -208,7 +217,8 @@ begin_proc(name, def) /* to be called when entering a procedure */
*/
lab_count = (label) 1;
return_label = text_label();
return_expr_occurred = 0;
/* return_expr_occurred = 0; */
LocalInit();
prc_entry(name);
if (! options['L']) { /* profiling */
if (strcmp(last_fn_given, FileName) != 0) {
@ -223,8 +233,8 @@ begin_proc(name, def) /* to be called when entering a procedure */
}
}
end_proc(fbytes, nbytes)
arith fbytes, nbytes;
end_proc(fbytes)
arith fbytes;
{
/* end_proc() deals with the code to be generated at the end of
a function, as there is:
@ -238,47 +248,57 @@ end_proc(fbytes, nbytes)
- use of special identifiers such as "setjmp"
- "end" + number of bytes used for local variables
*/
static int mes_flt_given = 0; /* once for the whole program */
arith nbytes;
#ifdef DATAFLOW
if (options['d'])
DfaEndFunction();
#endif DATAFLOW
prc_exit();
C_ret((arith)0);
if (return_expr_occurred != 0) {
C_df_ilb(return_label);
prc_exit();
if (func_res_label != 0) {
C_lae_dlb(func_res_label, (arith)0);
store_block(func_tp->tp_size, func_tp->tp_align);
C_lae_dlb(func_res_label, (arith)0);
C_ret(pointer_size);
}
else
C_ret(ATW(func_tp->tp_size));
C_asp(-func_size); /* arbitrary return value */
C_df_ilb(return_label);
prc_exit();
if (func_res_label != 0) {
C_lae_dlb(func_res_label, (arith)0);
store_block(func_size, func_tp->tp_align);
C_lae_dlb(func_res_label, (arith)0);
C_ret(pointer_size);
}
#ifndef NOFLOAT
if (fp_used && mes_flt_given == 0) {
/* floating point used */
C_ms_flt();
mes_flt_given++;
}
#endif NOFLOAT
else
C_ret(func_size);
/* getting the number of "local" bytes is posponed until here,
because copying the function result in "func_res_label" may
need temporaries! However, local_level is now L_FORMAL2, because
L_LOCAL is already unstacked. Therefore, "unstack_level" must
also pass "sl_max_block" to the level above L_LOCAL.
*/
nbytes = ATW(- local_level->sl_max_block);
#ifdef USE_TMP
C_beginpart(pro_id);
C_pro(pro_name, nbytes);
#endif
C_ms_par(fbytes); /* # bytes for formals */
if (sp_occurred[SP_SETJMP]) { /* indicate use of "setjmp" */
C_ms_gto();
sp_occurred[SP_SETJMP] = 0;
}
C_end(ATW(nbytes));
#ifdef USE_TMP
C_endpart(pro_id);
#endif
LocalFinish();
C_end(nbytes);
}
do_return()
{
/* do_return generates a direct return */
/* isn't a jump to the return label smarter ??? */
prc_exit();
C_ret((arith)0);
/* do_return handles the case of a return without expression.
This version branches to the return label, which is
probably smarter than generating a direct return.
Return sequences may be expensive.
*/
C_asp(-func_size); /* arbitrary return value */
C_bra(return_label);
}
do_return_expr(expr)
@ -290,7 +310,7 @@ do_return_expr(expr)
ch7cast(&expr, RETURN, func_tp);
code_expr(expr, RVAL, TRUE, NO_LABEL, NO_LABEL);
C_bra(return_label);
return_expr_occurred = 1;
/* return_expr_occurred = 1; */
}
code_declaration(idf, expr, lvl, sc)
@ -322,7 +342,6 @@ code_declaration(idf, expr, lvl, sc)
while at the same time forbidding
extern int a = 5;
*/
char *text = idf->id_text;
register struct def *def = idf->id_def;
register arith size = def->df_type->tp_size;
int def_sc = def->df_sc;
@ -330,7 +349,7 @@ code_declaration(idf, expr, lvl, sc)
if (def_sc == TYPEDEF) /* no code for typedefs */
return;
if (sc == EXTERN && expr && !is_anon_idf(idf))
error("%s is extern; cannot initialize", text);
error("%s is extern; cannot initialize", idf->id_text);
if (lvl == L_GLOBAL) { /* global variable */
/* is this an allocating declaration? */
if ( (sc == 0 || sc == STATIC)
@ -339,12 +358,11 @@ code_declaration(idf, expr, lvl, sc)
)
def->df_alloc = ALLOC_SEEN;
if (expr) { /* code only if initialized */
#ifdef USE_TMP
if (options['N'])
#ifndef USE_TMP
code_scope(idf->id_text, def);
#endif USE_TMP
code_scope(text, def);
def->df_alloc = ALLOC_DONE;
C_df_dnam(text);
C_df_dnam(idf->id_text);
}
}
else
@ -364,7 +382,7 @@ code_declaration(idf, expr, lvl, sc)
}
else { /* produce blank space */
if (size <= 0) {
error("size of %s unknown", text);
error("size of %s unknown", idf->id_text);
size = (arith)0;
}
C_bss_cst(ATW(size), (arith)0, 1);
@ -374,10 +392,9 @@ code_declaration(idf, expr, lvl, sc)
case GLOBAL:
case IMPLICIT:
/* we are sure there is no expression */
#ifdef USE_TMP
if (options['N'])
#ifndef USE_TMP
code_scope(idf->id_text, def);
#endif USE_TMP
code_scope(text, def);
break;
case AUTO:
case REGISTER:
@ -399,8 +416,8 @@ loc_init(expr, id)
expression expr to the local variable described by id.
It frees the expression afterwards.
*/
register struct type *tp = id->id_def->df_type;
register struct expr *e = expr;
register struct type *tp = id->id_def->df_type;
ASSERT(id->id_def->df_sc != STATIC);
switch (tp->tp_fund) {
@ -446,10 +463,9 @@ bss(idf)
*/
arith size = idf->id_def->df_type->tp_size;
#ifdef USE_TMP
if (options['N'])
#endif USE_TMP
#ifndef USE_TMP
code_scope(idf->id_text, idf->id_def);
#endif USE_TMP
/* Since bss() is only called if df_alloc is non-zero, and
since df_alloc is only non-zero if size >= 0, we have:
*/
@ -475,13 +491,11 @@ formal_cvt(df)
if (tp->tp_size != int_size &&
(tp->tp_fund == CHAR || tp->tp_fund == SHORT)
) {
C_lol(df->df_address);
LoadLocal(df->df_address, int_size);
/* conversion(int_type, df->df_type); ???
No, you can't do this on the stack! (CJ)
*/
C_lal(df->df_address);
C_sti(tp->tp_size);
df->df_register = REG_NONE;
StoreLocal(df->df_address, tp->tp_size);
}
}
@ -563,15 +577,15 @@ unstack_stmt()
free_stmt_block(sbp);
}
static label l1;
static label prc_name;
prc_entry(name)
char *name;
{
if (options['p']) {
C_df_dlb(l1 = data_label());
C_df_dlb(prc_name = data_label());
C_rom_scon(name, (arith) (strlen(name) + 1));
C_lae_dlb(l1, (arith) 0);
C_lae_dlb(prc_name, (arith) 0);
C_cal("procentry");
C_asp(pointer_size);
}
@ -580,7 +594,7 @@ prc_entry(name)
prc_exit()
{
if (options['p']) {
C_lae_dlb(l1, (arith) 0);
C_lae_dlb(prc_name, (arith) 0);
C_cal("procexit");
C_asp(pointer_size);
}

View file

@ -15,7 +15,6 @@ struct def { /* for ordinary tags */
FORMAL, AUTO,
ENUM, LABEL
*/
int df_register; /* REG_NONE, REG_DEFAULT or REG_BONUS */
char df_initialized; /* an initialization has been generated */
char df_alloc; /* 0, ALLOC_SEEN or ALLOC_DONE */
char df_used; /* set if idf is used */
@ -26,8 +25,7 @@ struct def { /* for ordinary tags */
#define ALLOC_SEEN 1 /* an allocating declaration has been seen */
#define ALLOC_DONE 2 /* the allocating declaration has been done */
#define REG_NONE 0 /* no register candidate */
#define REG_DEFAULT 1 /* register candidate, not declared as such */
#define REG_DEFAULT 0 /* register candidate, not declared as such */
#define REG_BONUS 10 /* register candidate, declared as such */
/* ALLOCDEF "def" 50 */

View file

@ -167,7 +167,6 @@ dumpdefs(def, opt)
print("L%d: %s %s%s%s%s%s %lo;",
def->df_level,
symbol2str(def->df_sc),
(def->df_register != REG_NONE) ? "reg " : "",
def->df_initialized ? "init'd " : "",
def->df_used ? "used " : "",
type2str(def->df_type),

View file

@ -9,7 +9,6 @@
#include <em.h>
#include "nopp.h"
#include "use_tmp.h"
#include "errout.h"
#include "debug.h"
@ -116,13 +115,7 @@ fatal(fmt, args)
char *fmt;
int args;
{
#ifdef USE_TMP
extern char *tmpfile; /* main.c */
if (tmpfile)
sys_remove(tmpfile); /* may not successful! */
#endif USE_TMP
if (C_busy()) C_close();
_error(FATAL, NILEXPR, fmt, &args);
sys_stop(S_EXIT);
}

View file

@ -7,6 +7,7 @@
#include "nofloat.h"
#include <em.h>
#include <em_reg.h>
#include "debug.h"
#include "nobitfield.h"
#include "dataflow.h"
@ -31,7 +32,8 @@
char *symbol2str();
char *long2str();
arith tmp_pointer_var();
arith NewLocal(); /* util.c */
#define LocalPtrVar() NewLocal(pointer_size, pointer_align, reg_pointer, 0)
/* EVAL() is the main expression-tree evaluator, which turns
any legal expression tree into EM code. Parameters:
@ -366,7 +368,7 @@ EVAL(expr, val, code, true_label, false_label)
case PLUSPLUS:
case MINMIN:
{
arith old_offset, tmp;
arith tmp;
int compl; /* Complexity of left operand */
int newcode = left->ex_type->tp_size > 0; /* CJ */
#ifndef NOBITFIELD
@ -389,10 +391,9 @@ EVAL(expr, val, code, true_label, false_label)
compl = 2; /* otherwise */
EVAL(left, LVAL, newcode, NO_LABEL, NO_LABEL);
if (newcode) {
tmp = tmp_pointer_var(&old_offset);
tmp = LocalPtrVar();
C_dup(pointer_size);
C_lal(tmp);
C_sti(pointer_size);
StoreLocal(tmp, pointer_size);
C_loi(left->ex_type->tp_size);
}
}
@ -423,15 +424,13 @@ EVAL(expr, val, code, true_label, false_label)
}
}
else {
C_lal(tmp); /* always init'd */
C_loi(pointer_size);
LoadLocal(tmp, pointer_size);
C_sti(left->ex_type->tp_size);
if (dupval) {
C_lal(tmp);
C_loi(pointer_size);
LoadLocal(tmp, pointer_size);
C_loi(left->ex_type->tp_size);
}
free_tmp_var(old_offset);
FreeLocal(tmp);
}
}
break;
@ -477,7 +476,7 @@ EVAL(expr, val, code, true_label, false_label)
if (gencode) {
if (is_struct_or_union(tp->tp_fund)) {
C_lfr(pointer_size);
load_block(tp->tp_size, tp->tp_align);
load_block(tp->tp_size, word_align);
}
else
C_lfr(ATW(tp->tp_size));
@ -758,33 +757,6 @@ assop(type, oper)
}
}
/* tmp_pointer_var() returns the EM address of a new temporary
pointer variable needed at increment, decrement and assignment
operations to store the address of some variable or lvalue-expression.
*/
arith
tmp_pointer_var(oldoffset)
arith *oldoffset; /* previous allocated address */
{
register struct stack_level *stl = local_level;
*oldoffset = stl->sl_local_offset;
stl->sl_local_offset =
- align(-stl->sl_local_offset + pointer_size, pointer_align);
if (stl->sl_local_offset < stl->sl_max_block)
stl->sl_max_block = stl->sl_local_offset;
return stl->sl_local_offset;
}
/* free_tmp_var() returns the address allocated by tmp_pointer_var()
and resets the last allocated address.
*/
free_tmp_var(oldoffset)
arith oldoffset;
{
local_level->sl_local_offset = oldoffset;
}
/* store_val() generates code for a store operation.
There are four ways of storing data:
- into a global variable
@ -828,15 +800,11 @@ store_val(vl, tp)
}
else {
ASSERT(df->df_sc != STATIC);
if (inword)
C_stl(df->df_address + val);
else
if (indword)
C_sdl(df->df_address + val);
if (inword || indword)
StoreLocal(df->df_address + val, size);
else {
C_lal(df->df_address + val);
AddrLocal(df->df_address + val);
store_block(size, tpalign);
df->df_register = REG_NONE;
}
}
}
@ -943,21 +911,16 @@ load_val(expr, rlval)
else {
ASSERT(df->df_sc != STATIC);
if (rvalue) {
if (inword)
C_lol(df->df_address + val);
else
if (indword)
C_ldl(df->df_address + val);
if (inword || indword)
LoadLocal(df->df_address + val, size);
else {
C_lal(df->df_address + val);
AddrLocal(df->df_address + val);
load_block(size, tpalign);
df->df_register = REG_NONE;
}
}
else {
C_lal(df->df_address);
AddrLocal(df->df_address);
C_adp(val);
df->df_register = REG_NONE;
}
}
}

View file

@ -9,6 +9,7 @@
#ifndef NOBITFIELD
#include <em.h>
#include <em_reg.h>
#include "debug.h"
#include "arith.h"
#include "type.h"
@ -18,10 +19,11 @@
#include "assert.h"
#include "expr.h"
#include "sizes.h"
#include "align.h"
#include "Lpars.h"
#include "field.h"
arith tmp_pointer_var(); /* eval.c */
arith NewLocal(); /* util.c */
char *symbol2str(); /* symbol2str.c */
/* Eval_field() evaluates expressions involving bit fields.
@ -45,7 +47,7 @@ eval_field(expr, code)
register struct expr *rightop = expr->OP_RIGHT;
register struct field *fd = leftop->ex_type->tp_field;
struct type *tp = leftop->ex_type->tp_up;
arith old_offset, tmpvar;
arith tmpvar;
struct type *atype = tp->tp_unsigned ? uword_type : word_type;
arith asize = atype->tp_size;
@ -75,18 +77,17 @@ eval_field(expr, code)
store_val(&(leftop->ex_object.ex_value), atype);
}
else { /* complex case */
tmpvar = tmp_pointer_var(&old_offset);
tmpvar = NewLocal(pointer_size, pointer_align,
reg_pointer, 0);
EVAL(leftop, LVAL, TRUE, NO_LABEL, NO_LABEL);
C_dup(pointer_size);
C_lal(tmpvar);
C_sti(pointer_size);
StoreLocal(tmpvar, pointer_size);
C_loi(asize);
C_and(asize);
C_ior(asize);
C_lal(tmpvar);
C_loi(pointer_size);
LoadLocal(tmpvar, pointer_size);
C_sti(asize);
free_tmp_var(old_offset);
FreeLocal(tmpvar);
}
}
else { /* treat ++F as F += 1 and --F as F -= 1 */
@ -96,11 +97,11 @@ eval_field(expr, code)
if (leftop->ex_depth == 0) /* simple case */
load_val(leftop, RVAL);
else { /* complex case */
tmpvar = tmp_pointer_var(&old_offset);
tmpvar = NewLocal(pointer_size, pointer_align,
reg_pointer, 0);
EVAL(leftop, LVAL, TRUE, NO_LABEL, NO_LABEL);
C_dup(pointer_size);
C_lal(tmpvar);
C_sti(pointer_size);
StoreLocal(tmpvar, pointer_size);
C_loi(asize);
}
if (atype->tp_unsigned) {
@ -146,15 +147,13 @@ eval_field(expr, code)
store_val(&(leftop->ex_object.ex_value), atype);
}
else {
C_lal(tmpvar);
C_loi(pointer_size);
LoadLocal(tmpvar, pointer_size);
C_loi(asize);
C_and(asize);
C_ior(asize);
C_lal(tmpvar);
C_loi(pointer_size);
LoadLocal(tmpvar, pointer_size);
C_sti(asize);
free_tmp_var(old_offset);
FreeLocal(tmpvar);
}
}
if (code == TRUE) {

View file

@ -5,6 +5,7 @@
/* $Header$ */
/* IDENTIFIER FIDDLING & SYMBOL TABLE HANDLING */
#include <em_reg.h>
#include "nofloat.h"
#include "debug.h"
#include "idfsize.h"
@ -31,6 +32,7 @@
int idfsize = IDFSIZE;
extern char options[];
extern arith NewLocal();
char sp_occurred[SP_TOTAL]; /* indicate occurrence of special id */
@ -292,7 +294,6 @@ declare_idf(ds, dc, lvl)
def->df_formal_array = formal_array;
def->df_sc = sc;
def->df_level = L_FORMAL2; /* CJ */
if (sc == REGISTER) def->df_register = REG_BONUS;
}
else
if ( lvl >= L_LOCAL &&
@ -318,8 +319,6 @@ declare_idf(ds, dc, lvl)
newdef->df_level = lvl;
newdef->df_type = type;
newdef->df_sc = sc;
if (lvl == L_FORMAL1) /* CJ */
newdef->df_register = REG_DEFAULT;
/* link it into the name list in the proper place */
idf->id_def = newdef;
update_ahead(idf);
@ -340,14 +339,13 @@ declare_idf(ds, dc, lvl)
idf->id_text);
/** type = idf->id_def->df_type = int_type; **/
}
newdef->df_register =
(sc == REGISTER) ? REG_BONUS
: REG_DEFAULT;
newdef->df_address =
stl->sl_max_block =
stl->sl_local_offset =
-align(-stl->sl_local_offset +
type->tp_size, type->tp_align);
NewLocal(type->tp_size,
type->tp_align,
regtype(type),
(sc == REGISTER) ? REG_BONUS
: REG_DEFAULT
);
break;
case STATIC:
newdef->df_address = (arith) data_label();
@ -615,10 +613,33 @@ declare_formals(fp)
formal_cvt(def); /* cvt int to char or short, if necessary */
se = se->next;
def->df_level = L_FORMAL2; /* CJ */
RegisterAccount(def->df_address, def->df_type->tp_size,
regtype(def->df_type),
(def->df_sc == REGISTER ? REG_BONUS
: REG_DEFAULT)
);
}
*fp = f_offset;
}
int
regtype(tp)
struct type *tp;
{
switch(tp->tp_fund) {
case INT:
return reg_any;
#ifndef NOFLOAT
case FLOAT:
case DOUBLE:
return reg_float;
#endif NOFLOAT
case POINTER:
return reg_pointer;
}
return -1;
}
add_def(idf, sc, tp, lvl)
struct idf *idf;
struct type *tp;

View file

@ -125,20 +125,9 @@ char *source = 0;
char *nmlist = 0;
#ifdef USE_TMP
extern char *strcpy(), *strcat();
extern char *mktemp(); /* library routine */
char *tmpfdir = "/tmp"; /* where to keep the temporary file */
static char *tmpfname = "/Cem.XXXXXX";
char *tmpfile = 0;
#endif USE_TMP
compile(argc, argv)
char *argv[];
{
#ifdef USE_TMP
char tmpf[256];
#endif
char *result;
register char *destination = 0;
@ -175,14 +164,6 @@ compile(argc, argv)
FileName = "standard input";
}
#ifdef USE_TMP
if (! options['N']) {
strcpy(tmpf, tmpfdir);
strcat(tmpf, tmpfname);
tmpfile = mktemp(tmpf);
}
#endif USE_TMP
if (destination && strcmp(destination, "-") == 0)
destination = 0;
if (!InsertFile(source, (char **) 0, &result)) /* read the source file */
@ -204,25 +185,15 @@ compile(argc, argv)
#endif DEBUG
{
#ifdef USE_TMP
if (!options['N']) {
init_code(tmpfile);
}
else
#endif USE_TMP
init_code(destination);
/* compile the source text */
C_program();
end_code();
#ifdef USE_TMP
if (! options['N']) {
prepend_scopes(destination);
AppendFile(tmpfile, destination);
sys_remove(tmpfile);
}
prepend_scopes();
#endif USE_TMP
end_code();
#ifdef DEBUG
if (options['u']) {
@ -399,33 +370,6 @@ preprocess()
#endif NOPP
#endif DEBUG
#ifdef USE_TMP
AppendFile(src, dst)
char *src, *dst;
{
File *fp_src, *fp_dst;
char buf[BUFSIZ];
int n;
if (sys_open(src, OP_READ, &fp_src) == 0)
fatal("cannot read %s", src);
if (dst) {
if (sys_open(dst, OP_APPEND, &fp_dst) == 0)
fatal("cannot write to %s", src);
}
else
fp_dst = STDOUT;
while (sys_read(fp_src, buf, BUFSIZ, &n) != 0 && n > 0)
if (sys_write(fp_dst, buf, n) == 0)
fatal("(AppendFile) write error");
if (n != 0)
fatal("(AppendFile) read error");
sys_close(fp_src);
if (fp_dst != STDOUT)
sys_close(fp_dst);
}
#endif USE_TMP
No_Mem()
{
fatal("out of memory");

View file

@ -30,9 +30,6 @@ extern int inc_total;
extern char options[];
extern int idfsize;
#ifdef USE_TMP
extern char *tmpfdir; /* main.c */
#endif USE_TMP
int txt2int();
@ -163,14 +160,6 @@ deleted, is now a debug-flag
fatal("maximum identifier length is %d", IDFSIZE);
break;
case 'N' :
#ifdef USE_TMP
options['N'] = 1;
#else USE_TMP
warning("-N option ignored");
#endif USE_TMP
break;
#ifdef ___XXX___
case 'P' : /* run preprocessor stand-alone, without #'s */
#ifndef NOPP
@ -183,15 +172,17 @@ deleted, is now a debug-flag
#endif ___XXX___
#ifdef USE_TMP
case 'T' :
case 'T' : {
extern char *C_tmpdir;
if (*text)
tmpfdir = text;
C_tmpdir = text;
else
tmpfdir = ".";
C_tmpdir = ".";
#else USE_TMP
warning("-T option ignored");
#endif USE_TMP
break;
}
case 'U' : { /* -Uname : undefine predefined */
#ifndef NOPP

View file

@ -180,10 +180,10 @@ function(struct declarator *dc;)
{
declare_formals(&fbytes);
}
compound_statement(&nbytes)
compound_statement
{
end_proc(fbytes);
unstack_level(); /* L_FORMAL2 declarations */
unstack_level(); /* L_FORMAL1 declarations */
end_proc(fbytes, nbytes);
}
;

View file

@ -8,7 +8,6 @@
#include "nofloat.h"
#include <system.h>
#include <em.h>
#include <em_reg.h>
#include "debug.h"
#include "botch_free.h"
#include <alloc.h>
@ -50,8 +49,7 @@ stack_level() {
loclev->sl_next = stl;
stl->sl_previous = loclev;
stl->sl_level = ++level;
stl->sl_local_offset =
stl->sl_max_block = loclev->sl_local_offset;
stl->sl_max_block = loclev->sl_max_block;
local_level = stl;
}
@ -115,36 +113,8 @@ unstack_level()
/* unlink it from the def list under the idf block */
if (def->df_sc == LABEL)
unstack_label(idf);
else
if (level == L_LOCAL || level == L_FORMAL1) {
if ( def->df_register != REG_NONE &&
def->df_sc != STATIC &&
def->df_type->tp_size > 0 &&
options['n'] == 0
) {
int reg;
switch (def->df_type->tp_fund) {
case POINTER:
reg = reg_pointer;
break;
#ifndef NOFLOAT
case FLOAT:
case DOUBLE:
reg = reg_float;
break;
#endif NOFLOAT
default:
reg = reg_any;
break;
}
C_ms_reg(def->df_address,
def->df_type->tp_size,
reg, def->df_register
);
}
}
else if (def->df_sc == REGISTER || def->df_sc == AUTO)
FreeLocal(def->df_address);
idf->id_def = def->next;
free_def(def);
update_ahead(idf);
@ -173,9 +143,7 @@ unstack_level()
*/
lastlvl = local_level;
local_level = local_level->sl_previous;
if ( level > L_LOCAL
&& lastlvl->sl_max_block < local_level->sl_max_block
) {
if (level >= L_LOCAL) {
local_level->sl_max_block = lastlvl->sl_max_block;
}
free_stack_level(lastlvl);

View file

@ -37,7 +37,7 @@ statement
|
label ':' statement
|
compound_statement((arith *)0)
compound_statement
|
if_statement
|
@ -353,7 +353,7 @@ jump
}
;
compound_statement(arith *nbytes;):
compound_statement:
'{'
{
stack_level();
@ -366,8 +366,6 @@ compound_statement(arith *nbytes;):
]*
'}'
{
if (nbytes)
*nbytes = (- local_level->sl_max_block);
unstack_level();
}
;

211
lang/cem/cemcom/util.c Normal file
View file

@ -0,0 +1,211 @@
/*
* (c) copyright 1987 by the Vrije Universiteit, Amsterdam, The Netherlands.
* See the copyright notice in the ACK home directory, in the file "Copyright".
*/
/* M I S C E L L A N E O U S U T I L I T I E S */
/* $Header$ */
/* Code for the allocation and de-allocation of temporary variables,
allowing re-use.
*/
#include <em.h>
#include <em_reg.h>
#include <alloc.h>
#include <em_mes.h>
#include "util.h"
#include "use_tmp.h"
#include "sizes.h"
#include "align.h"
#include "stack.h"
static struct localvar *FreeTmps;
#ifdef USE_TMP
static int loc_id;
#endif USE_TMP
extern char options[];
LocalInit()
{
#ifdef USE_TMP
C_insertpart(loc_id = C_getid());
#endif USE_TMP
}
arith
LocalSpace(sz, al)
arith sz;
{
register struct stack_level *stl = local_level;
stl->sl_max_block = - align(sz - stl->sl_max_block, al);
return stl->sl_max_block;
}
#define TABSIZ 32
static struct localvar *regs[TABSIZ];
arith
NewLocal(sz, al, regtype, init)
arith sz;
{
register struct localvar *tmp = FreeTmps;
struct localvar *prev = 0;
register int index;
while (tmp) {
if (tmp->t_align >= al &&
tmp->t_size >= sz &&
tmp->t_regtype == regtype) {
if (prev) {
prev->next = tmp->next;
}
else FreeTmps = tmp->next;
break;
}
prev = tmp;
tmp = tmp->next;
}
if (! tmp) {
tmp = new_localvar();
tmp->t_offset = LocalSpace(sz, al);
tmp->t_align = al;
tmp->t_size = sz;
tmp->t_regtype = regtype;
tmp->t_count = init;
}
index = (int) (tmp->t_offset >> 2) & (TABSIZ - 1);
tmp->next = regs[index];
regs[index] = tmp;
return tmp->t_offset;
}
FreeLocal(off)
arith off;
{
int index = (int) (off >> 2) & (TABSIZ - 1);
register struct localvar *tmp = regs[index];
struct localvar *prev = 0;
while (tmp && tmp->t_offset != off) {
prev = tmp;
tmp = tmp->next;
}
if (tmp) {
if (prev) prev->next = tmp->next;
else regs[index] = tmp->next;
tmp->next = FreeTmps;
FreeTmps = tmp;
}
}
LocalFinish()
{
register struct localvar *tmp, *tmp1;
register int i;
#ifdef USE_TMP
C_beginpart(loc_id);
#endif
tmp = FreeTmps;
while (tmp) {
tmp1 = tmp;
if (! options['n'] && tmp->t_regtype >= 0) {
C_ms_reg(tmp->t_offset, tmp->t_size, tmp->t_regtype, tmp->t_count);
}
tmp = tmp->next;
free_localvar(tmp1);
}
FreeTmps = 0;
for (i = 0; i < TABSIZ; i++) {
tmp = regs[i];
while (tmp) {
tmp1 = tmp;
if (! options['n'] && tmp->t_regtype >= 0) {
C_ms_reg(tmp->t_offset,
tmp->t_size,
tmp->t_regtype,
tmp->t_count);
}
tmp = tmp->next;
free_localvar(tmp1);
}
regs[i] = 0;
}
#ifdef USE_TMP
C_mes_begin(ms_reg);
C_mes_end();
C_endpart(loc_id);
#endif
}
RegisterAccount(offset, size, regtype, init)
arith offset, size;
{
register struct localvar *p;
int index;
if (regtype < 0) return;
p = new_localvar();
index = (int) (offset >> 2) & (TABSIZ - 1);
p->t_offset = offset;
p->t_regtype = regtype;
p->t_count = init;
p->t_size = size;
p->next = regs[index];
regs[index] = p;
}
static struct localvar *
find_reg(off)
arith off;
{
register struct localvar *p = regs[(int)(off >> 2) & (TABSIZ - 1)];
while (p && p->t_offset != off) p = p->next;
return p;
}
LoadLocal(off, sz)
arith off, sz;
{
register struct localvar *p = find_reg(off);
if (p) p->t_count++;
if (sz == word_size) C_lol(off);
else if (sz == dword_size) C_ldl(off);
else {
if (p) p->t_regtype = -1;
C_lal(off);
C_loi(sz);
}
}
StoreLocal(off, sz)
arith off, sz;
{
register struct localvar *p = find_reg(off);
if (p) p->t_count++;
if (sz == word_size) C_stl(off);
else if (sz == dword_size) C_sdl(off);
else {
if (p) p->t_regtype = -1;
C_lal(off);
C_sti(sz);
}
}
AddrLocal(off)
arith off;
{
register struct localvar *p = find_reg(off);
if (p) p->t_regtype = -1;
C_lal(off);
}

10
lang/cem/cemcom/util.str Normal file
View file

@ -0,0 +1,10 @@
struct localvar {
struct localvar *next;
arith t_offset; /* offset from LocalBase */
arith t_size;
int t_align;
int t_regtype;
int t_count;
};
/* ALLOCDEF "localvar" 10 */