re-write qfo writing from progs, make qfo creation easier, (mostly) finish

the linker. now for testing :)
This commit is contained in:
Bill Currie 2002-07-11 20:17:26 +00:00
parent 4b83c6592c
commit 4d1dbc8cc1
4 changed files with 135 additions and 58 deletions

View File

@ -132,8 +132,13 @@ typedef struct qfo_s {
#define QFO_POINTER(q, t,o) ((t *)((q)->data + o))
#define QFO_STRUCT(q, t,o) (*QFO_POINTER (q, t, o))
int write_obj_file (const char *filename);
qfo_t *read_obj_file (const char *filename);
struct pr_info_s;
qfo_t *qfo_from_progs (struct pr_info_s *pr);
int qfo_write (qfo_t *qfo, const char *filename);
qfo_t *qfo_read (const char *filename);
int qfo_to_progs (qfo_t *qfo, struct pr_info_s *pr);
qfo_t *qfo_new (void);
void qfo_add_code (qfo_t *qfo, dstatement_t *code, int code_size);
void qfo_add_data (qfo_t *qfo, pr_type_t *data, int data_size);
@ -142,6 +147,7 @@ void qfo_add_strings (qfo_t *qfo, const char *strings, int strings_size);
void qfo_add_relocs (qfo_t *qfo, qfo_reloc_t *relocs, int num_relocs);
void qfo_add_defs (qfo_t *qfo, qfo_def_t *defs, int num_defs);
void qfo_add_functions (qfo_t *qfo, qfo_function_t *functions, int num_functions);
void qfo_add_lines (qfo_t *qfo, pr_lineno_t *lines, int num_lines);
void qfo_add_types (qfo_t *qfo, const char *types, int types_size);
void qfo_delete (qfo_t *qfo);

View File

@ -75,12 +75,18 @@ static struct {
int num_funcs;
int max_funcs;
} funcs;
static struct {
pr_lineno_t *lines;
int num_lines;
int max_lines;
} lines;
static int code_base;
static int data_base;
static int far_data_base;
static int reloc_base;
static int def_base;
static int func_base;
static int line_base;
static const char *
defs_get_key (void *_def, void *unused)
@ -219,10 +225,34 @@ add_funcs (qfo_t *qfo)
func->def += def_base;
if (func->local_defs)
func->local_defs += def_base;
if (func->line_info)
func->line_info += line_base;
func->relocs += reloc_base;
}
}
static void
add_lines (qfo_t *qfo)
{
int i;
if (lines.num_lines + qfo->num_lines > lines.max_lines) {
lines.max_lines = RUP (lines.num_lines + qfo->num_lines, 16384);
lines.lines = realloc (lines.lines,
lines.max_lines * sizeof (pr_lineno_t));
}
lines.num_lines += qfo->num_lines;
memcpy (lines.lines + line_base, qfo->lines,
qfo->num_lines * sizeof (pr_lineno_t));
for (i = line_base; i < lines.num_lines; i++) {
pr_lineno_t *line = lines.lines + i;
if (line->line)
line->fa.addr += code_base;
else
line->fa.func += func_base;
}
}
static void
fixup_relocs (qfo_t *qfo)
{
@ -283,7 +313,7 @@ linker_add_object_file (const char *filename)
{
qfo_t *qfo;
qfo = read_obj_file (filename);
qfo = qfo_read (filename);
if (!qfo)
return;
@ -295,6 +325,7 @@ linker_add_object_file (const char *filename)
reloc_base = relocs.num_relocs;
def_base = defs.num_defs;
func_base = funcs.num_funcs;
line_base = lines.num_lines;
codespace_addcode (code, qfo->code, qfo->code_size);
defspace_adddata (data, qfo->data, qfo->data_size);
@ -303,6 +334,7 @@ linker_add_object_file (const char *filename)
add_relocs (qfo);
add_defs (qfo);
add_funcs (qfo);
add_lines (qfo);
fixup_relocs (qfo);

View File

@ -170,9 +170,9 @@ setup_data (void)
pr_type_t *var;
pr_lineno_t *line;
for (d = pr.scope->head; d; d = d->def_next)
write_def (d, def++, &reloc);
for (f = pr.func_head; f; f = f->next) {
for (d = pr.scope->head; d; d = d->def_next, def++)
write_def (d, def, &reloc);
for (f = pr.func_head; f; f = f->next, func++) {
func->name = LittleLong (f->s_name);
func->file = LittleLong (f->s_file);
func->line = LittleLong (f->def->line);
@ -219,71 +219,87 @@ setup_data (void)
}
}
int
write_obj_file (const char *filename)
qfo_t *
qfo_from_progs (pr_info_t *pr)
{
qfo_header_t hdr;
VFile *file;
qfo_t *qfo;
types = strpool_new ();
allocate_stuff ();
setup_data ();
file = Qopen (filename, "wbz9");
pr->strings->size = RUP (pr->strings->size, 4);
types->size = RUP (types->size, 4);
pr.strings->size = (pr.strings->size + 3) & ~3;
types->size = (types->size + 3) & ~3;
memset (&hdr, 0, sizeof (hdr));
memcpy (hdr.qfo, QFO, sizeof (hdr.qfo));
hdr.version = LittleLong (QFO_VERSION);
hdr.code_size = LittleLong (pr.code->size);
hdr.data_size = LittleLong (pr.near_data->size);
if (pr.far_data) {
hdr.far_data_size = LittleLong (pr.far_data->size);
}
hdr.strings_size = LittleLong (pr.strings->size);
hdr.num_relocs = LittleLong (num_relocs);
hdr.num_defs = LittleLong (num_defs);
hdr.num_functions = LittleLong (num_functions);
hdr.num_lines = LittleLong (num_linenos);
hdr.types_size = LittleLong (types->size);
Qwrite (file, &hdr, sizeof (hdr));
if (pr.code->size)
Qwrite (file, pr.code->code, pr.code->size * sizeof (dstatement_t));
if (pr.near_data->size)
Qwrite (file, pr.near_data->data,
pr.near_data->size * sizeof (pr_type_t));
if (pr.far_data && pr.far_data->size) {
Qwrite (file, pr.far_data->data,
pr.far_data->size * sizeof (pr_type_t));
}
if (pr.strings->size)
Qwrite (file, pr.strings->strings, pr.strings->size);
if (num_relocs)
Qwrite (file, relocs, num_relocs * sizeof (qfo_reloc_t));
if (num_defs)
Qwrite (file, defs, num_defs * sizeof (qfo_def_t));
if (num_functions)
Qwrite (file, functions, num_functions * sizeof (qfo_function_t));
if (num_linenos)
Qwrite (file, linenos, num_linenos * sizeof (pr_lineno_t));
if (types->size)
Qwrite (file, types->strings, types->size);
Qclose (file);
qfo = qfo_new ();
qfo_add_code (qfo, pr->code->code, pr->code->size);
qfo_add_data (qfo, pr->near_data->data, pr->near_data->size);
if (pr->far_data)
qfo_add_far_data (qfo, pr->far_data->data, pr->far_data->size);
qfo_add_strings (qfo, pr->strings->strings, pr->strings->size);
qfo_add_relocs (qfo, relocs, num_relocs);
qfo_add_defs (qfo, defs, num_defs);
qfo_add_functions (qfo, functions, num_functions);
qfo_add_lines (qfo, linenos, num_linenos);
qfo_add_types (qfo, types->strings, types->size);
free (defs);
free (relocs);
free (functions);
strpool_delete (types);
return qfo;
}
int
qfo_write (qfo_t *qfo, const char *filename)
{
qfo_header_t hdr;
VFile *file;
file = Qopen (filename, "wbz9");
memset (&hdr, 0, sizeof (hdr));
memcpy (hdr.qfo, QFO, sizeof (hdr.qfo));
hdr.version = LittleLong (QFO_VERSION);
hdr.code_size = LittleLong (qfo->code_size);
hdr.data_size = LittleLong (qfo->data_size);
hdr.far_data_size = LittleLong (qfo->far_data_size);
hdr.strings_size = LittleLong (qfo->strings_size);
hdr.num_relocs = LittleLong (qfo->num_relocs);
hdr.num_defs = LittleLong (qfo->num_defs);
hdr.num_functions = LittleLong (qfo->num_functions);
hdr.num_lines = LittleLong (qfo->num_lines);
hdr.types_size = LittleLong (qfo->types_size);
Qwrite (file, &hdr, sizeof (hdr));
if (qfo->code_size)
Qwrite (file, qfo->code, qfo->code_size * sizeof (dstatement_t));
if (qfo->data_size)
Qwrite (file, qfo->data, qfo->data_size * sizeof (pr_type_t));
if (qfo->far_data_size)
Qwrite (file, qfo->far_data, qfo->far_data_size * sizeof (pr_type_t));
if (qfo->strings_size)
Qwrite (file, qfo->strings, qfo->strings_size);
if (qfo->num_relocs)
Qwrite (file, qfo->relocs, qfo->num_relocs * sizeof (qfo_reloc_t));
if (qfo->num_defs)
Qwrite (file, qfo->defs, qfo->num_defs * sizeof (qfo_def_t));
if (qfo->num_functions)
Qwrite (file, qfo->functions,
qfo->num_functions * sizeof (qfo_function_t));
if (qfo->num_lines)
Qwrite (file, qfo->lines, qfo->num_lines * sizeof (pr_lineno_t));
if (qfo->types_size)
Qwrite (file, qfo->types, qfo->types_size);
Qclose (file);
return 0;
}
qfo_t *
read_obj_file (const char *filename)
qfo_read (const char *filename)
{
VFile *file;
qfo_header_t hdr;
@ -510,6 +526,7 @@ void
qfo_add_code (qfo_t *qfo, dstatement_t *code, int code_size)
{
qfo->code = malloc (code_size * sizeof (dstatement_t));
qfo->code_size = code_size;
memcpy (qfo->code, code, code_size * sizeof (dstatement_t));
}
@ -517,6 +534,7 @@ void
qfo_add_data (qfo_t *qfo, pr_type_t *data, int data_size)
{
qfo->data = malloc (data_size * sizeof (pr_type_t));
qfo->data_size = data_size;
memcpy (qfo->data, data, data_size * sizeof (pr_type_t));
}
@ -524,6 +542,7 @@ void
qfo_add_far_data (qfo_t *qfo, pr_type_t *far_data, int far_data_size)
{
qfo->far_data = malloc (far_data_size * sizeof (pr_type_t));
qfo->far_data_size = far_data_size;
memcpy (qfo->far_data, far_data, far_data_size * sizeof (pr_type_t));
}
@ -531,6 +550,7 @@ void
qfo_add_strings (qfo_t *qfo, const char *strings, int strings_size)
{
qfo->strings = malloc (strings_size);
qfo->strings_size = strings_size;
memcpy (qfo->strings, strings, strings_size);
}
@ -538,6 +558,7 @@ void
qfo_add_relocs (qfo_t *qfo, qfo_reloc_t *relocs, int num_relocs)
{
qfo->relocs = malloc (num_relocs * sizeof (qfo_reloc_t));
qfo->num_relocs = num_relocs;
memcpy (qfo->relocs, relocs, num_relocs * sizeof (qfo_reloc_t));
}
@ -545,6 +566,7 @@ void
qfo_add_defs (qfo_t *qfo, qfo_def_t *defs, int num_defs)
{
qfo->defs = malloc (num_defs * sizeof (qfo_def_t));
qfo->num_defs = num_defs;
memcpy (qfo->defs, defs, num_defs * sizeof (qfo_def_t));
}
@ -552,13 +574,23 @@ void
qfo_add_functions (qfo_t *qfo, qfo_function_t *functions, int num_functions)
{
qfo->functions = malloc (num_functions * sizeof (qfo_function_t));
qfo->num_functions = num_functions;
memcpy (qfo->functions, functions, num_functions * sizeof (qfo_function_t));
}
void
qfo_add_lines (qfo_t *qfo, pr_lineno_t *lines, int num_lines)
{
qfo->lines = malloc (num_lines * sizeof (pr_lineno_t));
qfo->num_lines = num_lines;
memcpy (qfo->lines, lines, num_lines * sizeof (pr_lineno_t));
}
void
qfo_add_types (qfo_t *qfo, const char *types, int types_size)
{
qfo->types = malloc (types_size);
qfo->types_size = types_size;
memcpy (qfo->types, types, types_size);
}
@ -581,6 +613,8 @@ qfo_delete (qfo_t *qfo)
free (qfo->defs);
if (qfo->functions)
free (qfo->functions);
if (qfo->lines)
free (qfo->lines);
if (qfo->types)
free (qfo->types);
free (qfo);

View File

@ -488,8 +488,11 @@ compile_to_obj (const char *file, const char *obj)
exit (1);
}
}
if (!err)
write_obj_file (obj);
if (!err) {
qfo_t *qfo = qfo_from_progs (&pr);
err = qfo_write (qfo, obj);
qfo_delete (qfo);
}
return err;
}
@ -615,7 +618,9 @@ progs_src_compile (void)
}
if (options.compile) {
write_obj_file (options.output_file);
qfo_t *qfo = qfo_from_progs (&pr);
qfo_write (qfo, options.output_file);
qfo_delete (qfo);
} else {
if (!finish_compilation ()) {
fprintf (stderr, "compilation errors\n");