Fix for "*" getting bad section attributes, reported by A. Seed.
[rmac] / debug.c
1 //
2 // RMAC - Reboot's Macro Assembler for the Atari Jaguar Console System
3 // DEBUG.C - Debugging Messages
4 // Copyright (C) 199x Landon Dyer, 2011-2012 Reboot and Friends
5 // RMAC derived from MADMAC v1.07 Written by Landon Dyer, 1986
6 // Source utilised with the kind permission of Landon Dyer
7 //
8
9 #include "debug.h"
10 #include "amode.h"
11 #include "direct.h"
12 #include "mark.h"
13 #include "sect.h"
14 #include "token.h"
15
16
17 static int siztab[4] = { 3, 5, 9, 9 };
18
19
20 //
21 // Print 'c' visibly
22 //
23 int visprt(char c)
24 {
25         if (c < 0x20 || c >= 0x7F)
26                 putchar('.');
27         else
28                 putchar(c);
29
30         return 0;
31 }
32
33
34 //
35 // Print expression, return ptr to just past the ENDEXPR
36 //
37 TOKEN * printexpr(TOKEN * tp)
38 {
39         if (tp != NULL)
40         {
41                 while (*tp != ENDEXPR)
42                 {
43                         switch ((int)*tp++)
44                         {
45                         case SYMBOL:
46 //                              printf("`%s' ", ((SYM *)*tp)->sname);
47                                 printf("`%s' ", symbolPtr[*tp]->sname);
48                                 tp++;
49                                 break;
50                         case CONST:
51                                 printf("$%X ", *tp++);
52                                 break;
53                         case ACONST:
54                                 printf("ACONST=($%X,$%X) ", *tp, tp[1]);
55                                 tp += 2;
56                                 break;
57                         default:
58                                 printf("%c ", (char)tp[-1]);
59                                 break;
60                         }
61                 }
62         }
63
64 //      printf(";\n");
65         return tp + 1;
66 }
67
68
69 //
70 // Dump data in a chunk (and maybe others) in the appropriate format
71 //
72 int chdump(CHUNK * ch, int format)
73 {
74         while (ch != NULL)
75         {
76                 printf("chloc=$%08X, chsize=$%X\n", ch->chloc, ch->ch_size);
77                 mdump(ch->chptr, ch->ch_size, format, ch->chloc);
78                 ch = ch->chnext;
79         }
80
81         return 0;
82 }
83
84
85 //
86 // Dump fixup records in printable format
87 //
88 int fudump(CHUNK * ch)
89 {
90         PTR p;
91         char * ep;
92         WORD attr, esiz;
93         WORD line, file;
94         LONG loc;
95
96         for(; ch!=NULL;)
97         {
98                 p.cp = ch->chptr;
99                 ep = ch->chptr + ch->ch_size;
100
101                 while (p.cp < ep)
102                 {
103                         attr = *p.wp++;
104                         loc = *p.lp++;
105                         file = *p.wp++;
106                         line = *p.wp++;
107
108                         printf("$%04X $%08X %d.%d: ", (int)attr, loc, (int)file, (int)line);
109
110                         if (attr & FU_EXPR)
111                         {
112                                 esiz = *p.wp++;
113                                 printf("(%d long) ", (int)esiz);
114                                 p.tk = printexpr(p.tk);
115                         }
116                         else
117                         {
118                                 printf("`%s' ;", (*p.sy)->sname);
119                                 p.sy++;
120                         }
121
122                         if ((attr & 0x0F00) == FU_JR)
123                         {
124                                 printf(" *=$%X", *p.lp);
125                                 p.lp++;
126                         }
127
128                         printf("\n");
129                 }
130
131                 ch = ch->chnext;
132         }
133
134         return 0;
135 }
136
137
138 //
139 // Dump marks
140 //
141 int mudump(void)
142 {
143         MCHUNK * mch;
144         PTR p;
145         WORD from;
146         WORD w;
147         LONG loc;
148         SYM * symbol;
149
150         from = 0;
151
152         for(mch=firstmch; mch!=NULL; mch=mch->mcnext)
153         {
154                 printf("mch=$%p mcptr=$%08X mcalloc=$%X mcused=$%X\n",
155                         mch, (mch->mcptr.lw), mch->mcalloc, (mch->mcused));
156
157                 p = mch->mcptr;
158                 
159                 for(;;)
160                 {
161                         w = *p.wp++;
162
163                         if (w & MCHEND)
164                                 break;
165
166                         symbol = NULL;
167                         loc = *p.lp++;
168
169                         if (w & MCHFROM)
170                                 from = *p.wp++;
171
172                         if (w & MSYMBOL)
173                                 symbol = *p.sy++;
174
175                         printf("m=$%04X to=%d loc=$%X from=%d siz=%s",
176                                         w, w & 0x00FF, loc, from, (w & MLONG) ? "long" : "word");
177
178                         if (symbol != NULL)
179                                 printf(" sym=`%s'", symbol->sname);
180
181                         printf("\n");
182                 }
183         }
184
185         return 0;
186 }
187
188
189 //
190 // Dump memory from 'start' for 'count' bytes; `flg' is the following ORed
191 // together:
192 // 0 - bytes
193 // 1 - words
194 // 2 - longwords
195 // 
196 // if `base' is not -1, then print it at the start of each line, incremented
197 // accordingly.
198 //
199 int mdump(char * start, LONG count, int flg, LONG base)
200 {
201         int i, j, k;
202         j = 0;
203
204         for(i=0; i<(int)count;)
205         {
206                 if ((i & 15) == 0)
207                 {
208                         if (j < i)
209                         {
210                                 printf("  ");
211
212                                 while(j < i)
213                                 visprt(start[j++]);
214
215                                 putchar('\n');
216                         }
217
218                         j = i;
219
220                         if (base != -1)
221                                 printf("%08X  ", base);
222                 }
223
224                 switch (flg & 3)
225                 {
226                 case 0:
227                         printf("%02X ", start[i] & 0xff);
228                         ++i;
229                         break;
230                 case 1:
231                         printf("%02X%02X ", start[i] & 0xff, start[i+1] & 0xff);
232                         i += 2;
233                         break;
234                 case 2:
235                         printf("%02X%02X%02X%02X ", start[i] & 0xff, start[i+1] & 0xff,
236                                 start[i+2] & 0xff, start[i+3] & 0xff);
237                         i += 4;
238                         break;
239                 case 3:
240                         break;
241                 }
242
243                 if (base != -1)
244                         base += 1 << (flg & 3);
245         }
246
247         // Print remaining bit of ASCII; the hairy expression computes the number
248         // of spaces to print to make the ASCII line up nicely.
249         if (j != i)
250         {
251                 k = ((16 - (i - j)) / (1 << (flg & 3))) * siztab[flg & 3];
252
253                 while(k--)
254                         putchar(' ');
255
256                 printf("  ");
257
258                 while(j < i)
259                         visprt(start[j++]);
260
261                 putchar('\n');
262         }
263
264         return 0;
265 }
266
267
268 //
269 // Dump list of tokens on stdout in printable form
270 //
271 int dumptok(TOKEN * tk)
272 {
273         int flg = 0;
274
275         while (*tk != EOL)
276         {
277                 if (flg++)
278                         printf(" ");
279
280                 if (*tk >= 128)
281                 {
282                         printf("REG=%u", *tk++ - 128);
283                         continue;
284                 }
285
286                 switch ((int)*tk++)
287                 {
288                 case CONST:                                        // CONST <value>
289                         printf("CONST=%u", *tk++);
290                         break;
291                 case STRING:                                       // STRING <address>
292                         printf("STRING='%s'", string[*tk++]);
293                         break;
294                 case SYMBOL:                                       // SYMBOL <address> 
295                         printf("SYMBOL='%s'", string[*tk++]);
296                         break;
297                 case EOL:                                          // End of line 
298                         printf("EOL");
299                         break;
300                 case TKEOF:                                        // End of file (or macro)
301                         printf("TKEOF");
302                         break;
303                 case DEQUALS:                                      // == 
304                         printf("DEQUALS");
305                         break;
306                 case DCOLON:                                       // :: 
307                         printf("DCOLON");
308                         break;
309                 case GE:                                           // >= 
310                         printf("GE");
311                         break;
312                 case LE:                                           // <= 
313                         printf("LE");
314                         break;
315                 case NE:                                           // <> or != 
316                         printf("NE");
317                         break;
318                 case SHR:                                          // >> 
319                         printf("SHR");
320                         break;
321                 case SHL:                                          // << 
322                         printf("SHL");
323                         break;
324                 default:
325                         printf("%c", (int)tk[-1]);
326                         break;
327                 }
328         }
329
330         printf("\n");
331
332         return 0;
333 }
334
335
336 //
337 // Dump everything
338 //
339 int dump_everything(void)
340 {
341         int i;
342
343         for(i=1; i<NSECTS; i++)
344         {
345                 if (sect[i].scattr & SUSED)
346                 {
347                         printf("Section %d sloc=$%X\n", i, sect[i].sloc);
348                         printf("Code:\n");
349                         chdump(sect[i].sfcode, 1);
350
351                         printf("Fixup:\n");
352                         fudump(sect[i].sffix);
353
354                         printf("\n");
355                 }
356         }
357
358         printf("\nMarks:\n");
359         mudump();                                                               // Dump marks
360 //      printf("Total memory allocated=$%X\n", amemtot);
361
362         return 0;
363 }