OpenCores
URL https://opencores.org/ocsvn/open8_urisc/open8_urisc/trunk

Subversion Repositories open8_urisc

[/] [open8_urisc/] [trunk/] [Open8 Tools/] [open8_src/] [open8_as/] [pass_1.c] - Blame information for rev 259

Go to most recent revision | Details | Compare with Previous | View Log

Line No. Rev Author Line
1 178 jshamlet
 
2
#include <ctype.h>
3
#include <stdio.h>
4
#include <stdlib.h>
5
#include <string.h>
6
#include <math.h>
7
#include <time.h>
8
 
9
#include "defines.h"
10
 
11
#include "include_file.h"
12
#include "parse.h"
13
#include "pass_1.h"
14
#include "pass_2.h"
15
#include "stack.h"
16
 
17
#define MAXADDRESS 0x10000
18
 
19
int org_defined = 1, background_defined = 0, background_size = 0;
20
int bank = 0, bank_defined = 0;
21
int rombanks = 0, rombanks_defined = 0, romtype = 0, max_address=0;
22
int rambanks = 0, rambanks_defined = 0;
23
int emptyfill, emptyfill_defined = 0;
24
int section_status = OFF, section_id = 1, line_count_status = ON;
25
int d, i, ind, inz, ifdef = 0, t, slots_amount = 1;
26
int memorymap_defined = 0;
27
int defaultslot_defined = 0, defaultslot, current_slot = 0;
28
int banksize_defined = 1, banksize = MAXADDRESS ;
29
int rombankmap_defined = 0, *banks = NULL, *bankaddress = NULL;
30
int bankheader_status = OFF;
31
int macro_active = 0;
32
int repeat_active = 0;
33
int smc_defined = 0;
34
int asciitable_defined = 0;
35
int block_status = 0;
36
unsigned char asciitable[256];
37
 
38
int unfolded_size;
39
char *unfolded_buffer = NULL;
40
FILE *fold_out;
41
 
42
extern struct stack *stacks_header_first, *stacks_header_last;
43
extern int stacks_inside, stacks_outside;
44
int stack_inserted;
45
 
46
extern int operand_hint;
47
 
48
char tmp[4096], emsg[256];
49
char *tmp_bf;
50
char cp[256];
51
 
52
unsigned char *rom_banks = NULL, *rom_banks_usage_table = NULL;
53
 
54
struct export_def *export_first = NULL, *export_last = NULL;
55
struct optcode *opt_tmp;
56
struct definition *defines = NULL, *tmp_def, *next_def;
57
struct macro_static *macros_first = NULL, *macros_last;
58
struct section_def *sections_first = NULL, *sections_last = NULL, *sec_tmp, *sec_next;
59
struct macro_runtime *macro_stack = NULL, *macro_runtime_current = NULL;
60
struct repeat_runtime *repeat_stack = NULL;
61
struct slot slots[256];
62
struct structure *structures_first = NULL;
63
struct filepointer *filepointers = NULL;
64
 
65
extern char *buffer, *unfolded_buffer, label[MAX_NAME_LENGTH], *include_dir, *full_name;
66
extern int size, unfolded_size, input_number_error_msg, verbose_mode, output_format, open_files;
67
extern int stack_id, latest_stack, ss, commandline_parsing, newline_beginning;
68
extern int extra_definitions, string_size, input_float_mode;
69
extern int include_dir_size, parse_floats, listfile_data, quiet;
70
extern FILE *file_out_ptr;
71
extern double flo;
72
extern char *final_name;
73
extern struct active_file_info *active_file_info_first, *active_file_info_last, *active_file_info_tmp;
74
extern struct file_name_info *file_name_info_first, *file_name_info_last, *file_name_info_tmp;
75
extern struct stack *stacks_first, *stacks_tmp, *stacks_last;
76
 
77
int opcode_n[256], opcode_p[256];
78
int macro_stack_size = 0, repeat_stack_size = 0;
79
 
80
int xbit_size = 0;
81
int accu_size = 8, index_size = 8;
82
 
83
 
84
#include "opcodes_v8urisc.c"
85
#include "opcodes_v8urisc_tables.c"
86
 
87
 
88
int strcaselesscmp(char *s1, char *s2) {
89
 
90
  if (s1 == NULL || s2 == NULL)
91
    return 0;
92
 
93
  while (*s1 != 0) {
94
    if (toupper((int)*s1) != toupper((int)*s2))
95
      return 1;
96
    s1++;
97
    s2++;
98
  }
99
 
100
  if (*s2 != 0)
101
    return 1;
102
 
103
  return 0;
104
}
105
 
106
 
107
int pass_1(void) {
108
 
109
  struct macro_runtime *mrc = NULL;
110
  struct macro_static *m = NULL;
111
  int o, p, q;
112
 
113
 
114
 
115
  if (verbose_mode == ON)
116
    printf("Pass 1...\n");
117
 
118
  /* mark all slots as empty */
119
  for (q = 0; q < 256; q++)
120
    slots[q].size = 0;
121
 
122
  /* except for the first - lay down some good defaults */
123
  slots[0].size = MAXADDRESS; /* default size */
124
 
125
  /* set up a default ROMBANKMAP */
126
  int b = 0, a = 0, bt = 0, bt_defined = 0, x, bs = 0, bs_defined = 0;
127
 
128
  //BANKSTOTAL
129
  o = 0; d = 1;
130
  banks = malloc(sizeof(int) * d);
131
  bankaddress = malloc(sizeof(int) * d);
132
  if (banks == NULL || bankaddress == NULL) {
133
    print_error("Out of memory while allocating ROM banks.\n", ERROR_DIR);
134
    return FAILED;
135
  }
136
  bt = d;
137
  bt_defined = 1;
138
  d=MAXADDRESS;
139
  bs = d;
140
  bs_defined = 1;
141
  d=1;
142
  for (x = 0; x < d; x++) {
143
    banks[o] = bs;
144
    bankaddress[o] = a;
145
    o++;
146
    b++;
147
    a += bs;
148
  }
149
  rombanks = b;
150
  rombanks_defined = 1;
151
  for (max_address = 0, q = 0; q < rombanks; q++)
152
    max_address += banks[q];
153
 
154
  if (rom_banks != NULL)
155
    free(rom_banks);
156
  if (rom_banks_usage_table != NULL)
157
    free(rom_banks_usage_table);
158
 
159
  rom_banks = malloc(sizeof(unsigned char) * max_address);
160
  rom_banks_usage_table = malloc(sizeof(unsigned char) * max_address);
161
  if (rom_banks == NULL || rom_banks_usage_table == NULL) {
162
    print_error("Out of memory while allocating ROM banks.\n", ERROR_DIR);
163
    return FAILED;
164
  }
165
 
166
  memset(rom_banks_usage_table, 0, sizeof(unsigned char) * max_address);
167
  rombankmap_defined = 1;
168
  bank=0;
169
  bank_defined=1;
170
 
171
 
172
 
173
 
174
 
175
 
176
  /* start from the very first character */
177
  i = 0;
178
 
179
  /* output the file id */
180
  fprintf(file_out_ptr, "f%d ", active_file_info_tmp->filename_id);
181
 
182
  /* BANK 0 SLOT 0 ORG 0 */
183
  if (output_format != OUTPUT_LIBRARY)
184
    fprintf(file_out_ptr, "B%d %d O%d", 0, 0, 0);
185
 
186
  while ((t = get_next_token()) == SUCCEEDED) {
187
    q = evaluate_token();
188
 
189
    if (q == SUCCEEDED)
190
      continue;
191
    else if (q == EVALUATE_TOKEN_EOP)
192
      return SUCCEEDED;
193
    else if (q == EVALUATE_TOKEN_NOT_IDENTIFIED) {
194
      /* check if it is of the form "LABEL:XYZ" */
195
      for (q = 0; q < ss; q++)
196
        if (tmp[q] == ':')
197
          break;
198
 
199
      /* is it a macro */
200
      if (q == ss) {
201
        m = macros_first;
202
        while (m != NULL) {
203
          if (strcmp(m->name, tmp) == 0)
204
            break;
205
          m = m->next;
206
        }
207
      }
208
 
209
      /* it is a label after all */
210
      if (q != ss || newline_beginning == ON) {
211
        tmp[q] = 0;
212
 
213
        /* reset the flag as there can be only one label / line */
214
        newline_beginning = OFF;
215
 
216
        if (output_format == OUTPUT_LIBRARY && section_status == OFF) {
217
          print_error("All labels must be inside sections when compiling a library.\n", ERROR_LOG);
218
          return FAILED;
219
        }
220
        if (org_defined == 0) {
221
          sprintf(emsg, "\"%s\" needs a position in memory.\n", tmp);
222
          print_error(emsg, ERROR_LOG);
223
          return FAILED;
224
        }
225
        if (ss > MAX_NAME_LENGTH - 1) {
226
          sprintf(emsg, "The label \"%s\" is too long. Max label length is %d bytes.\n", tmp, MAX_NAME_LENGTH - 1);
227
          print_error(emsg, ERROR_NONE);
228
          return FAILED;
229
        }
230
        if (bankheader_status == ON) {
231
          print_error("BANKHEADER sections don't take labels.\n", ERROR_LOG);
232
          return FAILED;
233
        }
234
 
235
        /* check out for \@-symbols */
236
        if (macro_active != 0) {
237
          if (tmp[q - 2] == '\\' && tmp[q - 1] == '@')
238
            sprintf(&tmp[q - 2], "%d%c", macro_runtime_current->macro->calls - 1, 0);
239
        }
240
 
241
        fprintf(file_out_ptr, "k%d L%s ", active_file_info_last->line_current, tmp);
242
 
243
        /* move to the end of the label */
244
        if (q != ss)
245
          i -= ss - q - 1;
246
        else
247
          i -= ss - q;
248
 
249
        continue;
250
      }
251
 
252
      if (m == NULL) {
253
        sprintf(emsg, "Unknown symbol \"%s\".\n", tmp);
254
        print_error(emsg, ERROR_ERR);
255
        return FAILED;
256
      }
257
 
258
      /* start running a macro... run until .ENDM */
259
      if (macro_active == macro_stack_size) {
260
 
261
        struct macro_runtime *mr;
262
 
263
 
264
        /* enlarge the macro stack */
265
        macro_stack_size = (macro_stack_size<<1)+2;
266
        mr = realloc(macro_stack, sizeof(struct macro_runtime) * macro_stack_size);
267
        if (mr == NULL) {
268
          print_error("Out of memory error while enlarging macro stack buffer.\n", ERROR_ERR);
269
          return FAILED;
270
        }
271
        macro_stack = mr;
272
      }
273
 
274
      mrc = &macro_stack[macro_active];
275
      mrc->argument_data = NULL;
276
 
277
      /* collect macro arguments */
278
      for (p = 0; 1; p++) {
279
        /* take away the white space */
280
        while (1) {
281
          if (buffer[i] == ' ' || buffer[i] == ',')
282
            i++;
283
          else
284
            break;
285
        }
286
 
287
        o = i;
288
        q = input_number();
289
        if (q == INPUT_NUMBER_EOL)
290
          break;
291
 
292
        mrc->argument_data = realloc(mrc->argument_data, (p+1)*sizeof(struct macro_argument *));
293
        mrc->argument_data[p] = malloc(sizeof(struct macro_argument));
294
        if (mrc->argument_data == NULL || mrc->argument_data[p] == NULL) {
295
          print_error("Out of memory error while collecting macro arguments.\n", ERROR_NONE);
296
          return FAILED;
297
        }
298
 
299
        mrc->argument_data[p]->start = o;
300
        mrc->argument_data[p]->type = q;
301
 
302
        if (q == INPUT_NUMBER_ADDRESS_LABEL)
303
          strcpy(mrc->argument_data[p]->string, label);
304
        else if (q == INPUT_NUMBER_STRING)
305
          strcpy(mrc->argument_data[p]->string, label);
306
        else if (q == INPUT_NUMBER_STACK)
307
          mrc->argument_data[p]->value = latest_stack;
308
        else if (q == SUCCEEDED)
309
          mrc->argument_data[p]->value = d;
310
        else
311
          return FAILED;
312
 
313
        /* do we have a name for this argument? */
314
        if (p < m->nargument_names) {
315
          if (q == INPUT_NUMBER_ADDRESS_LABEL)
316
            redefine(m->argument_names[p], 0.0, label, DEFINITION_TYPE_STRING, strlen(label));
317
          else if (q == INPUT_NUMBER_STRING)
318
            redefine(m->argument_names[p], 0.0, label, DEFINITION_TYPE_STRING, strlen(label));
319
          else if (q == INPUT_NUMBER_STACK)
320
            redefine(m->argument_names[p], (double)latest_stack, NULL, DEFINITION_TYPE_STACK, 0);
321
          else if (q == SUCCEEDED)
322
            redefine(m->argument_names[p], (double)d, NULL, DEFINITION_TYPE_VALUE, 0);
323
        }
324
      }
325
 
326
      macro_runtime_current = mrc;
327
      macro_active++;
328
      m->calls++;
329
      mrc->supplied_arguments = p;
330
 
331
      next_line();
332
 
333
      mrc->macro = m;
334
      mrc->macro_end = i;
335
      mrc->macro_end_line = active_file_info_last->line_current;
336
      mrc->macro_end_filename_id = active_file_info_last->filename_id;
337
 
338
      if ((extra_definitions == ON) && (active_file_info_last->filename_id != m->filename_id)) {
339
        redefine("WLA_FILENAME", 0.0, get_file_name(m->filename_id), DEFINITION_TYPE_STRING, strlen(get_file_name(m->filename_id)));
340
        redefine("wla_filename", 0.0, get_file_name(m->filename_id), DEFINITION_TYPE_STRING, strlen(get_file_name(m->filename_id)));
341
      }
342
 
343
      active_file_info_last->line_current = m->start_line;
344
      active_file_info_last->filename_id = m->filename_id;
345
      i = m->start;
346
 
347
      /* redefine NARGS */
348
      if (redefine("NARGS", (double)p, NULL, DEFINITION_TYPE_VALUE, 0) == FAILED)
349
        return FAILED;
350
      if (redefine("nargs", (double)p, NULL, DEFINITION_TYPE_VALUE, 0) == FAILED)
351
        return FAILED;
352
 
353
      continue;
354
    }
355
    else if (q == FAILED) {
356
      sprintf(emsg, "Couldn't parse \"%s\".\n", tmp);
357
      print_error(emsg, ERROR_ERR);
358
      return FAILED;
359
    }
360
    else {
361
      printf("PASS_1: Internal error, unknown return type %d.\n", q);
362
      return FAILED;
363
    }
364
  }
365
 
366
  return FAILED;
367
}
368
 
369
 
370
int evaluate_token(void) {
371
 
372
  int f, z = 0, x, y;
373
 
374
 
375
  /* is it a directive? */
376
  if (tmp[0] == '.')
377
    return parse_directive();
378
 
379
  /* is it a label? */
380
  if (tmp[ss - 1] == ':' && newline_beginning == ON) {
381
 
382
    tmp[ss - 1] = 0;
383
    newline_beginning = OFF;
384
 
385
    if (output_format == OUTPUT_LIBRARY && section_status == OFF) {
386
      print_error("All labels must be inside sections when compiling a library.\n", ERROR_LOG);
387
      return FAILED;
388
    }
389
    if (org_defined == 0) {
390
      sprintf(emsg, "\"%s\" needs a position in memory.\n", tmp);
391
      print_error(emsg, ERROR_LOG);
392
      return FAILED;
393
    }
394
    if (ss > MAX_NAME_LENGTH - 1) {
395
      sprintf(emsg, "The label \"%s\" is too long. Max label length is %d bytes.\n", tmp, MAX_NAME_LENGTH - 1);
396
      print_error(emsg, ERROR_NONE);
397
      return FAILED;
398
    }
399
    if (bankheader_status == ON) {
400
      print_error("BANKHEADER sections don't take labels.\n", ERROR_LOG);
401
      return FAILED;
402
    }
403
 
404
    /* check for \@-symbols */
405
    if (macro_active != 0) {
406
      if (tmp[ss - 3] == '\\' && tmp[ss - 2] == '@')
407
        sprintf(&tmp[ss - 3], "%d%c", macro_runtime_current->macro->calls - 1, 0);
408
    }
409
 
410
    fprintf(file_out_ptr, "k%d L%s ", active_file_info_last->line_current, tmp);
411
 
412
    return SUCCEEDED;
413
  }
414
 
415
  /* OPCODE? */
416
 
417
  ind = opcode_p[(unsigned int)tmp[0]];
418
  opt_tmp = &opt_table[ind];
419
 
420
  for (f = opcode_n[(unsigned int)tmp[0]]; f > 0; f--) {
421
 
422
    for (inz = 0, d = SUCCEEDED; inz < OP_SIZE_MAX; inz++) {
423
      if (tmp[inz] == 0 && opt_tmp->op[inz] == 0 && buffer[i] == 0x0A) {
424
        if (opt_tmp->type == 0)
425
          fprintf(file_out_ptr, "d%d ", opt_tmp->hex);
426
        else
427
          fprintf(file_out_ptr, "y%d ", opt_tmp->hex);
428
        return SUCCEEDED;
429
      }
430
      if (tmp[inz] == 0 && opt_tmp->op[inz] == ' ' && buffer[i] == ' ')
431
        break;
432
      if (opt_tmp->op[inz] != toupper((int)tmp[inz])) {
433
        d = FAILED;
434
        break;
435
      }
436
    }
437
 
438
    if (d == FAILED) {
439
      opt_tmp = &opt_table[++ind];
440
      continue;
441
    }
442
 
443
    /* beginning matches the input */
444
    x = inz + 1;
445
    inz = i + 1;
446
 
447
    /* no stack rollback */
448
    stack_inserted = STACK_NONE;
449
 
450
    switch (opt_tmp->type) {
451
 
452
#include "decode_v8urisc.c"
453
 
454
    }
455
 
456
    /* perform stack rollback? */
457
    if (stack_inserted != STACK_NONE) {
458
 
459
      struct stack *s;
460
 
461
 
462
      if (stack_inserted == STACK_OUTSIDE) {
463
        if (stacks_outside == 1) {
464
          stacks_outside = 0;
465
          delete_stack(stacks_first);
466
          stacks_first = NULL;
467
          stacks_last = NULL;
468
        }
469
        else {
470
          s = stacks_first;
471
          stacks_outside--;
472
 
473
          for (y = 0; y < stacks_outside - 1; y++)
474
            s = s->next;
475
 
476
          delete_stack(s->next);
477
          s->next = NULL;
478
          stacks_last = s;
479
        }
480
      }
481
      else {
482
        if (stacks_inside == 1) {
483
          stacks_inside = 0;
484
          delete_stack(stacks_header_first);
485
          stacks_header_first = NULL;
486
          stacks_header_last = NULL;
487
        }
488
        else {
489
          s = stacks_header_first;
490
          stacks_inside--;
491
 
492
          for (y = 0; y < stacks_inside - 1; y++)
493
            s = s->next;
494
 
495
          delete_stack(s->next);
496
          s->next = NULL;
497
          stacks_header_last = s;
498
        }
499
      }
500
    }
501
 
502
    opt_tmp = &opt_table[++ind];
503
  }
504
 
505
  /* allow error messages from input_numbers() */
506
  input_number_error_msg = YES;
507
 
508
  return EVALUATE_TOKEN_NOT_IDENTIFIED;
509
}
510
 
511
 
512
int redefine(char *name, double value, char *string, int type, int size) {
513
 
514
  struct definition *d;
515
 
516
 
517
  d = defines;
518
  while (d != NULL) {
519
    if (strcmp(d->alias, name) == 0)
520
      break;
521
    d = d->next;
522
  }
523
 
524
  /* it wasn't defined previously */
525
  if (d == NULL) {
526
    return add_a_new_definition(name, value, string, type, size);
527
  }
528
 
529
  d->type = type;
530
 
531
  if (type == DEFINITION_TYPE_VALUE)
532
    d->value = value;
533
  else if (type == DEFINITION_TYPE_STACK)
534
    d->value = value;
535
  else if (type == DEFINITION_TYPE_STRING) {
536
    memcpy(d->string, string, size);
537
    d->string[size] = 0;
538
    d->size = size;
539
  }
540
 
541
  return SUCCEEDED;
542
}
543
 
544
 
545
int undefine(char *name) {
546
 
547
  struct definition *d, *p;
548
 
549
 
550
  d = defines;
551
  p = NULL;
552
  while (d != NULL) {
553
    if (strcmp(name, d->alias) == 0) {
554
      if (p != NULL)
555
        p->next = d->next;
556
      else
557
        defines = d->next;
558
      free(d);
559
      return SUCCEEDED;
560
    }
561
    p = d;
562
    d = d->next;
563
  }
564
 
565
  return FAILED;
566
}
567
 
568
 
569
int add_a_new_definition(char *name, double value, char *string, int type, int size) {
570
 
571
  struct definition *d, *l;
572
 
573
 
574
  l = NULL;
575
  d = defines;
576
  while (d != NULL) {
577
    l = d;
578
    if (strcmp(name, d->alias) == 0) {
579
      sprintf(emsg, "\"%s\" was defined for the second time.\n", name);
580
      if (commandline_parsing == OFF)
581
        print_error(emsg, ERROR_DIR);
582
      else
583
        fprintf(stderr, "ADD_A_NEW_DEFINITION: %s", emsg);
584
      return FAILED;
585
    }
586
    d = d->next;
587
  }
588
 
589
  d = malloc(sizeof(struct definition));
590
  if (d == NULL) {
591
    sprintf(emsg, "Out of memory while trying to add a new definition (\"%s\").\n", name);
592
    if (commandline_parsing == OFF)
593
      print_error(emsg, ERROR_DIR);
594
    else
595
      fprintf(stderr, "ADD_A_NEW_DEFINITION: %s", emsg);
596
    return FAILED;
597
  }
598
 
599
  if (defines == NULL)
600
    defines = d;
601
  else
602
    l->next = d;
603
 
604
  strcpy(d->alias, name);
605
  d->next = NULL;
606
  d->type = type;
607
 
608
  if (type == DEFINITION_TYPE_VALUE)
609
    d->value = value;
610
  else if (type == DEFINITION_TYPE_STACK)
611
    d->value = value;
612
  else if (type == DEFINITION_TYPE_STRING) {
613
    memcpy(d->string, string, size);
614
    d->string[size] = 0;
615
    d->size = size;
616
  }
617
 
618
  return SUCCEEDED;
619
}
620
 
