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

📄 lpgutil.c

📁 一个非常好的检索工具
💻 C
📖 第 1 页 / 共 3 页
字号:
    len = PRINT_LINE_SIZE - 5;    print_large_token(line, tok, "", len);    strcat(line, " ::= ");    i = (PRINT_LINE_SIZE / 2) - 1;    offset = MIN(strlen(line)-1, i);    len = PRINT_LINE_SIZE - (offset + 4);    i = rules[rule_no].rhs;  /* symbols before dot */    k = ((rules[rule_no].rhs + item_table[item_no].dot) - 1);    for (; i <= k; i++)    {        symbol = rhs_sym[i];        restore_symbol(tok, RETRIEVE_STRING(symbol));        if (strlen(tok) + strlen(line) > PRINT_LINE_SIZE - 4)        {            fprintf(syslis,"\n%s", line);            ENDPAGE_CHECK;            fill_in(tempstr, offset, SPACE);            print_large_token(line, tok, tempstr, len);        }        else            strcat(line, tok);        strcat(line, BLANK);    }    /*********************************************************************/    /* We now add a DOT "." to the output line and print the remaining   */    /* symbols in the right hand side.  If ITEM_NO is a complete item,   */    /* we also print the rule number.                                    */    /*********************************************************************/    if (item_table[item_no].dot == 0 || item_table[item_no].symbol == empty)        strcpy(tok, ".");    else        strcpy(tok, " .");    strcat(line, tok);    len = PRINT_LINE_SIZE - (offset + 1);    for (i = rules[rule_no].rhs +              item_table[item_no].dot;/* symbols after dot*/          i <= rules[rule_no + 1].rhs - 1; i++)    {        symbol = rhs_sym[i];        restore_symbol(tok, RETRIEVE_STRING(symbol));        if (strlen(tok) + strlen(line) > PRINT_LINE_SIZE -1)        {            fprintf(syslis, "\n%s", line);            ENDPAGE_CHECK;            fill_in(tempstr, offset, SPACE);            print_large_token(line, tok, tempstr, len);        }        else            strcat(line, tok);        strcat(line, BLANK);    }    if (item_table[item_no].symbol == empty)   /* complete item */    {        sprintf(tok, " (%d)", rule_no);        if (strlen(tok) + strlen(line) > PRINT_LINE_SIZE - 1)        {            fprintf(syslis, "\n%s", line);            ENDPAGE_CHECK;            fill_in(line,offset, SPACE);        }        strcat(line,tok);    }    fprintf(syslis, "\n%s", line);    ENDPAGE_CHECK;    return;}/*****************************************************************************//*                               PRINT_STATE:                                *//*****************************************************************************//* PRINT_STATE prints all the items in a state.  NOTE that when single       *//* productions are eliminated, certain items that were added in a state by   *//* CLOSURE, will no longer show up in the output.  Example: If we have the   *//* item [A ::= .B]  in a state, and the GOTO_REDUCE generated on B has been  *//* replaced by say the GOTO or GOTO_REDUCE of A, the item above can no longer*//* be retrieved, since transitions in a given state are reconstructed from   *//* the KERNEL and ADEQUATE items of the actions in the GOTO and SHIFT maps.  *//*****************************************************************************/void print_state(int state_no){    struct shift_header_type sh;    struct goto_header_type  go_to;    short *item_list;    int kernel_size,        i,        n,        item_no,        next_state;    BOOLEAN end_node,            *state_seen,            *item_seen;    struct node *q;    char buffer[PRINT_LINE_SIZE + 1],         line[PRINT_LINE_SIZE + 1];    /*********************************************************************/    /* ITEM_SEEN is used to construct sets of items, to help avoid       */    /* adding duplicates in a list.  Duplicates can occur because an     */    /* item from the kernel set will either be shifted on if it is not a */    /* complete item, or it will be a member of the Complete_items set.  */    /* Duplicates can also occur because of the elimination of single    */    /* productions.                                                      */    /*********************************************************************/    state_seen = Allocate_boolean_array(max_la_state + 1);    item_seen  = Allocate_boolean_array(num_items + 1);    item_list  = Allocate_short_array(num_items + 1);/* INITIALIZATION -----------------------------------------------------------*/    for ALL_STATES(i)        state_seen[i] = FALSE;    for ALL_ITEMS(i)        item_seen[i] = FALSE;    kernel_size = 0;/* END OF INITIALIZATION ----------------------------------------------------*/    i = number_len(state_no) + 8; /* 8 = length("STATE") + 2 spaces + newline*/    fill_in(buffer, (PRINT_LINE_SIZE - i) ,'-');    fprintf(syslis, "\n\n\nSTATE %d %s",state_no, buffer);    output_line_no +=3;    /*********************************************************************/    /* Print the set of states that have transitions to STATE_NO.        */    /*********************************************************************/    n = 0;    strcpy(line, "( ");    for (end_node = ((q = in_stat[state_no]) == NULL);         ! end_node;         end_node = (q == in_stat[state_no]))    {/* copy list of IN_STAT into array */        q = q -> next;        if (! state_seen[q -> value])        {            state_seen[q -> value] = TRUE;            if (strlen(line) + number_len(q -> value) > PRINT_LINE_SIZE-2)            {                fprintf(syslis,"\n%s",line);                ENDPAGE_CHECK;                strcpy(line, "  ");            }            if (q -> value != 0)            {                sprintf(buffer, "%d ", q -> value);                strcat(line, buffer);            }        }    }    strcat(line, ")");    fprintf(syslis,"\n%s\n", line);    output_line_no++;    ENDPAGE_CHECK;    /*********************************************************************/    /* Add the set of kernel items to the array ITEM_LIST, and mark all  */    /* items seen to avoid duplicates.                                   */    /*********************************************************************/    for (q = statset[state_no].kernel_items; q != NULL; q = q -> next)    {        kernel_size++;        item_no = q -> value;        item_list[kernel_size] = item_no;    /* add to array */        item_seen[item_no] = TRUE;         /* Mark as "seen" */    }    /*********************************************************************/    /* Add the Complete Items to the array ITEM_LIST, and mark used.     */    /*********************************************************************/    n = kernel_size;    for (q = statset[state_no].complete_items; q != NULL; q = q -> next)    {        item_no = q -> value;        if (! item_seen[item_no])        {            item_seen[item_no] = TRUE; /* Mark as "seen" */            item_list[++n] = item_no;        }    }    /*********************************************************************/    /* Iterate over the shift map.  Shift-Reduce actions are identified  */    /* by a negative integer that indicates the rule in question , and   */    /* the associated item can be retrieved by indexing the array        */    /* ADEQUATE_ITEMS at the location of the rule.  For shift-actions, we*/    /* simply take the predecessor-items of all the items in the kernel  */    /* of the following state.                                           */    /* If the shift-action is a look-ahead shift, we check to see if the */    /* look-ahead state contains shift actions, and retrieve the next    */    /* state from one of those shift actions.                            */    /*********************************************************************/    sh = shift[statset[state_no].shift_number];    for (i = 1; i <= sh.size; i++)    {        next_state = SHIFT_ACTION(sh, i);        while (next_state > (int) num_states)        {            struct shift_header_type next_sh;            next_sh = shift[lastats[next_state].shift_number];            if (next_sh.size > 0)                next_state = SHIFT_ACTION(next_sh, 1);            else                next_state = 0;        }        if (next_state == 0)            q = NULL;        else if (next_state < 0)            q = adequate_item[-next_state];        else        {            q = statset[next_state].kernel_items;            if (q == NULL) /* single production state? */                q = statset[next_state].complete_items;        }        for (; q != NULL; q = q -> next)        {            item_no = q -> value - 1;            if (! item_seen[item_no])            {                item_seen[item_no] = TRUE;                item_list[++n] = item_no;            }        }    }    /*********************************************************************/    /* GOTOS and GOTO-REDUCES are analogous to SHIFTS and SHIFT-REDUCES. */    /*********************************************************************/    go_to = statset[state_no].go_to;    for (i = 1; i <= go_to.size; i++)    {        if (GOTO_ACTION(go_to, i) > 0)        {            q = statset[GOTO_ACTION(go_to, i)].kernel_items;            if (q == NULL)          /* single production state? */                q = statset[GOTO_ACTION(go_to, i)].complete_items;        }        else            q = adequate_item[- GOTO_ACTION(go_to, i)];        for (; q != NULL; q = q -> next)        {            item_no = q -> value - 1;            if (! item_seen[item_no])            {                item_seen[item_no] = TRUE;                item_list[++n] = item_no;            }        }    }    /*********************************************************************/    /* Print the Kernel items.  If there are any closure items, skip a   */    /* line, sort then, then print them.  The kernel items are in sorted */    /* order.                                                            */    /*********************************************************************/    for (item_no = 1; item_no <= kernel_size; item_no++)         print_item(item_list[item_no]);    if (kernel_size < n)    {        fprintf(syslis, "\n");        ENDPAGE_CHECK;        qcksrt(item_list, kernel_size + 1, n);        for (item_no = kernel_size + 1; item_no <= n; item_no++)            print_item(item_list[item_no]);    }    ffree(item_list);    ffree(item_seen);    ffree(state_seen);    return;}/*****************************************************************************//*                                 NOSPACE:                                  *//*****************************************************************************//* This procedure is invoked when a call to MALLOC, CALLOC or REALLOC fails. *//*****************************************************************************/void nospace(char *file_name, long line_number){    fprintf(stderr,            "*** Cannot allocate space ... LPG terminated in "            "file %s at line %d\n", file_name, line_number);    exit(12);}/************************************************************************//*                               STRUPR:                                *//************************************************************************//* StrUpr and StrLwr.                                                   *//* These routines set all characters in a string to upper case and lower*//*  case (respectively.)  These are library routines in DOS, but        *//*  are defined here for the 370 compiler.                              *//************************************************************************/char *strupr(char *string){    char *s;    /*********************************************************************/    /* While not at end of string, change all lower case to upper case.  */    /*********************************************************************/    for (s = string; *s != '\0'; s++)        *s = (islower((int) *s) ? toupper((int) *s) : *s);    return string;}/************************************************************************//*                               STRLWR:                                *//************************************************************************/char *strlwr(char *string){    char *s;    /*********************************************************************/    /* While not at end of string, change all upper case to lower case.  */    /*********************************************************************/    for (s = string; *s != '\0'; s++)        *s = (isupper((int) *s) ? tolower((int) *s) : *s);    return string;}

⌨️ 快捷键说明

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