/[gxemul]/upstream/0.3.3.1/experiments/rssb_as.c
This is repository of my old source code which isn't updated any more. Go to git.rot13.org for current projects!
ViewVC logotype

Annotation of /upstream/0.3.3.1/experiments/rssb_as.c

Parent Directory Parent Directory | Revision Log Revision Log


Revision 7 - (hide annotations)
Mon Oct 8 16:18:14 2007 UTC (16 years, 8 months ago) by dpavlin
File MIME type: text/plain
File size: 6750 byte(s)
0.3.3.1
1 dpavlin 2 /*
2     * Copyright (C) 2002,2005 Anders Gavare. All rights reserved.
3     *
4     * Redistribution and use in source and binary forms, with or without
5     * modification, are permitted provided that the following conditions are met:
6     *
7     * 1. Redistributions of source code must retain the above copyright
8     * notice, this list of conditions and the following disclaimer.
9     * 2. Redistributions in binary form must reproduce the above copyright
10     * notice, this list of conditions and the following disclaimer in the
11     * documentation and/or other materials provided with the distribution.
12     * 3. The name of the author may not be used to endorse or promote products
13     * derived from this software without specific prior written permission.
14     *
15     * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
16     * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
17     * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
18     * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
19     * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
20     * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
21     * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
22     * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
23     * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
24     * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
25     * SUCH DAMAGE.
26     *
27     * $Id: rssb_as.c,v 1.2 2005/03/08 23:10:10 debug Exp $
28     *
29     * A simple assembler for URISC ("reverse subtract and skip on borrow").
30     */
31    
32     #include <stdio.h>
33     #include <stdlib.h>
34     #include <string.h>
35     #include <inttypes.h>
36    
37    
38     #define MAX_SYMBOL_LEN 64
39    
40     struct symbol {
41     char name[MAX_SYMBOL_LEN];
42     uint32_t addr;
43     struct symbol *next;
44     };
45    
46    
47     struct symbol *first_symbol = NULL;
48    
49    
50     int debug = 0;
51    
52    
53     uint32_t get_symbol(char *symbol)
54     {
55     struct symbol *s;
56    
57     s = first_symbol;
58     while (s != NULL) {
59     if (strcmp(symbol, s->name) == 0)
60     return s->addr;
61    
62     s = s->next;
63     }
64    
65     fprintf(stderr, "undefined symbol '%s'\n", symbol);
66     exit(1);
67     }
68    
69    
70     void add_symbol(char *symbol, uint32_t addr)
71     {
72     struct symbol *s;
73    
74     if (strlen(symbol) > MAX_SYMBOL_LEN-1) {
75     fprintf(stderr, "symbol '%s' too long\n", symbol);
76     exit(1);
77     }
78    
79     s = malloc(sizeof(struct symbol));
80     if (s == NULL) {
81     fprintf(stderr, "out of memory\n");
82     exit(1);
83     }
84    
85     strcpy(s->name, symbol);
86     s->name[strlen(symbol)] = 0;
87     s->addr = addr;
88    
89     if (debug > 1)
90     printf(" %08x = %s\n", addr, symbol);
91    
92     s->next = first_symbol;
93     first_symbol = s;
94     }
95    
96    
97     uint32_t pass1(FILE *fin)
98     {
99     uint32_t curaddr = 0;
100     char line[200];
101     int lineno = 0;
102    
103     if (debug > 0)
104     printf("Pass 1\n");
105    
106     while (!feof(fin)) {
107     line[0] = '\0';
108     fgets(line, sizeof(line), fin);
109     lineno++;
110     if (line[0]) {
111     if (line[strlen(line)-1]=='\n')
112     line[strlen(line)-1]=0;
113    
114     if (debug > 2)
115     printf(" addr=%08x line='%s'\n",
116     curaddr,line);
117    
118     switch (line[0]) {
119     case '\0':
120     case '#':
121     break;
122     case 'L':
123     /* Add a symbol: */
124     add_symbol(line+1, curaddr);
125     break;
126     case 'A':
127     case 'D':
128     case 'E':
129     /* Increase addr by 4: */
130     curaddr += sizeof(uint32_t);
131     break;
132     case 'O':
133     /* Set orig manually: */
134     curaddr = atoi(line+1);
135     break;
136     default:
137     fprintf(stderr, "error on input line %i\n",
138     lineno);
139     exit(1);
140     }
141     }
142     }
143    
144     return curaddr;
145     }
146    
147    
148     void pass2(FILE *fin, FILE *fout, uint32_t first_diffaddr)
149     {
150     uint32_t curaddr = 0;
151     uint32_t curdiffaddr = first_diffaddr;
152     uint32_t value, value2;
153     char line[200];
154     int lineno = 0;
155     char *p;
156     unsigned char b1;
157     unsigned char b2;
158     unsigned char b3;
159     unsigned char b4;
160    
161     if (debug > 0)
162     printf("Pass 2\n");
163    
164     while (!feof(fin)) {
165     line[0] = '\0';
166     fgets(line, sizeof(line), fin);
167     lineno++;
168     if (line[0]) {
169     if (line[strlen(line)-1]=='\n')
170     line[strlen(line)-1]=0;
171    
172     if (debug > 2)
173     printf(" addr=%08x line='%s'\n",
174     curaddr,line);
175    
176     switch (line[0]) {
177     case '\0':
178     case '#':
179     case 'L':
180     break;
181     case 'A':
182     /* Output value and increase addr by 4: */
183     fseek(fout, curaddr, SEEK_SET);
184     if (line[1]>='0' && line[1]<='9')
185     value = atoi(line+1);
186     else
187     value = get_symbol(line+1);
188     b1 = value >> 24;
189     b2 = value >> 16;
190     b3 = value >> 8;
191     b4 = value;
192     fwrite(&b1, 1, 1, fout);
193     fwrite(&b2, 1, 1, fout);
194     fwrite(&b3, 1, 1, fout);
195     fwrite(&b4, 1, 1, fout);
196    
197     curaddr += sizeof(uint32_t);
198     break;
199     case 'D':
200     case 'E':
201     /* Address differance calculation: */
202     p = line+1;
203     while (*p && *p!=' ')
204     p++;
205     if (!*p) {
206     fprintf(stderr, "error on input line"
207     " %i, D syntax error\n", lineno);
208     exit(1);
209     }
210     p[0]=0; p++;
211    
212     if (line[1]>='0' && line[1]<='9')
213     value = atoi(line+1);
214     else
215     value = get_symbol(line+1);
216    
217     if (p[0]>='0' && p[0]<='9')
218     value2 = atoi(p);
219     else
220     value2 = get_symbol(p);
221    
222     if (line[0]=='D') {
223     if (value < value2)
224     value = value - value2 + 4;
225     else
226     value = value - value2;
227     } else {
228     /* In conditional jumps: The -4
229     is because PC is already
230     updated when it is written
231     back to: */
232     value = value - value2 - 4;
233     }
234    
235     /* Output value in the diff section: */
236     fseek(fout, curdiffaddr, SEEK_SET);
237     b1 = value >> 24;
238     b2 = value >> 16;
239     b3 = value >> 8;
240     b4 = value;
241     fwrite(&b1, 1, 1, fout);
242     fwrite(&b2, 1, 1, fout);
243     fwrite(&b3, 1, 1, fout);
244     fwrite(&b4, 1, 1, fout);
245    
246     /* Output the diff addr to the code section: */
247     fseek(fout, curaddr, SEEK_SET);
248     value = curdiffaddr;
249     b1 = value >> 24;
250     b2 = value >> 16;
251     b3 = value >> 8;
252     b4 = value;
253     fwrite(&b1, 1, 1, fout);
254     fwrite(&b2, 1, 1, fout);
255     fwrite(&b3, 1, 1, fout);
256     fwrite(&b4, 1, 1, fout);
257    
258     curaddr += sizeof(uint32_t);
259     curdiffaddr += sizeof(uint32_t);
260     break;
261     case 'O':
262     /* Set orig manually: */
263     curaddr = atoi(line+1);
264     break;
265     default:
266     fprintf(stderr, "error on input line %i\n",
267     lineno);
268     exit(1);
269     }
270     }
271     }
272     }
273    
274    
275     int main(int argc, char *argv[])
276     {
277     FILE *fin, *fout;
278     uint32_t first_diffaddr;
279    
280     if (argc != 3) {
281     fprintf(stderr, "usage: %s asmsource binimage\n", argv[0]);
282     fprintf(stderr, "Input is read from asmsource and "
283     "output is written to binimage\n");
284     exit(1);
285     }
286    
287     fin = fopen(argv[1], "r");
288     if (fin == NULL) {
289     perror(argv[1]);
290     exit(2);
291     }
292    
293     fout = fopen(argv[2], "w");
294     if (fout = NULL) {
295     perror(argv[2]);
296     exit(2);
297     }
298    
299     first_diffaddr = pass1(fin);
300     fseek(fin, 0, SEEK_SET);
301     pass2(fin, fout, first_diffaddr);
302    
303     fclose(fin);
304     fclose(fout);
305    
306     return 0;
307     }
308    

  ViewVC Help
Powered by ViewVC 1.1.26