621
 
622
int localize_path(char *path) {
623
 
624
  int i;
625
 
626
 
627
  if (path == NULL)
628
    return FAILED;
629
 
630
  for (i = 0; path[i] != 0; i++) {
631
#if defined(AMIGA) || defined(UNIX)
632
    /* '\' -> '/' */
633
    if (path[i] == '\\')
634
      path[i] = '/';
635
#else
636
    /* '/' -> '\' */
637
    if (path[i] == '/')
638
      path[i] = '\\';
639
#endif
640
  }
641
 
642
  return SUCCEEDED;
643
}
644
 
645
 
646
void print_error(char *error, int i) {
647
 
648
  char error_dir[] = "DIRECTIVE_ERROR:";
649
  char error_unf[] = "UNFOLD_ALIASES:";
650
  char error_num[] = "INPUT_NUMBER:";
651
  char error_inc[] = "INCLUDE_FILE:";
652
  char error_inb[] = "INCBIN_FILE:";
653
  char error_inp[] = "INPUT_ERROR:";
654
  char error_log[] = "LOGIC_ERROR:";
655
  char error_stc[] = "STACK_CALCULATE:";
656
  char error_wrn[] = "WARNING:";
657
  char error_err[] = "ERROR:";
658
  char *t = NULL;
659
 
660
 
661
  switch (i) {
662
  case ERROR_LOG:
663
    t = error_log;
664
    break;
665
  case ERROR_UNF:
666
    t = error_unf;
667
    break;
668
  case ERROR_INC:
669
    t = error_inc;
670
    break;
671
  case ERROR_INB:
672
    t = error_inb;
673
    break;
674
  case ERROR_DIR:
675
    t = error_dir;
676
    break;
677
  case ERROR_INP:
678
    t = error_inp;
679
    break;
680
  case ERROR_NUM:
681
    t = error_num;
682
    break;
683
  case ERROR_STC:
684
    t = error_stc;
685
    break;
686
  case ERROR_WRN:
687
    t = error_wrn;
688
    break;
689
  case ERROR_ERR:
690
    t = error_err;
691
    break;
692
  case ERROR_NONE:
693
    fprintf(stderr, "%s:%d: %s", get_file_name(active_file_info_last->filename_id), active_file_info_last->line_current, error);
694
    return;
695
  }
696
 
697
  fprintf(stderr, "%s:%d: %s %s", get_file_name(active_file_info_last->filename_id), active_file_info_last->line_current, t, error);
698
  return;
699
}
700
 
701
 
702
void next_line(void) {
703
 
704
  newline_beginning = ON;
705
 
706
  if (line_count_status == OFF)
707
    return;
708
 
709
  /* output the file number for list file structure building */
710
  if (listfile_data == YES)
711
    fprintf(file_out_ptr, "k%d ", active_file_info_last->line_current);
712
 
713
  if (active_file_info_last != NULL)
714
    active_file_info_last->line_current++;
715
}
716
 
717
 
718
int parse_directive(void) {
719
 
720
  char bak[256];
721
  int o, q;
722
 
723
 
724
  /* ORG */
725
 
726
  if (strcmp(cp, "ORG") == 0) {
727
    if (output_format == OUTPUT_LIBRARY) {
728
      print_error("Library files don't take .ORG definitions.\n", ERROR_DIR);
729
      return FAILED;
730
    }
731
    if (bank_defined == 0) {
732
      print_error("No .BANK is defined.\n", ERROR_LOG);
733
      return FAILED;
734
    }
735
    if (section_status == ON) {
736
      print_error("You can't issue .ORG inside a .SECTION.\n", ERROR_DIR);
737
      return FAILED;
738
    }
739
 
740
    q = input_number();
741
 
742
    if (q == FAILED)
743
      return FAILED;
744
 
745
    if (q != SUCCEEDED) {
746
      print_error(".ORG needs a positive or zero integer value.\n", ERROR_DIR);
747
      return FAILED;
748
    }
749
 
750
    org_defined = 1;
751
    fprintf(file_out_ptr, "O%d ", d);
752
    return SUCCEEDED;
753
  }
754
 
755
  /* ORGA */
756
 
757
  if (strcmp(cp, "ORGA") == 0) {
758
    if (output_format == OUTPUT_LIBRARY) {
759
      print_error("Library files don't take .ORGA definitions.\n", ERROR_DIR);
760
      return FAILED;
761
    }
762
    if (bank_defined == 0) {
763
      print_error("No .BANK is defined.\n", ERROR_LOG);
764
      return FAILED;
765
    }
766
    if (section_status == ON) {
767
      print_error("You can't issue .ORGA inside a .SECTION.\n", ERROR_DIR);
768
      return FAILED;
769
    }
770
 
771
    q = input_number();
772
 
773
    if (q == FAILED)
774
      return FAILED;
775
 
776
    if (q != SUCCEEDED) {
777
      print_error(".ORGA needs a positive or zero integer value.\n", ERROR_DIR);
778
      return FAILED;
779
    }
780
 
781
    org_defined = 1;
782
 
783
    ind = slots[current_slot].address;
784
    if (d < ind || d > (ind + slots[current_slot].size)) {
785
      print_error(".ORGA is outside the current SLOT.\n", ERROR_DIR);
786
      return FAILED;
787
    }
788
 
789
    fprintf(file_out_ptr, "O%d ", d - ind);
790
 
791
    return SUCCEEDED;
792
  }
793
 
794
  /* SLOT */
795
 
796
  if (strcmp(cp, "SLOT") == 0) {
797
    if (output_format == OUTPUT_LIBRARY) {
798
      print_error("Library files don't take .SLOT definitions.\n", ERROR_DIR);
799
      return FAILED;
800
    }
801
    if (section_status == ON) {
802
      print_error("You can't issue .SLOT inside a .SECTION.\n", ERROR_DIR);
803
      return FAILED;
804
    }
805
 
806
    q = input_number();
807
 
808
    if (q == FAILED)
809
      return FAILED;
810
 
811
    if (q != SUCCEEDED) {
812
      print_error(".SLOT needs a positive or zero integer value.\n", ERROR_DIR);
813
      return FAILED;
814
    }
815
 
816
    if (slots[d].size == 0) {
817
      sprintf(emsg, "There is no SLOT number %d.\n", d);
818
      print_error(emsg, ERROR_DIR);
819
      return FAILED;
820
    }
821
 
822
    fprintf(file_out_ptr, "B%d %d ", bank, d);
823
 
824
    current_slot = d;
825
 
826
    return SUCCEEDED;
827
  }
828
 
829
  /* BANK */
830
 
831
  if (strcmp(cp, "BANK") == 0) {
832
    if (output_format == OUTPUT_LIBRARY) {
833
      print_error("Library files don't take .BANK definitions.\n", ERROR_DIR);
834
      return FAILED;
835
    }
836
    if (section_status == ON) {
837
      sprintf(emsg, "Section \"%s\" is open. Do not try to change the bank.\n", sections_last->name);
838
      print_error(emsg, ERROR_LOG);
839
      return FAILED;
840
    }
841
    if (rombanks_defined == 0 && output_format != OUTPUT_LIBRARY) {
842
      print_error(".ROMBANKS is not yet defined.\n", ERROR_DIR);
843
      return FAILED;
844
    }
845
 
846
    q = input_number();
847
 
848
    if (q == FAILED)
849
      return FAILED;
850
    if (q != SUCCEEDED || d < 0) {
851
      print_error(".BANK number must be zero or positive.\n", ERROR_DIR);
852
      return FAILED;
853
    }
854
 
855
    if (rombanks <= d && output_format != OUTPUT_LIBRARY) {
856
      sprintf(emsg, "ROM banks == %d, selected bank %d.\n", rombanks, d);
857
      print_error(emsg, ERROR_DIR);
858
      return FAILED;
859
    }
860
 
861
    bank = d;
862
    bank_defined = 1;
863
 
864
    if (compare_next_token("SLOT", 4) == SUCCEEDED) {
865
      skip_next_token();
866
 
867
      q = input_number();
868
 
869
      if (q == FAILED)
870
        return FAILED;
871
      if (q != SUCCEEDED || d > 255 || d < 0) {
872
        print_error("SLOT needs an unsigned 8bit value as an ID.\n", ERROR_DIR);
873
        return FAILED;
874
      }
875
 
876
      if (slots[d].size == 0) {
877
        sprintf(emsg, "There is no SLOT number %d.\n", d);
878
        print_error(emsg, ERROR_DIR);
879
        return FAILED;
880
      }
881
 
882
      if (output_format != OUTPUT_LIBRARY)
883
        fprintf(file_out_ptr, "B%d %d ", bank, d);
884
 
885
      ind = bank;
886
      inz = d;
887
      current_slot = d;
888
    }
889
    else if (output_format != OUTPUT_LIBRARY) {
890
      fprintf(file_out_ptr, "B%d %d ", d, defaultslot);
891
      ind = d;
892
      inz = defaultslot;
893
      current_slot = defaultslot;
894
    }
895
 
896
    if (slots[inz].size < banks[ind]) {
897
      sprintf(emsg, "SLOT %d's size %d < BANK %d's size %d.\n", inz, slots[inz].size, ind, banks[ind]);
898
      print_error(emsg, ERROR_DIR);
899
      return FAILED;
900
    }
901
    if (slots[inz].size > banks[ind]) {
902
      sprintf(emsg, "SLOT %d's size %d > BANK %d's size %d, but the bank fits inside.\n", inz, slots[inz].size, ind, banks[ind]);
903
      print_error(emsg, ERROR_WRN);
904
    }
905
 
906
    return SUCCEEDED;
907
  }
908
 
909
  /* DB/BYT/BYTE? */
910
 
911
  if (strcmp(cp, "DB") == 0 || strcmp(cp, "BYT") == 0 || strcmp(cp, "BYTE") == 0) {
912
    strcpy(bak, cp);
913
 
914
    inz = input_number();
915
    for (ind = 0; inz == SUCCEEDED || inz == INPUT_NUMBER_STRING || inz == INPUT_NUMBER_ADDRESS_LABEL || inz == INPUT_NUMBER_STACK; ind++) {
916
      if (inz == INPUT_NUMBER_STRING) {
917
        for (o = 0; o < string_size; o++)
918
          fprintf(file_out_ptr, "d%d ", (int)label[o]);
919
        inz = input_number();
920
        continue;
921
      }
922
 
923
      if (inz == SUCCEEDED && (d < -127 || d > 255)) {
924
        sprintf(emsg, ".%s expects 8bit data, %d is out of range!\n", bak, d);
925
        print_error(emsg, ERROR_DIR);
926
        return FAILED;
927
      }
928
 
929
      if (inz == SUCCEEDED)
930
        fprintf(file_out_ptr, "d%d ", d);
931
      else if (inz == INPUT_NUMBER_ADDRESS_LABEL)
932
        fprintf(file_out_ptr, "k%d Q%s ", active_file_info_last->line_current, label);
933
      else if (inz == INPUT_NUMBER_STACK)
934
        fprintf(file_out_ptr, "c%d ", latest_stack);
935
 
936
      inz = input_number();
937
    }
938
 
939
    if (inz == FAILED)
940
      return FAILED;
941
 
942
    if (inz == INPUT_NUMBER_EOL && ind == 0) {
943
      sprintf(emsg, ".%s needs data.\n", bak);
944
      print_error(emsg, ERROR_INP);
945
      return FAILED;
946
    }
947
 
948
    if (inz == INPUT_NUMBER_EOL)
949
      next_line();
950
 
951
    return SUCCEEDED;
952
  }
953
 
954
  /* ASCTABLE/ASCIITABLE? */
955
  if (strcmp(cp, "ASCTABLE") == 0 || strcmp(cp, "ASCIITABLE") == 0) {
956
 
957
    int astart, aend;
958
 
959
 
960
    strcpy(bak, cp);
961
 
962
    /* clear the table (to the default n->n -mapping) */
963
    for (o = 0; o < 256; o++)
964
      asciitable[o] = o;
965
 
966
    /* read the entries */
967
    while ((ind = get_next_token()) == SUCCEEDED) {
968
      if (strcaselesscmp(tmp, ".ENDA") == 0)
969
        break;
970
      else if (strcaselesscmp(tmp, "MAP") == 0) {
971
        q = input_number();
972
 
973
        while (q == INPUT_NUMBER_EOL) {
974
          next_line();
975
          q = input_number();
976
        }
977
 
978
        if (q == FAILED)
979
          return FAILED;
980
        if (q == SUCCEEDED && (d < 0 || d > 255)) {
981
          print_error("The entry must be a positive 8bit immediate value or one letter string.\n", ERROR_DIR);
982
          return FAILED;
983
        }
984
        if (q == INPUT_NUMBER_STRING) {
985
          if (string_size != 1) {
986
            print_error("The entry must be a positive 8bit immediate value or one letter string.\n", ERROR_DIR);
987
            return FAILED;
988
          }
989
          else {
990
            d = label[0];
991
            if (d < 0)
992
              d += 256;
993
          }
994
        }
995
 
996
        astart = d;
997
        aend = d+1;
998
 
999
        /* do we have a range? */
1000
        if (compare_next_token("TO", 2) == SUCCEEDED) {
1001
          skip_next_token();
1002
 
1003
          q = input_number();
1004
 
1005
          if (q == FAILED)
1006
            return FAILED;
1007
          if (q == SUCCEEDED && (d < 0 || d > 255)) {
1008
            print_error("The entry must be a positive 8bit immediate value or one letter string.\n", ERROR_DIR);
1009
            return FAILED;
1010
          }
1011
          if (q == INPUT_NUMBER_STRING) {
1012
            if (string_size != 1) {
1013
              print_error("The entry must be a positive 8bit immediate value or one letter string.\n", ERROR_DIR);
1014
              return FAILED;
1015
            }
1016
            else {
1017
              d = label[0];
1018
              if (d < 0)
1019
                d += 256;
1020
            }
1021
          }
1022
 
1023
          aend = d+1;
1024
        }
1025
 
1026
        if (aend <= astart) {
1027
          print_error("The end address of the mapping must be larger than the staring address.\n", ERROR_DIR);
1028
          return FAILED;
1029
        }
1030
 
1031
        /* skip the "=" */
1032
        if (compare_next_token("=", 1) != SUCCEEDED) {
1033
          ind = FAILED;
1034
          break;
1035
        }
1036
        skip_next_token();
1037
 
1038
        /* read the starting address */
1039
        q = input_number();
1040
 
1041
        if (q == FAILED)
1042
          return FAILED;
1043
        if (q == SUCCEEDED && (d < 0 || d > 255)) {
1044
          print_error("The entry must be a positive 8bit immediate value or one letter string.\n", ERROR_DIR);
1045
          return FAILED;
1046
        }
1047
        if (q != SUCCEEDED) {
1048
          print_error("The entry must be a positive 8bit immediate value.\n", ERROR_DIR);
1049
          return FAILED;
1050
        }
1051
 
1052
        /* build the mapping */
1053
        for (o = astart; o < aend; o++) {
1054
          if (d >= 256) {
1055
            print_error("The mapping overflows from the ASCII table!\n", ERROR_DIR);
1056
            return FAILED;
1057
          }
1058
          asciitable[o] = d++;
1059
        }
1060
      }
1061
      else {
1062
        ind = FAILED;
1063
        break;
1064
      }
1065
    }
1066
 
1067
    if (ind != SUCCEEDED) {
1068
      sprintf(emsg, "Error in .%s data structure.\n", bak);
1069
      print_error(emsg, ERROR_DIR);
1070
      return FAILED;
1071
    }
1072
 
1073
    asciitable_defined = 1;
1074
 
1075
    return SUCCEEDED;
1076
  }
1077
 
1078
  /* ASC? */
1079
  if (strcmp(cp, "ASC") == 0) {
1080
    strcpy(bak, cp);
1081
 
1082
    if (asciitable_defined == 0) {
1083
      print_error("No .ASCIITABLE defined. Using the default n->n -mapping.\n", ERROR_WRN);
1084
      for (o = 0; o < 256; o++)
1085
        asciitable[o] = o;
1086
    }
1087
 
1088
    while (1) {
1089
      q = input_number();
1090
      if (q == INPUT_NUMBER_EOL) {
1091
        next_line();
1092
        break;
1093
      }
1094
 
1095
      if (!q == INPUT_NUMBER_STRING) {
1096
        sprintf(emsg, ".%s needs string data.\n", bak);
1097
        print_error(emsg, ERROR_INP);
1098
        return FAILED;
1099
      }
1100
 
1101
      /* remap the data */
1102
      for (o = 0; o < string_size; o++) {
1103
        ind = label[o];
1104
        if (ind < 0)
1105
          ind += 256;
1106
        ind = (int)asciitable[ind];
1107
        fprintf(file_out_ptr, "d%d ", ind);
1108
      }
1109
    }
1110
 
1111
    return SUCCEEDED;
1112
  }
1113
 
1114
  /* DW/WORD? */
1115
 
1116
  if (strcmp(cp, "DW") == 0 || strcmp(cp, "WORD") == 0) {
1117
    strcpy(bak, cp);
1118
 
1119
    inz = input_number();
1120
    for (ind = 0; inz == SUCCEEDED || inz == INPUT_NUMBER_ADDRESS_LABEL || inz == INPUT_NUMBER_STACK; ind++) {
1121
      if (inz == SUCCEEDED && (d < -32768 || d > 65535)) {
1122
        sprintf(emsg, ".%s expects 16bit data, %d is out of range!\n", bak, d);
1123
        print_error(emsg, ERROR_DIR);
1124
        return FAILED;
1125
      }
1126
 
1127
      if (inz == SUCCEEDED)
1128
        fprintf(file_out_ptr, "y%d", d);
1129
      else if (inz == INPUT_NUMBER_ADDRESS_LABEL)
1130
        fprintf(file_out_ptr, "k%d r%s ", active_file_info_last->line_current, label);
1131
      else if (inz == INPUT_NUMBER_STACK)
1132
        fprintf(file_out_ptr, "C%d ", latest_stack);
1133
 
1134
      inz = input_number();
1135
    }
1136
 
1137
    if (inz == FAILED)
1138
      return FAILED;
1139
 
1140
    if ((inz == INPUT_NUMBER_EOL || inz == INPUT_NUMBER_STRING) && ind == 0) {
1141
      sprintf(emsg, ".%s needs data.\n", bak);
1142
      print_error(emsg, ERROR_INP);
1143
      return FAILED;
1144
    }
1145
 
1146
    if (inz == INPUT_NUMBER_EOL)
1147
      next_line();
1148
 
1149
    return SUCCEEDED;
1150
  }
1151
 
1152
  /* DSTRUCT */
1153
 
1154
  if (strcmp(cp, "DSTRUCT") == 0) {
1155
 
1156
    struct structure_item *it;
1157
    struct structure *s;
1158
    char iname[256];
1159
    int c, f;
1160
 
1161
 
1162
    /* get instance name */
1163
    q = input_number();
1164
    if (q == FAILED)
1165
      return FAILED;
1166
    if (q != INPUT_NUMBER_ADDRESS_LABEL) {
1167
      print_error(".DSTRUCT needs a name for the instance.\n", ERROR_INP);
1168
      return FAILED;
1169
    }
1170
 
1171
    strcpy(iname, label);
1172
 
1173
    if (compare_next_token("INSTANCEOF", 10) == SUCCEEDED)
1174
      skip_next_token();
1175
 
1176
    /* get structure name */
1177
    q = input_number();
1178
    if (q == FAILED)
1179
      return FAILED;
1180
    if (q != INPUT_NUMBER_ADDRESS_LABEL) {
1181
      print_error(".DSTRUCT needs a structure name.\n", ERROR_INP);
1182
      return FAILED;
1183
    }
1184
 
1185
    /* find the structure */
1186
    s = structures_first;
1187
    while (s != NULL) {
1188
      if (strcmp(label, s->name) == 0)
1189
        break;
1190
      s = s->next;
1191
    }
1192
 
1193
    if (s == NULL) {
1194
      sprintf(emsg, "Reference to an unidentified structure \"%s\".\n", label);
1195
      print_error(emsg, ERROR_DIR);
1196
      return FAILED;
1197
    }
1198
 
1199
    if (compare_next_token("DATA", 4) == SUCCEEDED)
1200
      skip_next_token();
1201
 
1202
    fprintf(file_out_ptr, "k%d L%s ", active_file_info_last->line_current, iname);
1203
 
1204
    /* read the data */
1205
    it = s->items;
1206
    inz = input_number();
1207
    for (ind = 0; it != NULL && (inz == SUCCEEDED || inz == INPUT_NUMBER_STRING || inz == INPUT_NUMBER_ADDRESS_LABEL || inz == INPUT_NUMBER_STACK); ind++) {
1208
 
1209
    fprintf(file_out_ptr, "k%d L%s.%s ", active_file_info_last->line_current, iname, it->name);
1210
 
1211
      /* take care of the strings */
1212
      if (inz == INPUT_NUMBER_STRING) {
1213
        if (it->size < string_size) {
1214
          sprintf(emsg, "String \"%s\" doesn't fit into the %d bytes of \"%s.%s\". Discarding the overflow.\n", label, it->size, s->name, it->name);
1215
          print_error(emsg, ERROR_WRN);
1216
          c = it->size;
1217
        }
1218
        else
1219
          c = string_size;
1220
 
1221
        /* copy the string */
1222
        for (o = 0; o < c; o++)
1223
          fprintf(file_out_ptr, "d%d ", (int)label[o]);
1224
      }
1225
      /* take care of the rest */
1226
      else {
1227
        if (it->size == 1) {
1228
          if ((inz == SUCCEEDED) && (d < -127 || d > 255)) {
1229
            sprintf(emsg, "\"%s.%s\" expects 8bit data, %d is out of range!\n", s->name, it->name, d);
1230
            print_error(emsg, ERROR_DIR);
1231
            return FAILED;
1232
          }
1233
 
1234
          if (inz == SUCCEEDED)
1235
            fprintf(file_out_ptr, "d%d ", d);
1236
          else if (inz == INPUT_NUMBER_ADDRESS_LABEL)
1237
            fprintf(file_out_ptr, "k%d Q%s ", active_file_info_last->line_current, label);
1238
          else if (inz == INPUT_NUMBER_STACK)
1239
            fprintf(file_out_ptr, "c%d ", latest_stack);
1240
 
1241
          o = 1;
1242
        }
1243
        else {
1244
          if (inz == SUCCEEDED && (d < -32768 || d > 65535)) {
1245
            sprintf(emsg, "\"%s.%s\" expects 16bit data, %d is out of range!\n", s->name, it->name, d);
1246
            print_error(emsg, ERROR_DIR);
1247
            return FAILED;
1248
          }
1249
 
1250
          if (inz == SUCCEEDED)
1251
            fprintf(file_out_ptr, "y%d", d);
1252
          else if (inz == INPUT_NUMBER_ADDRESS_LABEL)
1253
            fprintf(file_out_ptr, "k%d r%s ", active_file_info_last->line_current, label);
1254
          else if (inz == INPUT_NUMBER_STACK)
1255
            fprintf(file_out_ptr, "C%d ", latest_stack);
1256
 
1257
          o = 2;
1258
        }
1259
      }
1260
 
1261
      /* fill the rest with emptyfill or zero */
1262
      if (emptyfill_defined != 0)
1263
        f = emptyfill;
1264
      else
1265
        f = 0;
1266
 
1267
      for (; o < it->size; o++)
1268
        fprintf(file_out_ptr, "d%d ", f);
1269
 
1270
      it = it->next;
1271
      inz = input_number();
1272
    }
1273
 
1274
    if (it != NULL) {
1275
      sprintf(emsg, "\"%s\" doesn't define all the members of \"%s\".\n", iname, s->name);
1276
      print_error(emsg, ERROR_DIR);
1277
      return FAILED;
1278
 
1279
    }
1280
 
1281
    if (inz == INPUT_NUMBER_EOL)
1282
      next_line();
1283
    else {
1284
      sprintf(emsg, "Too much data for structure \"%s\".\n", s->name);
1285
      print_error(emsg, ERROR_DIR);
1286
      return FAILED;
1287
    }
1288
 
1289
    return SUCCEEDED;
1290
  }
1291
 
1292
  /* DS/DSB? */
1293
 
1294
  if (strcmp(cp, "DSB") == 0 || strcmp(cp, "DS") == 0) {
1295
    strcpy(bak, cp);
1296
 
1297
    q = input_number();
1298
    if (q == FAILED)
1299
      return FAILED;
1300
    if (q != SUCCEEDED) {
1301
      sprintf(emsg, ".%s needs size.\n", bak);
1302
      print_error(emsg, ERROR_INP);
1303
      return FAILED;
1304
    }
1305
 
1306
    if (d < 1 || d > 65535) {
1307
      sprintf(emsg, ".%s expects a 16bit positive integer as size, %d is out of range!\n", bak, d);
1308
      print_error(emsg, ERROR_DIR);
1309
      return FAILED;
1310
    }
1311
 
1312
    inz = d;
1313
 
1314
    q = input_number();
1315
    if (q == FAILED)
1316
      return FAILED;
1317
    if (!(q == SUCCEEDED || q == INPUT_NUMBER_ADDRESS_LABEL || q == INPUT_NUMBER_STACK)) {
1318
      sprintf(emsg, ".%s needs data.\n", bak);
1319
      print_error(emsg, ERROR_INP);
1320
      return FAILED;
1321
    }
1322
 
1323
    if (q == SUCCEEDED && (d > 255 || d < -127)) {
1324
      sprintf(emsg, ".%s expects 8bit data, %d is out of range!\n", bak, d);
1325
      print_error(emsg, ERROR_DIR);
1326
      return FAILED;
1327
    }
1328
 
1329
    if (q == SUCCEEDED)
1330
      fprintf(file_out_ptr, "x%d %d ", inz, d);
1331
    else if (q == INPUT_NUMBER_ADDRESS_LABEL) {
1332
      fprintf(file_out_ptr, "k%d ", active_file_info_last->line_current);
1333
      for (q = 0; q < inz; q++)
1334
        fprintf(file_out_ptr, "R%s ", label);
1335
    }
1336
    else if (q == INPUT_NUMBER_STACK) {
1337
      for (q = 0; q < inz; q++)
1338
        fprintf(file_out_ptr, "c%d ", latest_stack);
1339
    }
1340
 
1341
    return SUCCEEDED;
1342
  }
1343
 
1344
  /* DSW? */
1345
 
1346
  if (strcmp(cp, "DSW") == 0) {
1347
    q = input_number();
1348
    if (q == FAILED)
1349
      return FAILED;
1350
    if (q != SUCCEEDED) {
1351
      print_error(".DSW needs size.\n", ERROR_INP);
1352
      return FAILED;
1353
    }
1354
 
1355
    if (d < 1 || d > 65535) {
1356
      sprintf(emsg, ".DSW expects a 16bit positive integer as size, %d is out of range!\n", d);
1357
      print_error(emsg, ERROR_DIR);
1358
      return FAILED;
1359
    }
1360
 
1361
    inz = d;
1362
 
1363
    q = input_number();
1364
    if (q == FAILED)
1365
      return FAILED;
1366
    if (!(q == SUCCEEDED || q == INPUT_NUMBER_ADDRESS_LABEL || q == INPUT_NUMBER_STACK)) {
1367
      print_error(".DSW needs data.\n", ERROR_INP);
1368
      return FAILED;
1369
    }
1370
 
1371
    if (q == SUCCEEDED && (d < -32768 || d > 65535)) {
1372
      sprintf(emsg, ".DSW expects 16bit data, %d is out of range!\n", d);
1373
      print_error(emsg, ERROR_DIR);
1374
      return FAILED;
1375
    }
1376
 
1377
    if (q == SUCCEEDED)
1378
      fprintf(file_out_ptr, "X%d %d ", inz, d);
1379
    else if (q == INPUT_NUMBER_ADDRESS_LABEL) {
1380
      fprintf(file_out_ptr, "k%d ", active_file_info_last->line_current);
1381
      for (q = 0; q < inz; q++)
1382
        fprintf(file_out_ptr, "r%s ", label);
1383
    }
1384
    else if (q == INPUT_NUMBER_STACK) {
1385
      for (q = 0; q < inz; q++)
1386
        fprintf(file_out_ptr, "C%d ", latest_stack);
1387
    }
1388
 
1389
    return SUCCEEDED;
1390
  }
1391
 
1392
  /* INCDIR */
1393
 
1394
  if (strcmp(cp, "INCDIR") == 0) {
1395
 
1396
    char *c;
1397
 
1398
 
1399
    if (get_next_token() != GET_NEXT_TOKEN_STRING) {
1400
      print_error(".INCDIR needs a directory string.\n", ERROR_DIR);
1401
      return FAILED;
1402
    }
1403
 
1404
    q = ss;
1405
 
1406
    /* use the default dir? */
1407
    if (q == 0) {
1408
      if (include_dir != NULL)
1409
        include_dir[0] = 0;
1410
      return SUCCEEDED;
1411
    }
1412
 
1413
    /* use the given dir */
1414
    o = strlen(tmp) + 2;
1415
    if (o > include_dir_size) {
1416
      c = realloc(include_dir, o);
1417
      if (c == NULL) {
1418
        print_error("Out of memory error.\n", ERROR_DIR);
1419
        return FAILED;
1420
      }
1421
      include_dir = c;
1422
      include_dir_size = o;
1423
    }
1424
 
1425
    /* convert the path string to local enviroment */
1426
    localize_path(tmp);
1427
 
1428
    strcpy(include_dir, tmp);
1429
 
1430
    /* terminate the string with '/' */
1431
#ifdef MSDOS
1432
    if (include_dir[q - 1] != '\\') {
1433
      include_dir[q] = '\\';
1434
      include_dir[q + 1] = 0;
1435
    }
1436
#else
1437
    if (include_dir[q - 1] != '/') {
1438
      include_dir[q] = '/';
1439
      include_dir[q + 1] = 0;
1440
    }
1441
#endif
1442
 
1443
    return SUCCEEDED;
1444
  }
1445
 
1446
  /* INCLUDE */
1447
 
1448
  if (strcmp(cp, "INCLUDE") == 0) {
1449
    o = input_number();
1450
    if (o != INPUT_NUMBER_STRING) {
1451
      print_error(".INCLUDE needs a file name string.\n", ERROR_DIR);
1452
      return FAILED;
1453
    }
1454
    if (macro_active != 0) {
1455
      print_error("You cannot include a file inside a MACRO.\n", ERROR_DIR);
1456
      return FAILED;
1457
    }
1458
 
1459
    /* convert the path to local enviroment */
1460
    localize_path(label);
1461
 
1462
    if (include_file(label) == FAILED)
1463
      return FAILED;
1464
 
1465
    fprintf(file_out_ptr, "f%d ", active_file_info_tmp->filename_id);
1466
 
1467
    return SUCCEEDED;
1468
  }
1469
 
1470
  /* INCBIN */
1471
 
1472
  if (strcmp(cp, "INCBIN") == 0) {
1473
 
1474
    int s, r;
1475
 
1476
 
1477
    if (org_defined == 0 && output_format != OUTPUT_LIBRARY) {
1478
      print_error("Before you can .INCBIN data you'll need to use ORG.\n", ERROR_LOG);
1479
      return FAILED;
1480
    }
1481
 
1482
    o = input_number();
1483
    if (o != INPUT_NUMBER_STRING) {
1484
      print_error(".INCBIN needs a file name string.\n", ERROR_DIR);
1485
      return FAILED;
1486
    }
1487
 
1488
    /* convert the path string to local enviroment */
1489
    localize_path(label);
1490
 
1491
    if (incbin_file(label, &ind, &inz, &s, &r) == FAILED)
1492
      return FAILED;
1493
 
1494
    /* D [id] [swap] [skip] [size] */
1495
    fprintf(file_out_ptr, "D%d %d %d %d ", ind, inz, s, r);
1496
 
1497
    return SUCCEEDED;
1498
  }
1499
 
1500
  /* OUTNAME */
1501
 
1502
  if (strcmp(cp, "OUTNAME") == 0) {
1503
 
1504
    inz = input_number();
1505
 
1506
    if (inz != INPUT_NUMBER_STRING) {
1507
      print_error(".OUTNAME needs a file name string.\n", ERROR_DIR);
1508
      return FAILED;
1509
    }
1510
 
1511
    strcpy(final_name, label);
1512
    return SUCCEEDED;
1513
  }
1514
 
1515
  /* STRUCT */
1516
 
1517
  if (strcmp(cp, "STRUCT") == 0) {
1518
 
1519
    struct structure_item *si, *ss, *sl = NULL;
1520
    struct structure *st;
1521
    char name[512];
1522
    int ssi = 0;
1523
 
1524
 
1525
    st = malloc(sizeof(struct structure));
1526
    if (st == NULL) {
1527
      print_error("Out of memory while allocating a new STRUCT.\n", ERROR_DIR);
1528
      return FAILED;
1529
    }
1530
 
1531
    if (get_next_token() == FAILED)
1532
      return FAILED;
1533
 
1534
    strcpy(st->name, tmp);
1535
 
1536
    st->next = structures_first;
1537
    structures_first = st;
1538
    st->items = NULL;
1539
 
1540
    while (1) {
1541
      if (get_next_token() == FAILED)
1542
        return FAILED;
1543
 
1544
      /* end of STRUCT? */
1545
      if (strcaselesscmp(tmp, ".ENDST") == 0) {
1546
        /* create the SIZEOF-definition */
1547
        st->size = ssi;
1548
        sprintf(name, "_sizeof_%s", st->name);
1549
 
1550
        if (add_a_new_definition(name, (double)ssi, NULL, DEFINITION_TYPE_VALUE, 0) == FAILED)
1551
          return FAILED;
1552
 
1553
        /* create the structure definitions */
1554
        ssi = 0;
1555
        ss = st->items;
1556
        while (ss != NULL) {
1557
          sprintf(name, "%s.%s", st->name, ss->name);
1558
          if (add_a_new_definition(name, (double)ssi, NULL, DEFINITION_TYPE_VALUE, 0) == FAILED)
1559
            return FAILED;
1560
          ssi += ss->size;
1561
          ss = ss->next;
1562
        }
1563
 
1564
        if (st->items == NULL) {
1565
          sprintf(emsg, "Structure \"%s\" is empty!\n", st->name);
1566
          print_error(emsg, ERROR_DIR);
1567
          return FAILED;
1568
        }
1569
 
1570
        return SUCCEEDED;
1571
      }
1572
 
1573
      if (tmp[strlen(tmp) - 1] == ':')
1574
        tmp[strlen(tmp) - 1] = 0;
1575
 
1576
      /* check for duplicate labels */
1577
      ss = st->items;
1578
      while (ss != NULL) {
1579
        if (strcmp(ss->name, tmp) == 0) {
1580
          sprintf(emsg, "Duplicate label \"%s\" inside .STRUCT \"%s\".\n", tmp, st->name);
1581
          print_error(emsg, ERROR_DIR);
1582
          return FAILED;
1583
        }
1584
        ss = ss->next;
1585
      }
1586
 
1587
      si = malloc(sizeof(struct structure_item));
1588
      if (si == NULL) {
1589
        print_error("Out of memory while allocating a new STRUCT.\n", ERROR_DIR);
1590
        return FAILED;
1591
      }
1592
      si->next = NULL;
1593
      strcpy(si->name, tmp);
1594
 
1595
      if (st->items == NULL)
1596
        st->items = si;
1597
      if (sl != NULL)
1598
        sl->next = si;
1599
      sl = si;
1600
 
1601
      /* get the item type */
1602
      if (get_next_token() == FAILED)
1603
        return FAILED;
1604
 
1605
      if (strcaselesscmp(tmp, "DB") == 0 || strcaselesscmp(tmp, "BYT") == 0 || strcaselesscmp(tmp, "BYTE") == 0)
1606
        si->size = 1;
1607
      else if (strcaselesscmp(tmp, "DW") == 0 || strcaselesscmp(tmp, "WORD") == 0)
1608
        si->size = 2;
1609
      else if (strcaselesscmp(tmp, "DS") == 0 || strcaselesscmp(tmp, "DSB") == 0) {
1610
        q = input_number();
1611
        if (q == FAILED)
1612
          return FAILED;
1613
        if (q != SUCCEEDED) {
1614
          print_error("DS/DSB needs size.\n", ERROR_DIR);
1615
          return FAILED;
1616
        }
1617
        si->size = d;
1618
      }
1619
      else if (strcaselesscmp(tmp, "DSW") == 0) {
1620
        q = input_number();
1621
        if (q == FAILED)
1622
          return FAILED;
1623
        if (q != SUCCEEDED) {
1624
          print_error("DSW needs size.\n", ERROR_DIR);
1625
          return FAILED;
1626
        }
1627
        si->size = d*2;
1628
      }
1629
      else if (tmp[0] == '.')
1630
        continue;
1631
      else {
1632
        sprintf(emsg, "Unexpected symbol \"%s\" in .STRUCT.\n", tmp);
1633
        print_error(emsg, ERROR_DIR);
1634
        return FAILED;
1635
      }
1636
      ssi += si->size;
1637
    }
1638
 
1639
    return FAILED;
1640
  }
1641
 
1642
  /* RAMSECTION */
1643
 
1644
  if (strcmp(cp, "RAMSECTION") == 0) {
1645
 
1646
    char namebak[256];
1647
 
1648
 
1649
    if (output_format == OUTPUT_LIBRARY) {
1650
      print_error("Libraries don't take RAMSECTIONs.\n", ERROR_DIR);
1651
      return FAILED;
1652
    }
1653
    if (section_id > 255) {
1654
      print_error("Out of section numbers. Please start a new file.\n", ERROR_DIR);
1655
      return FAILED;
1656
    }
1657
    if (section_status == ON) {
1658
      sprintf(emsg, "There is already an open section called \"%s\".", sections_last->name);
1659
      print_error(emsg, ERROR_DIR);
1660
      return FAILED;
1661
    }
1662
 
1663
    if (get_next_token() == FAILED)
1664
      return FAILED;
1665
 
1666
    sec_tmp = calloc(sizeof(struct section_def), 1);
1667
    if (sec_tmp == NULL) {
1668
      sprintf(emsg, "Out of memory while allocating room for a new RAMSECTION \"%s\".\n", tmp);
1669
      print_error(emsg, ERROR_DIR);
1670
      return FAILED;
1671
    }
1672
 
1673
    sec_tmp->listfile_items = 0;
1674
    sec_tmp->listfile_ints = NULL;
1675
    sec_tmp->listfile_cmds = NULL;
1676
    sec_tmp->maxsize_status = OFF;
1677
    sec_tmp->status = SECTION_STATUS_RAM;
1678
    sec_tmp->alive = ON;
1679
    sec_tmp->data = NULL;
1680
    sec_tmp->filename_id = active_file_info_last->filename_id;
1681
    sec_tmp->id = section_id;
1682
    sec_tmp->alignment = 1;
1683
    sec_tmp->advance_org = YES;
1684
    section_id++;
1685
 
1686
    strcpy(sec_tmp->name, tmp);
1687
    sec_tmp->next = NULL;
1688
 
1689
    /* look for duplicate sections */
1690
    sec_next = sections_first;
1691
    while (sec_next != NULL) {
1692
      if (strcmp(sec_next->name, tmp) == 0) {
1693
        sprintf(emsg, "SECTION \"%s\" was defined for the second time.\n", tmp);
1694
        print_error(emsg, ERROR_DIR);
1695
        free(sec_tmp);
1696
        return FAILED;
1697
      }
1698
      sec_next = sec_next->next;
1699
    }
1700
 
1701
    if (sections_first == NULL) {
1702
      sections_first = sec_tmp;
1703
      sections_last = sec_tmp;
1704
    }
1705
    else {
1706
      sections_last->next = sec_tmp;
1707
      sections_last = sec_tmp;
1708
    }
1709
 
1710
    /* check for optional BANK */
1711
    if (compare_next_token("BANK", 4) != SUCCEEDED)
1712
      sec_tmp->bank = 0;
1713
    else {
1714
      skip_next_token();
1715
 
1716
      q = input_number();
1717
 
1718
      if (q == FAILED)
1719
        return FAILED;
1720
      if (q != SUCCEEDED || d < 0) {
1721
        print_error("BANK number must be zero or positive.\n", ERROR_DIR);
1722
        return FAILED;
1723
      }
1724
 
1725
      if (rombanks <= d && output_format != OUTPUT_LIBRARY) {
1726
        sprintf(emsg, "ROM banks == %d, selected bank %d.\n", rombanks, d);
1727
        print_error(emsg, ERROR_DIR);
1728
        return FAILED;
1729
      }
1730
 
1731
      sec_tmp->bank = d;
1732
    }
1733
 
1734
    if (compare_next_token("SLOT", 4) != SUCCEEDED) {
1735
      if (get_next_token() == FAILED)
1736
        return FAILED;
1737
      sprintf(emsg, "Unknown symbol \"%s\".\n", tmp);
1738
      print_error(emsg, ERROR_DIR);
1739
      return FAILED;
1740
    }
1741
 
1742
    skip_next_token();
1743
 
1744
    q = input_number();
1745
    if (q == FAILED)
1746
      return FAILED;
1747
    if (q != SUCCEEDED || d > 255 || d < 0) {
1748
      print_error(".RAMSECTION needs an unsigned 8bit value as the SLOT number.\n", ERROR_DIR);
1749
      return FAILED;
1750
    }
1751
 
1752
    if (slots[d].size == 0) {
1753
      sprintf(emsg, "There is no SLOT number %d.\n", d);
1754
      print_error(emsg, ERROR_DIR);
1755
      return FAILED;
1756
    }
1757
 
1758
    sec_tmp->slot = d;
1759
    fprintf(file_out_ptr, "S%d ", sec_tmp->id);
1760
 
1761
    /* ram section - read labels */
1762
    if (sec_tmp->status == SECTION_STATUS_RAM) {
1763
      while ((t = get_next_token()) != FAILED) {
1764
        if (strcaselesscmp(tmp, ".ENDS") == 0) {
1765
          fprintf(file_out_ptr, "s ");
1766
          section_status = OFF;
1767
          return SUCCEEDED;
1768
        }
1769
        if (tmp[strlen(tmp) - 1] == ':')
1770
          tmp[strlen(tmp) - 1] = 0;
1771
        fprintf(file_out_ptr, "k%d L%s ", active_file_info_last->line_current, tmp);
1772
        strcpy(namebak, tmp);
1773
        if (get_next_token() == FAILED)
1774
          return FAILED;
1775
        if (strcaselesscmp(tmp, "DB") == 0 || strcaselesscmp(tmp, "BYT") == 0 || strcaselesscmp(tmp, "BYTE") == 0)
1776
          fprintf(file_out_ptr, "d0 ");
1777
        else if (strcaselesscmp(tmp, "DW") == 0 || strcaselesscmp(tmp, "WORD") == 0)
1778
          fprintf(file_out_ptr, "y0 ");
1779
        else if (strcaselesscmp(tmp, "DS") == 0 || strcaselesscmp(tmp, "DSB") == 0) {
1780
          q = input_number();
1781
          if (q == FAILED)
1782
            return FAILED;
1783
          if (q != SUCCEEDED) {
1784
            print_error("DS/DSB needs size.\n", ERROR_DIR);
1785
            return FAILED;
1786
          }
1787
          fprintf(file_out_ptr, "x%d 0 ", d);
1788
        }
1789
        else if (strcaselesscmp(tmp, "DSW") == 0) {
1790
          q = input_number();
1791
          if (q == FAILED)
1792
            return FAILED;
1793
          if (q != SUCCEEDED) {
1794
            print_error("DSW needs size.\n", ERROR_DIR);
1795
            return FAILED;
1796
          }
1797
          fprintf(file_out_ptr, "x%d 0 ", d*2);
1798
        }
1799
        /* it's an instance of a structure! */
1800
        else if (strcaselesscmp(tmp, "INSTANCEOF") == 0) {
1801
 
1802
          struct structure_item *si;
1803
          struct structure *st;
1804
          int g;
1805
 
1806
 
1807
          if (get_next_token() == FAILED)
1808
            return FAILED;
1809
 
1810
          st = structures_first;
1811
          while (st != NULL) {
1812
            if (strcmp(st->name, tmp) == 0)
1813
              break;
1814
            st = st->next;
1815
          }
1816
 
1817
          if (st == NULL) {
1818
            sprintf(emsg, "No STRUCT named \"%s\" available.\n", tmp);
1819
            print_error(emsg, ERROR_DIR);
1820
            return FAILED;
1821
          }
1822
 
1823
          /* amount of structures? */
1824
          inz = input_number();
1825
          if (inz == SUCCEEDED && d > 1)
1826
            fprintf(file_out_ptr, "k%d L%s.1 ", active_file_info_last->line_current, namebak);
1827
 
1828
          /* generate labels */
1829
          si = st->items;
1830
          while (si != NULL) {
1831
            if (inz == SUCCEEDED && d > 1)
1832
              fprintf(file_out_ptr, "k%d L%s.%s L%s.1.%s x%d 0 ", active_file_info_last->line_current, namebak, si->name, namebak, si->name, si->size);
1833
            else
1834
              fprintf(file_out_ptr, "k%d L%s.%s x%d 0 ", active_file_info_last->line_current, namebak, si->name, si->size);
1835
            si = si->next;
1836
          }
1837
 
1838
          if (inz == INPUT_NUMBER_EOL)
1839
            next_line();
1840
          else if (inz == SUCCEEDED) {
1841
            if (d < 1) {
1842
              print_error("The amount of structures must be greater than 0.\n", ERROR_DIR);
1843
              return FAILED;
1844
            }
1845
 
1846
            g = 2;
1847
            while (d > 1) {
1848
              si = st->items;
1849
              fprintf(file_out_ptr, "k%d L%s.%d ", active_file_info_last->line_current, namebak, g);
1850
              while (si != NULL) {
1851
                fprintf(file_out_ptr, "k%d L%s.%d.%s x%d 0 ", active_file_info_last->line_current, namebak, g, si->name, si->size);
1852
                si = si->next;
1853
              }
1854
              g++;
1855
              d--;
1856
            }
1857
          }
1858
          else {
1859
            if (inz == INPUT_NUMBER_STRING)
1860
              sprintf(emsg, "Expected the amount of structures, got \"%s\" instead.\n", label);
1861
            else
1862
              sprintf(emsg, "Expected the amount of structures.\n");
1863
            print_error(emsg, ERROR_DIR);
1864
            return FAILED;
1865
          }
1866
        }
1867
        else if (tmp[0] == '.' && strcaselesscmp(tmp, ".ENDS") != 0)
1868
          continue;
1869
        else {
1870
          sprintf(emsg, "Unexpected symbol \"%s\".\n", tmp);
1871
          print_error(emsg, ERROR_DIR);
1872
          return FAILED;
1873
        }
1874
      }
1875
      return FAILED;
1876
    }
1877
 
1878
    return SUCCEEDED;
1879
  }
1880
 
1881
  /* SECTION */
1882
 
1883
  if (strcmp(cp, "SECTION") == 0) {
1884
 
1885
    int l, m;
1886
 
1887
 
1888
    if (section_id > 255) {
1889
      print_error("Out of section numbers. Please start a new file.\n", ERROR_DIR);
1890
      return FAILED;
1891
    }
1892
    if (section_status == ON) {
1893
      sprintf(emsg, "There is already an open section called \"%s\".", sections_last->name);
1894
      print_error(emsg, ERROR_DIR);
1895
      return FAILED;
1896
    }
1897
    else if (output_format != OUTPUT_LIBRARY && bank_defined == 0) {
1898
      print_error(".SECTION requires a predefined bank.\n", ERROR_DIR);
1899
      return FAILED;
1900
    }
1901
    else if (output_format != OUTPUT_LIBRARY && org_defined == 0) {
1902
      print_error(".SECTION requires a starting address for positioning.\n", ERROR_DIR);
1903
      return FAILED;
1904
    }
1905
 
1906
    if (get_next_token() == FAILED)
1907
      return FAILED;
1908
 
1909
    /* every library section starts @ the beginning of the bank */
1910
    if (output_format == OUTPUT_LIBRARY)
1911
      org_defined = 1;
1912
 
1913
    sec_tmp = calloc(sizeof(struct section_def), 1);
1914
    if (sec_tmp == NULL) {
1915
      sprintf(emsg, "Out of memory while allocating room for a new SECTION \"%s\".\n", tmp);
1916
      print_error(emsg, ERROR_DIR);
1917
      return FAILED;
1918
    }
1919
 
1920
    sec_tmp->listfile_items = 0;
1921
    sec_tmp->listfile_ints = NULL;
1922
    sec_tmp->listfile_cmds = NULL;
1923
    sec_tmp->maxsize_status = OFF;
1924
    sec_tmp->data = NULL;
1925
    sec_tmp->alignment = 1;
1926
    sec_tmp->advance_org = YES;
1927
 
1928
    /* check if the section size is supplied inside the name */
1929
    l = strlen(tmp) - 1;
1930
 
1931
    for (; l >= 0 && tmp[l] != '_'; l--);
1932
 
1933
    if (tmp[l] == '_') {
1934
      l++;
1935
      if (tmp[l] == '$') {
1936
        for (l++, m = 0; tmp[l] != 0; l++) {
1937
          if (tmp[l] >= '0' && tmp[l] <= '9')
1938
            m = (m << 4) + tmp[l] - '0';
1939
          else if (tmp[l] >= 'a' && tmp[l] <= 'f')
1940
            m = (m << 4) + tmp[l] - 'a' + 10;
1941
          else if (tmp[l] >= 'A' && tmp[l] <= 'F')
1942
            m = (m << 4) + tmp[l] - 'A' + 10;
1943
          else
1944
            break;
1945
        }
1946
 
1947
        if (tmp[l] == 0) {
1948
          sec_tmp->maxsize_status = ON;
1949
          sec_tmp->maxsize = m;
1950
        }
1951
      }
1952
      else if (tmp[l] >= '0' && tmp[l] <= '9') {
1953
        for (m = 0; tmp[l] != 0; l++) {
1954
          if (tmp[l] >= '0' && tmp[l] <= '9')
1955
            m = (m * 10) + tmp[l] - '0';
1956
          else
1957
            break;
1958
        }
1959
 
1960
        if (tmp[l] == 0) {
1961
          sec_tmp->maxsize_status = ON;
1962
          sec_tmp->maxsize = m;
1963
        }
1964
      }
1965
    }
1966
 
1967
    if (strcmp(tmp, "BANKHEADER") == 0) {
1968
      if (output_format == OUTPUT_LIBRARY) {
1969
        print_error("Library files don't take bank header sections.\n", ERROR_DIR);
1970
        return FAILED;
1971
      }
1972
      sec_next = sections_first;
1973
      while (sec_next != NULL) {
1974
        if (strcmp(sec_next->name, tmp) == 0 && sec_next->bank == bank) {
1975
          sprintf(emsg, "BANKHEADER section was defined for the second time for bank %d.\n", bank);
1976
          print_error(emsg, ERROR_DIR);
1977
          return FAILED;
1978
        }
1979
        sec_next = sec_next->next;
1980
      }
1981
    }
1982
    else {
1983
      sec_next = sections_first;
1984
      while (sec_next != NULL) {
1985
        if (strcmp(sec_next->name, tmp) == 0) {
1986
          sprintf(emsg, "SECTION \"%s\" was defined for the second time.\n", tmp);
1987
          print_error(emsg, ERROR_DIR);
1988
          free(sec_tmp);
1989
          return FAILED;
1990
        }
1991
        sec_next = sec_next->next;
1992
      }
1993
    }
1994
 
1995
    strcpy(sec_tmp->name, tmp);
1996
    sec_tmp->next = NULL;
1997
 
1998
    if (sections_first == NULL) {
1999
      sections_first = sec_tmp;
2000
      sections_last = sec_tmp;
2001
    }
2002
    else {
2003
      sections_last->next = sec_tmp;
2004
      sections_last = sec_tmp;
2005
    }
2006
 
2007
    /* the size of the section? */
2008
    if (compare_next_token("SIZE", 4) == SUCCEEDED) {
2009
      if (sec_tmp->maxsize_status == ON) {
2010
        print_error("The size of the section has already been defined.\n", ERROR_DIR);
2011
        return FAILED;
2012
      }
2013
 
2014
      if (skip_next_token() == FAILED)
2015
        return FAILED;
2016
 
2017
      inz = input_number();
2018
      if (inz != SUCCEEDED) {
2019
        print_error("Could not parse the size.\n", ERROR_DIR);
2020
        return FAILED;
2021
      }
2022
 
2023
      sec_tmp->maxsize_status = ON;
2024
      sec_tmp->maxsize = d;
2025
    }
2026
 
2027
    /* align the section? */
2028
    if (compare_next_token("ALIGN", 5) == SUCCEEDED) {
2029
      if (skip_next_token() == FAILED)
2030
        return FAILED;
2031
 
2032
      inz = input_number();
2033
      if (inz != SUCCEEDED) {
2034
        print_error("Could not parse the section alignment.\n", ERROR_DIR);
2035
        return FAILED;
2036
      }
2037
 
2038
      sec_tmp->alignment = d;
2039
    }
2040
 
2041
    /* the type of the section */
2042
    if (compare_next_token("FORCE", 5) == SUCCEEDED) {
2043
      if (output_format == OUTPUT_LIBRARY) {
2044
        print_error("Libraries don't take FORCE sections.\n", ERROR_DIR);
2045
        return FAILED;
2046
      }
2047
      sec_tmp->status = SECTION_STATUS_FORCE;
2048
      if (skip_next_token() == FAILED)
2049
        return FAILED;
2050
    }
2051
    else if (compare_next_token("FREE", 4) == SUCCEEDED) {
2052
      sec_tmp->status = SECTION_STATUS_FREE;
2053
      if (skip_next_token() == FAILED)
2054
        return FAILED;
2055
    }
2056
    else if (compare_next_token("SUPERFREE", 9) == SUCCEEDED) {
2057
      sec_tmp->status = SECTION_STATUS_SUPERFREE;
2058
      if (skip_next_token() == FAILED)
2059
        return FAILED;
2060
    }
2061
    else if (compare_next_token("SEMIFREE", 8) == SUCCEEDED) {
2062
      if (output_format == OUTPUT_LIBRARY) {
2063
        print_error("Libraries don't take SEMIFREE sections.\n", ERROR_DIR);
2064
        return FAILED;
2065
      }
2066
      sec_tmp->status = SECTION_STATUS_SEMIFREE;
2067
      if (skip_next_token() == FAILED)
2068
        return FAILED;
2069
    }
2070
    else if (compare_next_token("OVERWRITE", 9) == SUCCEEDED) {
2071
      if (output_format == OUTPUT_LIBRARY) {
2072
        print_error("Libraries don't take OVERWRITE sections.\n", ERROR_DIR);
2073
        return FAILED;
2074
      }
2075
      sec_tmp->status = SECTION_STATUS_OVERWRITE;
2076
      if (skip_next_token() == FAILED)
2077
        return FAILED;
2078
    }
2079
    else
2080
      sec_tmp->status = SECTION_STATUS_FREE;
2081
 
2082
    /* return the org after the section? */
2083
    if (compare_next_token("RETURNORG", 9) == SUCCEEDED) {
2084
      if (skip_next_token() == FAILED)
2085
        return FAILED;
2086
 
2087
      sec_tmp->advance_org = NO;
2088
    }
2089
 
2090
    /* bankheader section? */
2091
    if (strcmp(sec_tmp->name, "BANKHEADER") == 0) {
2092
      sec_tmp->status = SECTION_STATUS_HEADER;
2093
      bankheader_status = ON;
2094
    }
2095
 
2096
    sec_tmp->id = section_id;
2097
    sec_tmp->alive = ON;
2098
    sec_tmp->filename_id = active_file_info_last->filename_id;
2099
    sec_tmp->bank = bank;
2100
    section_id++;
2101
    section_status = ON;
2102
    fprintf(file_out_ptr, "S%d ", sec_tmp->id);
2103
 
2104
    return SUCCEEDED;
2105
  }
2106
 
2107
  /* ELSE */
2108
 
2109
  if (strcmp(cp, "ELSE") == 0) {
2110
 
2111
    int m, r;
2112
 
2113
 
2114
    if (ifdef == 0) {
2115
      print_error("There must be .IFxxx before .ELSE.\n", ERROR_DIR);
2116
      return FAILED;
2117
    }
2118
 
2119
    /* find the next compiling point */
2120
    r = 1;
2121
    m = macro_active;
2122
    /* disable macro decoding */
2123
    macro_active = 0;
2124
    while (get_next_token() != FAILED) {
2125
      if (tmp[0] == '.') {
2126
        if (strcmp(cp, "ENDIF") == 0)
2127
          r--;
2128
        if (strcmp(cp, "E") == 0)
2129
          break;
2130
        if (strcmp(cp, "IFDEF") == 0 || strcmp(cp, "IFNDEF") == 0 || strcmp(cp, "IFGR") == 0 || strcmp(cp, "IFLE") == 0 || strcmp(cp, "IFEQ") == 0 ||
2131
            strcmp(cp, "IFNEQ") == 0 || strcmp(cp, "IFDEFM") == 0 || strcmp(cp, "IFNDEFM") == 0 || strcmp(cp, "IF") == 0 || strcmp(cp, "IFEXISTS") == 0 ||
2132
            strcmp(cp, "IFGREQ") == 0 || strcmp(cp, "IFLEEQ") == 0)
2133
          r++;
2134
      }
2135
      if (r == 0) {
2136
        ifdef--;
2137
        macro_active = m;
2138
        return SUCCEEDED;
2139
      }
2140
    }
2141
 
2142
    print_error(".ELSE must end to .ENDIF.\n", ERROR_DIR);
2143
    return FAILED;
2144
  }
2145
 
2146
  /* ENDIF */
2147
 
2148
  if (strcmp(cp, "ENDIF") == 0) {
2149
 
2150
    if (ifdef == 0) {
2151
      print_error(".ENDIF was given before any .IF directive.\n", ERROR_DIR);
2152
      return FAILED;
2153
    }
2154
 
2155
    ifdef--;
2156
    return SUCCEEDED;
2157
  }
2158
 
2159
  /* IFDEF */
2160
 
2161
  if (strcmp(cp, "IFDEF") == 0) {
2162
 
2163
    struct definition *d;
2164
 
2165
 
2166
    if (get_next_token() == FAILED)
2167
      return FAILED;
2168
 
2169
    d = defines;
2170
    while (d != NULL) {
2171
      if (strcmp(tmp, d->alias) == 0) {
2172
        ifdef++;
2173
        return SUCCEEDED;
2174
      }
2175
      d = d->next;
2176
    }
2177
 
2178
    return find_next_point("IFDEF");
2179
  }
2180
 
2181
  /* IF */
2182
 
2183
  if (strcmp(cp, "IF") == 0) {
2184
 
2185
    char k[256];
2186
    int y, o, s;
2187
 
2188
 
2189
    q = input_number();
2190
    if (q != SUCCEEDED && q != INPUT_NUMBER_STRING) {
2191
      sprintf(emsg, ".IF needs immediate data.\n");
2192
      print_error(emsg, ERROR_INP);
2193
      return FAILED;
2194
    }
2195
 
2196
    strncpy(k, label, 255);
2197
    k[255] = 0;
2198
    y = d;
2199
    s = q;
2200
 
2201
    if (get_next_token() == FAILED)
2202
      return FAILED;
2203
 
2204
    if (strcmp(tmp, "<") == 0)
2205
      o = 0;
2206
    else if (strcmp(tmp, ">") == 0)
2207
      o = 1;
2208
    else if (strcmp(tmp, "==") == 0)
2209
      o = 2;
2210
    else if (strcmp(tmp, "!=") == 0)
2211
      o = 3;
2212
    else if (strcmp(tmp, ">=") == 0)
2213
      o = 4;
2214
    else if (strcmp(tmp, "<=") == 0)
2215
      o = 5;
2216
    else {
2217
      print_error(".IF needs an operator. Supported operators are '<', '>', '>=', '<=', '!=' and '=='.\n", ERROR_INP);
2218
      return FAILED;
2219
    }
2220
 
2221
    q = input_number();
2222
    if (q != SUCCEEDED && q != INPUT_NUMBER_STRING) {
2223
      sprintf(emsg, ".IF needs immediate data.\n");
2224
      print_error(emsg, ERROR_INP);
2225
      return FAILED;
2226
    }
2227
 
2228
    /* different types? */
2229
    if (s != q) {
2230
      print_error("Cannot compare strings with immediate values.\n", ERROR_INP);
2231
      return FAILED;
2232
    }
2233
 
2234
    /* values? */
2235
    if (s == SUCCEEDED) {
2236
      if ((o == 0 && y < d) || (o == 1 && y > d) || (o == 2 && y == d) || (o == 3 && y != d) || (o == 4 && y >= d) || (o == 5 && y <= d))
2237
        q = SUCCEEDED;
2238
      else
2239
        q = FAILED;
2240
    }
2241
    /* strings? */
2242
    else {
2243
      if ((o == 0 && strcmp(k, label) < 0) || (o == 1 && strcmp(k, label) > 0) || (o == 2 && strcmp(k, label) == 0) || (o == 3 && strcmp(k, label) != 0) || (o == 4 && strcmp(k, label) >= 0) || (o == 5 && strcmp(k, label) <= 0))
2244
        q = SUCCEEDED;
2245
      else
2246
        q = FAILED;
2247
    }
2248
 
2249
    if (q == SUCCEEDED) {
2250
      ifdef++;
2251
      return SUCCEEDED;
2252
    }
2253
    else
2254
      return find_next_point("IF");
2255
  }
2256
 
2257
  /* IFGR/IFLE/IFEQ/IFNEQ/IFGREQ/IFLEEQ */
2258
 
2259
  if (strcmp(cp, "IFGR") == 0 || strcmp(cp, "IFLE") == 0 || strcmp(cp, "IFEQ") == 0 || strcmp(cp, "IFNEQ") == 0 || strcmp(cp, "IFGREQ") == 0 || strcmp(cp, "IFLEEQ") == 0) {
2260
 
2261
    char k[256];
2262
    int y, o, s;
2263
 
2264
 
2265
    strcpy(bak, cp);
2266
 
2267
    if (strcmp(&cp[2], "LE") == 0)
2268
      o = 0;
2269
    else if (strcmp(&cp[2], "GR") == 0)
2270
      o = 1;
2271
    else if (strcmp(&cp[2], "EQ") == 0)
2272
      o = 2;
2273
    else if (strcmp(&cp[2], "NEQ") == 0)
2274
      o = 3;
2275
    else if (strcmp(&cp[2], "GREQ") == 0)
2276
      o = 4;
2277
    else
2278
      o = 5;
2279
 
2280
    q = input_number();
2281
    if (q != SUCCEEDED && q != INPUT_NUMBER_STRING) {
2282
      sprintf(emsg, ".%s needs immediate data.\n", bak);
2283
      print_error(emsg, ERROR_INP);
2284
      return FAILED;
2285
    }
2286
 
2287
    strncpy(k, label, 255);
2288
    k[255] = 0;
2289
    y = d;
2290
    s = q;
2291
 
2292
    q = input_number();
2293
    if (q != SUCCEEDED && q != INPUT_NUMBER_STRING) {
2294
      sprintf(emsg, ".%s needs immediate data.\n", bak);
2295
      print_error(emsg, ERROR_INP);
2296
      return FAILED;
2297
    }
2298
 
2299
    /* different types? */
2300
    if (s != q) {
2301
      print_error("Cannot compare strings with immediate values.\n", ERROR_INP);
2302
      return FAILED;
2303
    }
2304
 
2305
    /* values? */
2306
    if (s == SUCCEEDED) {
2307
      if ((o == 0 && y < d) || (o == 1 && y > d) || (o == 2 && y == d) || (o == 3 && y != d) || (o == 4 && y >= d) || (o == 5 && y <= d))
2308
        q = SUCCEEDED;
2309
      else
2310
        q = FAILED;
2311
    }
2312
    /* strings? */
2313
    else {
2314
      if ((o == 0 && strcmp(k, label) < 0) || (o == 1 && strcmp(k, label) > 0) || (o == 2 && strcmp(k, label) == 0) || (o == 3 && strcmp(k, label) != 0) || (o == 4 && strcmp(k, label) >= 0) || (o == 5 && strcmp(k, label) <= 0))
2315
        q = SUCCEEDED;
2316
      else
2317
        q = FAILED;
2318
    }
2319
 
2320
    if (q == SUCCEEDED) {
2321
      ifdef++;
2322
      return SUCCEEDED;
2323
    }
2324
    else {
2325
      strcpy(k, cp);
2326
      return find_next_point(k);
2327
    }
2328
  }
2329
 
2330
  /* IFEXISTS */
2331
 
2332
  if (strcmp(cp, "IFEXISTS") == 0) {
2333
 
2334
    FILE *f;
2335
 
2336
 
2337
    inz = input_number();
2338
 
2339
    if (inz != INPUT_NUMBER_STRING) {
2340
      print_error(".IFEXISTS needs a file name string.\n", ERROR_DIR);
2341
      return FAILED;
2342
    }
2343
 
2344
    f = fopen(label, "r");
2345
    if (f == NULL)
2346
      return find_next_point("IFEXISTS");
2347
 
2348
    fclose(f);
2349
    ifdef++;
2350
 
2351
    return SUCCEEDED;
2352
  }
2353
 
2354
  /* IFNDEF */
2355
 
2356
  if (strcmp(cp, "IFNDEF") == 0) {
2357
 
2358
    struct definition *d;
2359
 
2360
 
2361
    if (get_next_token() == FAILED)
2362
      return FAILED;
2363
 
2364
    d = defines;
2365
    while (d != NULL) {
2366
      if (strcmp(tmp, d->alias) == 0) {
2367
        strcpy(emsg, cp);
2368
        return find_next_point(emsg);
2369
      }
2370
      d = d->next;
2371
    }
2372
 
2373
    ifdef++;
2374
    return SUCCEEDED;
2375
  }
2376
 
2377
  /* IFDEFM/IFNDEFM */
2378
 
2379
  if (strcmp(cp, "IFDEFM") == 0 || strcmp(cp, "IFNDEFM") == 0) {
2380
 
2381
    int k, o;
2382
    char e;
2383
 
2384
 
2385
    strcpy(bak, cp);
2386
 
2387
    if (macro_active == 0) {
2388
      sprintf(emsg, ".%s can be only used inside a macro.\n", bak);
2389
      print_error(emsg, ERROR_DIR);
2390
      return FAILED;
2391
    }
2392
 
2393
    if (cp[2] == 'N')
2394
      o = 0;
2395
    else
2396
      o = 1;
2397
 
2398
    for (; i < size; i++) {
2399
 
2400
      if (buffer[i] == 0x0A)
2401
        break;
2402
      else if (buffer[i] == '\\') {
2403
        e = buffer[++i];
2404
        if (e >= '0' && e <= '9') {
2405
          d = (e - '0') * 10;
2406
          for (k = 2; k < 8; k++, d *= 10) {
2407
            e = buffer[++i];
2408
            if (e >= '0' && e <= '9')
2409
              d += e - '0';
2410
            else
2411
              break;
2412
          }
2413
 
2414
          d /= 10;
2415
          if ((o == 0 && macro_runtime_current->supplied_arguments < d) ||
2416
              (o == 1 && macro_runtime_current->supplied_arguments >= d)) {
2417
            ifdef++;
2418
            return SUCCEEDED;
2419
          }
2420
          else {
2421
            strcpy(emsg, cp);
2422
            return find_next_point(emsg);
2423
          }
2424
        }
2425
        break;
2426
      }
2427
    }
2428
 
2429
    sprintf(emsg, ".%s needs an argument.\n", bak);
2430
    print_error(emsg, ERROR_DIR);
2431
    return FAILED;
2432
  }
2433
 
2434
  /* FOPEN */
2435
 
2436
  if (strcmp(cp, "FOPEN") == 0) {
2437
 
2438
    struct filepointer *f;
2439
    char *c;
2440
 
2441
 
2442
    o = input_number();
2443
    if (o != INPUT_NUMBER_STRING) {
2444
      print_error(".FOPEN needs a file name string.\n", ERROR_DIR);
2445
      return FAILED;
2446
    }
2447
 
2448
    /* convert the path to local enviroment */
2449
    localize_path(label);
2450
 
2451
    c = malloc(strlen(label) + 1);
2452
    if (c == NULL) {
2453
      print_error("Out of memory error.\n", ERROR_DIR);
2454
      return FAILED;
2455
    }
2456
    strcpy(c, label);
2457
 
2458
    /* get the file pointer name */
2459
    if (get_next_token() == FAILED)
2460
      return FAILED;
2461
 
2462
    /* is it defined already? */
2463
    f = filepointers;
2464
    while (f != NULL) {
2465
      if (strcmp(tmp, f->name) == 0)
2466
        break;
2467
      f = f->next;
2468
    }
2469
 
2470
    if (f != NULL) {
2471
      /* it exists already! close the old handle and open the new one. */
2472
      if (f->f != NULL) {
2473
        fclose(f->f);
2474
        f->f = NULL;
2475
      }
2476
      if (f->filename != NULL) {
2477
        free(f->filename);
2478
        f->filename = NULL;
2479
      }
2480
    }
2481
    else {
2482
      /* allocate a new filepointer */
2483
      f = malloc(sizeof(struct filepointer));
2484
      if (f == NULL) {
2485
        print_error("Out of memory error.\n", ERROR_DIR);
2486
        return FAILED;
2487
      }
2488
 
2489
      f->f = NULL;
2490
      f->filename = NULL;
2491
      f->next = filepointers;
2492
      filepointers = f;
2493
    }
2494
 
2495
    f->filename = c;
2496
    strcpy(f->name, tmp);
2497
 
2498
    /* open the file */
2499
    f->f = fopen(f->filename, "rb");
2500
    if (f->f == NULL) {
2501
      sprintf(emsg, "Error opening file \"%s\" for reading.\n", f->filename);
2502
      print_error(emsg, ERROR_DIR);
2503
      return FAILED;
2504
    }
2505
 
2506
    return SUCCEEDED;
2507
  }
2508
 
2509
  /* FCLOSE */
2510
 
2511
  if (strcmp(cp, "FCLOSE") == 0) {
2512
 
2513
    struct filepointer *f, **t;
2514
 
2515
 
2516
    /* get the file pointer name */
2517
    if (get_next_token() == FAILED)
2518
      return FAILED;
2519
 
2520
    f = filepointers;
2521
    t = &filepointers;
2522
    while (f != NULL) {
2523
      if (strcmp(tmp, f->name) == 0)
2524
        break;
2525
      t = &(f->next);
2526
      f = f->next;
2527
    }
2528
 
2529
    if (f == NULL) {
2530
      sprintf(emsg, "Couldn't find filepointer \"%s\".\n", tmp);
2531
      print_error(emsg, ERROR_DIR);
2532
      return FAILED;
2533
    }
2534
 
2535
    /* close the file pointer */
2536
    if (f->f != NULL) {
2537
      fclose(f->f);
2538
      f->f = NULL;
2539
    }
2540
    *t = f->next;
2541
 
2542
    free(f->filename);
2543
    free(f);
2544
 
2545
    return SUCCEEDED;
2546
  }
2547
 
2548
  /* FSIZE */
2549
 
2550
  if (strcmp(cp, "FSIZE") == 0) {
2551
 
2552
    struct filepointer *f;
2553
    long l, b;
2554
 
2555
 
2556
    /* get the file pointer name */
2557
    if (get_next_token() == FAILED)
2558
      return FAILED;
2559
 
2560
    /* fetch the file pointer */
2561
    f = filepointers;
2562
    while (f != NULL) {
2563
      if (strcmp(tmp, f->name) == 0)
2564
        break;
2565
      f = f->next;
2566
    }
2567
 
2568
    if (f == NULL) {
2569
      sprintf(emsg, "Couldn't find filepointer \"%s\".\n", tmp);
2570
      print_error(emsg, ERROR_DIR);
2571
      return FAILED;
2572
    }
2573
 
2574
    l = ftell(f->f);
2575
    fseek(f->f, 0, SEEK_END);
2576
    b = ftell(f->f);
2577
    fseek(f->f, l, SEEK_SET);
2578
 
2579
    /* get the definition label */
2580
    if (get_next_token() == FAILED)
2581
      return FAILED;
2582
 
2583
    add_a_new_definition(tmp, (double)b, NULL, DEFINITION_TYPE_VALUE, 0);
2584
 
2585
    return SUCCEEDED;
2586
  }
2587
 
2588
  /* FREAD */
2589
 
2590
  if (strcmp(cp, "FREAD") == 0) {
2591
 
2592
    struct filepointer *f;
2593
    unsigned char c;
2594
 
2595
 
2596
    /* get the file pointer name */
2597
    if (get_next_token() == FAILED)
2598
      return FAILED;
2599
 
2600
    f = filepointers;
2601
    while (f != NULL) {
2602
      if (strcmp(tmp, f->name) == 0)
2603
        break;
2604
      f = f->next;
2605
    }
2606
 
2607
    if (f == NULL) {
2608
      sprintf(emsg, "Couldn't find filepointer \"%s\".\n", tmp);
2609
      print_error(emsg, ERROR_DIR);
2610
      return FAILED;
2611
    }
2612
 
2613
    fscanf(f->f, "%c", &c);
2614
 
2615
    /* get the definition label */
2616
    if (get_next_token() == FAILED)
2617
      return FAILED;
2618
 
2619
    redefine(tmp, (double)c, NULL, DEFINITION_TYPE_VALUE, 0);
2620
 
2621
    return SUCCEEDED;
2622
  }
2623
 
2624
  /* BLOCK */
2625
 
2626
  if (strcmp(cp, "BLOCK") == 0) {
2627
    if ((ind = get_next_token()) == FAILED)
2628
      return FAILED;
2629
 
2630
    if (ind != GET_NEXT_TOKEN_STRING) {
2631
      print_error(".BLOCK requires a name string.\n", ERROR_DIR);
2632
      return FAILED;
2633
    }
2634
 
2635
    block_status++;
2636
    fprintf(file_out_ptr, "g%s ", tmp);
2637
 
2638
    return SUCCEEDED;
2639
  }
2640
 
2641
  /* ENDB */
2642
 
2643
  if (strcmp(cp, "ENDB") == 0) {
2644
 
2645
    if (block_status <= 0) {
2646
      print_error("There is no open .BLOCK.\n", ERROR_DIR);
2647
      return FAILED;
2648
    }
2649
 
2650
    block_status--;
2651
    fprintf(file_out_ptr, "G ");
2652
 
2653
    return SUCCEEDED;
2654
  }
2655
 
2656
  /* SHIFT */
2657
 
2658
  if (strcmp(cp, "SHIFT") == 0) {
2659
 
2660
    struct macro_argument *ma;
2661
    struct macro_runtime *rt;
2662
    struct macro_static *st;
2663
 
2664
 
2665
    if (macro_active == 0) {
2666
      print_error(".SHIFT can only be used inside a MACRO.\n", ERROR_DIR);
2667
      return FAILED;
2668
    }
2669
 
2670
    rt = &macro_stack[macro_active - 1];
2671
    st = rt->macro;
2672
 
2673
    if (st->nargument_names <= rt->supplied_arguments)
2674
      o = st->nargument_names;
2675
    else
2676
      o = rt->supplied_arguments;
2677
 
2678
    /* free the argument definitions */
2679
    for (q = 0; q < o; q++)
2680
      undefine(st->argument_names[q]);
2681
 
2682
    /* free the first argument data */
2683
    free(rt->argument_data[0]);
2684
 
2685
    /* shift the arguments one down */
2686
    for (q = 0; q < rt->supplied_arguments - 1; q++)
2687
      rt->argument_data[q] = rt->argument_data[q + 1];
2688
 
2689
    /* remove the last one */
2690
    rt->argument_data[q] = NULL;
2691
    rt->supplied_arguments--;
2692
 
2693
    if (st->nargument_names <= rt->supplied_arguments)
2694
      o = st->nargument_names;
2695
    else
2696
      o = rt->supplied_arguments;
2697
 
2698
    /* redo the definitions if any */
2699
    for (q = 0; q < o; q++) {
2700
      ma = rt->argument_data[q];
2701
      if (ma->type == SUCCEEDED)
2702
        redefine(st->argument_names[q], (double)ma->value, NULL, DEFINITION_TYPE_VALUE, 0);
2703
      else if (ma->type == INPUT_NUMBER_STACK)
2704
        redefine(st->argument_names[q], (double)ma->value, NULL, DEFINITION_TYPE_STACK, 0);
2705
      else if (ma->type == INPUT_NUMBER_ADDRESS_LABEL)
2706
        redefine(st->argument_names[q], 0.0, ma->string, DEFINITION_TYPE_STRING, strlen(ma->string));
2707
      else if (ma->type == INPUT_NUMBER_STRING)
2708
        redefine(st->argument_names[q], 0.0, ma->string, DEFINITION_TYPE_STRING, strlen(ma->string));
2709
    }
2710
 
2711
    /* redefine NARGS */
2712
    if (redefine("NARGS", (double)rt->supplied_arguments, NULL, DEFINITION_TYPE_VALUE, 0) == FAILED)
2713
      return FAILED;
2714
    if (redefine("nargs", (double)rt->supplied_arguments, NULL, DEFINITION_TYPE_VALUE, 0) == FAILED)
2715
      return FAILED;
2716
 
2717
    return SUCCEEDED;
2718
  }
2719
 
2720
  /* ENDS */
2721
 
2722
  if (strcmp(cp, "ENDS") == 0) {
2723
 
2724
    if (section_status == OFF) {
2725
      print_error("There is no open section.\n", ERROR_DIR);
2726
      return FAILED;
2727
    }
2728
 
2729
    section_status = OFF;
2730
    bankheader_status = OFF;
2731
    fprintf(file_out_ptr, "s ");
2732
 
2733
    return SUCCEEDED;
2734
  }
2735
 
2736
  /* ROMBANKS */
2737
 
2738
  if (strcmp(cp, "ROMBANKS") == 0) {
2739
 
2740
    if (output_format == OUTPUT_LIBRARY) {
2741
      print_error("Library files don't take .ROMBANKS.\n", ERROR_DIR);
2742
      return FAILED;
2743
    }
2744
    if (banksize_defined == 0) {
2745
      print_error("No .ROMBANKSIZE defined.\n", ERROR_DIR);
2746
      return FAILED;
2747
    }
2748
 
2749
    q = input_number();
2750
 
2751
    if (q == FAILED)
2752
      return FAILED;
2753
    if (q != SUCCEEDED || d < 1) {
2754
      print_error(".ROMBANKS needs a positive integer value.\n", ERROR_DIR);
2755
      return FAILED;
2756
    }
2757
 
2758
    /* check that the old bank map (smaller) and the new one equal as much as they can */
2759
    if (rombanks_defined != 0) {
2760
      if (rombanks < d)
2761
        inz = rombanks;
2762
      else
2763
        inz = d;
2764
 
2765
      for (ind = 0; ind < inz; ind++) {
2766
        if (banks[ind] != banksize) {
2767
          print_error("The old and the new .ROMBANKMAP's don't match.\n", ERROR_DIR);
2768
          return FAILED;
2769
        }
2770
      }
2771
 
2772
      if (d <= rombanks)
2773
        return SUCCEEDED;
2774
 
2775
      sprintf(emsg, "Upgrading from %d to %d ROM banks.\n", rombanks, d);
2776
      print_error(emsg, ERROR_WRN);
2777
    }
2778
 
2779
    rombanks = d;
2780
    rombanks_defined = 1;
2781
    max_address = d * banksize;
2782
 
2783
    if (rom_banks != NULL)
2784
      free(rom_banks);
2785
    if (rom_banks_usage_table != NULL)
2786
      free(rom_banks_usage_table);
2787
 
2788
    rom_banks = malloc(sizeof(unsigned char) * max_address);
2789
    rom_banks_usage_table = malloc(sizeof(unsigned char) * max_address);
2790
    if (rom_banks == NULL || rom_banks_usage_table == NULL) {
2791
      print_error("Out of memory while allocating ROM banks.\n", ERROR_DIR);
2792
      return FAILED;
2793
    }
2794
 
2795
    memset(rom_banks_usage_table, 0, sizeof(unsigned char) * max_address);
2796
 
2797
    if (banks != NULL)
2798
      free(banks);
2799
    if (bankaddress != NULL)
2800
      free(bankaddress);
2801
 
2802
    banks = malloc(sizeof(int) * rombanks);
2803
    bankaddress = malloc(sizeof(int) * rombanks);
2804
    if (banks == NULL || bankaddress == NULL) {
2805
      print_error("Out of memory while allocating ROM banks.\n", ERROR_DIR);
2806
      return FAILED;
2807
    }
2808
 
2809
    for (inz = 0, ind = 0; ind < d; ind++) {
2810
      banks[ind] = banksize;
2811
      bankaddress[ind] = inz;
2812
      inz += banksize;
2813
    }
2814
 
2815
    return SUCCEEDED;
2816
  }
2817
 
2818
  /* ROMBANKMAP */
2819
 
2820
  if (strcmp(cp, "ROMBANKMAP") == 0) {
2821
 
2822
    int b = 0, a = 0, bt = 0, bt_defined = 0, x, bs = 0, bs_defined = 0;
2823
 
2824
 
2825
    if (output_format == OUTPUT_LIBRARY) {
2826
      print_error("Library files don't take .ROMBANKMAP.\n", ERROR_DIR);
2827
      return FAILED;
2828
    }
2829
 
2830
    /* ROMBANKMAP has been defined previously */
2831
    if (rombankmap_defined != 0 || rombanks_defined != 0) {
2832
      o = 0;
2833
      while ((ind = get_next_token()) == SUCCEEDED) {
2834
        if (strcaselesscmp(tmp, ".ENDRO") == 0) {
2835
          break;
2836
        }
2837
        else if (strcaselesscmp(tmp, "BANKSTOTAL") == 0) {
2838
          q = input_number();
2839
 
2840
          if (q == FAILED)
2841
            return FAILED;
2842
          if (q != SUCCEEDED || d <= 0) {
2843
            print_error("BANKSTOTAL needs a positive value.\n", ERROR_DIR);
2844
            return FAILED;
2845
          }
2846
 
2847
          if (rombanks < d) {
2848
            banks = realloc(banks, sizeof(int) * d);
2849
            bankaddress = realloc(bankaddress, sizeof(int) * d);
2850
            if (banks == NULL || bankaddress == NULL) {
2851
              print_error("Out of memory while allocating ROM banks.\n", ERROR_DIR);
2852
              return FAILED;
2853
            }
2854
          }
2855
 
2856
          bt = d;
2857
          bt_defined = 1;
2858
        }
2859
        else if (strcaselesscmp(tmp, "BANKSIZE") == 0) {
2860
          if (bt_defined == 0) {
2861
            print_error("BANKSTOTAL needs to be defined prior to BANKSIZE.\n", ERROR_DIR);
2862
            return FAILED;
2863
          }
2864
 
2865
          q = input_number();
2866
 
2867
          if (q == FAILED)
2868
            return FAILED;
2869
          if (q != SUCCEEDED || d <= 0) {
2870
            print_error("BANKSIZE needs a positive value.\n", ERROR_DIR);
2871
            return FAILED;
2872
          }
2873
 
2874
          bs = d;
2875
          bs_defined = 1;
2876
        }
2877
        else if (strcaselesscmp(tmp, "BANKS") == 0) {
2878
          if (bs_defined == 0) {
2879
            print_error("BANKSIZE needs to be defined prior to BANKS.\n", ERROR_DIR);
2880
            return FAILED;
2881
          }
2882
 
2883
          q = input_number();
2884
 
2885
          if (q == FAILED)
2886
            return FAILED;
2887
          if (q != SUCCEEDED || d <= 0) {
2888
            print_error("BANKS needs a positive value.\n", ERROR_DIR);
2889
            return FAILED;
2890
          }
2891
 
2892
          for (x = 0; x < d; x++) {
2893
            if (b > bt) {
2894
              print_error("More BANKS than BANKSTOTAL suggests.\n", ERROR_DIR);
2895
              return FAILED;
2896
            }
2897
 
2898
            /* new banks? */
2899
            if (x >= rombanks) {
2900
              banks[o] = bs;
2901
              bankaddress[o] = a;
2902
            }
2903
            /* compare old banks */
2904
            else if (banks[o] != bs) {
2905
              print_error("The old and the new ROMBANKMAPs don't match.\n", ERROR_DIR);
2906
              return FAILED;
2907
            }
2908
 
2909
            o++;
2910
            b++;
2911
            a += bs;
2912
          }
2913
        }
2914
        else {
2915
          ind = FAILED;
2916
          break;
2917
        }
2918
      }
2919
    }
2920
    /* no ROMBANKMAP has been defined */
2921
    else {
2922
      o = 0;
2923
      while ((ind = get_next_token()) == SUCCEEDED) {
2924
        if (strcaselesscmp(tmp, ".ENDRO") == 0)
2925
          break;
2926
        else if (strcaselesscmp(tmp, "BANKSTOTAL") == 0) {
2927
          q = input_number();
2928
 
2929
          if (q == FAILED)
2930
            return FAILED;
2931
          if (q != SUCCEEDED || d <= 0) {
2932
            print_error("BANKSTOTAL needs a positive value.\n", ERROR_DIR);
2933
            return FAILED;
2934
          }
2935
 
2936
          banks = malloc(sizeof(int) * d);
2937
          bankaddress = malloc(sizeof(int) * d);
2938
          if (banks == NULL || bankaddress == NULL) {
2939
            print_error("Out of memory while allocating ROM banks.\n", ERROR_DIR);
2940
            return FAILED;
2941
          }
2942
 
2943
          bt = d;
2944
          bt_defined = 1;
2945
        }
2946
        else if (strcaselesscmp(tmp, "BANKSIZE") == 0) {
2947
          if (bt_defined == 0) {
2948
            print_error("BANKSTOTAL needs to be defined prior to BANKSIZE.\n", ERROR_DIR);
2949
            return FAILED;
2950
          }
2951
 
2952
          q = input_number();
2953
 
2954
          if (q == FAILED)
2955
            return FAILED;
2956
          if (q != SUCCEEDED || d <= 0) {
2957
            print_error("BANKSIZE needs a positive value.\n", ERROR_DIR);
2958
            return FAILED;
2959
          }
2960
 
2961
          bs = d;
2962
          bs_defined = 1;
2963
        }
2964
        else if (strcaselesscmp(tmp, "BANKS") == 0) {
2965
          if (bs_defined == 0) {
2966
            print_error("BANKSIZE needs to be defined prior to BANKS.\n", ERROR_DIR);
2967
            return FAILED;
2968
          }
2969
 
2970
          q = input_number();
2971
 
2972
          if (q == FAILED)
2973
            return FAILED;
2974
          if (q != SUCCEEDED || d <= 0) {
2975
            print_error("BANKS needs a positive value.\n", ERROR_DIR);
2976
            return FAILED;
2977
          }
2978
 
2979
          for (x = 0; x < d; x++) {
2980
            if (b > bt) {
2981
              print_error("More BANKS than BANKSTOTAL suggests.\n", ERROR_DIR);
2982
              return FAILED;
2983
            }
2984
            banks[o] = bs;
2985
            bankaddress[o] = a;
2986
            o++;
2987
            b++;
2988
            a += bs;
2989
          }
2990
        }
2991
        else {
2992
          ind = FAILED;
2993
          break;
2994
        }
2995
      }
2996
    }
2997
 
2998
    if (ind != SUCCEEDED) {
2999
      print_error("Error in .ROMBANKMAP data structure.\n", ERROR_DIR);
3000
      return FAILED;
3001
    }
3002
 
3003
    /* no banks definded? */
3004
    if (bt == 0) {
3005
      print_error("No ROM banks were defined inside the .ROMBANKMAP.\n", ERROR_DIR);
3006
      return FAILED;
3007
    }
3008
    if (bt != b) {
3009
      print_error("Not all ROM banks were defined inside the .ROMBANKMAP.\n", ERROR_DIR);
3010
      return FAILED;
3011
    }
3012
 
3013
    if (rombanks_defined != 0) {
3014
      if (b > rombanks) {
3015
        sprintf(emsg, "Upgrading from %d to %d ROM banks.\n", rombanks, b);
3016
        print_error(emsg, ERROR_WRN);
3017
      }
3018
      else
3019
        return SUCCEEDED;
3020
    }
3021
 
3022
    rombanks = b;
3023
    rombanks_defined = 1;
3024
    for (max_address = 0, q = 0; q < rombanks; q++)
3025
      max_address += banks[q];
3026
 
3027
    if (rom_banks != NULL)
3028
      free(rom_banks);
3029
    if (rom_banks_usage_table != NULL)
3030
      free(rom_banks_usage_table);
3031
 
3032
    rom_banks = malloc(sizeof(unsigned char) * max_address);
3033
    rom_banks_usage_table = malloc(sizeof(unsigned char) * max_address);
3034
    if (rom_banks == NULL || rom_banks_usage_table == NULL) {
3035
      print_error("Out of memory while allocating ROM banks.\n", ERROR_DIR);
3036
      return FAILED;
3037
    }
3038
 
3039
    memset(rom_banks_usage_table, 0, sizeof(unsigned char) * max_address);
3040
    rombankmap_defined = 1;
3041
 
3042
    return SUCCEEDED;
3043
  }
3044
 
3045
  /* MEMORYMAP */
3046
 
3047
  if (strcmp(cp, "MEMORYMAP") == 0) {
3048
 
3049
    int slotsize = 0, slotsize_defined = 0, s = 0;
3050
    slots_amount=0;
3051
 
3052
 
3053
    if (memorymap_defined == 1) {
3054
      print_error(".MEMORYMAP can be defined only once.\n", ERROR_DIR);
3055
      return FAILED;
3056
    }
3057
    if (output_format == OUTPUT_LIBRARY)
3058
      print_error("Libraries don't need .MEMORYMAP.\n", ERROR_WRN);
3059
 
3060
    while ((ind = get_next_token()) == SUCCEEDED) {
3061
      if (strcaselesscmp(tmp, ".ENDME") == 0) {
3062
        if (defaultslot_defined == 0) {
3063
          print_error("No DEFAULTSLOT defined.\n", ERROR_DIR);
3064
          return FAILED;
3065
        }
3066
 
3067
        if (slots[defaultslot].size == 0) {
3068
          sprintf(emsg, "Unknown DEFAULTSLOT %d.\n", defaultslot);
3069
          print_error(emsg, ERROR_DIR);
3070
          return FAILED;
3071
        }
3072
 
3073
        break;
3074
      }
3075
      else if (strcaselesscmp(tmp, "SLOTSIZE") == 0) {
3076
        q = input_number();
3077
 
3078
        if (q == FAILED)
3079
          return FAILED;
3080
        if (q != SUCCEEDED) {
3081
          print_error("SLOTSIZE needs an immediate value.\n", ERROR_DIR);
3082
          return FAILED;
3083
        }
3084
 
3085
        slotsize = d;
3086
        slotsize_defined = 1;
3087
      }
3088
      else if (strcaselesscmp(tmp, "DEFAULTSLOT") == 0) {
3089
        if (defaultslot_defined != 0) {
3090
          print_error("DEFAULTSLOT can be defined only once.\n", ERROR_DIR);
3091
          return FAILED;
3092
        }
3093
 
3094
        q = input_number();
3095
 
3096
        if (q == FAILED)
3097
          return FAILED;
3098
        if (q != SUCCEEDED || d > 255 || d < 0) {
3099
          print_error("DEFAULTSLOT needs an immediate value (0-255) as an ID.\n", ERROR_DIR);
3100
          return FAILED;
3101
        }
3102
 
3103
        defaultslot_defined = 1;
3104
        defaultslot = d;
3105
      }
3106
      else if (strcaselesscmp(tmp, "SLOT") == 0) {
3107
        q = input_number();
3108
 
3109
        if (q == FAILED)
3110
          return FAILED;
3111
        if (q != SUCCEEDED || d > 255 || d < 0) {
3112
          print_error("SLOT needs a positive value (0-255) as an ID.\n", ERROR_DIR);
3113
          return FAILED;
3114
        }
3115
 
3116
        if (s != d) {
3117
          print_error("Error in SLOT's ID. ID's start from 0.\n", ERROR_DIR);
3118
          return FAILED;
3119
        }
3120
 
3121
        o = d;
3122
 
3123
        /* skip "START" if present */
3124
        if (compare_next_token("START", 5) == SUCCEEDED)
3125
          skip_next_token();
3126
 
3127
        q = input_number();
3128
 
3129
        if (q == FAILED)
3130
          return FAILED;
3131
        if (q != SUCCEEDED || d < 0) {
3132
          print_error("The starting address has to be a non-negative value.\n", ERROR_DIR);
3133
          return FAILED;
3134
        }
3135
 
3136
        slots[o].address = d;
3137
 
3138
        /* skip "SIZE" if present */
3139
        if (compare_next_token("SIZE", 4) == SUCCEEDED)
3140
          skip_next_token();
3141
 
3142
        q = input_number();
3143
        if (q == INPUT_NUMBER_EOL) {
3144
          if (slotsize_defined == 0) {
3145
            print_error("SLOTSIZE must be defined if you don't explicitly give the size.\n", ERROR_DIR);
3146
            return FAILED;
3147
          }
3148
 
3149
          next_line();
3150
 
3151
          d = slotsize;
3152
        }
3153
        else {
3154
          if (q == FAILED)
3155
            return FAILED;
3156
          if (q != SUCCEEDED) {
3157
            print_error("The size of the slot needs to be an immediate value.\n", ERROR_DIR);
3158
            return FAILED;
3159
          }
3160
        }
3161
 
3162
        slots[o].size = d;
3163
        slots_amount++;
3164
        s++;
3165
      }
3166
      else {
3167
        ind = FAILED;
3168
        break;
3169
      }
3170
    }
3171
 
3172
    if (ind != SUCCEEDED) {
3173
      print_error("Error in .MEMORYMAP data structure.\n", ERROR_DIR);
3174
      return FAILED;
3175
    }
3176
 
3177
    memorymap_defined=1;
3178
 
3179
    return SUCCEEDED;
3180
  }
3181
 
3182
  /* UNBACKGROUND */
3183
 
3184
  if (strcmp(cp, "UNBACKGROUND") == 0) {
3185
 
3186
    int start, end;
3187
 
3188
 
3189
    if (output_format != OUTPUT_OBJECT) {
3190
      print_error(".UNBACKGROUND can only be used in OBJECT output mode.\n", ERROR_DIR);
3191
      return FAILED;
3192
    }
3193
    if (background_defined == 0) {
3194
      print_error("No .BACKGROUND specified.\n", ERROR_DIR);
3195
      return FAILED;
3196
    }
3197
 
3198
    /* get the starting address */
3199
    q = input_number();
3200
 
3201
    if (q == FAILED)
3202
      return FAILED;
3203
    if (q != SUCCEEDED || q < 0) {
3204
      print_error(".UNBACKGROUND needs the block's starting address.\n", ERROR_DIR);
3205
      return FAILED;
3206
    }
3207
 
3208
    start = d;
3209
 
3210
    /* get the ending address */
3211
    q = input_number();
3212
 
3213
    if (q == FAILED)
3214
      return FAILED;
3215
    if (q != SUCCEEDED || q < 0) {
3216
      print_error(".UNBACKGROUND needs the block's ending address.\n", ERROR_DIR);
3217
      return FAILED;
3218
    }
3219
 
3220
    end = d;
3221
 
3222
    if (end < start) {
3223
      print_error("The block's ending address is smaller than the starting address!\n", ERROR_DIR);
3224
      return FAILED;
3225
    }
3226
    if (start >= max_address) {
3227
      sprintf(emsg, "The block's starting address $%x is beyond the ROM's ending address $%x.\n", start, max_address-1);
3228
      print_error(emsg, ERROR_DIR);
3229
      return FAILED;
3230
    }
3231
    if (end >= max_address) {
3232
      sprintf(emsg, "The block's ending address $%x is beyond the ROM's ending address $%x. Using the ROM's ending address instead.\n", end, max_address-1);
3233
      end = max_address;
3234
      print_error(emsg, ERROR_WRN);
3235
    }
3236
 
3237
    /* clear the memory [start, end] */
3238
    memset(rom_banks + start, 0, end - start + 1);
3239
    memset(rom_banks_usage_table + start, 0, end - start + 1);
3240
 
3241
    return SUCCEEDED;
3242
  }
3243
 
3244
  /* BACKGROUND */
3245
 
3246
  if (strcmp(cp, "BACKGROUND") == 0) {
3247
 
3248
    FILE *file_in_ptr;
3249
 
3250
 
3251
    if (output_format != OUTPUT_OBJECT) {
3252
      print_error(".BACKGROUND can only be used in OBJECT output mode.\n", ERROR_DIR);
3253
      return FAILED;
3254
    }
3255
    if (background_defined == 1) {
3256
      print_error("Only one .BACKGROUND can be specified.\n", ERROR_DIR);
3257
      return FAILED;
3258
    }
3259
 
3260
    q = input_number();
3261
    if (q == FAILED)
3262
      return FAILED;
3263
    if (q != INPUT_NUMBER_STRING) {
3264
      print_error(".BACKGROUND needs a file name string.\n", ERROR_DIR);
3265
      return FAILED;
3266
    }
3267
 
3268
#ifdef abba
3269
    if (memorymap_defined == 0) {
3270
        /* Set up some default values for the PV2 */
3271
        slots[0].address = 0;
3272
        slots[0].size = MAXADDRESS;
3273
        slots_amount++;
3274
        memorymap_defined=1;
3275
    }
3276
#endif
3277
 
3278
    if (rombanks_defined == 0) {
3279
      print_error("No .ROMBANKS defined.\n", ERROR_DIR);
3280
      return FAILED;
3281
    }
3282
 
3283
    create_full_name(include_dir, label);
3284
 
3285
    if ((file_in_ptr = fopen(full_name, "rb")) == NULL) {
3286
      sprintf(emsg, "Error opening .BACKGROUND file \"%s\".\n", full_name);
3287
      print_error(emsg, ERROR_DIR);
3288
      return FAILED;
3289
    }
3290
 
3291
    fseek(file_in_ptr, 0, SEEK_END);
3292
    background_size = ftell(file_in_ptr);
3293
    fseek(file_in_ptr, 0, SEEK_SET);
3294
 
3295
    if (max_address != background_size) {
3296
      sprintf(emsg, ".BACKGROUND file \"%s\" size (%d) and ROM size (%d) don't match.\n", full_name,
3297
              background_size, max_address);
3298
      print_error(emsg, ERROR_DIR);
3299
      return FAILED;
3300
    }
3301
 
3302
    memset(rom_banks_usage_table, 2, max_address);
3303
    fread(rom_banks, 1, max_address, file_in_ptr);
3304
 
3305
    background_defined = 1;
3306
    fclose(file_in_ptr);
3307
 
3308
    return SUCCEEDED;
3309
  }
3310
 
3311
  /* EMPTYFILL */
3312
 
3313
  if (strcmp(cp, "EMPTYFILL") == 0) {
3314
 
3315
    if (output_format == OUTPUT_LIBRARY) {
3316
      print_error("Library files don't take .EMPTYFILL.\n", ERROR_DIR);
3317
      return FAILED;
3318
    }
3319
 
3320
    q = input_number();
3321
 
3322
    if (q == FAILED)
3323
      return FAILED;
3324
    if (q != SUCCEEDED || d < -127 || d > 255) {
3325
      print_error(".EMPTYFILL needs a 8bit value.\n", ERROR_DIR);
3326
      return FAILED;
3327
    }
3328
 
3329
    if (emptyfill_defined != 0) {
3330
      if (emptyfill != d) {
3331
        print_error(".EMPTYFILL was defined for the second time.\n", ERROR_DIR);
3332
        return FAILED;
3333
      }
3334
      return SUCCEEDED;
3335
    }
3336
 
3337
    emptyfill = d;
3338
    emptyfill_defined = 1;
3339
 
3340
    return SUCCEEDED;
3341
  }
3342
 
3343
  /* DEFINE/DEF/EQU */
3344
 
3345
  if (strcmp(cp, "DEFINE") == 0 || strcmp(cp, "DEF") == 0 || strcmp(cp, "EQU") == 0) {
3346
 
3347
    double dou;
3348
    char k[256];
3349
    int j, size;
3350
 
3351
 
3352
    if (get_next_token() == FAILED)
3353
      return FAILED;
3354
 
3355
    /* check the user doesn't try to define reserved labels */
3356
    if (strcmp(tmp, "WLA_TIME") == 0 || strcmp(tmp, "wla_time") == 0 ||
3357
        strcmp(tmp, "WLA_VERSION") == 0 || strcmp(tmp, "wla_version") == 0 ||
3358
        strcmp(tmp, "WLA_FILENAME") == 0 || strcmp(tmp, "wla_filename") == 0 ||
3359
        strcmp(tmp, "NARGS") == 0 || strcmp(tmp, "nargs") == 0 ||
3360
        strcmp(tmp, "CADDR") == 0 || strcmp(tmp, "caddr") == 0) {
3361
 
3362
      sprintf(emsg, "\"%s\" is a reserved definition label and is not user definiable.\n", tmp);
3363
      print_error(emsg, ERROR_DIR);
3364
      return FAILED;
3365
    }
3366
 
3367
    /* skip "=", if present */
3368
    if (compare_next_token("=", 1) == SUCCEEDED)
3369
      skip_next_token();
3370
 
3371
    input_float_mode = ON;
3372
    q = get_new_definition_data(&j, k, &size, &dou);
3373
    input_float_mode = OFF;
3374
    if (q == FAILED)
3375
      return FAILED;
3376
 
3377
    if (!(q == INPUT_NUMBER_EOL || q == INPUT_NUMBER_FLOAT || q == SUCCEEDED || q == INPUT_NUMBER_STRING || q == INPUT_NUMBER_STACK)) {
3378
      print_error("Could not parse the definition data.\n", ERROR_DIR);
3379
      return FAILED;
3380
    }
3381
 
3382
    if (q == SUCCEEDED)
3383
      add_a_new_definition(tmp, (double)j, NULL, DEFINITION_TYPE_VALUE, 0);
3384
    else if (q == INPUT_NUMBER_FLOAT)
3385
      add_a_new_definition(tmp, dou, NULL, DEFINITION_TYPE_VALUE, 0);
3386
    else if (q == INPUT_NUMBER_STRING)
3387
      add_a_new_definition(tmp, 0.0, k, DEFINITION_TYPE_STRING, size);
3388
    else if (q == INPUT_NUMBER_STACK)
3389
      add_a_new_definition(tmp, (double)j, NULL, DEFINITION_TYPE_STACK, 0);
3390
    else if (q == INPUT_NUMBER_EOL) {
3391
      add_a_new_definition(tmp, 0, NULL, DEFINITION_TYPE_VALUE, 0);
3392
      next_line();
3393
    }
3394
 
3395
    return SUCCEEDED;
3396
  }
3397
 
3398
  /* INPUT */
3399
 
3400
  if (strcmp(cp, "INPUT") == 0) {
3401
 
3402
    char k[256];
3403
    int j, v;
3404
 
3405
 
3406
    if (get_next_token() == FAILED)
3407
      return FAILED;
3408
 
3409
    fgets(k, 254, stdin);
3410
 
3411
    for (j = 0; j < 254; j++) {
3412
      if (k[j] == 0)
3413
        break;
3414
      if (k[j] == 0x0A) {
3415
        k[j] = 0;
3416
        break;
3417
      }
3418
      if (k[j] == 0x0D) {
3419
        k[j] = 0;
3420
        break;
3421
      }
3422
    }
3423
 
3424
    if (j == 254) {
3425
      print_error("Error in .INPUT.\n", ERROR_DIR);
3426
      return FAILED;
3427
    }
3428
 
3429
    for (j = 0; j < 254; j++) {
3430
      if (k[j] == 0) {
3431
        print_error("No .INPUT?\n", ERROR_DIR);
3432
        return FAILED;
3433
      }
3434
      if (!(k[j] == ' ' || k[j] == 0x09))
3435
        break;
3436
    }
3437
 
3438
    if (k[j] == '%') {
3439
      v = 0;
3440
      j++;
3441
      for ( ; j < 254; j++) {
3442
        if (k[j] == 0)
3443
          break;
3444
        if (k[j] == '0' || k[j] == '1')
3445
          v = (v << 1) + k[j] - '0';
3446
        else
3447
          break;
3448
      }
3449
      if (k[j] == 0) {
3450
        redefine(tmp, (double)v, NULL, DEFINITION_TYPE_VALUE, 0);
3451
        return SUCCEEDED;
3452
      }
3453
    }
3454
    else if (k[j] == '$') {
3455
      j++;
3456
      v = 0;
3457
      for ( ; j < 254; j++) {
3458
        if (k[j] == 0)
3459
          break;
3460
        if (k[j] >= '0' && k[j] <= '9')
3461
          v = (v << 4) + k[j] - '0';
3462
        else if (k[j] >= 'a' && k[j] <= 'f')
3463
          v = (v << 4) + k[j] - 'a' + 10;
3464
        else if (k[j] >= 'A' && k[j] <= 'F')
3465
          v = (v << 4) + k[j] - 'A' + 10;
3466
        else
3467
          break;
3468
      }
3469
      if (k[j] == 0) {
3470
        redefine(tmp, (double)v, NULL, DEFINITION_TYPE_VALUE, 0);
3471
        return SUCCEEDED;
3472
      }
3473
    }
3474
    else if (k[j] >= '0' && k[j] <= '9') {
3475
      v = 0;
3476
      for ( ; j < 254; j++) {
3477
        if (k[j] == 0)
3478
          break;
3479
        if (k[j] >= '0' && k[j] <= '9')
3480
          v = (v * 10) + k[j] - '0';
3481
        else
3482
          break;
3483
      }
3484
      if (k[j] == 0) {
3485
        redefine(tmp, (double)v, NULL, DEFINITION_TYPE_VALUE, 0);
3486
        return SUCCEEDED;
3487
      }
3488
    }
3489
 
3490
    /* it's a string */
3491
    redefine(tmp, 0.0, k, DEFINITION_TYPE_STRING, strlen(k));
3492
 
3493
    return SUCCEEDED;
3494
  }
3495
 
3496
  /* REDEFINE/REDEF */
3497
 
3498
  if (strcmp(cp, "REDEFINE") == 0 || strcmp(cp, "REDEF") == 0) {
3499
 
3500
    double dou;
3501
    char k[256];
3502
    int j, size;
3503
 
3504
 
3505
    if (get_next_token() == FAILED)
3506
      return FAILED;
3507
 
3508
    /* check the user doesn't try to define reserved labels */
3509
    if (strcmp(tmp, "WLA_TIME") == 0 || strcmp(tmp, "wla_time") == 0 ||
3510
        strcmp(tmp, "WLA_VERSION") == 0 || strcmp(tmp, "wla_version") == 0 ||
3511
        strcmp(tmp, "WLA_FILENAME") == 0 || strcmp(tmp, "wla_filename") == 0 ||
3512
        strcmp(tmp, "NARGS") == 0 || strcmp(tmp, "nargs") == 0 ||
3513
        strcmp(tmp, "CADDR") == 0 || strcmp(tmp, "caddr") == 0) {
3514
 
3515
      sprintf(emsg, "\"%s\" is a reserved definition label and is not user definiable.\n", tmp);
3516
      print_error(emsg, ERROR_DIR);
3517
      return FAILED;
3518
    }
3519
 
3520
    /* skip "=", if present */
3521
    if (compare_next_token("=", 1) == SUCCEEDED)
3522
      skip_next_token();
3523
 
3524
    input_float_mode = ON;
3525
    q = get_new_definition_data(&j, k, &size, &dou);
3526
    input_float_mode = OFF;
3527
    if (q == FAILED)
3528
      return FAILED;
3529
 
3530
    if (!(q == INPUT_NUMBER_FLOAT || q == SUCCEEDED || q == INPUT_NUMBER_STRING || q == INPUT_NUMBER_STACK)) {
3531
      print_error("Could not parse the definition data.\n", ERROR_DIR);
3532
      return FAILED;
3533
    }
3534
 
3535
    if (q == SUCCEEDED)
3536
      redefine(tmp, (double)j, NULL, DEFINITION_TYPE_VALUE, 0);
3537
    else if (q == INPUT_NUMBER_FLOAT)
3538
      redefine(tmp, dou, NULL, DEFINITION_TYPE_VALUE, 0);
3539
    else if (q == INPUT_NUMBER_STRING)
3540
      redefine(tmp, 0.0, k, DEFINITION_TYPE_STRING, size);
3541
    else if (q == INPUT_NUMBER_STACK)
3542
      redefine(tmp, (double)j, NULL, DEFINITION_TYPE_STACK, 0);
3543
 
3544
    return SUCCEEDED;
3545
  }
3546
 
3547
  /* EXPORT */
3548
 
3549
  if (strcmp(cp, "EXPORT") == 0) {
3550
    q = 0;
3551
    while (1) {
3552
      ind = input_next_string();
3553
      if (ind == FAILED)
3554
        return FAILED;
3555
      if (ind == INPUT_NUMBER_EOL) {
3556
        if (q != 0) {
3557
          next_line();
3558
          return SUCCEEDED;
3559
        }
3560
        print_error(".EXPORT requires definition name(s).\n", ERROR_DIR);
3561
        return FAILED;
3562
      }
3563
 
3564
      q++;
3565
 
3566
      if (export_a_definition(tmp) == FAILED)
3567
        return FAILED;
3568
    }
3569
 
3570
    return FAILED;
3571
  }
3572
 
3573
  /* SYM/SYMBOL */
3574
 
3575
  if (strcmp(cp, "SYM") == 0 || strcmp(cp, "SYMBOL") == 0) {
3576
    ind = input_next_string();
3577
    if (ind != SUCCEEDED) {
3578
      print_error(".SYM requires a symbol name.\n", ERROR_DIR);
3579
      return FAILED;
3580
    }
3581
 
3582
    fprintf(file_out_ptr, "Y%s ", tmp);
3583
 
3584
    return SUCCEEDED;
3585
  }
3586
 
3587
  /* BR/BREAKPOINT */
3588
 
3589
  if (strcmp(cp, "BR") == 0 || strcmp(cp, "BREAKPOINT") == 0) {
3590
    fprintf(file_out_ptr, "Z ");
3591
    return SUCCEEDED;
3592
  }
3593
 
3594
  /* ENUM */
3595
 
3596
  if (strcmp(cp, "ENUM") == 0) {
3597
 
3598
    char tmpname[MAX_NAME_LENGTH];
3599
    int exp = NO, ord = 1, type;
3600
 
3601
 
3602
    q = input_number();
3603
    if (q == FAILED)
3604
      return FAILED;
3605
    if (q != SUCCEEDED) {
3606
      print_error(".ENUM needs a starting address.\n", ERROR_DIR);
3607
      return FAILED;
3608
    }
3609
 
3610
    o = d;
3611
 
3612
    /* "ASC" or "DESC"? */
3613
    if (compare_next_token("ASC", 3) == SUCCEEDED) {
3614
      ord = 1;
3615
      skip_next_token();
3616
    }
3617
    else if (compare_next_token("DESC", 4) == SUCCEEDED) {
3618
      ord = -1;
3619
      skip_next_token();
3620
    }
3621
 
3622
    /* do we have "EXPORT" defined? */
3623
    if (compare_next_token("EXPORT", 6) == SUCCEEDED) {
3624
      skip_next_token();
3625
      exp = YES;
3626
    }
3627
 
3628
    while ((t = get_next_token()) != FAILED) {
3629
      if (strcaselesscmp(tmp, ".ENDE") == 0)
3630
        return SUCCEEDED;
3631
      if (tmp[strlen(tmp) - 1] == ':')
3632
        tmp[strlen(tmp) - 1] = 0;
3633
      strcpy(tmpname, tmp);
3634
 
3635
      /* ASC? */
3636
      if (ord == 1) {
3637
        if (add_a_new_definition(tmpname, (double)o, NULL, DEFINITION_TYPE_VALUE, 0) == FAILED)
3638
          return FAILED;
3639
        if (exp == YES)
3640
          if (export_a_definition(tmpname) == FAILED)
3641
            return FAILED;
3642
      }
3643
 
3644
      /* get the size/type */
3645
      if (get_next_token() == FAILED)
3646
        return FAILED;
3647
 
3648
      type = 0;
3649
 
3650
      if (strcaselesscmp(tmp, "DB") == 0 || strcaselesscmp(tmp, "BYT") == 0 || strcaselesscmp(tmp, "BYTE") == 0)
3651
        o += 1*ord;
3652
      else if (strcaselesscmp(tmp, "DW") == 0 || strcaselesscmp(tmp, "WORD") == 0)
3653
        o += 2*ord;
3654
      else if (strcaselesscmp(tmp, "DS") == 0 || strcaselesscmp(tmp, "DSB") == 0) {
3655
        strcpy(bak, tmp);
3656
        q = input_number();
3657
        if (q == FAILED)
3658
          return FAILED;
3659
        if (q != SUCCEEDED) {
3660
          sprintf(emsg, ".%s needs size.\n", bak);
3661
          print_error(emsg, ERROR_DIR);
3662
          return FAILED;
3663
        }
3664
        o += d*ord;
3665
      }
3666
      else if (strcaselesscmp(tmp, "DSW") == 0) {
3667
        q = input_number();
3668
        if (q == FAILED)
3669
          return FAILED;
3670
        if (q != SUCCEEDED) {
3671
          print_error("DSW needs size.\n", ERROR_DIR);
3672
          return FAILED;
3673
        }
3674
        o += d*2*ord;
3675
      }
3676
      /* it's an instance of a structure! */
3677
      else if (strcaselesscmp(tmp, "INSTANCEOF") == 0) {
3678
 
3679
        struct structure_item *si;
3680
        struct structure *st;
3681
        int g;
3682
 
3683
 
3684
        type = 1;
3685
 
3686
        if (get_next_token() == FAILED)
3687
          return FAILED;
3688
 
3689
        st = structures_first;
3690
        while (st != NULL) {
3691
          if (strcmp(st->name, tmp) == 0)
3692
            break;
3693
          st = st->next;
3694
        }
3695
 
3696
        if (st == NULL) {
3697
          sprintf(emsg, "No STRUCT named \"%s\" available.\n", tmp);
3698
          print_error(emsg, ERROR_DIR);
3699
          return FAILED;
3700
        }
3701
 
3702
        /* generate labels (first the basic ones, without index number) */
3703
        if (ord == -1) {
3704
          o -= st->size;
3705
          if (add_a_new_definition(tmpname, (double)o, NULL, DEFINITION_TYPE_VALUE, 0) == FAILED)
3706
            return FAILED;
3707
          if (exp == YES)
3708
            if (export_a_definition(tmpname) == FAILED)
3709
              return FAILED;
3710
        }
3711
 
3712
        si = st->items;
3713
        while (si != NULL) {
3714
          sprintf(tmp, "%s.%s%c", tmpname, si->name, 0);
3715
          if (add_a_new_definition(tmp, (double)o, NULL, DEFINITION_TYPE_VALUE, 0) == FAILED)
3716
            return FAILED;
3717
          if (exp == YES)
3718
            if (export_a_definition(tmp) == FAILED)
3719
              return FAILED;
3720
          o += si->size;
3721
          si = si->next;
3722
        }
3723
 
3724
        if (ord == -1)
3725
          o -= st->size;
3726
 
3727
        /* the number of structures? */
3728
        inz = input_number();
3729
        if (inz == INPUT_NUMBER_EOL)
3730
          next_line();
3731
        else if (inz == SUCCEEDED) {
3732
          if (d < 1) {
3733
            print_error("The number of structures must be greater than 0.\n", ERROR_DIR);
3734
            return FAILED;
3735
          }
3736
 
3737
          /* generate labels (now with the index numbers) */
3738
          if (d > 1) {
3739
            g = 1;
3740
 
3741
            if (ord == 1)
3742
              o -= st->size;
3743
 
3744
            while (d > 0) {
3745
              si = st->items;
3746
              sprintf(tmp, "%s.%d%c", tmpname, g, 0);
3747
              if (add_a_new_definition(tmp, (double)o, NULL, DEFINITION_TYPE_VALUE, 0) == FAILED)
3748
                return FAILED;
3749
              if (exp == YES)
3750
                if (export_a_definition(tmp) == FAILED)
3751
                  return FAILED;
3752
              while (si != NULL) {
3753
                sprintf(tmp, "%s.%d.%s%c", tmpname, g, si->name, 0);
3754
                if (add_a_new_definition(tmp, (double)o, NULL, DEFINITION_TYPE_VALUE, 0) == FAILED)
3755
                  return FAILED;
3756
                if (exp == YES)
3757
                  if (export_a_definition(tmp) == FAILED)
3758
                    return FAILED;
3759
                o += si->size;
3760
                si = si->next;
3761
              }
3762
              g++;
3763
              d--;
3764
              if (ord == -1) {
3765
                if (d > 0)
3766
                  o -= st->size*2;
3767
                else
3768
                  o -= st->size;
3769
              }
3770
            }
3771
          }
3772
        }
3773
        else {
3774
          if (inz == INPUT_NUMBER_STRING)
3775
            sprintf(emsg, "Expected the number of structures, got \"%s\" instead.\n", label);
3776
          else
3777
            sprintf(emsg, "Expected the number of structures.\n");
3778
          print_error(emsg, ERROR_DIR);
3779
          return FAILED;
3780
        }
3781
      }
3782
      else if (tmp[0] == '.' && strcaselesscmp(tmp, ".ENDE") != 0)
3783
        ;
3784
      else {
3785
        sprintf(emsg, "Unexpected symbol \"%s\" in .ENUM.\n", tmp);
3786
        print_error(emsg, ERROR_DIR);
3787
        return FAILED;
3788
      }
3789
 
3790
      /* DESC? */
3791
      if (ord == -1 && type == 0) {
3792
        if (add_a_new_definition(tmpname, (double)o, NULL, DEFINITION_TYPE_VALUE, 0) == FAILED)
3793
          return FAILED;
3794
        if (exp == YES)
3795
          if (export_a_definition(tmpname) == FAILED)
3796
            return FAILED;
3797
      }
3798
    }
3799
 
3800
    return FAILED;
3801
  }
3802
 
3803
 
3804
  /* MACRO */
3805
 
3806
  if (strcmp(cp, "MACRO") == 0) {
3807
 
3808
    struct macro_static *m;
3809
    int macro_start;
3810
 
3811
 
3812
    if (get_next_token() == FAILED)
3813
      return FAILED;
3814
 
3815
    macro_start = active_file_info_last->line_current;
3816
 
3817
    m = macros_first;
3818
    while (m != NULL) {
3819
      if (strcmp(tmp, m->name) == 0) {
3820
        sprintf(emsg, "MACRO \"%s\" was defined for the second time.\n", tmp);
3821
        print_error(emsg, ERROR_DIR);
3822
        return FAILED;
3823
      }
3824
      m = m->next;
3825
    }
3826
 
3827
    m = malloc(sizeof(struct macro_static));
3828
    if (m == NULL) {
3829
      print_error("Out of memory while allocating room for a new MACRO.\n", ERROR_DIR);
3830
      return FAILED;
3831
    }
3832
 
3833
    if (macros_first == NULL) {
3834
      macros_first = m;
3835
      macros_last = m;
3836
    }
3837
    else {
3838
      macros_last->next = m;
3839
      macros_last = m;
3840
    }
3841
 
3842
    strcpy(m->name, tmp);
3843
    m->next = NULL;
3844
    m->calls = 0;
3845
    m->filename_id = active_file_info_last->filename_id;
3846
    m->argument_names = NULL;
3847
 
3848
    /* is ARGS defined? */
3849
    q = 0;
3850
    if (compare_next_token("ARGS", 4) == SUCCEEDED) {
3851
      skip_next_token();
3852
 
3853
      while (1) {
3854
        ind = input_next_string();
3855
        if (ind == FAILED)
3856
          return FAILED;
3857
        if (ind == INPUT_NUMBER_EOL) {
3858
          if (q != 0) {
3859
            next_line();
3860
            break;
3861
          }
3862
          sprintf(emsg, "MACRO \"%s\" is missing argument names?\n", m->name);
3863
          print_error(emsg, ERROR_DIR);
3864
          return FAILED;
3865
        }
3866
        q++;
3867
 
3868
        /* store the label */
3869
        m->argument_names = realloc(m->argument_names, sizeof(char *)*q);
3870
        if (m->argument_names == NULL) {
3871
          print_error("Out of memory error.\n", ERROR_NONE);
3872
          return FAILED;
3873
        }
3874
        m->argument_names[q-1] = malloc(strlen(tmp)+1);
3875
        if (m->argument_names[q-1] == NULL) {
3876
          print_error("Out of memory error.\n", ERROR_NONE);
3877
          return FAILED;
3878
        }
3879
 
3880
        strcpy(m->argument_names[q-1], tmp);
3881
      }
3882
    }
3883
 
3884
    m->nargument_names = q;
3885
    m->start = i;
3886
    m->start_line = active_file_info_last->line_current;
3887
 
3888
    /* go to the end of the macro */
3889
    for (; i < size; i++) {
3890
      if (buffer[i] == 0x0A) {
3891
        next_line();
3892
        continue;
3893
      }
3894
      else if ((strncmp(&buffer[i], ".E", 2) == 0) && (buffer[i + 2] == 0x0A || buffer[i + 2] == ' ')) {
3895
        active_file_info_last->line_current = macro_start;
3896
        sprintf(emsg, "MACRO \"%s\" wasn't terminated with .ENDM.\n", m->name);
3897
        print_error(emsg, ERROR_DIR);
3898
        return FAILED;
3899
      }
3900
      else if ((strncmp(&buffer[i], ".ENDM", 5) == 0 || strncmp(&buffer[i], ".endm", 5) == 0) && (buffer[i + 5] == 0x0A || buffer[i + 5] == ' ')) {
3901
        i += 5;
3902
        break;
3903
      }
3904
    }
3905
 
3906
    return SUCCEEDED;
3907
  }
3908
 
3909
  /* REPT/REPEAT */
3910
 
3911
  if (strcmp(cp, "REPT") == 0 || strcmp(cp, "REPEAT") == 0) {
3912
 
3913
    char c[16];
3914
 
3915
 
3916
    strcpy(c, cp);
3917
 
3918
    q = input_number();
3919
    if (q == FAILED)
3920
      return FAILED;
3921
    if (q != SUCCEEDED) {
3922
      sprintf(emsg, ".%s needs a count.\n", c);
3923
      print_error(emsg, ERROR_INP);
3924
      return FAILED;
3925
    }
3926
 
3927
    if (d < 0) {
3928
      sprintf(emsg, ".%s count value must be positive or zero.\n", c);
3929
      print_error(emsg, ERROR_DIR);
3930
      return FAILED;
3931
    }
3932
 
3933
    if (d == 0) {
3934
      int l, r, m;
3935
 
3936
      l = active_file_info_last->line_current;
3937
      /* find the next compiling point */
3938
      r = 1;
3939
      m = macro_active;
3940
      /* disable macro decoding */
3941
      macro_active = 0;
3942
      while (get_next_token() != FAILED) {
3943
        if (tmp[0] == '.') {
3944
          if (strcmp(cp, "ENDR") == 0)
3945
            r--;
3946
          if (strcmp(cp, "E") == 0)
3947
            break;
3948
          if (strcmp(cp, "REPT") == 0 || strcmp(cp, "REPEAT") == 0)
3949
            r++;
3950
        }
3951
        if (r == 0) {
3952
          macro_active = m;
3953
          return SUCCEEDED;
3954
        }
3955
      }
3956
 
3957
      /* return the condition's line number */
3958
      active_file_info_last->line_current = l;
3959
      sprintf(emsg, ".%s must end to .ENDR.\n", c);
3960
      print_error(emsg, ERROR_DIR);
3961
      return FAILED;
3962
    }
3963
 
3964
    if (repeat_active == repeat_stack_size) {
3965
      struct repeat_runtime *rr;
3966
 
3967
      repeat_stack_size = (repeat_stack_size<<1)+2;
3968
      rr = realloc(repeat_stack, sizeof(struct repeat_runtime) * repeat_stack_size);
3969
      if (rr == NULL) {
3970
        print_error("Out of memory error while enlarging repeat stack buffer.\n", ERROR_ERR);
3971
        return FAILED;
3972
      }
3973
      repeat_stack = rr;
3974
    }
3975
 
3976
    repeat_stack[repeat_active].start = i;
3977
    repeat_stack[repeat_active].counter = d;
3978
    repeat_stack[repeat_active].start_line = active_file_info_last->line_current;
3979
 
3980
    repeat_active++;
3981
 
3982
    return SUCCEEDED;
3983
  }
3984
 
3985
  /* ENDR */
3986
 
3987
  if (strcmp(cp, "ENDR") == 0) {
3988
 
3989
    if (repeat_active == 0) {
3990
      print_error("There is no open repetition.\n", ERROR_DIR);
3991
      return FAILED;
3992
    }
3993
 
3994
    repeat_stack[repeat_active - 1].counter--;
3995
    if (repeat_stack[repeat_active - 1].counter == 0) {
3996
      repeat_active--;
3997
      return SUCCEEDED;
3998
    }
3999
 
4000
    i = repeat_stack[repeat_active - 1].start;
4001
    active_file_info_last->line_current = repeat_stack[repeat_active - 1].start_line;
4002
 
4003
    return SUCCEEDED;
4004
  }
4005
 
4006
  /* E */
4007
 
4008
  if (strcmp(cp, "E") == 0) {
4009
    if (active_file_info_last != NULL) {
4010
      active_file_info_tmp = active_file_info_last;
4011
      active_file_info_last = active_file_info_last->prev;
4012
      free(active_file_info_tmp);
4013
      if (active_file_info_last == NULL)
4014
        active_file_info_first = NULL;
4015
      else
4016
        fprintf(file_out_ptr, "f%d ", active_file_info_last->filename_id);
4017
    }
4018
    fprintf(file_out_ptr, "E ");
4019
    open_files--;
4020
    if (open_files == 0)
4021
      return EVALUATE_TOKEN_EOP;
4022
 
4023
    if (extra_definitions == ON) {
4024
      redefine("WLA_FILENAME", 0.0, get_file_name(active_file_info_last->filename_id), DEFINITION_TYPE_STRING,
4025
               strlen(get_file_name(active_file_info_last->filename_id)));
4026
      redefine("wla_filename", 0.0, get_file_name(active_file_info_last->filename_id), DEFINITION_TYPE_STRING,
4027
               strlen(get_file_name(active_file_info_last->filename_id)));
4028
    }
4029
 
4030
    return SUCCEEDED;
4031
  }
4032
 
4033
  /* M */
4034
 
4035
  if (strcmp(cp, "M") == 0) {
4036
    if (line_count_status == OFF)
4037
      line_count_status = ON;
4038
    else
4039
      line_count_status = OFF;
4040
    return SUCCEEDED;
4041
  }
4042
 
4043
  /* ROMBANKSIZE */
4044
 
4045
  if (strcmp(cp, "ROMBANKSIZE") == 0 || strcmp(cp, "BANKSIZE") == 0) {
4046
    q = input_number();
4047
 
4048
    if (q == FAILED)
4049
      return FAILED;
4050
    if (q != SUCCEEDED || d < 0) {
4051
      print_error(".ROMBANKSIZE needs a positive integer value.\n", ERROR_DIR);
4052
      return FAILED;
4053
    }
4054
 
4055
    if (banksize_defined != 0) {
4056
      if (banksize != d) {
4057
        print_error(".ROMBANKSIZE was defined for the second time.\n", ERROR_DIR);
4058
        return FAILED;
4059
      }
4060
      return SUCCEEDED;
4061
    }
4062
 
4063
    banksize = d;
4064
    banksize_defined = 1;
4065
 
4066
    return SUCCEEDED;
4067
  }
4068
 
4069
  /* ENDM */
4070
 
4071
  if (strcmp(cp, "ENDM") == 0) {
4072
    if (macro_active != 0) {
4073
      macro_active--;
4074
 
4075
      /* free the arguments */
4076
      if (macro_stack[macro_active].supplied_arguments > 0) {
4077
        for (d = 0; d < macro_stack[macro_active].supplied_arguments; d++)
4078
          free(macro_stack[macro_active].argument_data[d]);
4079
        free(macro_stack[macro_active].argument_data);
4080
        macro_stack[macro_active].argument_data = NULL;
4081
      }
4082
 
4083
      /* free the argument definitions */
4084
      for (q = 0; q < macro_stack[macro_active].macro->nargument_names; q++)
4085
        undefine(macro_stack[macro_active].macro->argument_names[q]);
4086
 
4087
      i = macro_stack[macro_active].macro_end;
4088
 
4089
      if ((extra_definitions == ON) && (active_file_info_last->filename_id != macro_stack[macro_active].macro_end_filename_id)) {
4090
        redefine("WLA_FILENAME", 0.0, get_file_name(macro_stack[macro_active].macro_end_filename_id), DEFINITION_TYPE_STRING,
4091
                 strlen(get_file_name(macro_stack[macro_active].macro_end_filename_id)));
4092
        redefine("wla_filename", 0.0, get_file_name(macro_stack[macro_active].macro_end_filename_id), DEFINITION_TYPE_STRING,
4093
                 strlen(get_file_name(macro_stack[macro_active].macro_end_filename_id)));
4094
      }
4095
 
4096
      active_file_info_last->filename_id = macro_stack[macro_active].macro_end_filename_id;
4097
      active_file_info_last->line_current = macro_stack[macro_active].macro_end_line;
4098
 
4099
      /* was this the last macro called? */
4100
      if (macro_active == 0) {
4101
        /* delete NARGS */
4102
        undefine("NARGS");
4103
        undefine("nargs");
4104
 
4105
        macro_runtime_current = NULL;
4106
 
4107
        return SUCCEEDED;
4108
      }
4109
 
4110
      /* redefine NARGS */
4111
      if (redefine("NARGS", (double)macro_stack[macro_active - 1].supplied_arguments, NULL, DEFINITION_TYPE_VALUE, 0) == FAILED)
4112
        return FAILED;
4113
      if (redefine("nargs", (double)macro_stack[macro_active - 1].supplied_arguments, NULL, DEFINITION_TYPE_VALUE, 0) == FAILED)
4114
        return FAILED;
4115
 
4116
      macro_runtime_current = &macro_stack[macro_active - 1];
4117
 
4118
      return SUCCEEDED;
4119
    }
4120
 
4121
    return EVALUATE_TOKEN_NOT_IDENTIFIED;
4122
  }
4123
 
4124
 
4125
  /* 8BIT */
4126
 
4127
  if (strcmp(cp, "8BIT") == 0) {
4128
    xbit_size = 8;
4129
    return SUCCEEDED;
4130
  }
4131
 
4132
  /* 16BIT */
4133
 
4134
  if (strcmp(cp, "16BIT") == 0) {
4135
    xbit_size = 16;
4136
    return SUCCEEDED;
4137
  }
4138
 
4139
 
4140
  /* PRINTT */
4141
 
4142
  if (strcmp(cp, "PRINTT") == 0) {
4143
 
4144
    char t[256];
4145
    int s, u;
4146
 
4147
 
4148
    inz = input_number();
4149
 
4150
    if (inz != INPUT_NUMBER_STRING) {
4151
      print_error(".PRINTT needs a string.\n", ERROR_DIR);
4152
      return FAILED;
4153
    }
4154
 
4155
    for (s = 0, u = 0; label[s] != 0;) {
4156
      if (label[s] == '\\' && label[s + 1] == 'n') {
4157
#ifdef MSDOS
4158
        t[u++] = '\r';
4159
        t[u++] = '\n';
4160
#else
4161
        t[u++] = '\n';
4162
#endif
4163
        s += 2;
4164
      }
4165
      else if (label[s] == '\\' && label[s + 1] == '\\') {
4166
        t[u++] = '\\';
4167
        s += 2;
4168
      }
4169
      else
4170
        t[u++] = label[s++];
4171
    }
4172
 
4173
    t[u] = 0;
4174
    if (quiet == NO)
4175
      printf("%s", t);
4176
 
4177
    return SUCCEEDED;
4178
  }
4179
 
4180
  /* PRINTV */
4181
 
4182
  if (strcmp(cp, "PRINTV") == 0) {
4183
 
4184
    int m;
4185
 
4186
 
4187
    if (get_next_token() == FAILED)
4188
      return FAILED;
4189
 
4190
    if (strcaselesscmp(tmp, "HEX") == 0)
4191
      m = 0;
4192
    else if (strcaselesscmp(tmp, "DEC") == 0)
4193
      m = 1;
4194
    else {
4195
      print_error(".PRINTV needs to know the format of the output, HEX or DEC.\n", ERROR_DIR);
4196
      return FAILED;
4197
    }
4198
 
4199
    q = input_number();
4200
    if (q == FAILED)
4201
      return FAILED;
4202
    if (q != SUCCEEDED) {
4203
      if (q == INPUT_NUMBER_ADDRESS_LABEL) {
4204
        sprintf(emsg, "\"%s\" is not known.\n", label);
4205
        print_error(emsg, ERROR_DIR);
4206
      }
4207
      print_error(".PRINTV can only print currently known values.\n", ERROR_DIR);
4208
      return FAILED;
4209
    }
4210
 
4211
    if (quiet == NO) {
4212
      if (m == 0)
4213
        printf("%x", d);
4214
      else
4215
        printf("%d", d);
4216
    }
4217
 
4218
    return SUCCEEDED;
4219
  }
4220
 
4221
  /* SEED */
4222
 
4223
  if (strcmp(cp, "SEED") == 0) {
4224
 
4225
    q = input_number();
4226
    if (q == FAILED)
4227
      return FAILED;
4228
    if (q != SUCCEEDED) {
4229
      print_error(".SEED needs a seed value for the randon number generator.\n", ERROR_DIR);
4230
      return FAILED;
4231
    }
4232
 
4233
    /* reseed the random number generator */
4234
    srand(d);
4235
 
4236
    return SUCCEEDED;
4237
  }
4238
 
4239
  /* DBRND/DWRND */
4240
  if (strcmp(cp, "DBRND") == 0 || strcmp(cp, "DWRND") == 0) {
4241
 
4242
    int o, c, min, max, f;
4243
 
4244
 
4245
    /* bytes or words? */
4246
    if (cp[1] == 'W')
4247
      o = 1;
4248
    else
4249
      o = 0;
4250
 
4251
    /* get the count */
4252
    q = input_number();
4253
    if (q == FAILED)
4254
      return FAILED;
4255
    if (q != SUCCEEDED) {
4256
      sprintf(emsg, ".%s needs the amount of random numbers.\n", cp);
4257
      print_error(emsg, ERROR_DIR);
4258
      return FAILED;
4259
    }
4260
 
4261
    c = d;
4262
 
4263
    if (c <= 0) {
4264
      sprintf(emsg, ".%s needs that the amount of random numbers is > 0.\n", cp);
4265
      print_error(emsg, ERROR_DIR);
4266
      return FAILED;
4267
    }
4268
 
4269
    /* get min */
4270
    q = input_number();
4271
    if (q == FAILED)
4272
      return FAILED;
4273
    if (q != SUCCEEDED) {
4274
      sprintf(emsg, ".%s needs the min value.\n", cp);
4275
      print_error(emsg, ERROR_DIR);
4276
      return FAILED;
4277
    }
4278
 
4279
    min = d;
4280
 
4281
    /* get max */
4282
    q = input_number();
4283
    if (q == FAILED)
4284
      return FAILED;
4285
    if (q != SUCCEEDED) {
4286
      sprintf(emsg, ".%s needs the max value.\n", cp);
4287
      print_error(emsg, ERROR_DIR);
4288
      return FAILED;
4289
    }
4290
 
4291
    max = d;
4292
 
4293
    if (min >= max) {
4294
      sprintf(emsg, ".%s needs that min < max.\n", cp);
4295
      print_error(emsg, ERROR_DIR);
4296
      return FAILED;
4297
    }
4298
 
4299
    /* generate the numbers */
4300
    for (f = 0; f < c; f++) {
4301
      d = (rand() % (max-min+1)) + min;
4302
 
4303
      if (o == 1) {
4304
        if (d < -32768 || d > 65535) {
4305
          sprintf(emsg, ".%s: Expected a 16bit value, computed %d.\n", cp, d);
4306
          print_error(emsg, ERROR_NONE);
4307
          return FAILED;
4308
        }
4309
        fprintf(file_out_ptr, "y %d ", d);
4310
      }
4311
      else {
4312
        if (d > 255 || d < -127) {
4313
          sprintf(emsg, ".%s: Expected a 8bit value, computed %d.\n", cp, d);
4314
          print_error(emsg, ERROR_NONE);
4315
          return FAILED;
4316
        }
4317
        fprintf(file_out_ptr, "d%d ", d);
4318
      }
4319
    }
4320
 
4321
    return SUCCEEDED;
4322
  }
4323
 
4324
  /* DWSIN/DBSIN/DWCOS/DBCOS */
4325
 
4326
  if (strcmp(cp, "DWSIN") == 0 || strcmp(cp, "DBSIN") == 0 || strcmp(cp, "DWCOS") == 0 || strcmp(cp, "DBCOS") == 0) {
4327
 
4328
    double m, a, s, n;
4329
    int p, c, o, f;
4330
 
4331
 
4332
    if (cp[1] == 'W')
4333
      o = 1;
4334
    else
4335
      o = 2;
4336
    if (cp[2] == 'S')
4337
      f = 1;
4338
    else
4339
      f = 2;
4340
 
4341
    input_float_mode = ON;
4342
    p = input_number();
4343
    input_float_mode = OFF;
4344
    if (p != SUCCEEDED && p != INPUT_NUMBER_FLOAT) {
4345
      sprintf(emsg, ".%s needs a value for starting angle.\n", cp);
4346
      print_error(emsg, ERROR_DIR);
4347
      return FAILED;
4348
    }
4349
 
4350
    if (p == SUCCEEDED)
4351
      a = d;
4352
    else
4353
      a = flo;
4354
 
4355
    if (input_number() != SUCCEEDED || d < 0) {
4356
      sprintf(emsg, ".%s needs an non-negative integer value for additional angles.\n", cp);
4357
      print_error(emsg, ERROR_DIR);
4358
      return FAILED;
4359
    }
4360
 
4361
    c = d;
4362
 
4363
    input_float_mode = ON;
4364
    p = input_number();
4365
    if (p != SUCCEEDED && p != INPUT_NUMBER_FLOAT) {
4366
      sprintf(emsg, ".%s needs a value for angle step.\n", cp);
4367
      print_error(emsg, ERROR_DIR);
4368
      return FAILED;
4369
    }
4370
 
4371
    if (p == SUCCEEDED)
4372
      s = d;
4373
    else
4374
      s = flo;
4375
 
4376
    p = input_number();
4377
    if (p != SUCCEEDED && p != INPUT_NUMBER_FLOAT) {
4378
      sprintf(emsg, ".%s needs a value to multiply the result with.\n", cp);
4379
      print_error(emsg, ERROR_DIR);
4380
      return FAILED;
4381
    }
4382
 
4383
    if (p == SUCCEEDED)
4384
      m = d;
4385
    else
4386
      m = flo;
4387
 
4388
    p = input_number();
4389
    input_float_mode = OFF;
4390
    if (p != SUCCEEDED && p != INPUT_NUMBER_FLOAT) {
4391
      sprintf(emsg, ".%s needs a value to add to the result.\n", cp);
4392
      print_error(emsg, ERROR_DIR);
4393
      return FAILED;
4394
    }
4395
 
4396
    if (p == SUCCEEDED)
4397
      n = d;
4398
    else
4399
      n = flo;
4400
 
4401
    for (c++; c > 0; c--) {
4402
      while (a >= 360)
4403
        a -= 360;
4404
 
4405
      if (f == 1)
4406
        d = (int)((m * sin(a*M_PI/180)) + n);
4407
      else
4408
        d = (int)((m * cos(a*M_PI/180)) + n);
4409
 
4410
      if (o == 1) {
4411
        if (d < -32768 || d > 65535) {
4412
          sprintf(emsg, ".%s: Expected a 16bit value, computed %d.\n", cp, d);
4413
          print_error(emsg, ERROR_NONE);
4414
          return FAILED;
4415
        }
4416
        fprintf(file_out_ptr, "y %d ", d);
4417
      }
4418
      else {
4419
        if (d > 255 || d < -127) {
4420
          sprintf(emsg, ".%s: Expected a 8bit value, computed %d.\n", cp, d);
4421
          print_error(emsg, ERROR_NONE);
4422
          return FAILED;
4423
        }
4424
        fprintf(file_out_ptr, "d%d ", d);
4425
      }
4426
 
4427
      a += s;
4428
    }
4429
 
4430
    return SUCCEEDED;
4431
  }
4432
 
4433
  /* FAIL */
4434
 
4435
  if (strcmp(cp, "FAIL") == 0) {
4436
    print_error("HALT: .FAIL found.\n", ERROR_NONE);
4437
 
4438
    /* make a silent exit */
4439
    exit(0);
4440
  }
4441
 
4442
  /* UNDEF/UNDEFINE */
4443
 
4444
  if (strcmp(cp, "UNDEF") == 0 || strcmp(cp, "UNDEFINE") == 0) {
4445
 
4446
    char c[16];
4447
 
4448
 
4449
    strcpy(c, cp);
4450
 
4451
    q = 0;
4452
    while (1) {
4453
      ind = input_next_string();
4454
      if (ind == FAILED)
4455
        return FAILED;
4456
      if (ind == INPUT_NUMBER_EOL) {
4457
        if (q != 0) {
4458
          next_line();
4459
          return SUCCEEDED;
4460
        }
4461
        sprintf(emsg, ".%s requires definition name(s).\n", c);
4462
        print_error(emsg, ERROR_DIR);
4463
        return FAILED;
4464
      }
4465
 
4466
      q++;
4467
 
4468
      if (undefine(tmp) == FAILED) {
4469
        sprintf(emsg, "Could not .%s \"%s\".\n", c, tmp);
4470
        print_error(emsg, ERROR_WRN);
4471
      }
4472
    }
4473
 
4474
    return SUCCEEDED;
4475
  }
4476
 
4477
  /* ASM */
4478
 
4479
  if (strcmp(cp, "ASM") == 0)
4480
    return SUCCEEDED;
4481
 
4482
  /* ENDASM */
4483
 
4484
  if (strcmp(cp, "ENDASM") == 0) {
4485
 
4486
    int assem = 1, x;
4487
 
4488
 
4489
    while (1) {
4490
      x = i;
4491
      q = get_next_token();
4492
      if (q == GET_NEXT_TOKEN_STRING)
4493
        continue;
4494
 
4495
      /* end of file? */
4496
      if (strcmp(tmp, ".E") == 0) {
4497
        i = x;
4498
        return SUCCEEDED;
4499
      }
4500
      if (strcaselesscmp(tmp, ".ASM") == 0) {
4501
        assem--;
4502
        if (assem == 0)
4503
          return SUCCEEDED;
4504
      }
4505
      if (strcaselesscmp(tmp, ".ENDASM") == 0)
4506
        assem++;
4507
    }
4508
  }
4509
 
4510
  sprintf(emsg, "Unknown directive \"%s\".\n", tmp);
4511
  print_error(emsg, ERROR_NONE);
4512
 
4513
  return FAILED;
4514
}
4515
 
4516
 
4517
int find_next_point(char *n) {
4518
 
4519
  int r, m, l;
4520
 
4521
 
4522
  l = active_file_info_last->line_current;
4523
  /* find the next compiling point */
4524
  r = 1;
4525
  m = macro_active;
4526
  /* disable macro decoding */
4527
  macro_active = 0;
4528
  while (get_next_token() != FAILED) {
4529
    if (tmp[0] == '.') {
4530
      if (strcmp(cp, "ENDIF") == 0)
4531
        r--;
4532
      if (strcmp(cp, "ELSE") == 0 && r == 1)
4533
        r--;
4534
      if (strcmp(cp, "E") == 0)
4535
        break;
4536
      if (strcmp(cp, "IFDEF") == 0 || strcmp(cp, "IFNDEF") == 0 || strcmp(cp, "IFGR") == 0 || strcmp(cp, "IFLE") == 0 ||
4537
          strcmp(cp, "IFEQ") == 0 || strcmp(cp, "IFNEQ") == 0 || strcmp(cp, "IFDEFM") == 0 || strcmp(cp, "IFNDEFM") == 0 ||
4538
          strcmp(cp, "IF") == 0 || strcmp(cp, "IFGREQ") == 0 || strcmp(cp, "IFLEEQ") == 0 || strcmp(cp, "IFEXISTS") == 0)
4539
        r++;
4540
    }
4541
    if (r == 0) {
4542
      if (strcmp(cp, "ELSE") == 0)
4543
        ifdef++;
4544
      macro_active = m;
4545
      return SUCCEEDED;
4546
    }
4547
  }
4548
 
4549
  /* return the condition's line number */
4550
  active_file_info_last->line_current = l;
4551
  sprintf(emsg, ".%s must end to .ENDIF/.ELSE.\n", n);
4552
  print_error(emsg, ERROR_DIR);
4553
 
4554
  return FAILED;
4555
}
4556
 
