int swstcase[SWSTSZ];
int swstlab[SWSTSZ];
int swstp;
-char litq[LITABSZ];
-int litptr;
char macq[MACQSIZE];
int macptr;
char line[LINESIZE];
/* miscellaneous storage */
int nxtlab,
- litlab,
stkp,
argstk,
ncmp,
int uflag; // undocumented 8085 instructions
INITIALS initials_table[NUMBER_OF_GLOBALS];
-char initials_data_table[INITIALS_SIZE]; // 5kB space for initialisation data
-int initials_idx = 0, initials_data_idx = 0;
+int initials_idx = 0;
extern int swstcase[];
extern int swstlab[];
extern int swstp;
-extern char litq[];
-extern int litptr;
extern char macq[];
extern int macptr;
extern char line[];
/* miscellaneous storage */
extern int nxtlab,
- litlab,
stkp,
argstk,
ncmp,
* possible entries for "type"
* high order 14 bits give length of object
* low order 2 bits make type unique within length
+ *
+ *
+ * Proposed new encoding
+ * 15: const
+ * 14: volatile
+ * 13: complex object
+ * 12-10: ptr depth
+ *
+ * complex object
+ * 9-0: pointer into object table (including function pointers so
+ * we can one day do type checking)
+ *
+ * simple object
+ *
+ * 9-8: unused
+ * 7: unsigned
+ * 6-5:
+ * 00 char/short/int/long
+ * 01 float/double
+ * 10 void
+ * 11 spare
+ * 0-4: size (1-8) not valid for complex objects
*/
#define UNSIGNED 1
#define STRUCT 2
#define UINT ((2 << 2) + 1)
#define VOID (0 << 2)
-// possible entries for storage
+/* possible entries for storage: to change */
+
#define PUBLIC 1
#define AUTO 2
#define EXTERN 3
/* "switch" label stack */
#define SWSTSZ 100
-/* literal pool */
-#ifdef TINY
-#define LITABSZ 2500
-#else
-#define LITABSZ 5000
-#endif
-#define LITMAX LITABSZ-1
-
/* input line */
#define LINESIZE 150
#define LINEMAX (LINESIZE-1)
#define HL_REG 1<<1
#define DE_REG 1<<2
+/* This we can switch to the new encoding when ready */
struct lvalue {
SYMBOL *symbol; // symbol table address, or 0 for constant
int indirect; // type of indirect object, 0 for static object
#define INIT_LENGTH NAMESIZE+1
#define INITIALS_SIZE 5*1024
+/* For arrays we need to use the type and point the type at the object
+ info so we can do multi-dimensional arrays properly */
struct initials_table {
char name[NAMESIZE]; // symbol name
int type; // type
#include "defs.h"
#include "data.h"
-void error (char *ptr)
+void error(char *ptr)
{
int tempfile;
output_string (" ******");
newline ();
}
-
/**
* glabel - generate label
- * not used ?
* @param lab label number
*/
void glabel(char *lab) {
*/
int find_symbol_initials(char *symbol_name) {
int result = 0;
- initials_data_idx = 0;
for (initials_idx=0; initials_table[initials_idx].type != 0; initials_idx++) {
if (initials_idx >= NUMBER_OF_GLOBALS) {
error("initials table overrun");
if (astreq (symbol_name, initials_table[initials_idx].name, NAMEMAX) != 0) {
result = 1;
break;
- } else { // move to next symbol
- // count position in data array
- initials_data_idx += initials_table[initials_idx].data_len;
}
}
return result;
}
-/**
- * add data to table for given symbol
- * @param symbol_name
- * @param type
- * @param value
- * @param tag
- */
-void add_data_initials(char *symbol_name, int type, int value, TAG_SYMBOL *tag) {
- int position;
- if (find_symbol_initials(symbol_name) == 0) {
- add_symbol_initials(symbol_name, tag == 0 ? type : STRUCT);
- }
- if (tag != 0) {
- // find number of members, dim is total number of values added
- int index = initials_table[initials_idx].dim % tag->number_of_members;
- int member_type = member_table[tag->member_idx + index].type;
- // add it recursively
- add_data_initials(symbol_name, member_type, value, 0);
- } else {
- position = initials_table[initials_idx].data_len;
- if (type & CCHAR) {
- initials_data_table[initials_data_idx + position] = 0xff & value;
- initials_table[initials_idx].data_len += 1;
- } else if (type & CINT) {
- initials_data_table[initials_data_idx + position] = (0xff00 & value) >> 8;
- initials_data_table[initials_data_idx + position + 1] = 0xff & value;
- initials_table[initials_idx].data_len += INTSIZE;
- }
- initials_table[initials_idx].dim += 1;
- }
-}
-
/**
* get number of data items for given symbol
* @param symbol_name
return result;
}
-/**
- * get item at position
- * @param symbol_name
- * @param position
- * @param itag index of tag in tag table
- * @return
- */
-int get_item_at(char *symbol_name, int position, TAG_SYMBOL *tag) {
- int result = 0, i, type;
- if (find_symbol_initials(symbol_name) != 0) {
- if (initials_table[initials_idx].type & CCHAR) {
- result = initials_data_table[initials_data_idx + position];
- } else if (initials_table[initials_idx].type & CINT) {
- position *= INTSIZE;
- result = (initials_data_table[initials_data_idx + position] << 8) +
- (unsigned char)initials_data_table[initials_data_idx + position+1];
- } else if (initials_table[initials_idx].type == STRUCT) {
- // find number of members
- int number_of_members = tag->number_of_members;
- // point behind the last full struct
- int index = (position / number_of_members) * tag->size;
- // move to required member
- for (i=0; i < (position % number_of_members); i++) {
- type = member_table[tag->member_idx + i].type;
- if (type & CCHAR) {
- index += 1;
- } else {
- index += INTSIZE;
- }
- }
- // get value
- type = member_table[tag->member_idx + i].type;
- if (type & CCHAR) {
- result = initials_data_table[initials_data_idx + index];
- } else {
- result = (initials_data_table[initials_data_idx + index] << 8) +
- (unsigned char)initials_data_table[initials_data_idx + index+1];
- }
- }
- }
- return result;
-}
iflevel =
skiplevel =
swstp =
- litptr =
stkp =
errcnt =
ncmp =
cmode = 1;
glbflag = 1;
nxtlab = 0;
- litlab = getlabel();
defmac("end\tmemory");
//add_global("memory", ARRAY, CCHAR, 0, EXTERN);
//add_global("stack", ARRAY, CCHAR, 0, EXTERN);
parse();
close(input);
data_segment_gdata();
- dumplits();
dumpglbs();
errorsummary();
trailer();
return (1);
}
-/**
- * dump the literal pool
- */
-void dumplits(void) {
- int j, k;
-
- if (litptr == 0)
- return;
- print_label(litlab);
- output_label_terminator();
- k = 0;
- while (k < litptr) {
- gen_def_byte();
- j = 8;
- while (j--) {
- output_number(litq[k++] & 127);
- if ((j == 0) | (k >= litptr)) {
- newline();
- break;
- }
- output_byte(',');
- }
- }
-}
-
/**
* dump all static variables
*/
current_symbol_table_idx = rglobal_table_index;
while (current_symbol_table_idx < global_table_index) {
SYMBOL *symbol = &symbol_table[current_symbol_table_idx];
- if (symbol->identity != FUNCTION) {
+ if (symbol->identity != FUNCTION)
ppubext(symbol);
- if (symbol->storage != EXTERN) {
- output_string(symbol->name);
- output_label_terminator();
- dim = symbol->offset;
- list_size = 0;
- line_count = 0;
- if (find_symbol_initials(symbol->name)) { // has initials
- list_size = get_size(symbol->name);
- if (dim == -1) {
- dim = list_size;
- }
- }
- for (i=0; i<dim; i++) {
- if (symbol->type == STRUCT) {
- dump_struct(symbol, i);
- } else {
- if (line_count % 10 == 0) {
- newline();
- if ((symbol->type & CINT) || (symbol->identity == POINTER)) {
- gen_def_word();
- } else {
- gen_def_byte();
- }
- }
- if (i < list_size) {
- // dump data
- value = get_item_at(symbol->name, i, &tag_table[symbol->tagidx]);
- output_number(value);
- } else {
- // dump zero, no more data available
- output_number(0);
- }
- line_count++;
- if (line_count % 10 == 0) {
- line_count = 0;
- } else {
- if (i < dim-1) {
- output_byte( ',' );
- }
- }
- }
- }
- newline();
- }
- } else {
+ else
fpubext(symbol);
- }
current_symbol_table_idx++;
}
}
-/**
- * dump struct data
- * @param symbol struct variable
- * @param position position of the struct in the array, or zero
- */
-void dump_struct(SYMBOL *symbol, int position) {
- int i, number_of_members, value;
- number_of_members = tag_table[symbol->tagidx].number_of_members;
- newline();
- for (i=0; i<number_of_members; i++) {
- // i is the index of current member, get type
- int member_type = member_table[tag_table[symbol->tagidx].member_idx + i].type;
- if (member_type & CINT) {
- gen_def_word();
- } else {
- gen_def_byte();
- }
- if (position < get_size(symbol->name)) {
- // dump data
- value = get_item_at(symbol->name, position*number_of_members+i, &tag_table[symbol->tagidx]);
- output_number(value);
- } else {
- // dump zero, no more data available
- output_number(0);
- }
- newline();
- }
-}
-
/**
* report errors
*/
if (errcnt) errfile = YES;
output_string(" error(s) in compilation");
newline();
- gen_comment();
- output_with_tab("literal pool:");
- output_decimal(litptr);
- newline();
- gen_comment();
- output_with_tab("global pool:");
- output_decimal(global_table_index - rglobal_table_index);
- newline();
- gen_comment();
- output_with_tab("Macro pool:");
- output_decimal(macptr);
- newline();
if (errcnt > 0)
pl("Error(s)");
}
gen_immediate ();
else if (quoted_char (val))
gen_immediate ();
- else if (quoted_string (val)) {
+ /* Quoted strings are constants so we don't need to do any mucking about
+ with segments - however we move them to data as we'd otherwise put
+ them mid code stream ! */
+ else if (quoted_string (NULL, val)) {
gen_immediate ();
- print_label (litlab);
- output_byte ('+');
+ print_label (val[0]);
+ newline();
+ return 1;
} else
return (0);
output_number (val[0]);
/**
* Test if we have string enclosed in double quotes. e.g. "abc".
* Load the string into literal pool.
- * @param position returns beginning of the string
+ * @param position returns label for this string
* @return 1 if such string found, 0 otherwise
*/
-int quoted_string(int *position) {
+int quoted_string(int *len, int *position) {
char c;
+ int x;
+ int l;
if (!match ("\""))
return (0);
- *position = litptr;
+ if (position) {
+ data_segment_gdata();
+ *position = getlabel();
+ generate_label(*position);
+ }
+ x = 0;
while (ch () != '"') {
- if (ch () == 0)
+ if (ch () == 0) {
+ /* Should error ?? FIXME */
break;
- if (litptr >= LITMAX) {
- error ("string space exhausted");
- while (!match ("\""))
- if (gch () == 0)
- break;
- return (1);
}
c = gch();
- litq[litptr++] = (c == '\\') ? spechar(): c;
+ c = (c == '\\') ? spechar(): c;
+ if (x == 0)
+ gen_def_byte();
+ else
+ output_byte(',');
+ output_number(c);
+ if (x++ == 7) {
+ x = 0;
+ newline();
+ }
+ l++;
}
gch ();
- litq[litptr++] = 0;
+ if (x != 0)
+ newline();
+ gen_def_byte();
+ output_number(0);
+ newline();
+ if (len)
+ *len = l + 1;
+ if (position)
+ code_segment_gtext();
return (1);
}
extern int constant(int val[]);
extern int number(int val[]);
extern int quoted_char(int *value);
-extern int quoted_string(int *position);
+extern int quoted_string(int *len, int *position);
extern int spechar(void);
extern void callfunction(char *ptr);
extern void needlval(void);
*/
int initials(char *symbol_name, int type, int identity, int dim, int otag) {
int dim_unknown = 0;
- litptr = 0;
+ int n;
+
if(dim == 0) { // allow for xx[] = {..}; declaration
dim_unknown = 1;
}
if (!(type & CCHAR) && !(type & CINT) && !(type == STRUCT)) {
error("unsupported storage size");
}
+ data_segment_gdata();
+ glabel(symbol_name);
if(match("=")) {
// an array or struct
if(match("{")) {
}
if(--dim_unknown == 0)
identity = POINTER;
+ else {
+ /* Pad any missing objects */
+ n = dim;
+ gen_def_storage();
+ if (identity != ARRAY && type != STRUCT) {
+ if (!(type & CCHAR))
+ n *= 2;
+ } else
+ n = tag_table[otag].size;
+
+ output_number(n);
+ newline();
+ }
}
needbrack("}");
// single constant
init(symbol_name, type, identity, &dim, 0);
}
}
+ code_segment_gtext();
return identity;
}
void struct_init(TAG_SYMBOL *tag, char *symbol_name) {
int dim ;
int member_idx;
+ int size = tag->size;
member_idx = tag->member_idx;
while (member_idx < tag->member_idx + tag->number_of_members) {
- init(symbol_name, member_table[tag->member_idx + member_idx].type,
+ size -= init(symbol_name, member_table[tag->member_idx + member_idx].type,
member_table[tag->member_idx + member_idx].identity, &dim, tag);
++member_idx;
+ /* FIXME: not an error - zero rest */
if ((match(",") == 0) && (member_idx != (tag->member_idx + tag->number_of_members))) {
- error("struct initialisaton out of data");
- break ;
+ gen_def_storage();
+ output_number(size);
+ newline();
+ break;
}
}
}
* @param dim
* @param tag
* @return
+ * returns size of initializer, or 0 for none (a null string is size 1)
+ *
*/
int init(char *symbol_name, int type, int identity, int *dim, TAG_SYMBOL *tag) {
- int value, number_of_chars;
+ int value, n;
if(identity == POINTER) {
error("cannot assign to pointer");
}
- if(quoted_string(&value)) {
+ /* FIXME: may need to distinguish const string v data in future */
+ if(quoted_string(&n, NULL)) {
if((identity == VARIABLE) || !(type & CCHAR))
error("found string: must assign to char pointer or array");
- number_of_chars = litptr - value;
- *dim = *dim - number_of_chars;
- while (number_of_chars > 0) {
- add_data_initials(symbol_name, CCHAR, litq[value++], tag);
- number_of_chars = number_of_chars - 1;
- }
- } else if (number(&value)) {
- add_data_initials(symbol_name, CINT, value, tag);
- *dim = *dim - 1;
- } else if(quoted_char(&value)) {
- add_data_initials(symbol_name, CCHAR, value, tag);
- *dim = *dim - 1;
- } else {
- return 0;
+ *dim = *dim - n; /* ??? FIXME arrays of char only */
+ return n;
}
- return 1;
+
+ if (type & CCHAR)
+ gen_def_byte();
+ else
+ gen_def_word();
+ if (!number(&value) && !quoted_char(&value))
+ return 0;
+ *dim = *dim - 1;
+ output_number(value);
+ newline();
+ return (type & CCHAR) ? 1 : 2;
}
/**
#include "defs.h"
#include "data.h"
-void addwhile(WHILE *ptr) {
-//int ptr[];
- //int k;
+char *noactive = "mo active do/for/while/switch";
- //if (wsptr == WSMAX) {
+void addwhile(WHILE *ptr) {
if (while_table_index == WSTABSZ) {
error ("too many active whiles");
return;
}
- //k = 0;
- //while (k < WSSIZ)
- // *wsptr++ = ptr[k++];
memcpy(&ws[while_table_index++], ptr, sizeof(WHILE));
}
void delwhile(void) {
- if (readwhile ()) {
- //wsptr = wsptr - WSSIZ;
+ if (readwhile ())
while_table_index--;
- }
}
WHILE *readwhile(void) {
if (while_table_index == 0) {
- //if (wsptr == ws) {
- error ("no active do/for/while/switch");
+ error (noactive);
return (0);
} else {
- //return (wsptr-WSSIZ);
return &ws[while_table_index - 1];
}
}
WHILE *findwhile(void) {
- //int *ptr;
int while_table_idx;
- //for (ptr = wsptr; ptr != ws;) {
while_table_idx = while_table_index;
for (; while_table_idx != 0;) {
- //ptr = ptr - WSSIZ;
while_table_idx--;
- //if (ptr[WSTYP] != WSSWITCH)
- // return (ptr);
if (ws[while_table_idx].type != WSSWITCH)
return &ws[while_table_idx];
}
- error ("no active do/for/while");
+ error (noactive);
return (0);
}
WHILE *readswitch(void) {
- WHILE *ptr; //int *ptr;
+ WHILE *ptr;
if ((ptr = readwhile ()) != 0) {
- //if (ptr[WSTYP] == WSSWITCH)
if (ptr->type == WSSWITCH) {
return (ptr);
}