Esempio n. 1
0
void CBotVar::SetInit(CBotVar::InitType initType)
{
    m_binit = initType;
    if (initType == CBotVar::InitType::IS_POINTER ) m_binit = CBotVar::InitType::DEF;                    // cas spécial

    if ( m_type.Eq(CBotTypPointer) && initType == CBotVar::InitType::IS_POINTER )
    {
        CBotVarClass* instance = GetPointer();
        if ( instance == nullptr )
        {
            instance = new CBotVarClass(CBotToken(), m_type);
//            instance->SetClass((static_cast<CBotVarPointer*>(this))->m_classes);
            SetPointer(instance);
        }
        instance->SetInit(CBotVar::InitType::DEF);
    }

    if ( m_type.Eq(CBotTypClass) || m_type.Eq(CBotTypIntrinsic) )
    {
        CBotVar*    p = (static_cast<CBotVarClass*>(this))->m_pVar;
        while( p != nullptr )
        {
            p->SetInit(initType);
            p->m_pMyThis = static_cast<CBotVarClass*>(this);
            p = p->GetNext();
        }
    }
}
Esempio n. 2
0
void CBotVar::SetInit(int bInit)
{
    m_binit = bInit;
    if ( bInit == 2 ) m_binit = IS_DEF;                    // cas spécial

    if ( m_type.Eq(CBotTypPointer) && bInit == 2 )
    {
        CBotVarClass* instance = GetPointer();
        if ( instance == NULL )
        {
            instance = new CBotVarClass(NULL, m_type);
//            instance->SetClass((static_cast<CBotVarPointer*>(this))->m_pClass);
            SetPointer(instance);
        }
        instance->SetInit(1);
    }

    if ( m_type.Eq(CBotTypClass) || m_type.Eq(CBotTypIntrinsic) )
    {
        CBotVar*    p = (static_cast<CBotVarClass*>(this))->m_pVar;
        while( p != NULL )
        {
            p->SetInit( bInit );
            p->m_pMyThis = static_cast<CBotVarClass*>(this);
            p = p->GetNext();
        }
    }
}
Esempio n. 3
0
bool CBotClass::SaveStaticState(FILE* pf)
{
    if (!WriteWord( pf, CBOTVERSION*2)) return false;

    // saves the state of static variables in classes
    CBotClass*  p = m_ExClass;

    while ( p != NULL )
    {
        if (!WriteWord( pf, 1)) return false;
        // save the name of the class
        if (!WriteString( pf, p->GetName() )) return false;

        CBotVar*    pv = p->GetVar();
        while( pv != NULL )
        {
            if ( pv->IsStatic() )
            {
                if (!WriteWord( pf, 1)) return false;
                if (!WriteString( pf, pv->GetName() )) return false;

                if ( !pv->Save0State(pf)) return false;             // common header
                if ( !pv->Save1State(pf) ) return false;                // saves as the child class
                if ( !WriteWord( pf, 0)) return false;
            }
            pv = pv->GetNext();
        }

        if (!WriteWord( pf, 0)) return false;
        p = p->m_ExNext;
    }

    if (!WriteWord( pf, 0)) return false;
    return true;
}
Esempio n. 4
0
CBotVar* CBotClass::GetItemRef(int nIdent)
{
    CBotVar*    p = m_pVar;

    while ( p != NULL )
    {
        if ( p->GetUniqNum() == nIdent ) return p;
        p = p->GetNext();
    }
    if ( m_pParent != NULL ) return m_pParent->GetItemRef(nIdent);
    return NULL;
}
Esempio n. 5
0
CBotVar* CBotClass::GetItem(const char* name)
{
    CBotVar*    p = m_pVar;

    while ( p != NULL )
    {
        if ( p->GetName() == name ) return p;
        p = p->GetNext();
    }
    if ( m_pParent != NULL ) return m_pParent->GetItem(name);
    return NULL;
}
Esempio n. 6
0
void CBotVar::debug()
{
//    const char*    p = static_cast<const char*>( m_token->GetString());
    CBotString  s = static_cast<const char*>( GetValString());
//    const char* v = static_cast<const char*> (s);

    if ( m_type.Eq(CBotTypClass) )
    {
        CBotVar*    pv = (static_cast<CBotVarClass*>(this))->m_pVar;
        while (pv != NULL)
        {
            pv->debug();
            pv = pv->GetNext();
        }
    }
}
Esempio n. 7
0
// compiles a new function
// bLocal allows of the declaration of parameters on the same level
// as the elements belonging to the class for methods
CBotFunction* CBotFunction::Compile(CBotToken* &p, CBotCStack* pStack, CBotFunction* finput, bool bLocal)
{
    CBotToken*      pp;
    CBotFunction* func = finput;
    if ( func == NULL ) func = new CBotFunction();

    CBotCStack* pStk = pStack->TokenStack(p, bLocal);

//  func->m_nFuncIdent = CBotVar::NextUniqNum();

    while (true)
    {
        if ( IsOfType(p, ID_PUBLIC) )
        {
            func->m_bPublic = true;
            continue;
        }
        pp = p;
        if ( IsOfType(p, ID_EXTERN) )
        {
            func->m_extern = pp;        // for the position of the word "extern"
            func->m_bExtern = true;
//          func->m_bPublic = true;     // therefore also public!
            continue;
        }
        break;
    }

    func->m_retToken = *p;
//  CBotClass*  pClass;
    func->m_retTyp = TypeParam(p, pStk);        // type of the result

    if (func->m_retTyp.GetType() >= 0)
    {
        CBotToken*  pp = p;
        func->m_token = *p;

        if ( IsOfType(p, ID_NOT) )
        {
            CBotToken d("~" + p->GetString());
            func->m_token = d;
        }

        // un nom de fonction est-il là ?
        if (IsOfType(p, TokenTypVar))
        {
            if ( IsOfType( p, ID_DBLDOTS ) )        // method for a class
            {
                func->m_MasterClass = pp->GetString();
                CBotClass* pClass = CBotClass::Find(pp);
                if ( pClass == NULL ) goto bad;

//              pp = p;
                func->m_token = *p;
                if (!IsOfType(p, TokenTypVar)) goto bad;

            }
            func->m_openpar = p;
            func->m_Param = CBotDefParam::Compile( p, pStk );
            func->m_closepar = p->GetPrev();
            if (pStk->IsOk())
            {
                pStk->SetRetType(func->m_retTyp);   // for knowledge what type returns

                if (!func->m_MasterClass.IsEmpty())
                {
                    // return "this" known
                    CBotVar* pThis = CBotVar::Create("this", CBotTypResult( CBotTypClass, func->m_MasterClass ));
                    pThis->SetInit(2);
//                  pThis->SetUniqNum(func->m_nThisIdent = -2); //CBotVar::NextUniqNum() will not
                    pThis->SetUniqNum(-2);
                    pStk->AddVar(pThis);

                    // initialize variables acording to This
                    // only saves the pointer to the first,
                    // the rest is chained
                    CBotVar* pv = pThis->GetItemList();
//                  int num = 1;
                    while (pv != NULL)
                    {
                        CBotVar* pcopy = CBotVar::Create(pv);
//                      pcopy->SetInit(2);
                        pcopy->Copy(pv);
                        pcopy->SetPrivate(pv->GetPrivate());
//                      pcopy->SetUniqNum(pv->GetUniqNum()); //num++);
                        pStk->AddVar(pcopy);
                        pv = pv->GetNext();
                    }
                }

                // and compiles the following instruction block 
                func->m_openblk = p;
                func->m_Block   = CBotBlock::Compile(p, pStk, false);
                func->m_closeblk = p->GetPrev();
                if ( pStk->IsOk() )
                {
                    if ( func->m_bPublic )  // public function, return known for all
                    {
                        CBotFunction::AddPublic(func);
                    }
                    return pStack->ReturnFunc(func, pStk);
                }
            }
        }
bad:
        pStk->SetError(TX_NOFONC, p);
    }
    pStk->SetError(TX_NOTYP, p);
    if ( finput == NULL ) delete func;
    return pStack->ReturnFunc(NULL, pStk);
}
Esempio n. 8
0
bool CBotClass::CompileDefItem(CBotToken* &p, CBotCStack* pStack, bool bSecond)
{
    bool    bStatic = false;
    int     mProtect = PR_PUBLIC;
    bool    bSynchro = false;

    while (IsOfType(p, ID_SEP)) ;

    CBotTypResult   type( -1 );

    if ( IsOfType(p, ID_SYNCHO) ) bSynchro = true;
    CBotToken*      pBase = p;

    if ( IsOfType(p, ID_STATIC) ) bStatic = true;
    if ( IsOfType(p, ID_PUBLIC) ) mProtect = PR_PUBLIC;
    if ( IsOfType(p, ID_PRIVATE) ) mProtect = PR_PRIVATE;
    if ( IsOfType(p, ID_PROTECTED) ) mProtect = PR_PROTECT;
    if ( IsOfType(p, ID_STATIC) ) bStatic = true;

//  CBotClass* pClass = NULL;
    type = TypeParam(p, pStack);        // type of the result

    if ( type.Eq(-1) )
    {
        pStack->SetError(TX_NOTYP, p);
        return false;
    }

    while (pStack->IsOk()) 
    {
        CBotToken*  pp = p;
        IsOfType(p, ID_NOT);    // skips ~ eventual (destructor)

        if (IsOfType(p, TokenTypVar))
        {
            CBotInstr* limites = NULL;
            while ( IsOfType( p, ID_OPBRK ) )   // a table?
            {
                CBotInstr* i = NULL;

                if ( p->GetType() != ID_CLBRK )
                    i = CBotExpression::Compile( p, pStack );           // expression for the value
                else
                    i = new CBotEmpty();                            // special if not a formula

                type = CBotTypResult(CBotTypArrayPointer, type);

                if (!pStack->IsOk() || !IsOfType( p, ID_CLBRK ) )
                {
                    pStack->SetError(TX_CLBRK, p->GetStart());
                    return false;
                }

/*              CBotVar* pv = pStack->GetVar();
                if ( pv->GetType()>= CBotTypBoolean )
                {
                    pStack->SetError(TX_BADTYPE, p->GetStart());
                    return false;
                }*/

                if (limites == NULL) limites = i;
                else limites->AddNext3(i);
            }

            if ( p->GetType() == ID_OPENPAR )
            {
                if ( !bSecond )
                {
                    p = pBase;
                    CBotFunction* f = 
                    CBotFunction::Compile1(p, pStack, this);

                    if ( f == NULL ) return false;

                    if (m_pMethod == NULL) m_pMethod = f;
                    else m_pMethod->AddNext(f);
                }
                else
                {
                    // return a method precompiled in pass 1
                    CBotFunction*   pf = m_pMethod;
                    CBotFunction*   prev = NULL;
                    while ( pf != NULL ) 
                    {
                        if (pf->GetName() == pp->GetString()) break;
                        prev = pf;
                        pf = pf->Next();
                    }

                    bool bConstructor = (pp->GetString() == GetName());
                    CBotCStack* pile = pStack->TokenStack(NULL, true);

                    // make "this" known
                    CBotToken TokenThis(CBotString("this"), CBotString());
                    CBotVar* pThis = CBotVar::Create(&TokenThis, CBotTypResult( CBotTypClass, this ) );
                    pThis->SetUniqNum(-2);
                    pile->AddVar(pThis);

                    if ( m_pParent )
                    {
                        // makes "super" known
                        CBotToken TokenSuper(CBotString("super"), CBotString());
                        CBotVar* pThis = CBotVar::Create(&TokenSuper, CBotTypResult( CBotTypClass, m_pParent ) );
                        pThis->SetUniqNum(-3);
                        pile->AddVar(pThis);
                    }

//                  int num = 1;
                    CBotClass*  my = this;
                    while (my != NULL)
                    {
                        // places a copy of variables of a class (this) on a stack
                        CBotVar* pv = my->m_pVar;
                        while (pv != NULL)
                        {
                            CBotVar* pcopy = CBotVar::Create(pv);
                            pcopy->SetInit(!bConstructor || pv->IsStatic());
                            pcopy->SetUniqNum(pv->GetUniqNum());
                            pile->AddVar(pcopy);
                            pv = pv->GetNext();
                        }
                        my = my->m_pParent;
                    }

                    // compiles a method
                    p = pBase;
                    CBotFunction* f = 
                    CBotFunction::Compile(p, pile, NULL/*, false*/);

                    if ( f != NULL )
                    {
                        f->m_pProg = pStack->GetBotCall();
                        f->m_bSynchro = bSynchro;
                        // replaces the element in the chain
                        f->m_next = pf->m_next;
                        pf->m_next = NULL;
                        delete pf;
                        if (prev == NULL) m_pMethod = f;
                        else prev->m_next = f;
                    }
                    pStack->Return(NULL, pile);
                }

                return pStack->IsOk();
            }

            // definition of an element
            if (type.Eq(0))
            {
                pStack->SetError(TX_ENDOF, p);
                return false;
            }

            CBotInstr* i = NULL;
            if ( IsOfType(p, ID_ASS ) )
            {
                if ( type.Eq(CBotTypArrayPointer) )
                {
                    i = CBotListArray::Compile(p, pStack, type.GetTypElem());
                }
                else
                {
                    // it has an assignmet to calculate
                    i = CBotTwoOpExpr::Compile(p, pStack);
                }
                if ( !pStack->IsOk() ) return false;
            }


            if ( !bSecond )
            {
                CBotVar*    pv = CBotVar::Create(pp->GetString(), type);
                pv -> SetStatic( bStatic );
                pv -> SetPrivate( mProtect );

                AddItem( pv );

                pv->m_InitExpr = i;
                pv->m_LimExpr = limites;


                if ( pv->IsStatic() && pv->m_InitExpr != NULL )
                {
                    CBotStack* pile = CBotStack::FirstStack();              // independent stack
                    while(pile->IsOk() && !pv->m_InitExpr->Execute(pile));  // evaluates the expression without timer
                    pv->SetVal( pile->GetVar() ) ;
                    pile->Delete();
                }
            }
            else
                delete i;

            if ( IsOfType(p, ID_COMMA) ) continue;
            if ( IsOfType(p, ID_SEP) ) break;
        }
        pStack->SetError(TX_ENDOF, p);
    }
    return pStack->IsOk();
}