BSD 4 release
[unix-history] / usr / src / cmd / as / as.h
CommitLineData
8c1020c4 1/* Copyright (c) 1980 Regents of the University of California */
31cef89c 2/* "@(#)as.h 4.8 11/5/80" */
8c1020c4
BJ
3#ifdef VMS
4# define vax 1
5# define VAX 1
6#endif VMS
7
451260e7
RH
8#include <sys/types.h>
9#ifdef UNIX
10
11#ifdef FLEXNAMES
12# include <a.out.h>
13# include <stab.h>
14#else not FLEXNAMES
0c940099
RH
15# define ONLIST
16# include "a.out.h"
451260e7
RH
17# include <stab.h>
18#endif FLEXNAMES
19
20#endif UNIX
21#ifdef VMS
22
23#ifdef UNIXDEVEL
24# include <a.out.h>
25#else not UNIXDEVEL
26# include <aout.h>
27#endif not UNIXDEVEL
28
29#endif VMS
8c1020c4 30
451260e7 31#define readonly
8c1020c4
BJ
32#define NINST 300
33
34#define NEXP 20 /* max number of expr. terms per instruction */
35#define NARG 6 /* max number of args per instruction */
36#define NHASH 1103 /* hash table is dynamically extended */
6cca131f 37#define TNAMESIZE 32 /* maximum length of temporary file names */
8c1020c4
BJ
38#define NLOC 4 /* number of location ctrs */
39
40#ifdef UNIX
41# ifndef FLEXNAMES
42# ifndef NCPS
43# define NCPS 8 /* number of characters per symbol*/
44# endif
45# else
46# ifdef NCPS
47# undef NCPS
48# endif
49# define NCPS BUFSIZ /* needed to allocate yytext */
50# endif
51# endif UNIX
52
53# ifdef VMS
54# ifdef NCPS
55# undef NCPS
56# endif NCPS
57# define NCPS 15
58# endif VMS
59
60/*
61 * Symbol types
62 */
63#define XUNDEF 0x0
64#define XABS 0x2
65#define XTEXT 0x4
66#define XDATA 0x6
67#define XBSS 0x8
68
69#define XXTRN 0x1
70#define XTYPE 0x1E
71
72#define XFORW 0x20 /* Was forward-referenced when undefined */
73
74#define ERR (-1)
75#define NBPW 32 /* Bits per word */
76
77#define AMASK 017
78
79/*
80 * Actual argument syntax types
81 */
6cca131f
RH
82#define AREG 1 /* %r */
83#define ABASE 2 /* (%r) */
84#define ADECR 3 /* -(%r) */
85#define AINCR 4 /* (%r)+ */
86#define ADISP 5 /* expr(%r) */
87#define AEXP 6 /* expr */
88#define AIMM 7 /* $ expr */
89#define ASTAR 8 /* * */
90#define AINDX 16 /* [%r] */
8c1020c4
BJ
91
92/*
93 * Argument access types used to test validity of operands to operators
94 */
301986ee
RH
95#define ACCR (1<<3) /* read */
96#define ACCW (2<<3) /* write */
97#define ACCB (4<<3) /* branch displacement */
98#define ACCA (8<<3) /* address only */
99#define ACCM (ACCR | ACCW) /* modify */
100#define ACCI (ACCB | ACCR) /* XFC code */
101
5b3c350a 102#define ACCESSMASK (ACCA | ACCR | ACCW | ACCB) /* the mask */
8c1020c4
BJ
103
104/*
5b3c350a
RH
105 * Argument data types
106 * Also used to tell outrel what it is relocating
107 * (possibly in combination with RELOC_PCREL and TYPNONE)
8c1020c4 108 */
5b3c350a
RH
109#define TYPB 0 /* byte */
110#define TYPW 1 /* word */
111#define TYPL 2 /* long */
112#define TYPQ 3 /* quad */
113#define TYPF 4 /* floating */
114#define TYPD 5 /* double floating */
115#define TYPNONE 6 /* when nothing */
116#define RELOC_PCREL 8 /* implicit argument to outrel; ==> PCREL */
8c1020c4 117
6cca131f 118#define TYPMASK 7
8c1020c4 119
5b3c350a
RH
120/*
121 * reference types for loader
122 */
6cca131f
RH
123#define PCREL 1
124#define LEN1 2
125#define LEN2 4
126#define LEN4 6
127#define LEN8 8
5b3c350a
RH
128
129extern int reflen[]; /* {LEN*+PCREL} ==> number of bytes */
130extern int lgreflen[]; /* {LEN*+PCREL} ==> lg number of bytes */
131extern int len124[]; /* {1,2,4,8} ==> {LEN1, LEN2, LEN4, LEN8} */
132extern char mod124[]; /* {1,2,4,8} ==> {bits to construct operands */
133extern int type_124[]; /* {1,2,4,8} ==> {TYPB, TYPW, TYPL, TYPQ} */
134extern int ty_NORELOC[]; /* {TYPB..TYPD} ==> {1 if relocation not OK */
135extern int ty_LEN[]; /* {TYPB..TYPD} ==> {LEN1..LEN8} */
136extern int ty_nbyte[]; /* {TYPB..TYPD} ==> {1,2,4,8} */
137extern int ty_nlg[]; /* {TYPB..TYPD} ==> lg{1,2,4,8} */
8c1020c4
BJ
138
139#define TMPC 7
140#define HW 01
141#define FW 03
142#define DW 07
143
144#ifdef UNIX
145# include <pagsiz.h>
146#endif UNIX
147
148#ifdef VMS
149# define PAGRND 0x1FFL
150#endif VMS
151
152#define round(x,y) (((x)+(y)) & ~(y))
153
154#define STABTYPS 0340
6cca131f 155#define STABFLAG 0200
8c1020c4
BJ
156
157/*
158 * Follows are the definitions for the symbol table tags, which are
159 * all unsigned characters..
160 * High value tags are generated by the asembler for internal
161 * use.
162 * Low valued tags are the parser coded tokens the scanner returns.
163 * There are several pertinant bounds in this ordering:
164 * a) Symbols greater than JXQUESTIONABLE
165 * are used by the jxxx bumper, indicating that
166 * the symbol table entry is a jxxx entry
167 * that has yet to be bumped.
168 * b) Symbols greater than IGNOREBOUND are not
169 * bequeathed to the loader; they are truly
170 * for assembler internal use only.
171 * c) Symbols greater than OKTOBUMP represent
172 * indices into the program text that should
173 * be changed in preceeding jumps or aligns
174 * must get turned into their long form.
175 */
176
6cca131f 177#define TAGMASK 0xFF
8c1020c4
BJ
178
179# define JXACTIVE 0xFF /*jxxx size unknown*/
180# define JXNOTYET 0xFE /*jxxx size known, but not yet expanded*/
181# define JXALIGN 0xFD /*align jxxx entry*/
182# define JXINACTIVE 0xFC /*jxxx size known and expanded*/
183
6cca131f 184#define JXQUESTIONABLE 0xFB
8c1020c4
BJ
185
186# define JXTUNNEL 0xFA /*jxxx that jumps to another*/
187# define OBSOLETE 0xF9 /*erroneously entered symbol*/
188
189#define IGNOREBOUND 0xF8 /*symbols greater than this are ignored*/
190# define STABFLOATING 0xF7
191# define LABELID 0xF6
192
193#define OKTOBUMP 0xF5
194# define STABFIXED 0xF4
195
196/*
197 * astoks.h contains reserved word codings the parser should
198 * know about
199 */
200#include "astoks.h"
201
202/*
203 * The structure for one symbol table entry.
204 * Symbol table entries are used for both user defined symbols,
205 * and symbol slots generated to create the jxxx jump from
206 * slots.
451260e7
RH
207 * Caution: the instructions are stored in a shorter version
208 * of the struct symtab, using all fields in sym_nm and
209 * tag. The fields used in sym_nm are carefully redeclared
210 * in struct Instab and struct instab (see below).
211 * If struct nlist gets changed, then Instab and instab may
212 * have to be changed.
8c1020c4
BJ
213 */
214
8c1020c4 215struct symtab{
451260e7
RH
216 struct nlist s_nm;
217 u_char s_tag; /* assembler tag */
218 u_char s_ptype; /* if tag == NAME */
219 u_char s_jxoveralign; /* if a JXXX, jumped over align */
220 short s_index; /* which segment */
221 struct symtab *s_dest; /* if JXXX, where going to */
8c1020c4 222#ifdef DJXXX
451260e7 223 short s_jxline; /* source line of the jump from */
8c1020c4
BJ
224#endif
225};
451260e7
RH
226/*
227 * Redefinitions of the fields in symtab for
228 * use when the symbol table entry marks a jxxx instruction.
229 */
230#define s_jxbump s_ptype /* tag == JX..., how far to expand */
231#define s_jxfear s_desc /* how far needs to be bumped */
232/*
233 * Redefinitions of fields in the struct nlist for symbols so that
234 * one saves typing, and so that they conform
235 * with the old naming conventions.
236 */
237#ifdef FLEXNAMES
238#define s_name s_nm.n_un.n_name /* name pointer */
239#define s_nmx s_nm.n_un.n_strx /* string table index */
240#else not FLEXNAMES
241#define s_name s_nm.n_name
242#endif
243#define s_type s_nm.n_type /* type of the symbol */
244#define s_other s_nm.n_other /* other information for sdb */
245#define s_desc s_nm.n_desc /* type descriptor */
246#define s_value s_nm.n_value /* value of the symbol, or sdb delta */
247
248struct instab{
249 struct nlist s_nm; /* instruction name, type (opcode) */
250 u_char s_tag;
0c940099 251 char s_pad[3]; /* round to 20 bytes */
8c1020c4 252};
451260e7
RH
253/*
254 * The fields nm.n_desc and nm.n_value total 6 bytes; this is
255 * just enough for the 6 bytes describing the argument types.
256 * We use a macro to define access to these 6 bytes, assuming that
257 * they are allocated adjacently.
258 * IF THE FORMAT OF STRUCT nlist CHANGES, THESE MAY HAVE TO BE CHANGED.
259 *
0c940099 260 * Instab is cleverly declared to look very much like the combination of
451260e7
RH
261 * a struct symtab and a struct nlist.
262 */
263struct Instab{
264#ifdef FLEXNAMES
265 char *I_name;
266#else not FLEXNAMES
267 char I_name[NCPS];
268#endif
269 u_char I_opcode;
270 char I_nargs;
271 char I_args[6];
272 u_char I_s_tag;
0c940099 273 char I_pad[3]; /* round to 20 bytes */
451260e7
RH
274};
275/*
276 * Redefinitions of fields in the struct nlist for instructions so that
277 * one saves typing, and conforms to the old naming conventions
278 */
279#define i_opcode s_nm.n_type /* use the same field as symtab.type */
280#define i_nargs s_nm.n_other /* number of arguments */
281#define fetcharg(ptr, n) ((struct Instab *)ptr)->I_args[n]
8c1020c4
BJ
282
283struct arg { /*one argument to an instruction*/
451260e7
RH
284 char a_atype;
285 char a_areg1;
286 char a_areg2;
287 char a_dispsize; /*usually d124, unless have B^, etc*/
288 struct exp *a_xp;
8c1020c4
BJ
289};
290
291struct exp {
451260e7
RH
292 long e_xvalue; /* MUST be the first field (look at union Double) */
293 long e_yvalue; /* MUST be second field; least sig word of a double */
294 char e_xtype;
295 char e_xloc;
296 struct symtab *e_xname;
8c1020c4
BJ
297};
298
451260e7
RH
299#define doub_MSW e_xvalue
300#define doub_LSW e_yvalue
8c1020c4 301
451260e7 302union Double {
8c1020c4
BJ
303 struct{
304 long doub_MSW;
305 long doub_LSW;
306 } dis_dvalue;
307 double dvalue;
308};
309
451260e7 310struct Quad {
8c1020c4
BJ
311 long quad_low_long;
312 long quad_high_long;
313};
314
315/*
316 * Magic layout macros
317 */
318#define MINBYTE -128
319#define MAXBYTE 127
320#define MINWORD -32768
321#define MAXWORD 32767
322
323#define LITFLTMASK 0x000043F0 /*really magic*/
324/*
325 * Is the floating point double word in xp a
326 * short literal floating point number?
327 */
328#define slitflt(xp) \
329 ( (xp->doub_LSW == 0) \
330 && ( (xp->doub_MSW & LITFLTMASK) \
331 == xp->doub_MSW) )
332/*
333 * If it is a slitflt, then extract the 6 interesting bits
334 */
335#define extlitflt(xp) \
336 xp->doub_MSW >> 4
337
338 extern struct arg arglist[NARG]; /*building operands in instructions*/
339 extern struct exp explist[NEXP]; /*building up a list of expressions*/
340 extern struct exp *xp; /*current free expression*/
341 /*
342 * Communication between the scanner and the jxxx handlers.
343 * lastnam: the last name seen on the input
344 * lastjxxx: pointer to the last symbol table entry for
345 * a jump from
346 */
347 extern struct symtab *lastnam;
348 extern struct symtab *lastjxxx;
349
350#ifdef VMS
451260e7
RH
351 extern char *vms_obj_ptr; /* object buffer pointer */
352 extern char sobuf[]; /* object buffer */
8c1020c4
BJ
353 extern int objfil; /* VMS object file descriptor */
354#endif VMS
355
356 /*
357 * Lgensym is used to make up funny names for local labels.
358 * lgensym[i] is the current funny number to put after
359 * references to if, lgensym[i]-1 is for ib.
360 * genref[i] is set when the label is referenced before
361 * it is defined (i.e. 2f) so that we can be sure these
362 * labels are always defined to avoid weird diagnostics
363 * from the loader later.
364 */
365 extern int lgensym[10];
366 extern char genref[10];
367
368 extern char tmpn1[TNAMESIZE]; /* Interpass temporary */
369 extern struct exp *dotp; /* the current dot location */
370 extern int loctr;
371
372 extern struct exec hdr; /* a.out header */
373 extern u_long tsize; /* total text size */
374 extern u_long dsize; /* total data size */
375 extern u_long trsize; /* total text relocation size */
376 extern u_long drsize; /* total data relocation size */
377 extern u_long datbase; /* base of the data segment */
378 /*
379 * Bitoff and bitfield keep track of the packing into
380 * bytes mandated by the expression syntax <expr> ':' <expr>
381 */
382 extern int bitoff;
383 extern long bitfield;
384
385 /*
386 * The lexical analyzer builds up symbols in yytext. Lookup
387 * expects its argument in this buffer
388 */
389 extern char yytext[NCPS+2]; /* text buffer for lexical */
390 /*
391 * Variables to manage the input assembler source file
392 */
393 extern int lineno; /*the line number*/
394 extern char *dotsname; /*the name of the as source*/
395
396 extern FILE *tmpfil; /* interpass communication*/
397
398 extern int passno; /* 1 or 2 */
399
400 extern int anyerrs; /*errors assembling arguments*/
401 extern int silent; /*don't mention the errors*/
402 extern int savelabels; /*save labels in a.out*/
403 extern int orgwarn; /* questionable origin ? */
404 extern int useVM; /*use virtual memory temp file*/
e5b9ebfb 405 extern int jxxxJUMP; /*use jmp instead of brw for jxxx */
030352e9 406 extern int readonlydata; /*initialized data into text space*/
8c1020c4
BJ
407#ifdef DEBUG
408 extern int debug;
409 extern int toktrace;
410#endif
411 /*
412 * Information about the instructions
413 */
414 extern struct instab *itab[NINST]; /*maps opcodes to instructions*/
451260e7 415 extern readonly struct Instab instab[];
8c1020c4
BJ
416
417 extern int curlen; /*current literal storage size*/
418 extern int d124; /*current pointer storage size*/
419
420 struct symtab **lookup(); /*argument in yytext*/
421 struct symtab *symalloc();
422
451260e7 423#define outb(val) {dotp->e_xvalue++; if (passno==2) bputc((val), (txtfil));}
8c1020c4 424
451260e7 425#define outs(cp, lg) dotp->e_xvalue += (lg); if (passno == 2) bwrite((cp), (lg), (txtfil))
8c1020c4
BJ
426
427/*
428 * Most of the time, the argument to flushfield is a power of two constant,
429 * the calculations involving it can be optimized to shifts.
430 */
431#define flushfield(n) if (bitoff != 0) Flushfield( ( (bitoff+n-1) /n ) * n)
432
433/*
434 * The biobuf structure and associated routines are used to write
435 * into one file at several places concurrently. Calling bopen
436 * with a biobuf structure sets it up to write ``biofd'' starting
437 * at the specified offset. You can then use ``bwrite'' and/or ``bputc''
438 * to stuff characters in the stream, much like ``fwrite'' and ``fputc''.
439 * Calling bflush drains all the buffers and MUST be done before exit.
440 */
441struct biobuf {
442 short b_nleft; /* Number free spaces left in b_buf */
443/* Initialize to be less than BUFSIZ initially, to boundary align in file */
444 char *b_ptr; /* Next place to stuff characters */
445 char b_buf[BUFSIZ]; /* The buffer itself */
446 off_t b_off; /* Current file offset */
447 struct biobuf *b_link; /* Link in chain for bflush() */
448};
449#define bputc(c,b) ((b)->b_nleft ? (--(b)->b_nleft, *(b)->b_ptr++ = (c)) \
450 : bflushc(b, c))
451#define BFILE struct biobuf
452
453 extern BFILE *biobufs; /* head of the block I/O buffer chain */
454 extern int biofd; /* file descriptor for block I/O file */
455 extern off_t boffset; /* physical position in logical file */
456
457 /*
458 * For each of the named .text .data segments
459 * (introduced by .text <expr>), we maintain
460 * the current value of the dot, and the BFILE where
461 * the information for each of the segments is placed
462 * during the second pass.
463 */
464 extern struct exp usedot[NLOC + NLOC];
465 extern BFILE *usefile[NLOC + NLOC];
466 extern BFILE *txtfil;/* file for text and data: into usefile */
467 /*
468 * Relocation information for each segment is accumulated
469 * seperately from the others. Writing the relocation
470 * information is logically viewed as writing to one
471 * relocation saving file for each segment; physically
472 * we have a bunch of buffers allocated internally that
473 * contain the relocation information.
474 */
475 struct relbufdesc *rusefile[NLOC + NLOC];
476 struct relbufdesc *relfil;