Пример #1
0
BOOL StrToU64( char *str, unsigned_64 *u64, BOOL neg )
{
    unsigned_64 r64;
    unsigned_64 v64;
    int         value;
    int         radix;

    str = eatSpace( str );
    U32ToU64( 0, u64 );
    if( neg == TRUE ) {
        if( *str == '-') {
            str++;
        } else {
            if( *str == '+' ) {
                str++;
                neg = FALSE;
            }
        }
    }
    str = eatSpace( str );
    switch( *str ){
    case '\0':
        return( FALSE );
    case '0':
        str++;
        if( tolower(*str) == 'x' ) {
            radix = 16;
            str++;
        } else {
            radix = 8;
        }
        break;
    default:
        radix = 10;
    }
    U32ToU64( radix, &r64 );
    while( *str != '\0' ) {
        if( isdigit( *str ) ) {
            value = *str - '0';
        } else {
            value = 10 + tolower( *str ) - 'a';
        }
        if( value < 0 || value >= radix ) {
            return ( FALSE );
        }
        U32ToU64( value, &v64 );
        U64Mul( u64, &r64, u64 );
        U64Add( &v64, u64, u64 );
        str++;
    }
    if( neg == TRUE) {
        U64Neg( u64, u64 );
    }
    return( TRUE );
}
Пример #2
0
OVL_EXTERN bool ConvU8( stack_entry *entry, conv_class from )
{
    unsigned_64  tmp;

    switch( from ) {
    case U1:
    case U2:
    case U4:
    case U8:
        tmp = entry->v.uint;
        break;
    case I1:
    case I2:
    case I4:
    case I8:
        tmp = entry->v.sint;
        break;
    case F4:
    case F8:
    case F10:
        //NYI: 64-bit support
        I32ToI64( LDToD( &entry->v.real ), &tmp );
        break;
    case C8:
    case C16:
    case C20:
        I32ToI64( LDToD( &entry->v.cmplx.re ), &tmp );
        break;
    case NP2:
    case NP4:
        //NYI: 64-bit offsets
        U32ToU64( entry->v.addr.mach.offset, &tmp );
        break;
    case FP4:
    case HP4:
        U32ToU64( entry->v.addr.mach.offset +
                ((long) entry->v.addr.mach.segment << 16), &tmp );
        break;
    case FP6:
        U32ToU64( entry->v.addr.mach.offset, &tmp );
        break;
    default:
        return( FALSE );
    }
    entry->v.uint = tmp;
    return( TRUE );
}
Пример #3
0
static bool GetNum( unsigned base )
{
    bool        ok;
    unsigned_64 num;
    unsigned_64 big_base;
    unsigned_64 big_dig;
    int         dig;

    ok = FALSE;
    U32ToU64( base, &big_base );
    U64Clear( num );
    for( ; ; ) {
        dig = GetDig( base );
        if( dig < 0 ) break;
        U32ToU64( dig, &big_dig );
        U64Mul( &num, &big_base, &num );
        U64Add( &num, &big_dig, &num );
        ++ScanPtr;
        ok = TRUE;
    }
    TokenVal.int_val = num;
    return( ok );
}
Пример #4
0
static char ScanNumber( void )
{
    rad_str *pref;
    bool    ret;
    char    *hold_scan;

    ret = FALSE;
    hold_scan = ScanPtr;
    if( ScanCCharNum && (*ScanPtr == '\'') ) {
        if( ScanPtr[ 1 ] != NULLCHAR && ScanPtr[ 2 ] == '\'' ) {
            U32ToU64( ScanPtr[1], &TokenVal.int_val );
            ScanPtr += 3;
            CurrToken = T_INT_NUM;
            return( TRUE );
        }
    } else {
        CurrToken = T_BAD_NUM; /* assume we'll find a bad number */
        pref = RadStrs;
        while( pref != NULL ) {
            if( memicmp( ScanPtr, &pref->radstr[1], pref->radstr[0] ) == 0 ) {
                ret = TRUE;
                ScanPtr += pref->radstr[0];
                hold_scan = ScanPtr;
                if( GetNum( pref->radval ) ) {
                    CurrToken = T_INT_NUM;
                    return( TRUE );
                }
                ScanPtr -= pref->radstr[0];
            }
            pref = pref->next;
        }
        if( isdigit( *ScanPtr ) && GetNum( CurrRadix ) ) {
            CurrToken = T_INT_NUM;
            return( TRUE );
        }
    }
    ScanPtr = hold_scan;
    return( ret );
}
Пример #5
0
local void StoreInt64( TYPEPTR typ )
{
    TREEPTR     tree;
    DATA_QUAD   dq;

    dq.type = typ->decl_type;
    dq.flags = Q_DATA;
    U32ToU64( 0, &dq.u.long64 );
    if( CurToken != T_RIGHT_BRACE ) {
        tree = SingleExpr();
        tree = InitAsgn( typ, tree ); // as if we are assigning
        if( tree->op.opr == OPR_PUSHINT || tree->op.opr == OPR_PUSHFLOAT ) {
            CastConstValue( tree, typ->decl_type );
            dq.u.long64 = tree->op.ulong64_value;
        } else {
            CErr1( ERR_NOT_A_CONSTANT_EXPR );
        }
        FreeExprTree( tree );
        CompFlags.non_zero_data = 1;
    }
    GenDataQuad( &dq, sizeof( int64 ) );
}
Пример #6
0
TYPEPTR EnumDecl( int flags )
{
    TYPEPTR     typ;
    TAGPTR      tag;

    flags = flags;
    NextToken();
    if( CurToken == T_ID ) {
        /* could be: (1) "enum" <id> ";"
                     (2) "enum" <id> <variable_name> ";"
                     (3) "enum" <id> "{" <enum_const_decl> ... "}"
        */
        tag = TagLookup();
        NextToken();
        if( CurToken != T_LEFT_BRACE ) {
            typ = tag->sym_type;
            if( typ == NULL ) {
                CErr1( ERR_INCOMPLETE_ENUM_DECL );
                typ = TypeDefault();
            } else {
                if( typ->decl_type != TYPE_ENUM ) {         /* 18-jan-89 */
                    CErr2p( ERR_DUPLICATE_TAG, tag->name );
                }
                typ->u.tag = tag;
            }
            return( typ );
        }
        tag = VfyNewTag( tag, TYPE_ENUM );
    } else {
        tag = NullTag();
    }
    typ = TypeNode( TYPE_ENUM, GetType( TYPE_INT ) );
    typ->u.tag = tag;
    tag->sym_type = typ;
    tag->size = TARGET_INT;
    tag->u.enum_list = NULL;
    if( CurToken == T_LEFT_BRACE ) {
        const_val       val;
        enum enum_rng   index;
        enum enum_rng   const_index;
        enum enum_rng   start_index;
        enum enum_rng   step;
        enum enum_rng   error;
        uint64          n;
        uint64          Inc;
        bool            minus;
        bool            has_sign;
        ENUMPTR         *prev_lnk;
        ENUMPTR         esym;
        source_loc      error_loc;
        char            buff[50];

        if( CompFlags.make_enums_an_int ) {
            start_index = ENUM_INT;
        } else {
            start_index = ENUM_S8;
        }
        const_index = ENUM_UNDEF;
        NextToken();
        if( CurToken == T_RIGHT_BRACE ) {
            CErr1( ERR_EMPTY_ENUM_LIST );
        }
        U32ToU64( 1, &Inc );
        U64Clear( n );
        minus = FALSE;
        has_sign = FALSE;
        step = 1;
        prev_lnk = &esym;
        esym = NULL;
        while( CurToken == T_ID ) {
            esym = EnumLkAdd( tag );
            *prev_lnk = esym;
            prev_lnk = &esym->thread;
            error_loc = TokenLoc;
            NextToken();
            if( CurToken == T_EQUAL ) {
                NextToken();
                error_loc = TokenLoc;
                ConstExprAndType( &val );
                switch( val.type ){
                case TYPE_ULONG:
                case TYPE_UINT:
                case TYPE_ULONG64:
                    minus = FALSE;
                    break;
                default:
                    if( val.value.u.sign.v ) {
                        minus = TRUE;
                        step = 2;
                    } else {
                        minus = FALSE;
                    }
                    break;
                }
                n = val.value;
            } else if( has_sign ) {
                if( n.u.sign.v ) {
                    minus = TRUE;
                } else {
                    minus = FALSE;
                }
            }
            for( index = start_index; index < ENUM_SIZE; index += step ) {
                if( minus ) {
                    if( I64Cmp( &n, &( RangeTable[ index ][LOW] ) ) >= 0 ) break;
                } else {
                    if( U64Cmp( &n, &( RangeTable[ index ][HIGH]) ) <= 0 ) break;
                }
            }
            error = ENUM_UNDEF;
            if( !CompFlags.extensions_enabled && ( index > ENUM_INT )) {
                error = ENUM_INT;
            }
            if( index >= ENUM_SIZE ) {
                // overflow signed maximum range
                if( error == ENUM_UNDEF ) {
                    error = const_index;
                }
            } else if(( const_index == ENUM_SIZE - 1 ) && minus ) {
                // overflow unsigned maximum range by any negative signed value
                if( error == ENUM_UNDEF )
                    error = const_index;
                step = 1;
            } else {
                if( !has_sign && minus) {
                    has_sign = TRUE;
                    if( index < const_index ) {
                        // round up to signed
                        index = ( const_index + 1 ) & ~1;
                    }
                }
                if( index > const_index ) {
                    const_index = index;
                    typ->object = GetType( ItypeTable[const_index].decl_type );
                    tag->size   = ItypeTable[const_index].size;
                }
            }
            if( error != ENUM_UNDEF ) {
                SetErrLoc( &error_loc );
                get_msg_range( buff, error );
                CErr2p( ERR_ENUM_CONSTANT_OUT_OF_RANGE, buff );
                InitErrLoc();
            }
            esym->value = n;
            EnumTable[ esym->hash ] = esym;             /* 08-nov-94 */
            if( CurToken == T_RIGHT_BRACE )
                break;
            U64Add( &n, &Inc, &n );
            MustRecog( T_COMMA );
            if( !CompFlags.extensions_enabled
              && !CompFlags.c99_extensions
              && ( CurToken == T_RIGHT_BRACE )) {
                ExpectIdentifier();         /* 13-may-91 */
            }
        }
        MustRecog( T_RIGHT_BRACE );
    }
    return( typ );
}
Пример #7
0
local FIELDPTR InitBitField( FIELDPTR field )
{
    TYPEPTR             typ;
    unsigned long       value;
    unsigned long       size;
    uint64              value64;
    unsigned long       bit_value;
    unsigned long       offset;
    TOKEN               token;
    int                 is64bit;

    token = CurToken;
    if( CurToken == T_LEFT_BRACE )
        NextToken();
    typ = field->field_type;
    size = SizeOfArg( typ );
    is64bit = ( typ->u.f.field_type == TYPE_LONG64 )
           || ( typ->u.f.field_type == TYPE_ULONG64 );
    if( is64bit )
        U32ToU64( 0, &value64 );
    offset = field->offset;
    value = 0;
    while( typ->decl_type == TYPE_FIELD ||
           typ->decl_type == TYPE_UFIELD ) {
        bit_value = 0;
        if( CurToken != T_RIGHT_BRACE )
            bit_value = ConstExpr();
        if( typ->u.f.field_type == TYPE_BOOL ) {
            if( bit_value != 0 ) {
                bit_value = 1;
            }
        } else {
            ChkConstant( bit_value, BitMask[typ->u.f.field_width - 1] );
            bit_value &= BitMask[typ->u.f.field_width - 1];
        }
        if( is64bit ) {
            uint64 tmp;
            U32ToU64( bit_value, &tmp );
            U64ShiftL( &tmp, typ->u.f.field_start, &tmp );
            value64.u._32[L] |= tmp.u._32[L];
            value64.u._32[H] |= tmp.u._32[H];
        } else {
            value |= bit_value << typ->u.f.field_start;
        }
        field = field->next_field;
        if( field == NULL )
            break;
        if( field->offset != offset )
            break;    /* bit field done */
        typ = field->field_type;
        if( CurToken == T_EOF )
            break;
        if( CurToken != T_RIGHT_BRACE ) {
            MustRecog( T_COMMA );
        }
    }
    if( is64bit ) {
        StoreIValue64( typ->u.f.field_type, value64 );
    } else {
        StoreIValue( typ->u.f.field_type, value, size );
    }
    if( token == T_LEFT_BRACE ) {
        if( CurToken == T_COMMA ) NextToken();
        MustRecog( T_RIGHT_BRACE );
    }
    return( field );
}
Пример #8
0
/*
 * ConvertTo -- convert 'entry' to the given 'class'.
 *      'entry' should be an rvalue.
 */
