dsname.c

来自「开放源码的编译器open watcom 1.6.0版的源代码」· C语言 代码 · 共 481 行 · 第 1/2 页

C
481
字号
static  void    ChkStructName(void) {
//===============================

    if( CITNode->typ == TY_STRUCTURE ) {
        // save the current FieldNode
        // consider:            STRUCTURE /S1/
        //                          INTEGER J
        //                      END STRUCTURE
        //                      STRUCTURE /S2/
        //                          RECORD /S1/ A(10)
        //                      END STRUCTURE
        //                      RECORD /S2/ X
        //                      RECORD /S1/ I
        //                      X%A(I%J)%K
        // when we are about to process I%J, save FieldNode for "A" so we can
        // later compute the offset of "K"
        CITNode->value.sc.struct_chain = FieldNode;
        FieldNode = CITNode;
    }
}


void    GetFunctionShadow(void) {
//===========================

    sym_id      fn_shadow;

    // update type in function shadow symbol in case an
    // IMPLICIT statement changed the type of the function
    fn_shadow = FindShadow( CITNode->sym_ptr );
    fn_shadow->ns.typ = CITNode->sym_ptr->ns.typ;
    if( fn_shadow->ns.typ == TY_STRUCTURE ) {
        fn_shadow->ns.xt.record = CITNode->sym_ptr->ns.xt.record;
    } else {
        fn_shadow->ns.xt.size = CITNode->sym_ptr->ns.xt.size;
    }
    CITNode->sym_ptr = fn_shadow;
    CITNode->flags = fn_shadow->ns.flags;
}


static  void    SubProg(void) {
//=========================

// Make sure subprograms are used correctly.

    unsigned_16 sp_type;

    sp_type = CITNode->flags & SY_SUBPROG_TYPE;
    if( ( sp_type == SY_REMOTE_BLOCK ) || ( sp_type == SY_PROGRAM ) ) {
        IllName( CITNode->sym_ptr );
    } else if( sp_type == SY_STMT_FUNC ) {
        if( RecNWL() ) {
            if( ASType & AST_ASF ) { // if defining s. f.
                if( CITNode->sym_ptr == SFSymId ) {
                    Error( SR_TRIED_RECURSION ); // check recursion
                }
            }
        } else {
            if( ( ASType & AST_ASF ) == 0 ) { // if not defining s. f.
                IllName( CITNode->sym_ptr );
            }
        }
    } else if( sp_type == SY_SUBROUTINE ) {
        if( RecNWL() ) {
            if( ( StmtProc == PR_CALL ) && RecTrmOpr() ) {
                if( ( CITNode->flags & SY_PS_ENTRY ) != 0 ) {
                    Extension( SR_TRIED_RECURSION );
                }
            } else {
                IllName( CITNode->sym_ptr );
            }
        } else if( ( ASType & AST_CNA ) == 0 ) {
            CkNameNoList();
        } else if( ( CITNode->flags & SY_PS_ENTRY ) != 0 ) {
            Extension( SR_TRIED_RECURSION );
        }
    } else if( sp_type == SY_FUNCTION ) {
        if( RecNWL() && SubStrung() && (CITNode->typ == TY_CHAR) &&
            (CITNode->flags & SY_PS_ENTRY) ) {
            GetFunctionShadow();
        } else if( !RecNWL() && !(ASType & AST_CNA) ) {
            if( CITNode->flags & SY_PS_ENTRY ) {
                GetFunctionShadow();
            } else {
                CkNameNoList();
            }
        } else if( ( CITNode->flags & SY_PS_ENTRY ) != 0 ) {
            Extension( SR_TRIED_RECURSION );
        } else if( CITNode->flags & SY_INTRINSIC ) {
            if( CITNode->sym_ptr->ns.si.fi.index == IF_ISIZEOF ) {
                ASType |= AST_ISIZEOF;
            }
        }
    } else if( sp_type == SY_FN_OR_SUB ) {
        if( RecNWL() ) {                        // if it's in a CALL statement
            CITNode->flags |= SY_FUNCTION;      // the class will already be
            SetTypeUsage( SY_TYPE | SY_USAGE ); // SUBROUTINE and we won't
        } else {                                // be in this part of the code
            CkNameNoList();
        }
    }
}


static  void    Function(void) {
//==========================

// Must be scanning a function.

    if( CITNode->flags & SY_PS_ENTRY ) {
        Extension( SR_TRIED_RECURSION );
    } else if( CITNode->flags & ( SY_USAGE | SY_DO_PARM | SY_IN_EC ) ) {
        IllName( CITNode->sym_ptr );
    } else if( CITNode->flags & SY_SAVED ) {
        Error( SA_SAVED );
    } else {
        CkIntrinsic();
        CITNode->flags |= SY_SUBPROGRAM | SY_FUNCTION;
        SetTypeUsage( SY_TYPE | SY_USAGE );
    }
}


static  void    CkIntrinsic(void) {
//=============================

// Check for intrinsic functions.
//
//     CASE 1: integer abs
//             y == abs( -1.0 )    -- this should call generic i.f. abs
//
//     CASE 2: real iabs
//             y == iabs( -1 )     -- this should give type mismatch error
//

    sym_id      sym_ptr;
    TYPE        typ;
    IFF         func;

    sym_ptr = CITNode->sym_ptr;
    if( ( CITNode->flags & SY_SUB_PARM ) == 0 ) {
        typ = CITNode->typ;
        func = IFLookUp();
        if( func > 0 ) {
            sym_ptr->ns.si.fi.index = func;
            if( func == IF_ISIZEOF ) {
                ASType |= AST_ISIZEOF;
            }
            sym_ptr->ns.si.fi.num_args = 0;
            CITNode->flags |= SY_INTRINSIC;
            IFChkExtension( func );
            if( !IFIsGeneric( func ) ) {
                CITNode->typ = IFType( func );
                CITNode->size = TypeSize( CITNode->typ );
                sym_ptr->ns.typ = CITNode->typ;
                sym_ptr->ns.xt.size = CITNode->size;
                if( ( CITNode->typ != typ ) && ( CITNode->flags & SY_TYPE ) ) {
                    Error( LI_WRONG_TYPE );
                }
            }
        }
    }
}


static  void    CkNameNoList(void) {
//==============================

// Check that array/subprogram with no list is alright.

    if( ( ASType & AST_IO ) && RecTrmOpr() && RecNextOpr( OPR_TRM ) ) {
        if( ( CITNode->opn.us & USOPN_WHAT ) != USOPN_ARR ) {
            ClassErr( SV_NO_LIST, CITNode->sym_ptr );
        }
        return;
    }
    if( ( !RecNextOpr( OPR_COM ) && !RecNextOpr( OPR_RBR ) ) ||
        ( !RecComma() && !RecFBr() ) ) {
        ClassErr( SV_NO_LIST, CITNode->sym_ptr );
    }
}


static  void    CkFieldNoList(void) {
//===============================

// Check that array field with no list is alright.

    itnode      *opr_node;

    // find the node that contains the structured symbol
    opr_node = FieldNode;
    while( opr_node->value.sc.struct_chain != NULL ) {
        opr_node = opr_node->value.sc.struct_chain;
    }
    if( ( ASType & AST_IO ) && ( opr_node->opr == OPR_TRM ) &&
        RecNextOpr( OPR_TRM ) ) {
        if( ( CITNode->opn.us & USOPN_WHAT ) != USOPN_ARR ) {
            KnownClassErr( SV_NO_LIST, NAME_ARRAY );
        }
        return;
    }
    if( ( !RecNextOpr( OPR_COM ) && !RecNextOpr( OPR_RBR ) ) ||
        ( ( opr_node->opr != OPR_COM ) && ( opr_node->opr != OPR_FBR ) ) ) {
        KnownClassErr( SV_NO_LIST, NAME_ARRAY );
    }
}


static  void    SetTypeUsage( unsigned_16 type_usage) {
//=====================================================

// Indicate that a names' use and type has been established.

    CITNode->sym_ptr->ns.flags = CITNode->flags;
    CkTypeDeclared();
    CITNode->flags |= type_usage;
    CITNode->sym_ptr->ns.flags |= type_usage;
}


void    CkTypeDeclared(void) {
//========================

// Make sure type has been explicitly declared.

    unsigned_16 flags;

    if( ( SgmtSw & SG_IMPLICIT_NONE ) || ( Options & OPT_EXPLICIT ) ) {
        flags = CITNode->sym_ptr->ns.flags;
        if( ( flags & SY_TYPE ) == 0 ) {
            if( ( flags & SY_CLASS ) == SY_SUBPROGRAM ) {
                if( flags & SY_INTRINSIC ) return;
            }
            NameErr( TY_UNDECLARED, CITNode->sym_ptr );
        }
    }
}

⌨️ 快捷键说明

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