⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 reader.c

📁 操作系统源代码
💻 C
📖 第 1 页 / 共 2 页
字号:
declare_types(){    register int c;    register bucket *bp;    char *tag;    c = nextc();    if (c == EOF) unexpected_EOF();    if (c != '<') syntax_error(lineno, line, cptr);    tag = get_tag();    for (;;)    {	c = nextc();	if (isalpha(c) || c == '_' || c == '.' || c == '$')	    bp = get_name();	else if (c == '\'' || c == '"')	    bp = get_literal();	else	    return;	if (bp->tag && tag != bp->tag)	    retyped_warning(bp->name);	bp->tag = tag;    }}declare_start(){    register int c;    register bucket *bp;    c = nextc();    if (c == EOF) unexpected_EOF();    if (!isalpha(c) && c != '_' && c != '.' && c != '$')	syntax_error(lineno, line, cptr);    bp = get_name();    if (bp->class == TERM)	terminal_start(bp->name);    if (goal && goal != bp)	restarted_warning();    goal = bp;}read_declarations(){    register int c, k;    cache_size = 256;    cache = MALLOC(cache_size);    if (cache == 0) no_space();    for (;;)    {	c = nextc();	if (c == EOF) unexpected_EOF();	if (c != '%') syntax_error(lineno, line, cptr);	switch (k = keyword())	{	case MARK:	    return;	case IDENT:	    copy_ident();	    break;	case TEXT:	    copy_text();	    break;	case UNION:	    copy_union();	    break;	case TOKEN:	case LEFT:	case RIGHT:	case NONASSOC:	    declare_tokens(k);	    break;	case TYPE:	    declare_types();	    break;	case START:	    declare_start();	    break;	}    }}initialize_grammar(){    nitems = 4;    maxitems = 300;    pitem = (bucket **) MALLOC(maxitems*sizeof(bucket *));    if (pitem == 0) no_space();    pitem[0] = 0;    pitem[1] = 0;    pitem[2] = 0;    pitem[3] = 0;    nrules = 3;    maxrules = 100;    plhs = (bucket **) MALLOC(maxrules*sizeof(bucket *));    if (plhs == 0) no_space();    plhs[0] = 0;    plhs[1] = 0;    plhs[2] = 0;    rprec = (short *) MALLOC(maxrules*sizeof(short));    if (rprec == 0) no_space();    rprec[0] = 0;    rprec[1] = 0;    rprec[2] = 0;    rassoc = (char *) MALLOC(maxrules*sizeof(char));    if (rassoc == 0) no_space();    rassoc[0] = TOKEN;    rassoc[1] = TOKEN;    rassoc[2] = TOKEN;}expand_items(){    maxitems += 300;    pitem = (bucket **) REALLOC(pitem, maxitems*sizeof(bucket *));    if (pitem == 0) no_space();}expand_rules(){    maxrules += 100;    plhs = (bucket **) REALLOC(plhs, maxrules*sizeof(bucket *));    if (plhs == 0) no_space();    rprec = (short *) REALLOC(rprec, maxrules*sizeof(short));    if (rprec == 0) no_space();    rassoc = (char *) REALLOC(rassoc, maxrules*sizeof(char));    if (rassoc == 0) no_space();}advance_to_start(){    register int c;    register bucket *bp;    char *s_cptr;    int s_lineno;    for (;;)    {	c = nextc();	if (c != '%') break;	s_cptr = cptr;	switch (keyword())	{	case MARK:	    no_grammar();	case TEXT:	    copy_text();	    break;	case START:	    declare_start();	    break;	default:	    syntax_error(lineno, line, s_cptr);	}    }    c = nextc();    if (!isalpha(c) && c != '_' && c != '.' && c != '_')	syntax_error(lineno, line, cptr);    bp = get_name();    if (goal == 0)    {	if (bp->class == TERM)	    terminal_start(bp->name);	goal = bp;    }    s_lineno = lineno;    c = nextc();    if (c == EOF) unexpected_EOF();    if (c != ':') syntax_error(lineno, line, cptr);    start_rule(bp, s_lineno);    ++cptr;}start_rule(bp, s_lineno)register bucket *bp;int s_lineno;{    if (bp->class == TERM)	terminal_lhs(s_lineno);    bp->class = NONTERM;    if (nrules >= maxrules)	expand_rules();    plhs[nrules] = bp;    rprec[nrules] = UNDEFINED;    rassoc[nrules] = TOKEN;}end_rule(){    register int i;    if (!last_was_action && plhs[nrules]->tag)    {	for (i = nitems - 1; pitem[i]; --i) continue;	if (pitem[i+1] == 0 || pitem[i+1]->tag != plhs[nrules]->tag)	    default_action_warning();    }    last_was_action = 0;    if (nitems >= maxitems) expand_items();    pitem[nitems] = 0;    ++nitems;    ++nrules;}insert_empty_rule(){    register bucket *bp, **bpp;    assert(cache);    sprintf(cache, "$$%d", ++gensym);    bp = make_bucket(cache);    last_symbol->next = bp;    last_symbol = bp;    bp->tag = plhs[nrules]->tag;    bp->class = NONTERM;    if ((nitems += 2) > maxitems)	expand_items();    bpp = pitem + nitems - 1;    *bpp-- = bp;    while (bpp[0] = bpp[-1]) --bpp;    if (++nrules >= maxrules)	expand_rules();    plhs[nrules] = plhs[nrules-1];    plhs[nrules-1] = bp;    rprec[nrules] = rprec[nrules-1];    rprec[nrules-1] = 0;    rassoc[nrules] = rassoc[nrules-1];    rassoc[nrules-1] = TOKEN;}add_symbol(){    register int c;    register bucket *bp;    int s_lineno = lineno;    c = *cptr;    if (c == '\'' || c == '"')	bp = get_literal();    else	bp = get_name();    c = nextc();    if (c == ':')    {	end_rule();	start_rule(bp, s_lineno);	++cptr;	return;    }    if (last_was_action)	insert_empty_rule();    last_was_action = 0;    if (++nitems > maxitems)	expand_items();    pitem[nitems-1] = bp;}copy_action(){    register int c;    register int i, n;    int depth;    int quote;    char *tag;    register FILE *f = action_file;    int a_lineno = lineno;    char *a_line = dup_line();    char *a_cptr = a_line + (cptr - line);    if (last_was_action)	insert_empty_rule();    last_was_action = 1;    fprintf(f, "case %d:\n", nrules - 2);    if (!lflag)	fprintf(f, line_format, lineno, input_file_name);    if (*cptr == '=') ++cptr;    n = 0;    for (i = nitems - 1; pitem[i]; --i) ++n;    depth = 0;loop:    c = *cptr;    if (c == '$')    {	if (cptr[1] == '<')	{	    int d_lineno = lineno;	    char *d_line = dup_line();	    char *d_cptr = d_line + (cptr - line);	    ++cptr;	    tag = get_tag();	    c = *cptr;	    if (c == '$')	    {		fprintf(f, "yyval.%s", tag);		++cptr;		FREE(d_line);		goto loop;	    }	    else if (isdigit(c))	    {		i = get_number();		if (i > n) dollar_warning(d_lineno, i);		fprintf(f, "yyvsp[%d].%s", i - n, tag);		FREE(d_line);		goto loop;	    }	    else if (c == '-' && isdigit(cptr[1]))	    {		++cptr;		i = -get_number() - n;		fprintf(f, "yyvsp[%d].%s", i, tag);		FREE(d_line);		goto loop;	    }	    else		dollar_error(d_lineno, d_line, d_cptr);	}	else if (cptr[1] == '$')	{	    if (ntags)	    {		tag = plhs[nrules]->tag;		if (tag == 0) untyped_lhs();		fprintf(f, "yyval.%s", tag);	    }	    else		fprintf(f, "yyval");	    cptr += 2;	    goto loop;	}	else if (isdigit(cptr[1]))	{	    ++cptr;	    i = get_number();	    if (ntags)	    {		if (i <= 0 || i > n)		    unknown_rhs(i);		tag = pitem[nitems + i - n - 1]->tag;		if (tag == 0) untyped_rhs(i, pitem[nitems + i - n - 1]->name);		fprintf(f, "yyvsp[%d].%s", i - n, tag);	    }	    else	    {		if (i > n)		    dollar_warning(lineno, i);		fprintf(f, "yyvsp[%d]", i - n);	    }	    goto loop;	}	else if (cptr[1] == '-')	{	    cptr += 2;	    i = get_number();	    if (ntags)		unknown_rhs(-i);	    fprintf(f, "yyvsp[%d]", -i - n);	    goto loop;	}    }    if (isalpha(c) || c == '_' || c == '$')    {	do	{	    putc(c, f);	    c = *++cptr;	} while (isalnum(c) || c == '_' || c == '$');	goto loop;    }    putc(c, f);    ++cptr;    switch (c)    {    case '\n':    next_line:	get_line();	if (line) goto loop;	unterminated_action(a_lineno, a_line, a_cptr);    case ';':	if (depth > 0) goto loop;	fprintf(f, "\nbreak;\n");	return;    case '{':	++depth;	goto loop;    case '}':	if (--depth > 0) goto loop;	fprintf(f, "\nbreak;\n");	return;    case '\'':    case '"':	{	    int s_lineno = lineno;	    char *s_line = dup_line();	    char *s_cptr = s_line + (cptr - line - 1);	    quote = c;	    for (;;)	    {		c = *cptr++;		putc(c, f);		if (c == quote)		{		    FREE(s_line);		    goto loop;		}		if (c == '\n')		    unterminated_string(s_lineno, s_line, s_cptr);		if (c == '\\')		{		    c = *cptr++;		    putc(c, f);		    if (c == '\n')		    {			get_line();			if (line == 0)			    unterminated_string(s_lineno, s_line, s_cptr);		    }		}	    }	}    case '/':	c = *cptr;	if (c == '/')	{	    putc('*', f);	    while ((c = *++cptr) != '\n')	    {		if (c == '*' && cptr[1] == '/')		    fprintf(f, "* ");		else		    putc(c, f);	    }	    fprintf(f, "*/\n");	    goto next_line;	}	if (c == '*')	{	    int c_lineno = lineno;	    char *c_line = dup_line();	    char *c_cptr = c_line + (cptr - line - 1);	    putc('*', f);	    ++cptr;	    for (;;)	    {		c = *cptr++;		putc(c, f);		if (c == '*' && *cptr == '/')		{		    putc('/', f);		    ++cptr;		    FREE(c_line);		    goto loop;		}		if (c == '\n')		{		    get_line();		    if (line == 0)			unterminated_comment(c_lineno, c_line, c_cptr);		}	    }	}	goto loop;    default:	goto loop;    }}intmark_symbol(){    register int c;    register bucket *bp;    c = cptr[1];    if (c == '%' || c == '\\')    {	cptr += 2;	return (1);    }    if (c == '=')	cptr += 2;    else if ((c == 'p' || c == 'P') &&	     ((c = cptr[2]) == 'r' || c == 'R') &&	     ((c = cptr[3]) == 'e' || c == 'E') &&	     ((c = cptr[4]) == 'c' || c == 'C') &&	     ((c = cptr[5], !IS_IDENT(c))))	cptr += 5;    else	syntax_error(lineno, line, cptr);    c = nextc();    if (isalpha(c) || c == '_' || c == '.' || c == '$')	bp = get_name();    else if (c == '\'' || c == '"')	bp = get_literal();    else    {	syntax_error(lineno, line, cptr);	/*NOTREACHED*/    }    if (rprec[nrules] != UNDEFINED && bp->prec != rprec[nrules])	prec_redeclared();    rprec[nrules] = bp->prec;    rassoc[nrules] = bp->assoc;    return (0);}read_grammar(){    register int c;    initialize_grammar();    advance_to_start();    for (;;)    {	c = nextc();	if (c == EOF) break;	if (isalpha(c) || c == '_' || c == '.' || c == '$' || c == '\'' ||		c == '"')	    add_symbol();	else if (c == '{' || c == '=')	    copy_action();	else if (c == '|')	{	    end_rule();	    start_rule(plhs[nrules-1], 0);	    ++cptr;	}	else if (c == '%')	{	    if (mark_symbol()) break;	}	else	    syntax_error(lineno, line, cptr);    }    end_rule();}free_tags(){    register int i;    if (tag_table == 0) return;    for (i = 0; i < ntags; ++i)    {	assert(tag_table[i]);	FREE(tag_table[i]);    }    FREE(tag_table);}pack_names(){    register bucket *bp;    register char *p, *s, *t;    name_pool_size = 13;  /* 13 == sizeof("$end") + sizeof("$accept") */    for (bp = first_symbol; bp; bp = bp->next)	name_pool_size += strlen(bp->name) + 1;    name_pool = MALLOC(name_pool_size);    if (name_pool == 0) no_space();    strcpy(name_pool, "$accept");    strcpy(name_pool+8, "$end");    t = name_pool + 13;    for (bp = first_symbol; bp; bp = bp->next)    {	p = t;	s = bp->name;	while (*t++ = *s++) continue;	FREE(bp->name);	bp->name = p;    }}check_symbols(){    register bucket *bp;    if (goal->class == UNKNOWN)	undefined_goal(goal->name);    for (bp = first_symbol; bp; bp = bp->next)    {	if (bp->class == UNKNOWN)	{	    undefined_symbol_warning(bp->name);	    bp->class = TERM;	}    }}pack_symbols(){    register bucket *bp;    register bucket **v;    register int i, j, k, n;    nsyms = 2;    ntokens = 1;    for (bp = first_symbol; bp; bp = bp->next)    {	++nsyms;	if (bp->class == TERM) ++ntokens;    }    start_symbol = ntokens;    nvars = nsyms - ntokens;    symbol_name = (char **) MALLOC(nsyms*sizeof(char *));    if (symbol_name == 0) no_space();    symbol_value = (short *) MALLOC(nsyms*sizeof(short));    if (symbol_value == 0) no_space();    symbol_prec = (short *) MALLOC(nsyms*sizeof(short));    if (symbol_prec == 0) no_space();    symbol_assoc = MALLOC(nsyms);    if (symbol_assoc == 0) no_space();    v = (bucket **) MALLOC(nsyms*sizeof(bucket *));    if (v == 0) no_space();    v[0] = 0;    v[start_symbol] = 0;    i = 1;    j = start_symbol + 1;    for (bp = first_symbol; bp; bp = bp->next)    {	if (bp->class == TERM)	    v[i++] = bp;	else	    v[j++] = bp;    }    assert(i == ntokens && j == nsyms);    for (i = 1; i < ntokens; ++i)	v[i]->index = i;    goal->index = start_symbol + 1;    k = start_symbol + 2;    while (++i < nsyms)	if (v[i] != goal)	{	    v[i]->index = k;	    ++k;	}    goal->value = 0;    k = 1;    for (i = start_symbol + 1; i < nsyms; ++i)    {	if (v[i] != goal)	{	    v[i]->value = k;	    ++k;	}    }    k = 0;    for (i = 1; i < ntokens; ++i)    {	n = v[i]->value;	if (n > 256)	{	    for (j = k++; j > 0 && symbol_value[j-1] > n; --j)		symbol_value[j] = symbol_value[j-1];	    symbol_value[j] = n;	}    }    if (v[1]->value == UNDEFINED)	v[1]->value = 256;    j = 0;    n = 257;    for (i = 2; i < ntokens; ++i)    {	if (v[i]->value == UNDEFINED)	{	    while (j < k && n == symbol_value[j])	    {		while (++j < k && n == symbol_value[j]) continue;		++n;	    }	    v[i]->value = n;	    ++n;	}    }    symbol_name[0] = name_pool + 8;    symbol_value[0] = 0;    symbol_prec[0] = 0;    symbol_assoc[0] = TOKEN;    for (i = 1; i < ntokens; ++i)    {	symbol_name[i] = v[i]->name;	symbol_value[i] = v[i]->value;	symbol_prec[i] = v[i]->prec;	symbol_assoc[i] = v[i]->assoc;    }    symbol_name[start_symbol] = name_pool;    symbol_value[start_symbol] = -1;    symbol_prec[start_symbol] = 0;    symbol_assoc[start_symbol] = TOKEN;    for (++i; i < nsyms; ++i)    {	k = v[i]->index;	symbol_name[k] = v[i]->name;	symbol_value[k] = v[i]->value;	symbol_prec[k] = v[i]->prec;	symbol_assoc[k] = v[i]->assoc;    }    FREE(v);}pack_grammar(){    register int i, j;    int assoc, prec;    ritem = (short *) MALLOC(nitems*sizeof(short));    if (ritem == 0) no_space();    rlhs = (short *) MALLOC(nrules*sizeof(short));    if (rlhs == 0) no_space();    rrhs = (short *) MALLOC((nrules+1)*sizeof(short));    if (rrhs == 0) no_space();    rprec = (short *) REALLOC(rprec, nrules*sizeof(short));    if (rprec == 0) no_space();    rassoc = REALLOC(rassoc, nrules);    if (rassoc == 0) no_space();    ritem[0] = -1;    ritem[1] = goal->index;    ritem[2] = 0;    ritem[3] = -2;    rlhs[0] = 0;    rlhs[1] = 0;    rlhs[2] = start_symbol;    rrhs[0] = 0;    rrhs[1] = 0;    rrhs[2] = 1;    j = 4;    for (i = 3; i < nrules; ++i)    {	rlhs[i] = plhs[i]->index;	rrhs[i] = j;	assoc = TOKEN;	prec = 0;	while (pitem[j])	{	    ritem[j] = pitem[j]->index;	    if (pitem[j]->class == TERM)	    {		prec = pitem[j]->prec;		assoc = pitem[j]->assoc;	    }	    ++j;	}	ritem[j] = -i;	++j;	if (rprec[i] == UNDEFINED)	{	    rprec[i] = prec;	    rassoc[i] = assoc;	}    }    rrhs[i] = j;    FREE(plhs);    FREE(pitem);}print_grammar(){    register int i, j, k;    int spacing;    register FILE *f = verbose_file;    if (!vflag) return;    k = 1;    for (i = 2; i < nrules; ++i)    {	if (rlhs[i] != rlhs[i-1])	{	    if (i != 2) fprintf(f, "\n");	    fprintf(f, "%4d  %s :", i - 2, symbol_name[rlhs[i]]);	    spacing = strlen(symbol_name[rlhs[i]]) + 1;	}	else	{	    fprintf(f, "%4d  ", i - 2);	    j = spacing;	    while (--j >= 0) putc(' ', f);	    putc('|', f);	}	while (ritem[k] >= 0)	{	    fprintf(f, " %s", symbol_name[ritem[k]]);	    ++k;	}	++k;	putc('\n', f);    }}reader(){    write_section(banner);    create_symbol_table();    read_declarations();    read_grammar();    free_symbol_table();    free_tags();    pack_names();    check_symbols();    pack_symbols();    pack_grammar();    free_symbols();    print_grammar();}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -