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

Subversion Repositories tiny64

[/] [tiny64/] [trunk/] [Assem/] [ASSEM.C] - Blame information for rev 4

Details | Compare with Previous | View Log

Line No. Rev Author Line
1 3 riedelx
/*******************************************
2
   assem.c
3
   an assembler for the TinyX CPU
4
         TGB Ulrich Riedel 20040313
5
*******************************************/
6
 
7
#include 
8
#include 
9
#include 
10
#include 
11
 
12
typedef struct _tag_Tmcode {
13
        struct _tag_Tmcode *prev;
14
        struct _tag_Tmcode *next;
15
        int linenumber;
16
        unsigned long addr;        // machinecode address
17
  char label[34];            // destination label
18
        char mnemo[16];            // mnemonic or directive
19
        char operand1[80];         // operands
20
        char operand2[80];
21
        char operand3[80];
22
        unsigned char mcod[128];   // machinecode ( maximum of 1024 bit instruction code )
23
        unsigned char imm[128];
24
        unsigned long oaddr1;      // operand address1
25
        unsigned long oaddr2;      // operand address2
26
        unsigned long oaddr3;      // operand address2
27
        char olabel1[34];          // operand label1
28
        char olabel2[34];          // operand label2
29
        char olabel3[34];          // operand label3
30
} Tmcode;
31
 
32
typedef struct {
33
        unsigned long addr;
34
        char label[40];
35
} Taddress;
36
 
37
int g_wordSize;  // processor word size
38
 
39
char *getvalue(char *str, unsigned char *val);  // reads string value
40
 
