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

Subversion Repositories tms1000

[/] [tms1000/] [trunk/] [assembler/] [casm.c] - Blame information for rev 5

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

Line No. Rev Author Line
1 2 nand_gates
/*
2
casm.c
3
 
4
CASM is an assembler for the tms1000 processor.
5
*/
6
 
7
#include <stdarg.h>
8
#include <stdio.h>
9
#include <string.h>
10
#include <unistd.h>
11
#include "symtab.h"
12
#include "casm.h"
13
 
14
char *progname;
15
int pass;
16
int lineno;
17
int errors;
18
int warnings;
19
 
20
int group;      /* current rom group */
21
int rom;        /* current rom */
22
int pc;         /* current pc */
23
 
24
int dsr;        /* delayed select rom */
25
int dsg;        /* delayed select group */
26
 
27
char flag_char;
28
 
29
int objflag;    /* used to remember args to emit() */
30
int objcode;
31
 
32
int symtab_flag;
33
 
34
int last_instruction_type;
35
 
36
 
37
int targflag;   /* used to remember args to target() */
38
int targgroup;
39
int targrom;
40
int targpc;
41
 
42
char linebuf [MAX_LINE];
43
char *lineptr;
44
 
45
#define MAX_ERRBUF 2048
46
char errbuf [MAX_ERRBUF];
47
char *errptr;
48
 
49
#define SRC_TAB 32
50
char listbuf [MAX_LINE];
51
char *listptr;
52
 
53
#ifndef PATH_MAX
54
#define PATH_MAX 256
55
#endif
56
 
57
char srcfn  [PATH_MAX];
58
char objfn  [PATH_MAX];
59
char listfn [PATH_MAX];
60
 
61
FILE *srcfile  = NULL;
62
FILE *objfile  = NULL;
63
FILE *listfile = NULL;
64
 
65
t_symtab symtab /*[MAXGROUP] [MAXROM]*/;  /* separate symbol tables for each ROM */
66
 
67
void format_listing (void)
68
{
69
  int i;
70
 
71
  sprintf (listptr, "%4d   ", lineno);
72
  listptr += strlen (listptr);
73
 
74
  if (objflag)
75
    {
76
      sprintf (listptr, "L%03x:  ", (rom << 6)+pc);
77
      listptr += strlen (listptr);
78
      for (i = 0x80; i; i >>= 1)
79
        *listptr++ = (objcode & i) ? '1' : '.';
80
      *listptr = '\0';
81
    }
82
  else
83
    {
84
      strcat (listptr, "                   ");
85
      listptr += strlen (listptr);
86
    }
87
 
88
  if (targflag)
89
    {
90
      sprintf (listptr, "  -> L%1o%1o%03o", targgroup, targrom, targpc);
91
      listptr += strlen (listptr);
92
    }
93
  else
94
    {
95
      strcat (listptr, "           ");
96
      listptr += strlen (listptr);
97
    }
98
 
99
  sprintf (listptr, "  %c%c%c%c%c    ", flag_char, flag_char, flag_char,
100
           flag_char, flag_char);
101
  listptr += strlen (listptr);
102
 
103
  strcat (listptr, linebuf);
104
  listptr += strlen (listptr);
105
}
106
 
107
void do_pass (int p)
108
{
109
  int i;
110
 
111
  pass = p;
112
  lineno = 0;
113
  errors = 0;
114
  warnings = 0;
115
  pc = 0;
116
  dsr = rom;
117
  dsg = group;
118
  last_instruction_type = OTHER_INST;
119
 
120
  printf ("Pass %d rom", pass);
121
 
122
  while (fgets (linebuf, MAX_LINE, srcfile))
123
    {
124
      /* remove newline */
125
      i = strlen (linebuf);
126
      if (linebuf [i - 1] == '\n')
127
        linebuf [i - 1] = '\0';
128
 
129
      lineno++;
130
      lineptr = & linebuf [0];
131
 
132
      listptr = & listbuf [0];
133
      listbuf [0] = '\0';
134
 
135
      errptr = & errbuf [0];
136
      errbuf [0] = '\0';
137
 
138
      objflag = 0;
139
      targflag = 0;
140
      flag_char = ' ';
141
      symtab_flag = 0;
142
 
143
      yyparse ();
144
 
145
      if (pass == 2)
146
        {
147
          if (symtab_flag)
148
            print_symbol_table (symtab, listfile);
149
          else
150
            {
151
              format_listing ();
152
              fprintf (listfile, "%s\n", listbuf);
153
              if (errptr != & errbuf [0])
154
                {
155
                  fprintf (stderr, "%s\n", listbuf);
156
                  fprintf (listfile, "%s", errbuf);
157
                  fprintf (stderr, "%s",   errbuf);
158
                }
159
            }
160
        }
161
 
162
      if (objflag) {
163
        pc = ((pc != 31) && ((pc >> 4) != 0) && (((pc & 0xf) == 15) || ((pc >> 4) != 3))) ?  (pc << 1) : (pc << 1)+1;
164
        pc = pc & 0x3f;
165
      }
166
        //pc = (pc + 1) & 0xff;
167
    }
168
 
169
  printf ("\n");
170
}
171
 
172
void munge_filename (char *dst, char *src, char *ext)
173
{
174
  int i;
175
  int lastdot = 0;
176
  for (i = 0; src [i]; i++)
177
    {
178
      if (src [i] == '.')
179
        lastdot = i;
180
    }
181
  if (lastdot == 0)
182
    lastdot = strlen (src);
183
  memcpy (dst, src, lastdot);
184
  dst [lastdot] = '\0';
185
  strcat (dst, ext);
186
}
187
 
188
int main (int argc, char *argv[])
189
{
190
  progname = argv [0];
191
 
192
  if (argc != 2)
193
    {
194
      fprintf (stderr, "Usage: %s sourcefile\n", progname);
195
      exit (1);
196
    }
197
 
198
  symtab = alloc_symbol_table ();
199
  if (! symtab )
200
    fatal ("symbol table allocation failed\n");
201
 
202
  strcpy (srcfn, argv [1]);
203
 
204
  srcfile = fopen (srcfn, "r");
205
 
206
  if (! srcfile)
207
    fatal ("can't open input file '%s'\n", srcfn);
208
 
209
  munge_filename (objfn, srcfn, ".mem");
210
  munge_filename (listfn, srcfn, ".lst");
211
 
212
  objfile = fopen (objfn, "w");
213
 
214
  if (! objfile)
215
    fatal ("can't open input file '%s'\n", objfn);
216
 
217
  listfile = fopen (listfn, "w");
218
 
219
  if (! listfile)
220
    fatal ("can't open listing file '%s'\n", listfn);
221
 
222
  rom = 0;
223
  group = 0;
224
 
225
  do_pass (1);
226
 
227
  rewind (srcfile);
228
 
229
  do_pass (2);
230
 
231
  err_printf ("%d errors, %d warnings\n", errors, warnings);
232
 
233
  fclose (srcfile);
234
  fclose (objfile);
235
  fclose (listfile);
236
}
237
 
238
void yyerror (char *s)
239
{
240
  error ("%s\n", s);
241
}
242
 
243
void do_label (char *s)
244
{
245
  int prev_val;
246
 
247
  if (pass == 1)
248
    {
249
      if (! create_symbol (symtab, s, (rom << 6) + pc, lineno))
250
        error ("multiply defined symbol '%s'\n", s);
251
    }
252
  else if (! lookup_symbol (symtab, s, & prev_val))
253
    error ("undefined symbol '%s'\n", s);
254
  else if (prev_val != ((rom << 6) + pc))
255
    error ("phase error for symbol '%s'\n", s);
256
}
257
 
258
static void emit_core (int op, int inst_type)
259
{
260
  objcode = op;
261
  objflag = 1;
262
  last_instruction_type = inst_type;
263
 
264
  if ((pass == 2) && objfile)
265
      fprintf (objfile, "@%03x %02x\n", (rom<<6)+pc, op);
266
}
267
 
268
void emit (int op)
269
{
270
  emit_core (op, OTHER_INST);
271
}
272
 
273
void emit_arith (int op)
274
{
275
  emit_core (op, ARITH_INST);
276
}
277
 
278
void emit_test (int op)
279
{
280
  emit_core (op, TEST_INST);
281
}
282
 
283
void target (int g, int r, int p)
284
{
285
  targflag = 1;
286
  targgroup = g;
287
  targrom = r;
288
  targpc = p;
289
}
290
 
291
int range (int val, int min, int max)
292
{
293
  if ((val < min) || (val > max))
294
    {
295
      error ("value out of range [%d to %d], using %d", min, max, min);
296
      return min;
297
    }
298
  return val;
299
}
300
 
301
char *newstr (char *orig)
302
{
303
  int len;
304
  char *r;
305
 
306
  len = strlen (orig);
307
  r = (char *) malloc (len + 1);
308
 
309
  if (! r)
310
    fatal ("memory allocation failed\n");
311
 
312
  memcpy (r, orig, len + 1);
313
  return (r);
314
}
315
 
316
/*
317
 * print to both listing error buffer and standard error
318
 *
319
 * Use this for general messages.  Don't use this for warnings or errors
320
 * generated by a particular line of the source file.  Use error() or
321
 * warning() for that.
322
 */
323
int err_vprintf (char *format, va_list ap)
324
{
325
  int res;
326
 
327
  if (listfile)
328
    vfprintf (listfile, format, ap);
329
  res = vfprintf (stderr, format, ap);
330
  return (res);
331
}
332
 
333
int err_printf (char *format, ...)
334
{
335
  int res;
336
  va_list ap;
337
 
338
  va_start (ap, format);
339
  res = err_vprintf (format, ap);
340
  va_end (ap);
341
  return (res);
342
}
343
 
344
 
345
/* generate fatal error message to stderr, doesn't return */
346
void fatal (char *format, ...)
347
{
348
  va_list ap;
349
 
350
  fprintf (stderr, "fatal error: ");
351
  va_start (ap, format);
352
  vfprintf (stderr, format, ap);
353
  va_end (ap);
354
  exit (2);
355
}
356
 
357
 
358
/* generate error or warning messages and increment appropriate counter */
359
/* actually just puts the message into the error buffer */
360
int error   (char *format, ...)
361
{
362
  int res;
363
  va_list ap;
364
 
365
  err_printf ("error in file %s line %d: ", srcfn, lineno);
366
  va_start (ap, format);
367
  res = err_vprintf (format, ap);
368
  va_end (ap);
369
  errptr += res;
370
  errors ++;
371
  return (res);
372
}
373
 
374
int warning (char *format, ...)
375
{
376
  int res;
377
  va_list ap;
378
 
379
  err_printf ("warning in file %s line %d: ", srcfn, lineno);
380
  va_start (ap, format);
381
  res = err_vprintf (format, ap);
382
  va_end (ap);
383
  errptr += res;
384
  warnings ++;
385
  return (res);
386
}
387
 
388
 

powered by: WebSVN 2.1.0

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