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

1.1       root        1: #include       "cem.h"
                      2: #define        STD_OBJ 1
                      3: #include       "stdobj.h"
                      4: #include       "types.h"
                      5: #include       "equiv.h"
                      6: #include       "symbol.h"
                      7: #include       "type.h"
                      8: #include       "var.h"
                      9: 
                     10: /*
                     11:  *     Variable routines.
                     12:  */
                     13: 
                     14: static long    new_var_index   = 1;
                     15: 
                     16: /*
                     17:  *     We keep a cache of data objects rather than allowing malloc
                     18:  *     to inefficiently recycle them.
                     19:  */
                     20: static arg     *arg_free;
                     21: static args    *args_free;
                     22: static var     *var_free;
                     23: 
                     24: /*
                     25:  *     Allocation routines.
                     26:  */
                     27: static var     *
                     28: new_var()
                     29: {
                     30:        register var    *p;
                     31: 
                     32:        if (var_free == NULL)
                     33:                return talloc(var);
                     34: 
                     35:        p = var_free;
                     36:        var_free = p->v_next;
                     37:        return p;
                     38: }
                     39: 
                     40: static void
                     41: free_arglist(a)
                     42: register arg   *a;
                     43: {
                     44:        register args   *p;
                     45:        register args   *q;
                     46: 
                     47:        for (p = a->a_head; p != NULL; p = q)
                     48:        {
                     49:                q = p->a_next;
                     50:                p->a_next = args_free;
                     51:                args_free = p;
                     52:        }
                     53: 
                     54:        a->a_next = arg_free;
                     55:        arg_free = a;
                     56: }
                     57: 
                     58: static arg     *
                     59: new_arg()
                     60: {
                     61:        register arg    *p;
                     62: 
                     63:        if ((p = arg_free) == NULL)
                     64:                p = talloc(arg);
                     65:        else
                     66:                arg_free = p->a_next;
                     67: 
                     68:        p->a_head = NULL;
                     69:        p->a_tail = &p->a_head;
                     70:        p->a_count = 0;
                     71:        p->a_next = NULL;
                     72:        return p;
                     73: }
                     74: 
                     75: static void
                     76: free_arguments(a)
                     77: register arg   *a;
                     78: {
                     79:        register arg    *b;
                     80: 
                     81:        while (a != NULL)
                     82:        {
                     83:                b = a->a_next;
                     84:                free_arglist(a);
                     85:                a = b;
                     86:        }
                     87: }
                     88: 
                     89: static void
                     90: add_argument(a, t)
                     91: register arg   *a;
                     92: type           *t;
                     93: {
                     94:        register args   *p;
                     95: 
                     96:        if ((p = args_free) == NULL)
                     97:                p = talloc(args);
                     98:        else
                     99:                args_free = p->a_next;
                    100: 
                    101:        p->a_type = t;
                    102:        p->a_next = NULL;
                    103:        *a->a_tail = p;
                    104:        a->a_tail = &p->a_next;
                    105:        a->a_count++;
                    106: }
                    107: 
                    108: /*
                    109:  *     Make a declaration.
                    110:  */
                    111: static var     *
                    112: declare(v, n, t, f, l)
                    113: obj_vars       v;
                    114: symbol         *n;
                    115: type           *t;
                    116: symbol         *f;
                    117: long           l;
                    118: {
                    119:        register var    *p;
                    120: 
                    121:        p = new_var();
                    122:        p->v_what = v;
                    123:        p->v_name = n;
                    124:        p->v_type = t;
                    125:        p->v_file = f;
                    126:        p->v_line = l;
                    127:        p->v_ifile = NULL;
                    128:        p->v_varargs = -1;
                    129:        p->v_argdefn = NULL;
                    130:        p->v_args = NULL;
                    131:        p->v_tail = &p->v_args;
                    132:        p->v_next = NULL;
                    133:        return p;
                    134: }
                    135: 
                    136: /*
                    137:  *     Set array size.
                    138:  */
                    139: static void
                    140: array_size(p, t)
                    141: var    *p;
                    142: type   *t;
                    143: {
                    144:        p->v_type = t;
                    145: }
                    146: 
                    147: /*
                    148:  *     Note initialisation.
                    149:  */
                    150: static void
                    151: initialisation(p, f, l)
                    152: var    *p;
                    153: symbol *f;
                    154: long   l;
                    155: {
                    156:        p->v_ifile = f;
                    157:        p->v_iline = l;
                    158: }
                    159: 
                    160: /*
                    161:  *     Note varargs count.
                    162:  */
                    163: static void
                    164: set_varargs(p, l)
                    165: var    *p;
                    166: long   l;
                    167: {
                    168:        p->v_varargs = l;
                    169: }
                    170: 
                    171: /*
                    172:  *     Add an instance of a variable to the symbol table instance list.
                    173:  */
                    174: static void
                    175: add_instance(v)
                    176: register var   *v;
                    177: {
                    178:        register inst   *p;
                    179:        register defn   *d;
                    180:        register init   *i;
                    181: 
                    182:        /*
                    183:         *      Don't let library definitions override.
                    184:         */
                    185:        if (in_lib && v->v_name->sy_inst != NULL && v->v_name->sy_inst->i_init)
                    186:                return;
                    187: 
                    188:        if ((p = v->v_name->sy_inst) == NULL)
                    189:        {
                    190:                p = talloc(inst);
                    191:                v->v_name->sy_inst = p;
                    192:                p->i_argdefn = v->v_argdefn;
                    193: 
                    194:                if ((p->i_args = v->v_args) == NULL)
                    195:                        p->i_tail = &p->i_args;
                    196:                else
                    197:                        p->i_tail = v->v_tail;
                    198: 
                    199:                d = talloc(defn);
                    200:                p->i_defn = d;
                    201:                p->i_init = NULL;
                    202:                p->i_name = v->v_name;
                    203:                d->d_what = v->v_what;
                    204:                d->d_type = v->v_type;
                    205: 
                    206:                if (in_lib)
                    207:                {
                    208:                        d->d_file = src_file;
                    209:                        d->d_line = 0;
                    210:                }
                    211:                else
                    212:                {
                    213:                        d->d_file = v->v_file;
                    214:                        d->d_line = v->v_line;
                    215:                }
                    216: 
                    217:                d->d_next = NULL;
                    218:                p->i_next = global_list;
                    219:                global_list = p;
                    220:        }
                    221:        else
                    222:        {
                    223:                if (v->v_argdefn != NULL)
                    224:                        p->i_argdefn = v->v_argdefn;
                    225: 
                    226:                if ((*p->i_tail = v->v_args) != NULL)
                    227:                        p->i_tail = v->v_tail;
                    228: 
                    229:                d = p->i_defn;
                    230: 
                    231:                loop
                    232:                {
                    233:                        if (d == NULL)
                    234:                        {
                    235:                                d = talloc(defn);
                    236:                                d->d_next = p->i_defn;
                    237:                                p->i_defn = d;
                    238: 
                    239:                        elab:
                    240:                                d->d_what = v->v_what;
                    241:                                d->d_type = v->v_type;
                    242: 
                    243:                                if (in_lib)
                    244:                                {
                    245:                                        d->d_file = src_file;
                    246:                                        d->d_line = 0;
                    247:                                }
                    248:                                else
                    249:                                {
                    250:                                        d->d_file = v->v_file;
                    251:                                        d->d_line = v->v_line;
                    252:                                }
                    253: 
                    254:                                break;
                    255:                        }
                    256: 
                    257:                        if (d->d_type == v->v_type)
                    258:                                break;
                    259: 
                    260:                        if (complex_elaboration(v->v_type, d->d_type))
                    261:                                goto elab;
                    262: 
                    263:                        if (array_elaboration(v->v_type, d->d_type))
                    264:                                goto elab;
                    265: 
                    266:                        if (compatible(d->d_type, v->v_type))
                    267:                                break;
                    268: 
                    269:                        d = d->d_next;
                    270:                }
                    271:        }
                    272: 
                    273:        if (v->v_ifile != NULL)
                    274:        {
                    275:                i = talloc(init);
                    276: 
                    277:                if (in_lib)
                    278:                {
                    279:                        i->i_file = src_file;
                    280:                        i->i_line = 0;
                    281:                }
                    282:                else
                    283:                {
                    284:                        i->i_file = v->v_ifile;
                    285:                        i->i_line = v->v_iline;
                    286:                }
                    287: 
                    288:                i->i_varargs = v->v_varargs;
                    289:                i->i_next = p->i_init;
                    290:                p->i_init = i;
                    291:        }
                    292: }
                    293: 
                    294: /*
                    295:  *     Add an arglist (call) to args list.  If it is ceorcible to
                    296:  *     the definition don't bother.
                    297:  */
                    298: static void
                    299: add_arglist(v, a)
                    300: register var   *v;
                    301: register arg   *a;
                    302: {
                    303:        if (v->v_argdefn != NULL && coercible_arglist(v->v_argdefn, a, -1))
                    304:        {
                    305:                free_arglist(a);
                    306:                return;
                    307:        }
                    308: 
                    309:        *v->v_tail = a;
                    310:        v->v_tail = &a->a_next;
                    311:        a->a_next = NULL;
                    312: }
                    313: 
                    314: /*
                    315:  *     Complain about improper calls.
                    316:  */
                    317: static void
                    318: put_improper_calls(d, u, v, af, tf)
                    319: register arg   *d;
                    320: register arg   *u;
                    321: int            v;
                    322: int            (*af)();
                    323: int            (*tf)();
                    324: {
                    325:        register args   *p;
                    326:        register args   *q;
                    327:        register char   *sep;
                    328:        register int    n;
                    329:        int             i;
                    330:        int             force;
                    331: 
                    332:        while (u != NULL)
                    333:        {
                    334:                if (!(*af)(d, u, v))
                    335:                {
                    336:                        putchar('\t');
                    337:                        put_file(u->a_file, u->a_line);
                    338: 
                    339:                        if (v >= 0 && u->a_count < v)
                    340:                                printf(", expected at least %d arg%s, found %d\n", v, v == 1 ? "" : "s", u->a_count);
                    341:                        else if (d->a_count != u->a_count)
                    342:                                printf(", expected %d arg%s, found %d\n", d->a_count, d->a_count == 1 ? "" : "s", u->a_count);
                    343:                        else
                    344:                        {
                    345:                                if (v < 0)
                    346:                                        n = d->a_count;
                    347:                                else
                    348:                                        n = v;
                    349: 
                    350:                                i = 1;
                    351:                                sep = ", ";
                    352:                                p = d->a_head;
                    353:                                q = u->a_head;
                    354: 
                    355:                                while (--n >= 0)
                    356:                                {
                    357:                                        if (p->a_type != q->a_type && !(*tf)(p->a_type, q->a_type))
                    358:                                        {
                    359:                                                force = different_vintage(p->a_type, q->a_type);
                    360:                                                printf("%sarg %d expected ", sep, i);
                    361:                                                put_type(p->a_type, force);
                    362:                                                printf(", found ");
                    363:                                                put_type(q->a_type, force);
                    364:                                                sep = "\n\t\t";
                    365:                                        }
                    366: 
                    367:                                        i++;
                    368:                                        p = p->a_next;
                    369:                                        q = q->a_next;
                    370:                                }
                    371: 
                    372:                                putchar('\n');
                    373:                        }
                    374:                }
                    375: 
                    376:                u = u->a_next;
                    377:        }
                    378: }
                    379: 
                    380: /*
                    381:  *     Enter vars from input file.  Check statics and enter instances.
                    382:  */
                    383: void
                    384: enter_vars(n)
                    385: register long  n;
                    386: {
                    387:        register int    i;
                    388:        register long   j;
                    389:        register var    *p;
                    390:        register var    **v;
                    391: 
                    392:        v = (var **)salloc(n * sizeof (var *));
                    393:        var_trans = v;
                    394: 
                    395:        for (j = 0; j < n; j++)
                    396:                *v++ = NULL;
                    397: 
                    398:        v = var_trans;
                    399: 
                    400:        while (data_ptr < data_end)
                    401:        {
                    402:                register long   l0;
                    403:                register long   l1;
                    404:                register long   l2;
                    405:                arg             *ap;
                    406: 
                    407:                i = getd();
                    408: 
                    409:                switch (obj_item(i))
                    410:                {
                    411:                case i_data:
                    412:                        l0 = getv();
                    413:                        l1 = getv();
                    414:                        initialisation(var_trans[l0], str_trans[l1], getv());
                    415: 
                    416:                        loop
                    417:                        {
                    418:                                i = getd();
                    419: 
                    420:                                switch (obj_item(i))
                    421:                                {
                    422:                                case d_addr:
                    423:                                        skip4();
                    424:                                        continue;
                    425: 
                    426:                                case d_bytes:
                    427:                                        if (obj_id(i) == 0)
                    428:                                                l0 = getv();
                    429:                                        else
                    430:                                                l0 = obj_id(i);
                    431: 
                    432:                                        data_ptr += l0;
                    433:                                        continue;
                    434: 
                    435:                                case d_end:
                    436:                                        break;
                    437: 
                    438:                                case d_istring:
                    439:                                        if (obj_id(i) == 0)
                    440:                                                l0 = getv();
                    441:                                        else
                    442:                                                l0 = obj_id(i);
                    443: 
                    444:                                        str_num++;
                    445:                                        data_ptr += l0;
                    446:                                        continue;
                    447: 
                    448:                                case d_irstring:
                    449:                                        if (obj_id(i) == 0)
                    450:                                                l0 = getv();
                    451:                                        else
                    452:                                                l0 = obj_id(i);
                    453: 
                    454:                                        str_num++;
                    455:                                        data_ptr += l0;
                    456:                                        skip4();
                    457:                                        continue;
                    458: 
                    459:                                case d_space:
                    460:                                        if (obj_id(i) == 0)
                    461:                                                skip();
                    462: 
                    463:                                        continue;
                    464: 
                    465:                                case d_string:
                    466:                                        skip();
                    467:                                        continue;
                    468: 
                    469:                                case d_reloc:
                    470:                                case d_rstring:
                    471:                                        skip();
                    472:                                        skip4();
                    473:                                        continue;
                    474: 
                    475:                                default:
                    476:                                        fprintf(stderr, "%s: unknown data id %d\n", my_name, i);
                    477:                                        exit(1);
                    478:                                }
                    479: 
                    480:                                break;
                    481:                        }
                    482: 
                    483:                        break;
                    484: 
                    485:                case i_lib:
                    486:                case i_src:
                    487:                        skip();
                    488:                        break;
                    489: 
                    490:                case i_string:
                    491:                        if (obj_id(i) == 0)
                    492:                                l0 = getv();
                    493:                        else
                    494:                                l0 = obj_id(i);
                    495: 
                    496:                        str_num++;
                    497:                        data_ptr += l0;
                    498:                        break;
                    499: 
                    500:                case i_type:
                    501:                        switch (obj_id(i))
                    502:                        {
                    503:                        case t_arrayof:
                    504:                        case t_bitfield:
                    505:                                skip();
                    506:                                skip();
                    507:                                break;
                    508: 
                    509:                        case t_basetype:
                    510:                                (void)getd();
                    511:                                break;
                    512: 
                    513:                        case t_dimless:
                    514:                        case t_ftnreturning:
                    515:                        case t_ptrto:
                    516:                                skip();
                    517:                                break;
                    518: 
                    519:                        case t_elaboration:
                    520:                                skip();
                    521:                                skip();
                    522:                                skip();
                    523:                                
                    524:                                switch (i = obj_id(getd()))
                    525:                                {
                    526:                                case t_enum:
                    527:                                        skip();
                    528:                                        goto elab_enum;
                    529: 
                    530:                                case t_structof:
                    531:                                        skip();
                    532: 
                    533:                                        do
                    534:                                        {
                    535:                                                skip();
                    536:                                                skip();
                    537:                                        }
                    538:                                        while (getv() != 0);
                    539: 
                    540:                                        skip();
                    541:                                        break;
                    542: 
                    543:                                case t_unionof:
                    544:                                        skip();
                    545: 
                    546:                                        do
                    547:                                                skip();
                    548:                                        while (getv() != 0);
                    549: 
                    550:                                        skip();
                    551:                                        break;
                    552: 
                    553:                                default:
                    554:                                        fprintf(stderr, "%s: unknown elaboration id %d\n", my_name, i);
                    555:                                        exit(1);
                    556:                                }
                    557: 
                    558:                                break;
                    559: 
                    560:                        case t_enum:
                    561:                                skip();
                    562:                                skip();
                    563:                                skip();
                    564: 
                    565:                                if (getv() == 0)
                    566:                                        break;
                    567: 
                    568:                        elab_enum:
                    569:                                do
                    570:                                        skip();
                    571:                                while (getv() != 0);
                    572: 
                    573:                                skip();
                    574:                                skip();
                    575:                                break;
                    576: 
                    577:                        case t_structof:
                    578:                        case t_unionof:
                    579:                                skip();
                    580:                                skip();
                    581:                                skip();
                    582:                                break;
                    583: 
                    584:                        default:
                    585:                                fprintf(stderr, "%s: unknown type id %d\n", my_name, obj_id(i));
                    586:                                exit(1);
                    587:                        }
                    588: 
                    589:                        break;
                    590: 
                    591:                case i_var:
                    592:                        switch (obj_id(i))
                    593:                        {
                    594:                        case v_arglist:
                    595:                                l0 = getv();
                    596:                                l1 = getv();
                    597:                                initialisation(var_trans[l0], str_trans[l1], getv());
                    598:                                ap = new_arg();
                    599: 
                    600:                                while (getv() != 0)
                    601:                                {
                    602:                                        add_argument(ap, type_trans[getv()]);
                    603:                                        skip();
                    604:                                        skip();
                    605:                                        var_index++;
                    606:                                }
                    607: 
                    608:                                var_trans[l0]->v_argdefn = ap;
                    609:                                break;
                    610: 
                    611:                        case v_array_size:
                    612:                                l0 = getv();
                    613:                                array_size(var_trans[l0], type_trans[getv()]);
                    614:                                break;
                    615: 
                    616:                        case v_auto:
                    617:                                var_index++;
                    618:                                skip();
                    619:                                skip();
                    620:                                skip();
                    621:                                skip();
                    622:                                break;
                    623: 
                    624:                        case v_call:
                    625:                                l0 = getv();
                    626:                                ap = new_arg();
                    627:                                ap->a_file = str_trans[getv()];
                    628:                                ap->a_line = getv();
                    629: 
                    630:                                while ((l1 = getv()) != 0)
                    631:                                        add_argument(ap, type_trans[l1]);
                    632: 
                    633:                                add_arglist(var_trans[l0], ap);
                    634:                                break;
                    635: 
                    636:                        case v_block_static:
                    637:                        case v_global:
                    638:                        case v_implicit_function:
                    639:                        case v_static:
                    640:                                l0 = getv();
                    641:                                l1 = getv();
                    642:                                l2 = getv();
                    643:                                var_trans[var_index++] = declare(obj_id(i), str_trans[l0], type_trans[l1], str_trans[l2], getv());
                    644:                                break;
                    645: 
                    646:                        case v_varargs:
                    647:                                l0 = getv();
                    648:                                set_varargs(var_trans[l0], getv());
                    649:                                break;
                    650: 
                    651:                        default:
                    652:                                fprintf(stderr, "%s: unknown var id %d\n", my_name, obj_id(i));
                    653:                                exit(1);
                    654:                        }
                    655: 
                    656:                        break;
                    657: 
                    658:                default:
                    659:                        fprintf(stderr, "%s: unknown obj_item %d\n", my_name, obj_item(i));
                    660:                        exit(1);
                    661:                }
                    662:        }
                    663: 
                    664:        for (j = 1; j < n; j++)
                    665:        {
                    666:                register arg    *a;
                    667: 
                    668:                if ((p = v[j]) == NULL)
                    669:                        continue;
                    670: 
                    671:                switch (p->v_what)
                    672:                {
                    673:                case v_block_static:
                    674:                        break;
                    675: 
                    676:                case v_global:
                    677:                case v_implicit_function:
                    678:                        add_instance(p);
                    679:                        break;
                    680: 
                    681:                case v_static:
                    682:                        switch (p->v_type->t_type)
                    683:                        {
                    684:                                char    *diag;
                    685: 
                    686:                        error:
                    687:                                say_file();
                    688:                                printf(", static %s %s, ", diag, p->v_name->sy_name);
                    689:                                put_file(p->v_file, p->v_line);
                    690:                                printf(", never defined\n");
                    691:                                errors++;
                    692:                                break;
                    693: 
                    694:                        case t_dimless:
                    695:                                diag = "array[]";
                    696:                                goto error;
                    697: 
                    698:                        case t_ftnreturning:
                    699:                                if (p->v_ifile == NULL)
                    700:                                {
                    701:                                        diag = "function";
                    702:                                        goto error;
                    703:                                }
                    704: 
                    705:                                for (a = p->v_args; a != NULL; a = a->a_next)
                    706:                                {
                    707:                                        if (!coercible_arglist(p->v_argdefn, a, p->v_varargs))
                    708:                                        {
                    709:                                                say_file();
                    710:                                                printf(": static function %s: ", p->v_name->sy_name);
                    711:                                                put_file(p->v_file, p->v_line);
                    712:                                                printf("\n");
                    713:                                                put_improper_calls(p->v_argdefn, a, p->v_varargs, coercible_arglist, coercible);
                    714:                                                errors++;
                    715:                                                break;
                    716:                                        }
                    717:                                }
                    718: 
                    719:                                free_arguments(p->v_args);
                    720:                                free_arguments(p->v_argdefn);
                    721:                        }
                    722: 
                    723:                        break;
                    724: 
                    725:                default:
                    726:                        fprintf(stderr, "%s: bad var type\n", my_name);
                    727:                        exit(1);
                    728:                }
                    729: 
                    730:                p->v_next = var_free;
                    731:                var_free = p;
                    732:        }
                    733: }
                    734: 
                    735: /*
                    736:  *     Check for mutliple declarations and definitions.
                    737:  *     Also check arglist compatibility.
                    738:  */
                    739: static void
                    740: check_instance(p)
                    741: register inst  *p;
                    742: {
                    743:        register defn   *d;
                    744:        register init   *i;
                    745:        register arg    *a;
                    746: 
                    747:        if (p->i_defn->d_next != NULL)
                    748:        {
                    749:                printf("%s multiply declared:\n", p->i_name->sy_name);
                    750: 
                    751:                for (d = p->i_defn; d != NULL; d = d->d_next)
                    752:                {
                    753:                        putchar('\t');
                    754:                        put_file(d->d_file, d->d_line);
                    755: 
                    756:                        if (d->d_what == v_implicit_function)
                    757:                                printf(" implicitly");
                    758: 
                    759:                        printf(" as ");
                    760:                        put_type(d->d_type, 0);
                    761:                        putchar('\n');
                    762:                }
                    763: 
                    764:                errors++;
                    765:        }
                    766: 
                    767:        if (p->i_init != NULL)
                    768:        {
                    769:                if (p->i_init->i_next != NULL)
                    770:                {
                    771:                        printf("%s multiply defined:\n", p->i_name->sy_name);
                    772: 
                    773:                        for (i = p->i_init; i != NULL; i = i->i_next)
                    774:                        {
                    775:                                putchar('\t');
                    776:                                put_file(i->i_file, i->i_line);
                    777:                                putchar('\n');
                    778:                        }
                    779: 
                    780:                        errors++;
                    781:                        return;
                    782:                }
                    783: 
                    784:                if (p->i_argdefn != NULL)
                    785:                {
                    786:                        for (a = p->i_args; a != NULL; a = a->a_next)
                    787:                        {
                    788:                                if (!compatible_arglist(p->i_argdefn, a, p->i_init->i_varargs))
                    789:                                {
                    790:                                        printf("function %s: ", p->i_name->sy_name);
                    791:                                        put_file(p->i_init->i_file, p->i_init->i_line);
                    792:                                        printf("\n");
                    793:                                        put_improper_calls(p->i_argdefn, a, p->i_init->i_varargs, compatible_arglist, compatible);
                    794:                                        errors++;
                    795:                                        break;
                    796:                                }
                    797:                        }
                    798:                }
                    799:        }
                    800: }
                    801: 
                    802: void
                    803: check_externs()
                    804: {
                    805:        register inst   *p;
                    806: 
                    807:        for (p = global_list; p != NULL; p = p->i_next)
                    808:                check_instance(p);
                    809: }

unix.superglobalmegacorp.com

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