41
int main(int argc,char *argv[])
42
{
43
        FILE *fp;
44
        char filename[256];
45
        unsigned char binTemp[128];
46
        char line[80];
47
        char tmpStr[40];
48
        char *tempPtr;
49
        int  linenumber, idx, maxi, jdx, sdx;
50
        unsigned short slen;
51
        Tmcode *head, *tail, *cPtr, *hPtr, *tPtr;
52
        unsigned long addr, val1, val2, val3;
53
        unsigned char code[128], chksum, lsn, msn;
54
        Taddress *address;
55
        unsigned char ccMode;
56
        unsigned char aluMode;
57
        unsigned char updateFlag;
58
        unsigned char carryUse;
59
        unsigned char writeCycle;
60
        unsigned char memRead;
61
        unsigned char immediate;
62
        unsigned char   valmux;
63
        unsigned char dstReg;
64
        unsigned char src1Reg;
65
        unsigned char src2Reg;
66
 
67
        g_wordSize = 0;
68
 
69
        if (argc == 1) {
70
    fprintf(stderr, "usage: tinyx file\n");
71
                return 1;
72
        }
73
 
74
        fp = fopen(argv[1], "r");
75
        if(NULL == fp) {
76
                fprintf(stderr, "%s doesn't exist\n", argv[1]);
77
                return 2;
78
        }
79
        strncpy(filename, argv[1], 120);
80
        strcat(filename, ".HEX");
81
 
82
        printf("prepass\n");
83
/////////// pre pass /////////////////////////////////////
84
  linenumber = 1;  // sourcecode linenumber count
85
        head = tail = NULL;
86
        while(fgets(line, 79, fp)) {
87
                if(line[0] == 0) {  // empty line
88
                        linenumber++;
89
                        continue;
90
                }
91
                sdx = strlen(line);
92
                for(idx=0; idx
93
      if(!isspace(line[idx])) break;
94
                }
95
                if(sdx == idx) {  // whitespace line
96
                        linenumber++;
97
                        continue;
98
                }
99
///////// make line to uppercase characters, ignoring comment lines
100
                for(idx=0; line[idx]; idx++) {
101
                        if(line[idx] == 13) { line[idx] = 0; continue; }   // return
102
                        if(line[idx] == 10) { line[idx] = 0; continue; }   // linefeed
103
                        if(line[idx] == 9)  { line[idx] = 32; continue; }  // tab
104
                        if((line[idx] & 0xE0) == 0) {
105
                                fprintf(stderr, "%d contains non printable characters.\n", linenumber);
106
                                return 3;
107
                        }
108
                        if(line[idx] < 0) {
109
                                fprintf(stderr, "%d contains non printable characters\n", linenumber);
110
                                return 3;
111
                        }
112
                        line[idx] = toupper(line[idx]);
113
                }
114
                if(line[0] == ';') { linenumber++; continue; } // skip comment lines
115
                if(line[0] == '.') {
116
      fprintf(stderr, "%d no directive first allowed\n", linenumber);
117
                        linenumber++;
118
                  continue;
119
                }
120
///////// break into up to 5 components //////////////////
121
////////  alloc mcode structure for this sourcecode line
122
    hPtr = (Tmcode *) malloc(sizeof(Tmcode));
123
                memset(hPtr, 0, sizeof(Tmcode));
124
    if(head == NULL) {
125
      head = hPtr;
126
                        tail = hPtr;
127
                        cPtr = head;
128
                } else {
129
                        tPtr = cPtr;
130
                        cPtr->next = hPtr;
131
                        cPtr = cPtr->next;
132
                        cPtr->prev = tPtr;
133
                        tail = cPtr;
134
                }
135
                hPtr->linenumber = linenumber;
136
///////// 1st component, label ///////////////////////////
137
    idx = 0; // start at beginning sourcecode line
138
    if(!isspace(line[0])) { // first char nonspace?
139
                        for(; line[idx] && (idx<32); idx++) {  // label max 32 chars
140
                                if(isspace(line[idx])) break;  // delimiter
141
                                if(line[idx] == ';')   break;  // comment
142
                                tmpStr[idx] = line[idx];
143
                        }
144
                        tmpStr[idx] = 0;
145
      strcpy(hPtr->label, tmpStr);  // save label
146
                }
147
                if(0 == line[idx]) {  // end of line?, label only
148
                        linenumber++;
149
                        continue;
150
                }
151
///////// 2nd component, mnemonic or directive ///////////
152
    while(isspace(line[idx])) idx++;  // skip space
153
    for(jdx=0; line[idx] && (jdx<15); jdx++) {
154
      if(isspace(line[idx])) break;  // delimiter
155
                        if(line[idx] == ';')   break;  // comment
156
                        tmpStr[jdx] = line[idx++];
157
                }
158
                tmpStr[jdx] = 0;
159
                strcpy(hPtr->mnemo, tmpStr);  // save mnemonic or directive
160
    if(0 == line[idx]) {  // suddenly end of line?
161
                        fprintf(stderr, "%d operand missing\n", linenumber);
162
                        linenumber++;
163
                        continue;
164
                }
165
    while(isspace(line[idx])) idx++;  // skip space
166
    if(0 == line[idx]) {  // suddenly end of line?
167
                        fprintf(stderr, "%d operand missing\n", linenumber);
168
                        linenumber++;
169
                        continue;
170
                }
171
///////// 3,4,5th component, operands /////////////////////////
172
//// fetch operads strings
173
    for(jdx=0; line[idx] && (jdx<80); jdx++) {
174
                        tmpStr[jdx] = line[idx++];
175
                }
176
                tmpStr[jdx] = 0;
177
                sdx = jdx;
178
                jdx = 0;
179
//// remove spaces between operands
180
                for(idx=0; idx
181
      if(isspace(tmpStr[idx])) continue;
182
                        if(tmpStr[idx] == ';') break; // comment
183
                        tmpStr[jdx++] = tmpStr[idx];
184
                }
185
                tmpStr[jdx] = 0;
186
                hPtr->operand1[0] = 0;
187
                hPtr->operand2[0] = 0;
188
                hPtr->operand3[0] = 0;
189
                idx = 0;
190
                for(jdx=0; tmpStr[idx] && jdx<70; jdx++) {
191
                        if(tmpStr[idx] == 0) break;
192
                        if(tmpStr[idx] == ',') break;
193
                        hPtr->operand1[jdx] = tmpStr[idx++];
194
                }
195
                hPtr->operand1[jdx] = 0;
196
                if(tmpStr[idx]) {
197
                  idx++;
198
                        for(jdx=0; tmpStr[idx] && jdx<70; jdx++) {
199
                                if(tmpStr[idx] == 0) break;
200
                                if(tmpStr[idx] == ',') break;
201
                                hPtr->operand2[jdx] = tmpStr[idx++];
202
                        }
203
                  hPtr->operand2[jdx] = 0;
204
                  if(tmpStr[idx]) {
205
                          idx++;
206
                                for(jdx=0; tmpStr[idx] && jdx<70; jdx++) {
207
                                        if(tmpStr[idx] == 0) break;
208
                                        if(tmpStr[idx] == ',') break;
209
                                        hPtr->operand3[jdx] = tmpStr[idx++];
210
                                }
211
                          hPtr->operand3[jdx] = 0;
212
                  }
213
          }
214
                hPtr->linenumber = linenumber;
215
                linenumber++;
216
        }
217
        fclose(fp);
218
 
219
#if 0
220
///////////////// test output //////////////////////////////////
221
  hPtr = head;
222
  while(hPtr) {
223
                printf("%d <%s><%s><%s><%s><%s>\n", hPtr->linenumber,
224
                                                 hPtr->label,
225
                                                 hPtr->mnemo,
226
                                                                                                                                                 hPtr->operand1,
227
                                                                                                                                                 hPtr->operand2,
228
                                                                                                                                                 hPtr->operand3);
229
                hPtr = hPtr->next;
230
        }
231
#endif
232
 
233
        printf("1st pass\n");
234
/////////// 1st pass ////////////////////////////////////
235
  addr = 0;
236
  hPtr = head;
237
        while(hPtr) {
238
    hPtr->addr = addr;
239
                if(!strlen(hPtr->mnemo)) {  // label only
240
      hPtr = hPtr->next;
241
                        continue;
242
                }
243
///////// check on directives ///////////////////////////
244
    if(!strcmp(hPtr->mnemo, ".WORDSIZE")) {  // set processor wordsize
245
      if(g_wordSize) {
246
                                fprintf(stderr, "processor wordsize already set!\n");
247
                                return 5;
248
                        }
249
                        g_wordSize = atoi(hPtr->operand1);
250
                        if(g_wordSize < 32) {
251
                                fprintf(stderr, "wordsize at least of 32 and multiple of 8 needed!\n");
252
                                return 6;
253
                        }
254
                        if(g_wordSize & 7) {
255
                                fprintf(stderr, "wordsize at least of 32 and multiple of 8 needed!\n");
256
                                return 7;
257
                        }
258
                        hPtr->linenumber = -1;
259
                        hPtr = hPtr->next;
260
                        continue;
261
                }
262
                if(g_wordSize == 0) {
263
                        fprintf(stderr, "missing, wordsize at least of 32 and multiple of 8 needed!\n");
264
                        return 8;
265
                }
266
    if(!strcmp(hPtr->mnemo, ".ORG")) {  // set location address
267
      addr = strtol(hPtr->operand1, &tempPtr, 16);
268
                        hPtr->addr = addr;
269
                        hPtr->linenumber = -1;
270
                        hPtr = hPtr->next;
271
                        continue;
272
                }
273
                if(!strcmp(hPtr->mnemo, ".DC")) {   // define constant
274
                        getvalue(hPtr->operand1, binTemp);
275
            idx = g_wordSize / 8;
276
                        memset(hPtr->mcod, 0, sizeof(hPtr->mcod));
277
                        memcpy(hPtr->mcod, &binTemp[128-idx], idx);
278
                        hPtr = hPtr->next;
279
                        addr++;
280
                        continue;
281
                }
282
                ccMode     = 16;
283
                aluMode    = 16;
284
                updateFlag = 0;
285
                carryUse   = 0;
286
                writeCycle = 0;
287
                memRead    = 0;
288
                immediate  = 0;
289
                valmux     = 0;
290
                dstReg     = 0;
291
                src1Reg    = 0;
292
                src2Reg    = 0;
293
                sdx        = 0;
294
          if(!memcmp(&hPtr->mnemo[sdx], "U", 1)) {  // update flag after alu operation ?
295
                        updateFlag = 1;
296
                        sdx++;
297
                }
298
                ////// scan condition code
299
                if(!memcmp(&hPtr->mnemo[sdx], "A", 1)) {          // always
300
                        ccMode = 0;   sdx++;
301
                } else if(!memcmp(&hPtr->mnemo[sdx], "CC", 2)) {  // carry clear
302
                        ccMode = 1;   sdx += 2;
303
                } else if(!memcmp(&hPtr->mnemo[sdx], "CS", 2)) {  // carry set
304
                        ccMode = 2;   sdx += 2;
305
                } else if(!memcmp(&hPtr->mnemo[sdx], "EQ", 2)) {  // equal
306
                        ccMode = 3;   sdx += 2;
307
                } else if(!memcmp(&hPtr->mnemo[sdx], "GE", 2)) {  // greater equal
308
                        ccMode = 4;   sdx += 2;
309
                } else if(!memcmp(&hPtr->mnemo[sdx], "GT", 2)) {  // greater than
310
                        ccMode = 5;   sdx += 2;
311
                } else if(!memcmp(&hPtr->mnemo[sdx], "HI", 2)) {  // higher
312
                        ccMode = 6;   sdx += 2;
313
                } else if(!memcmp(&hPtr->mnemo[sdx], "LE", 2)) {  // less equal
314
                        ccMode = 7;   sdx += 2;
315
                } else if(!memcmp(&hPtr->mnemo[sdx], "LS", 2)) {  // less
316
                        ccMode = 8;   sdx += 2;
317
                } else if(!memcmp(&hPtr->mnemo[sdx], "LT", 2)) {  // less than
318
                  ccMode = 9;   sdx += 2;
319
                } else if(!memcmp(&hPtr->mnemo[sdx], "MI", 2)) {  // minus
320
                        ccMode = 10;  sdx += 2;
321
                } else if(!memcmp(&hPtr->mnemo[sdx], "NE", 2)) {  // not equal
322
                        ccMode = 11;  sdx += 2;
323
                } else if(!memcmp(&hPtr->mnemo[sdx], "PL", 2)) {  // plus
324
                        ccMode = 12;  sdx += 2;
325
                } else if(!memcmp(&hPtr->mnemo[sdx], "VC", 2)) {  // overflow clear
326
                        ccMode = 13;  sdx += 2;
327
                } else if(!memcmp(&hPtr->mnemo[sdx], "VS", 2)) {  // overflow set
328
                        ccMode = 14;  sdx += 2;
329
                } else if(!memcmp(&hPtr->mnemo[sdx], "N", 1)) {   // never
330
                        ccMode = 15;  sdx++;
331
                }
332
    ////// scan alu mode
333
                if(!memcmp(&hPtr->mnemo[sdx], "MOV", 3)) {         // mov
334
                        aluMode = 0;
335
                } else if(!memcmp(&hPtr->mnemo[sdx], "AND", 3)) {  // and
336
                        aluMode = 1;
337
                } else if(!memcmp(&hPtr->mnemo[sdx], "OR", 2)) {   // or
338
                        aluMode = 2;
339
                } else if(!memcmp(&hPtr->mnemo[sdx], "XOR", 3)) {  // xor
340
                        aluMode = 3;
341
                } else if(!memcmp(&hPtr->mnemo[sdx], "ADD", 3)) {  // add
342
                        aluMode = 4;
343
                        if(hPtr->mnemo[sdx+3] == 'C') carryUse = 1;
344
                } else if(!memcmp(&hPtr->mnemo[sdx], "SUB", 3)) {  // sub
345
                        aluMode = 5;
346
                        if(hPtr->mnemo[sdx+3] == 'C') carryUse = 1;
347
                } else if(!memcmp(&hPtr->mnemo[sdx], "ROR", 3)) {  // ror
348
                        aluMode = 6;
349
                } else if(!memcmp(&hPtr->mnemo[sdx], "LSR", 3)) {  // lsr
350
                        aluMode = 7;
351
                } else if(!memcmp(&hPtr->mnemo[sdx], "LSRA", 4)) { // lsra
352
                        aluMode = 8;
353
                } else if(!memcmp(&hPtr->mnemo[sdx], "SWAP", 4)) { // swap
354
                        aluMode = 9;
355
                } else if(!memcmp(&hPtr->mnemo[sdx], "SWAPB", 5)) {// swapb
356
                        aluMode = 10;
357
                } else if(!memcmp(&hPtr->mnemo[sdx], "INC", 3)) {  // inc
358
                        aluMode = 11;
359
                        if(hPtr->mnemo[sdx+3] == 'C') carryUse = 1;
360
                } else if(!memcmp(&hPtr->mnemo[sdx], "DEC", 3)) {  // dec
361
                        aluMode = 12;
362
                        if(hPtr->mnemo[sdx+3] == 'C') carryUse = 1;
363
                } else if(!memcmp(&hPtr->mnemo[sdx], "RORB", 4)) { // rorb
364
                        aluMode = 13;
365
                }
366
////////////// destination operand
367
    if(hPtr->operand1[0] == 0) {
368
                  hPtr = hPtr->next; // goto next line
369
                        fprintf(stderr, "%d destination operand missing\n", hPtr->linenumber);
370
                        continue;
371
                }
372
                sdx = 0;
373
                if(hPtr->operand1[0] == '[') {
374
                        sdx++;
375
                        writeCycle = 1;
376
          }
377
                if(hPtr->operand1[sdx] != 'R') {
378
                        fprintf(stderr, "%d destination operand error\n", hPtr->linenumber);
379
                } else {
380
                        if(!isdigit(hPtr->operand1[sdx+1])) {
381
                                fprintf(stderr, "%d destination operand number error\n", hPtr->linenumber);
382
                        } else {
383
                                dstReg = hPtr->operand1[sdx+1] - '0';
384
                        }
385
                }
386
                src1Reg = dstReg;  // set default register
387
                src2Reg = dstReg;  // set default register, improve to opcode kontext register
388
//////////// source1 operand
389
                if(hPtr->operand2[0]) {
390
            sdx = 0;
391
                        if(hPtr->operand2[0] == '[') {
392
                                if(writeCycle) {
393
                                hPtr = hPtr->next; // goto next line
394
                                        fprintf(stderr, "%d both memory accesses not supported\n", hPtr->linenumber);
395
                                        continue;
396
                                }
397
                                sdx++;
398
                                memRead = 1;
399
                  }
400
                        if(hPtr->operand2[sdx] != 'R') {  // immediate
401
                                if((hPtr->operand2[0] == '$') || isdigit(hPtr->operand2[0])) {
402
                                        getvalue(hPtr->operand2, binTemp);
403
                                        memcpy(hPtr->imm, &binTemp[128-g_wordSize/8], g_wordSize/8);
404
                                  immediate = 1;
405
                          } else {  // label
406
                                        strcpy(hPtr->olabel2, hPtr->operand2);
407
                                }
408
                        } else {
409
                                if(!isdigit(hPtr->operand2[sdx+1])) {
410
                                        fprintf(stderr, "%d source1 operand number error\n", hPtr->linenumber);
411
                                } else {
412
                                        src1Reg = hPtr->operand2[sdx+1] - '0';
413
                                        if(writeCycle) {
414
                                                src2Reg = dstReg;
415
                                        }
416
                                }
417
                        }
418
        ///////// source2 operand
419
                        if(hPtr->operand3[0] == 0) {
420
                                if(writeCycle == 0) {
421
                                  src2Reg = src1Reg;
422
                          }
423
                        } else {
424
                                if(hPtr->operand3[0] != 'R') {
425
                                                fprintf(stderr, "%d source2 operand number error\n", hPtr->linenumber);
426
                                        continue;
427
                                } else {
428
                                        if(!isdigit(hPtr->operand3[1])) {
429
                                                fprintf(stderr, "%d source2 operand number error\n", hPtr->linenumber);
430
                                        } else {
431
                                                src2Reg = hPtr->operand3[1] - '0';
432
                                        }
433
                                }
434
                        }
435
                } // if(hPtr->operand2[0] == 0)
436
///////// build machine code
437
                memset(hPtr->mcod, 0, sizeof(hPtr->mcod));
438
                hPtr->mcod[0] = (ccMode << 4) | aluMode;
439
                hPtr->mcod[1] = (memRead << 7) | (dstReg << 4) | (writeCycle << 3) | src1Reg;
440
                hPtr->mcod[2] = (immediate << 7) | (src2Reg << 4) | (updateFlag << 3) | (carryUse << 2);
441
    idx = g_wordSize / 8;
442
                memcpy(&hPtr->mcod[3], &hPtr->imm[3], idx-3);
443
                addr++;            // goto next program address
444
                hPtr = hPtr->next; // goto next line
445
        }
446
/////////// count label addresses ///////////////////////
447
  hPtr = head;
448
        maxi = 0;
449
        while(hPtr) {
450
                if(hPtr->label[0]) maxi++;
451
                hPtr = hPtr->next;
452
        }
453
/////////// table with label address ////////////////////
454
  address = (Taddress *) malloc(maxi * sizeof(Taddress));
455
        hPtr = head;
456
        idx = 0;
457
        while(hPtr) {
458
                if(hPtr->label[0]) {
459
                        address[idx].addr = hPtr->addr;
460
                        strcpy(address[idx].label, hPtr->label);
461
                        idx++;
462
                }
463
                hPtr = hPtr->next;
464
        }
465
 
466
        printf("2nd pass\n");
467
/////////// 2nd pass ////////////////////////////////////
468
  hPtr = head;
469
        while(hPtr) {
470
    if(hPtr->olabel2[0]) {  // resolve label, treated as immediate operand
471
      for(idx=0; idx
472
                                if(!strcmp(address[idx].label, hPtr->olabel2)) {
473
                                        hPtr->mcod[2] |= 0x80; // set immediate operand flag
474
                                        jdx = g_wordSize / 8;
475
                                        switch(jdx) {
476
                                                case 4:
477
                                                        hPtr->mcod[3] = (unsigned char) address[idx].addr;
478
                                                break;
479
                                                case 5:
480
                                                        hPtr->mcod[3] = (unsigned char) (address[idx].addr >> 8);
481
                                                        hPtr->mcod[4] = (unsigned char)  address[idx].addr;
482
                                                break;
483
                                                case 6:
484
                                                        hPtr->mcod[3] = (unsigned char) (address[idx].addr >> 16);
485
                                                        hPtr->mcod[4] = (unsigned char) (address[idx].addr >> 8);
486
                                                        hPtr->mcod[5] = (unsigned char)  address[idx].addr;
487
                                                break;
488
                                                default:
489
                                                  jdx -= 4;
490
                                                        hPtr->mcod[jdx++] = (unsigned char) (address[idx].addr >> 24);
491
                                                        hPtr->mcod[jdx++] = (unsigned char) (address[idx].addr >> 16);
492
                                                        hPtr->mcod[jdx++] = (unsigned char) (address[idx].addr >>  8);
493
                                                        hPtr->mcod[jdx++] = (unsigned char)  address[idx].addr;
494
                                        }
495
                                        break;
496
                                }
497
                        }
498
                        if(idx == maxi) {
499
                                fprintf(stderr, "%d unknown label\n", hPtr->linenumber);
500
                        }
501
                }
502
                hPtr = hPtr->next;
503
        }
504
 
505
////////// output ///////////////////////////////////////
506
  fp = fopen(filename, "w");  // write into Intel HEX file
507
        if(NULL == fp) {
508
                fprintf(stderr, "can't write to %s\n", filename);
509
                return 0;
510
        }
511
  hPtr = head;
512
        maxi = g_wordSize / 8;
513
  while(hPtr) {
514
                if(hPtr->linenumber < 0) {
515
                        hPtr = hPtr->next;
516
                        continue;
517
                }
518
                /*
519
                printf("%04X ", hPtr->addr);
520
    for(idx=0; idxmcod[idx]);
521
                printf("<%s><%s><%s><%s><%s>\n", hPtr->label, hPtr->mnemo, hPtr->operand1, hPtr->operand2, hPtr->operand3);
522
                */
523
 
524
                if(maxi) {
525
      sprintf(line, ":%02X%04X00", maxi, hPtr->addr);
526
                        for(idx=0; idx
527
                                sprintf(tmpStr, "%02X", hPtr->mcod[idx]);
528
                                strcat(line, tmpStr);
529
                        }
530
                        chksum = 0;
531
                        for(idx=1; line[idx]; idx += 2) {
532
        msn = line[idx] - '0';
533
                                if(msn > 9) msn -= 7;
534
        lsn = line[idx+1] - '0';
535
                                if(lsn > 9) lsn -= 7;
536
                                chksum += ((msn<<4) + lsn);
537
                        }
538
      chksum = 256 - chksum;
539
                        sprintf(tmpStr, "%02X", chksum);
540
                        strcat(line, tmpStr);
541
                        fprintf(fp, "%s\015\012", line);
542
          }
543
                hPtr = hPtr->next;
544
  }
545
        fprintf(fp, ":00000001FF\015\012");  // end of HEX file
546
        fclose(fp);
547
        return 0;
548
}
549
 