4557
 
4558
void delete_stack(struct stack *s) {
4559
 
4560
  if (s == NULL) {
4561
    sprintf(emsg, "Deleting a non-existing computation stack. This can lead to problems.\n");
4562
    print_error(emsg, ERROR_WRN);
4563
    return;
4564
  }
4565
 
4566
  free(s->stack);
4567
  free(s);
4568
}
4569
 
4570
 
4571
int get_new_definition_data(int *b, char *c, int *size, double *data) {
4572
 
4573
  int a, x, n, s;
4574
 
4575
 
4576
  x = input_number();
4577
  a = x;
4578
  n = 0;
4579
  s = 0;
4580
 
4581
  if (x == INPUT_NUMBER_ADDRESS_LABEL) {
4582
    /* address label -> stack */
4583
    stack_create_label_stack(label);
4584
    x = INPUT_NUMBER_STACK;
4585
  }
4586
 
4587
  if (x == INPUT_NUMBER_STACK) {
4588
    *b = stacks_tmp->id;
4589
    stacks_tmp->position = STACK_POSITION_DEFINITION;
4590
    x = input_number();
4591
    if (x != INPUT_NUMBER_EOL) {
4592
      print_error("A computation cannot be output as a string.\n", ERROR_DIR);
4593
      return SUCCEEDED;
4594
    }
4595
    return INPUT_NUMBER_STACK;
4596
  }
4597
 
4598
  while (x != INPUT_NUMBER_EOL) {
4599
    /* the first fetch will conserve both classes */
4600
    if (n == 0) {
4601
      if (x == SUCCEEDED)
4602
        *b = d;
4603
      else if (x == INPUT_NUMBER_STRING) {
4604
        strcpy(c, label);
4605
        s = strlen(label);
4606
      }
4607
      else if (x == INPUT_NUMBER_FLOAT) {
4608
        *data = flo;
4609
        *b = flo;
4610
      }
4611
      else
4612
        return x;
4613
 
4614
      n++;
4615
      x = input_number();
4616
      continue;
4617
    }
4618
    /* the next fetches will produce strings */
4619
    else if (n == 1 && (a == SUCCEEDED || a == INPUT_NUMBER_FLOAT)) {
4620
      if (*b > 255) {
4621
        c[0] = (*b & 255);
4622
        c[1] = (*b >> 8) & 255;
4623
        c[2] = 0;
4624
        s = 2;
4625
      }
4626
      else {
4627
        c[0] = *b;
4628
        c[1] = 0;
4629
        s = 1;
4630
      }
4631
      a = INPUT_NUMBER_STRING;
4632
    }
4633
 
4634
    /* transform floats to integers */
4635
    if (x == INPUT_NUMBER_FLOAT) {
4636
      d = flo;
4637
      x = SUCCEEDED;
4638
    }
4639
 
4640
    if (x == INPUT_NUMBER_STRING) {
4641
      strcpy(&c[s], label);
4642
      s += strlen(label);
4643
    }
4644
    else if (x == SUCCEEDED) {
4645
      if (d > 255) {
4646
        c[s] = (d & 255);
4647
        c[s + 1] = (d >> 8) & 255;
4648
        c[s + 2] = 0;
4649
        s += 2;
4650
      }
4651
      else {
4652
        c[s] = d;
4653
        c[s + 1] = 0;
4654
        s++;
4655
      }
4656
    }
4657
    else
4658
      return x;
4659
 
4660
    n++;
4661
    x = input_number();
4662
  }
4663
 
4664
  next_line();
4665
 
4666
  if (a == INPUT_NUMBER_STRING)
4667
    c[s] = 0;
4668
 
4669
  *size = s;
4670
 
4671
  return a;
4672
}
4673
 