void ConvertTo( stack_entry *entry, type_kind k, type_modifier m, unsigned s )
{
    conv_class  from;
    char        *dest;

    if( s == 0 && k == TK_INTEGER ) {
        s = DefaultSize( DK_INT );
    }
    if( entry->info.kind == k
     && entry->info.modifier == m
     && entry->info.size == s ) return;
    from = ConvIdx( &entry->info );
    switch( from ) {
    case U1:
        U32ToU64( U8FetchTrunc( entry->v.uint ), &entry->v.uint );
        break;
    case U2:
        U32ToU64( U16FetchTrunc( entry->v.uint ), &entry->v.uint );
        break;
    case U4:
        U32ToU64( U32FetchTrunc( entry->v.uint ), &entry->v.uint );
        break;
    case I1:
        I32ToI64( I8FetchTrunc( entry->v.uint ), &entry->v.uint );
        break;
    case I2:
        I32ToI64( I16FetchTrunc( entry->v.uint ), &entry->v.uint );
        break;
    case I4:
        I32ToI64( I32FetchTrunc( entry->v.uint ), &entry->v.uint );
        break;
    case F4:
        DToLD( (float)LDToD( &entry->v.real ), &entry->v.real );
        break;
    case F8:
        DToLD( (double)LDToD( &entry->v.real ), &entry->v.real );
        break;
    case C8:
        DToLD( (float)LDToD( &entry->v.cmplx.re ), &entry->v.cmplx.re );
        DToLD( (float)LDToD( &entry->v.cmplx.im ), &entry->v.cmplx.im );
        break;
    case C16:
        DToLD( (double)LDToD( &entry->v.cmplx.re ), &entry->v.cmplx.re );
        DToLD( (double)LDToD( &entry->v.cmplx.im ), &entry->v.cmplx.im );
        break;
    case NP2:
    case FP4:
        entry->v.addr.mach.offset &= 0xffff;
        break;
    case STR:
        if( k != TK_STRING ) {
            Error( ERR_NONE, LIT( ERR_TYPE_CONVERSION ) );
        }
        if( s > entry->info.size ) {
            /* have to expand string */
            _ChkAlloc( dest, s, LIT( ERR_NO_MEMORY_FOR_EXPR ) );
            memcpy( dest, entry->v.string.loc.e[0].u.p, entry->info.size );
            memset( &dest[entry->info.size], ' ', s - entry->info.size );
            if( AllocatedString( entry ) ) {
                _Free( entry->v.string.allocated );
            }
            entry->v.string.allocated = dest;
            LocationCreate( &entry->v.string.loc, LT_INTERNAL, dest );
        }
        break;
    default:
        break;
    }
    entry->info.kind = k;
    entry->info.modifier = m;
    entry->info.size = s;
    if( !ConvFunc[ ConvIdx( &entry->info ) ]( entry, from ) ) {
        Error( ERR_NONE, LIT( ERR_TYPE_CONVERSION ) );
    }
    entry->th = NULL;
}
Пример #9
0
OVL_EXTERN bool ConvU4( stack_entry *entry, conv_class from )
{
    if( !ConvU8( entry, from ) ) return( FALSE );
    U32ToU64( (unsigned_32)U32FetchTrunc( entry->v.uint ), &entry->v.uint );
    return( TRUE );
}
Пример #10
0
OVL_EXTERN bool ConvU2( stack_entry *entry, conv_class from )
{
    if( !ConvU8( entry, from ) ) return( false );
    U32ToU64( (unsigned_16)U32FetchTrunc( entry->v.uint ), &entry->v.uint );
    return( true );
}