550
////////// gets a decimal or hexadecimal value
551
// decimal     is ddd
552
// hexadecimal is $hhh
553
// returns ptr after value
554
char *getvalue(char *str, unsigned char *val)
555
{
556
        int idx, jdx, kdx, radix, cy;
557
        unsigned short temp[128];
558
        unsigned short help[128];
559
 
560
        memset(temp, 0, sizeof(temp));
561
        memset(help, 0, sizeof(help));
562
        radix = 10;
563
        if(str[0] == '$') radix = 16;
564
  if(radix == 10) {
565
    for(idx=0; str[idx]; idx++) {
566
                  if(!isdigit(str[idx])) break;
567
                        cy = 0;
568
      for(jdx=127; jdx >=0; jdx--) { // shift left
569
                                temp[jdx] <<= 1;
570
                                if(cy) temp[jdx]++;
571
                                cy = 0;
572
                                if(temp[jdx] > 255) {
573
                                        cy++;
574
                                        temp[jdx] &= 255;
575
                                }
576
                        }
577
                        memcpy(help, temp, sizeof(help));
578
                        for(kdx=0; kdx<2; kdx++) {
579
                                cy = 0;
580
              for(jdx=127; jdx >=0; jdx--) { // shift left
581
                                        temp[jdx] <<= 1;
582
                                        if(cy) temp[jdx]++;
583
                                        cy = 0;
584
                                        if(temp[jdx] > 255) {
585
                                                cy++;
586
                                                temp[jdx] &= 255;
587
                                        }
588
                                }
589
                        }
590
      cy = 0;
591
                        for(jdx=127; jdx >=0; jdx--) {  // add
592
                                temp[jdx] += help[jdx];
593
                                if(cy) temp[jdx]++;
594
                                cy = 0;
595
                                if(temp[jdx] > 255) {
596
                                        cy++;
597
                                        temp[jdx] &= 255;
598
                                }
599
                        }
600
                        temp[127] += (str[idx] - '0');
601
                        cy = 0;
602
                        if(temp[127] > 255) {
603
                                cy++;
604
                                temp[127] &= 255;
605
                        }
606
                        for(jdx=126; jdx >=0; jdx--) {
607
                                temp[jdx] += cy;
608
                                cy = 0;
609
                                if(temp[jdx] > 255) {
610
                                        cy++;
611
                                        temp[jdx] &= 255;
612
                                }
613
                        }
614
                } // end for
615
        } else {
616
                for(idx=1; str[idx]; idx++) {
617
                        if(!isxdigit(str[idx])) break;
618
      for(jdx=0; jdx<127; jdx++) {  // shift 4 bits left
619
        temp[jdx] <<= 4;
620
                                temp[jdx] |= (15 & (temp[jdx+1] >> 4));
621
                        }
622
                        temp[127] <<= 4;
623
      jdx = str[idx] - '0';
624
                        if(jdx > 9) jdx -= 7;
625
                        temp[127] |= jdx;
626
                } // end for
627
        }
628
        for(idx=128-(g_wordSize/8); idx<128; idx++) {
629
                val[idx] = temp[idx];
630
        }
631
        return &str[idx];
632
}

powered by: WebSVN 2.1.0

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