Annotation of researchv8dc/cmd/cyntax/cem/diag.c, revision 1.1.1.1

1.1       root        1: #define        STD_OBJ 1
                      2: #include       "stdobj.h"
                      3: #include       "types.h"
                      4: #include       "cem.h"
                      5: #include       "symbol.h"
                      6: #include       "type.h"
                      7: 
                      8: /*
                      9:  *     Routines for generating diagnostics.
                     10:  */
                     11: 
                     12: #define        err(c)          putchar(c)
                     13: #define        err_str(s)      printf(str_fmt, (s))
                     14: #define        err_num(l)      printf(num_fmt, (l))
                     15: 
                     16: static char    *num_fmt        = "%ld";
                     17: static char    *str_fmt        = "%s";
                     18: static int     time_forced;
                     19: 
                     20: extern char    *strchr();
                     21: 
                     22: /*
                     23:  *     File names match and so do modtimes.
                     24:  */
                     25: int
                     26: match_times(s, t)
                     27: symbol *s;
                     28: symbol *t;
                     29: {
                     30:        return s == t && strchr(s->sy_name, TIME_SEP) != NULL;
                     31: }
                     32: 
                     33: /*
                     34:  *     Print the name of a basetype.
                     35:  */
                     36: void
                     37: print_basetype(my_type)
                     38: register int   my_type;
                     39: {
                     40:        register int    bit;
                     41:        register int    spoken;
                     42: 
                     43:        static char             *type_names[] =
                     44:        {
                     45:                "unsigned",
                     46:                "long",
                     47:                "char",
                     48:                "short",
                     49:                "int",
                     50:                "float",
                     51:                "void",
                     52:                "<bad type>",
                     53:        };
                     54: 
                     55:        if (!pedantic)
                     56:        {
                     57:                if ((my_type & (LONG | FLOAT)) == (LONG | FLOAT))
                     58:                {
                     59:                        err_str("double");
                     60:                        return;
                     61:                }
                     62:                else if ((my_type & (LONG | SHORT)) != 0)
                     63:                        my_type &= ~INT;
                     64:        }
                     65: 
                     66:        spoken = 0;
                     67:        
                     68:        for (bit = 0; my_type != 0; bit++, my_type >>= 1)
                     69:        {
                     70:                if ((my_type & 1) != 0)
                     71:                {
                     72:                        if (spoken)
                     73:                                err(' ');
                     74: 
                     75:                        spoken++;
                     76:                        err_str(type_names[bit]);
                     77:                }
                     78:        }
                     79: }
                     80: 
                     81: /*
                     82:  *     Print a type as one might say it.
                     83:  */
                     84: static void
                     85: put_verbose_type(t)
                     86: register type  *t;
                     87: {
                     88:        register int    spoken;
                     89:        register int    plural;
                     90: 
                     91:        spoken = 0;
                     92:        plural = 0;
                     93: 
                     94:        while (t != NULL)
                     95:        {
                     96:                if (spoken)
                     97:                        err(' ');
                     98: 
                     99:                switch (t->t_type)
                    100:                {
                    101:                case t_arrayof:
                    102:                        printf("array[%ld]", t->d.dim);
                    103: 
                    104:                        if (plural)
                    105:                                err('s');
                    106: 
                    107:                        err_str(" of");
                    108:                        plural = 1;
                    109:                        break;
                    110: 
                    111:                case t_basetype:
                    112:                        print_basetype(t->d.mask);
                    113: 
                    114:                        if (plural)
                    115:                                err('s');
                    116: 
                    117:                        return;
                    118: 
                    119:                case t_bitfield:
                    120:                        err_str("bitfield");
                    121: 
                    122:                        if (plural)
                    123:                                err('s');
                    124: 
                    125:                        err_str(" of");
                    126:                        break;
                    127: 
                    128:                case t_dimless:
                    129:                        err_str("array[]");
                    130: 
                    131:                        if (plural)
                    132:                                err('s');
                    133: 
                    134:                        err_str(" of");
                    135:                        plural = 1;
                    136:                        break;
                    137: 
                    138:                case t_ftnreturning:
                    139:                        err_str("function");
                    140: 
                    141:                        if (plural)
                    142:                                err('s');
                    143: 
                    144:                        err_str(" returning");
                    145:                        break;
                    146: 
                    147:                case t_ptrto:
                    148:                        err_str("pointer");
                    149: 
                    150:                        if (plural)
                    151:                                err('s');
                    152: 
                    153:                        err_str(" to");
                    154:                        break;
                    155: 
                    156:                case t_enum:
                    157:                        err_str("enum");
                    158: 
                    159:                        if (t->d.e->e_name != NULL)
                    160:                                printf(" %s", t->d.e->e_name->sy_name);
                    161: 
                    162:                        err_str(" (");
                    163:                        put_file(t->d.e->e_file, t->d.e->e_line);
                    164:                        err(')');
                    165:                        return;
                    166: 
                    167:                case t_structof:
                    168:                        err_str("struct");
                    169: 
                    170:                        if (t->d.s->s_name != NULL)
                    171:                                printf(" %s", t->d.s->s_name->sy_name);
                    172: 
                    173:                        err_str(" (");
                    174:                        put_file(t->d.s->s_file, t->d.s->s_line);
                    175:                        err(')');
                    176:                        return;
                    177: 
                    178:                case t_unionof:
                    179:                        err_str("union");
                    180: 
                    181:                        if (t->d.u->u_name != NULL)
                    182:                                printf(" %s", t->d.u->u_name->sy_name);
                    183: 
                    184:                        err_str(" (");
                    185:                        put_file(t->d.u->u_file, t->d.u->u_line);
                    186:                        err(')');
                    187:                        return;
                    188: 
                    189:                default:
                    190:                        err_str("unknown");
                    191: 
                    192:                        if (plural)
                    193:                                err('s');
                    194:                }
                    195: 
                    196:                t = t->t_subtype;
                    197:                spoken = 1;
                    198:        }
                    199: }
                    200: 
                    201: /*
                    202:  *     Stash routines for 'put_c_type'.  We need to be able
                    203:  *     to build up a type by 'outputing' characters before and
                    204:  *     after what we have already said.  The average type is
                    205:  *     expected to take up no more than TYPE_SIZE chars (not counting
                    206:  *     basetype or complex base which always comes first).  The
                    207:  *     amount of backup is expected not to exceed HEAD_SIZE chars.
                    208:  *     If these are exceeded we extend in the appropriate direction
                    209:  *     by TYPE_EXTEND chars.
                    210:  *
                    211:  *     str_buff:
                    212:  *
                    213:  *     0 - unused - str_head - stuff - str_tail - unused - str_limit
                    214:  */
                    215: static int     str_head;
                    216: static int     str_tail;
                    217: static int     str_start;
                    218: static int     str_limit;
                    219: static char    *str_buff;
                    220: 
                    221: #define        TYPE_SIZE       64
                    222: #define        TYPE_EXTEND     32
                    223: #define        HEAD_SIZE       16
                    224: 
                    225: static void
                    226: str_init()
                    227: {
                    228:        str_limit = TYPE_SIZE;
                    229:        str_start = HEAD_SIZE;
                    230:        str_buff = salloc((long)str_limit);
                    231: }
                    232: 
                    233: static void
                    234: str_extend(ext, head)
                    235: int    ext;
                    236: int    head;
                    237: {
                    238:        register char   *p;
                    239:        register char   *q;
                    240: 
                    241:        str_limit += ext;
                    242:        str_buff = srealloc(str_buff, (long)str_limit);
                    243: 
                    244:        if (head)
                    245:        {
                    246:                str_start += ext;
                    247:                str_head += ext;
                    248:                str_tail += ext;
                    249:                p = str_buff + str_limit;
                    250:                q = p - ext;
                    251: 
                    252:                while (q > str_buff)
                    253:                        *--p = *--q;
                    254:        }
                    255: }
                    256: 
                    257: static void
                    258: head_char(c)
                    259: int    c;
                    260: {
                    261:        if (--str_head < 0)
                    262:                str_extend(HEAD_SIZE, 1);
                    263: 
                    264:        str_buff[str_head] = c;
                    265: }
                    266: 
                    267: static void
                    268: tail_char(c)
                    269: int    c;
                    270: {
                    271:        if (str_tail == str_limit)
                    272:                str_extend(TYPE_EXTEND, 0);
                    273: 
                    274:        str_buff[str_tail++] = c;
                    275: }
                    276: 
                    277: static void
                    278: tail_str(s)
                    279: register char  *s;
                    280: {
                    281:        while (*s != '\0')
                    282:                tail_char(*s++);
                    283: }
                    284: 
                    285: /*
                    286:  *     Print a type as it may have been declared.
                    287:  */
                    288: static void
                    289: put_c_type(ct)
                    290: type   *ct;
                    291: {
                    292:        register type   *t;
                    293:        char            buff[16];
                    294: 
                    295:        for (t = ct; t != NULL; t = t->t_subtype)
                    296:        {
                    297:                switch (t->t_type)
                    298:                {
                    299:                case t_arrayof:
                    300:                        sprintf(buff, "[%ld]", t->d.dim);
                    301:                        tail_str(buff);
                    302:                        break;
                    303: 
                    304:                case t_basetype:
                    305:                        print_basetype(t->d.mask);
                    306:                        goto finish;
                    307: 
                    308:                case t_bitfield:
                    309:                        sprintf(buff, ":%ld", t->d.size);
                    310:                        tail_str(buff);
                    311:                        break;
                    312: 
                    313:                case t_dimless:
                    314:                        tail_str("[]");
                    315:                        break;
                    316: 
                    317:                case t_ftnreturning:
                    318:                        if (t != ct)
                    319:                        {
                    320:                                head_char('(');
                    321:                                tail_char(')');
                    322:                        }
                    323: 
                    324:                        tail_str("()");
                    325:                        break;
                    326: 
                    327:                case t_ptrto:
                    328:                        head_char('*');
                    329:                        break;
                    330: 
                    331:                case t_enum:
                    332:                        err_str("enum");
                    333: 
                    334:                        if (t->d.e->e_name != NULL)
                    335:                                printf(" %s", t->d.e->e_name->sy_name);
                    336: 
                    337:                        err_str(" (");
                    338:                        put_file(t->d.e->e_file, t->d.e->e_line);
                    339:                        err(')');
                    340:                        goto finish;
                    341: 
                    342:                case t_structof:
                    343:                        err_str("struct");
                    344: 
                    345:                        if (t->d.s->s_name != NULL)
                    346:                                printf(" %s", t->d.s->s_name->sy_name);
                    347: 
                    348:                        err_str(" (");
                    349:                        put_file(t->d.s->s_file, t->d.s->s_line);
                    350:                        err(')');
                    351:                        goto finish;
                    352: 
                    353:                case t_unionof:
                    354:                        err_str("union");
                    355: 
                    356:                        if (t->d.u->u_name != NULL)
                    357:                                printf(" %s", t->d.u->u_name->sy_name);
                    358: 
                    359:                        err_str(" (");
                    360:                        put_file(t->d.u->u_file, t->d.u->u_line);
                    361:                        err(')');
                    362:                        goto finish;
                    363: 
                    364:                default:
                    365:                        err_str("unknown");
                    366: 
                    367:                finish:
                    368:                        if (t != ct)
                    369:                                err(' ');
                    370: 
                    371:                        return;
                    372:                }
                    373:        }
                    374: }
                    375: 
                    376: /*
                    377:  *     Print a type, choose between the two formats.
                    378:  */
                    379: void
                    380: put_type(t, force)
                    381: register type  *t;
                    382: int            force;
                    383: {
                    384:        time_forced = force;
                    385: 
                    386:        if (verbose)
                    387:                put_verbose_type(t);
                    388:        else
                    389:        {
                    390:                if (str_buff == NULL)
                    391:                        str_init();
                    392: 
                    393:                str_head = str_start;
                    394:                str_tail = str_start;
                    395:                put_c_type(t);
                    396:                tail_char('\0');
                    397:                err_str(&str_buff[str_head]);
                    398:        }
                    399: 
                    400:        time_forced = 0;
                    401: }
                    402: 
                    403: /*
                    404:  *     Print a filename.  Strip leading occurences of "./".
                    405:  *     Perhaps also print the mod time.
                    406:  */
                    407: static void
                    408: format_filename(s)
                    409: register char  *s;
                    410: {
                    411:        register char   *p;
                    412:        register long   l;
                    413:        extern char     *strrchr();
                    414:        extern long     atol();
                    415: 
                    416:        while (s[0] == '.' && s[1] == '/' && s[2] != '\0')
                    417:                s += 2;
                    418: 
                    419:        if ((p = strrchr(s, TIME_SEP)) == NULL)
                    420:                printf("%s", s);
                    421:        else
                    422:        {
                    423:                *p++ = '\0';
                    424:                err_str(s);
                    425: 
                    426:                if ((time_forced || tell_times) && (l = atol(p)) != 0)
                    427:                        printf(" [%s]", stime(l));
                    428: 
                    429:                *--p = TIME_SEP;
                    430:        }
                    431: }
                    432: 
                    433: /*
                    434:  *     Print the current filename and note that this file has errors.
                    435:  *     Used for file-static errors.
                    436:  */
                    437: void
                    438: say_file()
                    439: {
                    440:        format_filename(src_file->sy_name);
                    441:        file_errors = 1;
                    442: }
                    443: 
                    444: /*
                    445:  *     Print a filename and line number.  Omit filename if it is
                    446:  *     the current file.
                    447:  */
                    448: 
                    449: void
                    450: put_file(f, l)
                    451: symbol *f;
                    452: long   l;
                    453: {
                    454:        if (f == src_file)
                    455:                printf("%ld", l);
                    456:        else
                    457:        {
                    458:                format_filename(f->sy_name);
                    459: 
                    460:                if (l != 0)
                    461:                        printf(": %ld", l);
                    462:        }       
                    463: }

unix.superglobalmegacorp.com

This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.