4674
 
4675
int export_a_definition(char *n) {
4676
 
4677
  struct export_def *e;
4678
 
4679
 
4680
  /* don't export it twice or more often */
4681
  e = export_first;
4682
  while (e != NULL) {
4683
    if (strcmp(e->name, n) == 0) {
4684
      sprintf(emsg, "\"%s\" was .EXPORTed for the second time.\n", n);
4685
      print_error(emsg, ERROR_WRN);
4686
      return SUCCEEDED;
4687
    }
4688
    e = e->next;
4689
  }
4690
 
4691
  e = malloc(sizeof(struct export_def));
4692
  if (e == NULL) {
4693
    sprintf(emsg, "Out of memory while allocating room for \".EXPORT %s\".\n", n);
4694
    print_error(emsg, ERROR_DIR);
4695
    return FAILED;
4696
  }
4697
 
4698
  strcpy(e->name, n);
4699
  e->next = NULL;
4700
 
4701
  if (export_first == NULL) {
4702
    export_first = e;
4703
    export_last = e;
4704
  }
4705
  else {
4706
    export_last->next = e;
4707
    export_last = e;
4708
  }
4709
 
4710
  return SUCCEEDED;
4711
}

powered by: WebSVN 2.1.0

© copyright 1999-2024 OpenCores.org, equivalent to Oliscience, all rights reserved. OpenCores®, registered trademark.