2015-11-11 21:36:18 +00:00
|
|
|
|
/*
|
|
|
|
|
* This file is part of the Colobot: Gold Edition source code
|
2016-02-13 13:11:30 +00:00
|
|
|
|
* Copyright (C) 2001-2016, Daniel Roux, EPSITEC SA & TerranovaTeam
|
2015-11-11 21:36:18 +00:00
|
|
|
|
* http://epsitec.ch; http://colobot.info; http://github.com/colobot
|
|
|
|
|
*
|
|
|
|
|
* This program is free software: you can redistribute it and/or modify
|
|
|
|
|
* it under the terms of the GNU General Public License as published by
|
|
|
|
|
* the Free Software Foundation, either version 3 of the License, or
|
|
|
|
|
* (at your option) any later version.
|
|
|
|
|
*
|
|
|
|
|
* This program is distributed in the hope that it will be useful,
|
|
|
|
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
|
|
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
|
|
|
|
|
* See the GNU General Public License for more details.
|
|
|
|
|
*
|
|
|
|
|
* You should have received a copy of the GNU General Public License
|
|
|
|
|
* along with this program. If not, see http://gnu.org/licenses
|
|
|
|
|
*/
|
|
|
|
|
|
2015-12-31 13:44:19 +00:00
|
|
|
|
#include "CBot/CBotInstr/CBotDefClass.h"
|
2015-11-22 14:47:46 +00:00
|
|
|
|
|
2015-11-23 20:59:56 +00:00
|
|
|
|
#include "CBot/CBotInstr/CBotInstrUtils.h"
|
2015-11-22 14:47:46 +00:00
|
|
|
|
|
2015-11-23 20:59:56 +00:00
|
|
|
|
#include "CBot/CBotInstr/CBotLeftExprVar.h"
|
|
|
|
|
#include "CBot/CBotInstr/CBotTwoOpExpr.h"
|
2015-12-31 13:44:19 +00:00
|
|
|
|
#include "CBot/CBotInstr/CBotDefArray.h"
|
2015-11-11 21:36:18 +00:00
|
|
|
|
|
2015-11-23 20:59:56 +00:00
|
|
|
|
#include "CBot/CBotStack.h"
|
|
|
|
|
#include "CBot/CBotCStack.h"
|
|
|
|
|
#include "CBot/CBotClass.h"
|
2015-11-14 11:56:16 +00:00
|
|
|
|
|
2015-11-23 20:59:56 +00:00
|
|
|
|
#include "CBot/CBotVar/CBotVarPointer.h"
|
|
|
|
|
#include "CBot/CBotVar/CBotVarClass.h"
|
2015-11-15 18:11:57 +00:00
|
|
|
|
|
2015-12-26 13:19:24 +00:00
|
|
|
|
namespace CBot
|
|
|
|
|
{
|
2015-11-11 21:36:18 +00:00
|
|
|
|
|
|
|
|
|
////////////////////////////////////////////////////////////////////////////////
|
2015-12-31 13:44:19 +00:00
|
|
|
|
CBotDefClass::CBotDefClass()
|
2015-11-11 21:36:18 +00:00
|
|
|
|
{
|
|
|
|
|
m_next = nullptr;
|
|
|
|
|
m_var = nullptr;
|
2015-12-27 15:51:57 +00:00
|
|
|
|
m_parameters = nullptr;
|
2015-11-11 21:36:18 +00:00
|
|
|
|
m_expr = nullptr;
|
|
|
|
|
m_hasParams = false;
|
|
|
|
|
m_nMethodeIdent = 0;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
////////////////////////////////////////////////////////////////////////////////
|
2015-12-31 13:44:19 +00:00
|
|
|
|
CBotDefClass::~CBotDefClass()
|
2015-11-11 21:36:18 +00:00
|
|
|
|
{
|
|
|
|
|
delete m_var;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
////////////////////////////////////////////////////////////////////////////////
|
2015-12-31 13:44:19 +00:00
|
|
|
|
CBotInstr* CBotDefClass::Compile(CBotToken* &p, CBotCStack* pStack, CBotClass* pClass)
|
2015-11-11 21:36:18 +00:00
|
|
|
|
{
|
|
|
|
|
// seeks the corresponding classes
|
|
|
|
|
if ( pClass == nullptr )
|
|
|
|
|
{
|
|
|
|
|
pStack->SetStartError(p->GetStart());
|
|
|
|
|
pClass = CBotClass::Find(p);
|
|
|
|
|
if ( pClass == nullptr )
|
|
|
|
|
{
|
|
|
|
|
// not found? is bizare
|
2015-12-20 18:01:03 +00:00
|
|
|
|
pStack->SetError(CBotErrNotClass, p);
|
2015-11-11 21:36:18 +00:00
|
|
|
|
return nullptr;
|
|
|
|
|
}
|
|
|
|
|
p = p->GetNext();
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
bool bIntrinsic = pClass->IsIntrinsic();
|
|
|
|
|
CBotTypResult type = CBotTypResult( bIntrinsic ? CBotTypIntrinsic : CBotTypPointer, pClass );
|
2015-12-31 13:44:19 +00:00
|
|
|
|
CBotDefClass* inst = static_cast<CBotDefClass*>(CompileArray(p, pStack, type));
|
2015-11-11 21:36:18 +00:00
|
|
|
|
if ( inst != nullptr || !pStack->IsOk() ) return inst;
|
|
|
|
|
|
|
|
|
|
CBotCStack* pStk = pStack->TokenStack();
|
|
|
|
|
|
2015-12-31 13:44:19 +00:00
|
|
|
|
inst = new CBotDefClass();
|
2015-11-11 21:36:18 +00:00
|
|
|
|
/// TODO Need to be revised and fixed after adding unit tests
|
2015-12-20 15:19:10 +00:00
|
|
|
|
CBotToken token(pClass->GetName(), std::string(), p->GetStart(), p->GetEnd());
|
2015-11-11 21:36:18 +00:00
|
|
|
|
inst->SetToken(&token);
|
|
|
|
|
CBotToken* vartoken = p;
|
|
|
|
|
|
|
|
|
|
if ( nullptr != (inst->m_var = CBotLeftExprVar::Compile( p, pStk )) )
|
|
|
|
|
{
|
|
|
|
|
(static_cast<CBotLeftExprVar*>(inst->m_var))->m_typevar = type;
|
|
|
|
|
if (pStk->CheckVarLocal(vartoken)) // redefinition of the variable
|
|
|
|
|
{
|
|
|
|
|
pStk->SetStartError(vartoken->GetStart());
|
2015-12-20 18:01:03 +00:00
|
|
|
|
pStk->SetError(CBotErrRedefVar, vartoken->GetEnd());
|
2015-11-11 21:36:18 +00:00
|
|
|
|
goto error;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
if (IsOfType(p, ID_OPBRK)) // with any clues?
|
|
|
|
|
{
|
2015-12-31 13:44:19 +00:00
|
|
|
|
delete inst; // is not type CBotDefInt
|
2015-11-11 21:36:18 +00:00
|
|
|
|
p = vartoken; // returns to the variable name
|
|
|
|
|
|
|
|
|
|
// compiles declaration an array
|
|
|
|
|
|
2015-12-31 13:44:19 +00:00
|
|
|
|
inst = static_cast<CBotDefClass*>(CBotDefArray::Compile(p, pStk, type ));
|
2015-11-11 21:36:18 +00:00
|
|
|
|
|
|
|
|
|
goto suite; // no assignment, variable already created
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
CBotVar* var;
|
|
|
|
|
var = CBotVar::Create(vartoken->GetString(), type); // creates the instance
|
|
|
|
|
// var->SetClass(pClass);
|
|
|
|
|
var->SetUniqNum(
|
|
|
|
|
(static_cast<CBotLeftExprVar*>(inst->m_var))->m_nIdent = CBotVar::NextUniqNum());
|
|
|
|
|
// its attribute a unique number
|
|
|
|
|
pStack->AddVar(var); // placed on the stack
|
|
|
|
|
|
|
|
|
|
// look if there are parameters
|
|
|
|
|
inst->m_hasParams = (p->GetType() == ID_OPENPAR);
|
|
|
|
|
|
|
|
|
|
CBotVar* ppVars[1000];
|
2015-12-27 15:51:57 +00:00
|
|
|
|
inst->m_parameters = CompileParams(p, pStk, ppVars);
|
2015-11-11 21:36:18 +00:00
|
|
|
|
if ( !pStk->IsOk() ) goto error;
|
|
|
|
|
|
|
|
|
|
// if there are parameters, is the equivalent to the stament "new"
|
|
|
|
|
// CPoint A ( 0, 0 ) is equivalent to
|
|
|
|
|
// CPoint A = new CPoint( 0, 0 )
|
|
|
|
|
|
2015-12-27 15:51:57 +00:00
|
|
|
|
// if ( nullptr != inst->m_parameters )
|
2015-11-11 21:36:18 +00:00
|
|
|
|
if ( inst->m_hasParams )
|
|
|
|
|
{
|
|
|
|
|
// the constructor is there?
|
2015-12-20 15:19:10 +00:00
|
|
|
|
// std::string noname;
|
2015-11-11 21:36:18 +00:00
|
|
|
|
CBotTypResult r = pClass->CompileMethode(pClass->GetName(), var, ppVars, pStk, inst->m_nMethodeIdent);
|
|
|
|
|
delete pStk->TokenStack(); // releases the supplement stack
|
|
|
|
|
int typ = r.GetType();
|
|
|
|
|
|
2015-12-20 18:01:03 +00:00
|
|
|
|
if (typ == CBotErrUndefCall)
|
2015-11-11 21:36:18 +00:00
|
|
|
|
{
|
|
|
|
|
// si le constructeur n'existe pas
|
2015-12-27 15:51:57 +00:00
|
|
|
|
if (inst->m_parameters != nullptr) // with parameters
|
2015-11-11 21:36:18 +00:00
|
|
|
|
{
|
2015-12-20 18:01:03 +00:00
|
|
|
|
pStk->SetError(CBotErrNoConstruct, vartoken);
|
2015-11-11 21:36:18 +00:00
|
|
|
|
goto error;
|
|
|
|
|
}
|
|
|
|
|
typ = 0;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
if (typ>20)
|
|
|
|
|
{
|
2015-12-20 18:16:01 +00:00
|
|
|
|
pStk->SetError(static_cast<CBotError>(typ), vartoken->GetEnd());
|
2015-11-11 21:36:18 +00:00
|
|
|
|
goto error;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
if (IsOfType(p, ID_ASS)) // with a assignment?
|
|
|
|
|
{
|
2016-03-20 11:54:41 +00:00
|
|
|
|
pStk->SetStartError(p->GetStart());
|
|
|
|
|
if ( IsOfType(p, ID_SEP) )
|
|
|
|
|
{
|
2016-03-21 00:55:22 +00:00
|
|
|
|
pStk->SetError(CBotErrNoExpression, p->GetPrev());
|
2016-03-20 11:54:41 +00:00
|
|
|
|
goto error;
|
|
|
|
|
}
|
2015-11-11 21:36:18 +00:00
|
|
|
|
if (inst->m_hasParams)
|
|
|
|
|
{
|
2015-12-20 18:01:03 +00:00
|
|
|
|
pStk->SetError(CBotErrNoTerminator, p->GetStart());
|
2015-11-11 21:36:18 +00:00
|
|
|
|
goto error;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
if ( nullptr == ( inst->m_expr = CBotTwoOpExpr::Compile( p, pStk )) )
|
|
|
|
|
{
|
|
|
|
|
goto error;
|
|
|
|
|
}
|
|
|
|
|
CBotClass* result = pStk->GetClass();
|
2015-12-25 18:16:54 +00:00
|
|
|
|
if ( !pStk->GetTypResult(CBotVar::GetTypeMode::CLASS_AS_POINTER).Eq(CBotTypNullPointer) &&
|
|
|
|
|
( !pStk->GetTypResult(CBotVar::GetTypeMode::CLASS_AS_POINTER).Eq(CBotTypPointer) ||
|
2015-11-11 21:36:18 +00:00
|
|
|
|
( result != nullptr && !pClass->IsChildOf(result) ))) // type compatible ?
|
|
|
|
|
{
|
2015-12-20 18:01:03 +00:00
|
|
|
|
pStk->SetError(CBotErrBadType1, p->GetStart());
|
2015-11-11 21:36:18 +00:00
|
|
|
|
goto error;
|
|
|
|
|
}
|
|
|
|
|
// if ( !bIntrinsic ) var->SetPointer(pStk->GetVar()->GetPointer());
|
|
|
|
|
if ( !bIntrinsic )
|
|
|
|
|
{
|
|
|
|
|
// does not use the result on the stack, to impose the class
|
|
|
|
|
CBotVar* pvar = CBotVar::Create("", pClass);
|
|
|
|
|
var->SetPointer( pvar ); // variable already declared instance pointer
|
|
|
|
|
delete pvar; // removes the second pointer
|
|
|
|
|
}
|
|
|
|
|
var->SetInit(CBotVar::InitType::DEF); // marks the pointer as init
|
|
|
|
|
}
|
|
|
|
|
else if (inst->m_hasParams)
|
|
|
|
|
{
|
2015-12-31 15:10:47 +00:00
|
|
|
|
// creates the object on the stack
|
2015-11-11 21:36:18 +00:00
|
|
|
|
// with a pointer to the object
|
|
|
|
|
if ( !bIntrinsic )
|
|
|
|
|
{
|
|
|
|
|
CBotVar* pvar = CBotVar::Create("", pClass);
|
|
|
|
|
var->SetPointer( pvar ); // variable already declared instance pointer
|
|
|
|
|
delete pvar; // removes the second pointer
|
|
|
|
|
}
|
|
|
|
|
var->SetInit(CBotVar::InitType::IS_POINTER); // marks the pointer as init
|
|
|
|
|
}
|
|
|
|
|
suite:
|
2016-03-20 11:54:41 +00:00
|
|
|
|
if (pStk->IsOk() && IsOfType(p, ID_COMMA)) // several chained definitions
|
2015-11-11 21:36:18 +00:00
|
|
|
|
{
|
2015-12-31 13:44:19 +00:00
|
|
|
|
if ( nullptr != ( inst->m_next = CBotDefClass::Compile(p, pStk, pClass) )) // compiles the following
|
2015-11-11 21:36:18 +00:00
|
|
|
|
{
|
|
|
|
|
return pStack->Return(inst, pStk);
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
2016-03-20 11:54:41 +00:00
|
|
|
|
if (!pStk->IsOk() || IsOfType(p, ID_SEP)) // complete instruction
|
2015-11-11 21:36:18 +00:00
|
|
|
|
{
|
|
|
|
|
return pStack->Return(inst, pStk);
|
|
|
|
|
}
|
|
|
|
|
|
2015-12-20 18:01:03 +00:00
|
|
|
|
pStk->SetError(CBotErrNoTerminator, p->GetStart());
|
2015-11-11 21:36:18 +00:00
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
error:
|
|
|
|
|
delete inst;
|
|
|
|
|
return pStack->Return(nullptr, pStk);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
////////////////////////////////////////////////////////////////////////////////
|
2015-12-31 13:44:19 +00:00
|
|
|
|
bool CBotDefClass::Execute(CBotStack* &pj)
|
2015-11-11 21:36:18 +00:00
|
|
|
|
{
|
|
|
|
|
CBotVar* pThis = nullptr;
|
|
|
|
|
|
|
|
|
|
CBotStack* pile = pj->AddStack(this);//essential for SetState()
|
|
|
|
|
// if ( pile == EOX ) return true;
|
|
|
|
|
|
|
|
|
|
CBotToken* pt = &m_token;
|
|
|
|
|
CBotClass* pClass = CBotClass::Find(pt);
|
|
|
|
|
|
|
|
|
|
bool bIntrincic = pClass->IsIntrinsic();
|
|
|
|
|
|
|
|
|
|
// creates the variable of type pointer to the object
|
|
|
|
|
|
|
|
|
|
if ( pile->GetState()==0)
|
|
|
|
|
{
|
2015-12-20 15:19:10 +00:00
|
|
|
|
std::string name = m_var->m_token.GetString();
|
2015-11-11 21:36:18 +00:00
|
|
|
|
if ( bIntrincic )
|
|
|
|
|
{
|
|
|
|
|
pThis = CBotVar::Create(name, CBotTypResult( CBotTypIntrinsic, pClass ));
|
|
|
|
|
}
|
|
|
|
|
else
|
|
|
|
|
{
|
|
|
|
|
pThis = CBotVar::Create(name, CBotTypResult( CBotTypPointer, pClass ));
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
pThis->SetUniqNum((static_cast<CBotLeftExprVar*>(m_var))->m_nIdent); // its attribute as unique number
|
|
|
|
|
pile->AddVar(pThis); // place on the stack
|
|
|
|
|
pile->IncState();
|
|
|
|
|
}
|
|
|
|
|
|
2015-12-24 13:39:38 +00:00
|
|
|
|
if ( pThis == nullptr ) pThis = pile->FindVar((static_cast<CBotLeftExprVar*>(m_var))->m_nIdent, false);
|
2015-11-11 21:36:18 +00:00
|
|
|
|
|
|
|
|
|
if ( pile->GetState()<3)
|
|
|
|
|
{
|
|
|
|
|
// ss there an assignment or parameters (contructor)
|
|
|
|
|
|
|
|
|
|
// CBotVarClass* pInstance = nullptr;
|
|
|
|
|
|
|
|
|
|
if ( m_expr != nullptr )
|
|
|
|
|
{
|
|
|
|
|
// evaluates the expression for the assignment
|
|
|
|
|
if (!m_expr->Execute(pile)) return false;
|
|
|
|
|
|
|
|
|
|
if ( bIntrincic )
|
|
|
|
|
{
|
|
|
|
|
CBotVar* pv = pile->GetVar();
|
|
|
|
|
if ( pv == nullptr || pv->GetPointer() == nullptr )
|
|
|
|
|
{
|
2015-12-20 18:01:03 +00:00
|
|
|
|
pile->SetError(CBotErrNull, &m_token);
|
2015-11-11 21:36:18 +00:00
|
|
|
|
return pj->Return(pile);
|
|
|
|
|
}
|
|
|
|
|
pThis->Copy(pile->GetVar(), false);
|
|
|
|
|
}
|
|
|
|
|
else
|
|
|
|
|
{
|
|
|
|
|
CBotVarClass* pInstance;
|
|
|
|
|
pInstance = (static_cast<CBotVarPointer*>(pile->GetVar()))->GetPointer(); // value for the assignment
|
|
|
|
|
pThis->SetPointer(pInstance);
|
|
|
|
|
}
|
|
|
|
|
pThis->SetInit(CBotVar::InitType::DEF);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
else if ( m_hasParams )
|
|
|
|
|
{
|
|
|
|
|
// evaluates the constructor of an instance
|
|
|
|
|
|
|
|
|
|
if ( !bIntrincic && pile->GetState() == 1)
|
|
|
|
|
{
|
|
|
|
|
CBotToken* pt = &m_token;
|
|
|
|
|
CBotClass* pClass = CBotClass::Find(pt);
|
|
|
|
|
|
|
|
|
|
// creates an instance of the requested class
|
|
|
|
|
|
|
|
|
|
CBotVarClass* pInstance;
|
|
|
|
|
pInstance = static_cast<CBotVarClass*>(CBotVar::Create("", pClass));
|
|
|
|
|
pThis->SetPointer(pInstance);
|
|
|
|
|
delete pInstance;
|
|
|
|
|
|
|
|
|
|
pile->IncState();
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
CBotVar* ppVars[1000];
|
|
|
|
|
CBotStack* pile2 = pile;
|
|
|
|
|
|
|
|
|
|
int i = 0;
|
|
|
|
|
|
2015-12-27 15:51:57 +00:00
|
|
|
|
CBotInstr* p = m_parameters;
|
2015-11-11 21:36:18 +00:00
|
|
|
|
// evaluates the parameters
|
|
|
|
|
// and places the values on the stack
|
|
|
|
|
// to (can) be interrupted (broken) at any time
|
|
|
|
|
|
|
|
|
|
if ( p != nullptr) while ( true )
|
|
|
|
|
{
|
|
|
|
|
pile2 = pile2->AddStack(); // place on the stack for the results
|
|
|
|
|
if ( pile2->GetState() == 0 )
|
|
|
|
|
{
|
|
|
|
|
if (!p->Execute(pile2)) return false; // interrupted here?
|
|
|
|
|
pile2->SetState(1);
|
|
|
|
|
}
|
|
|
|
|
ppVars[i++] = pile2->GetVar();
|
|
|
|
|
p = p->GetNext();
|
|
|
|
|
if ( p == nullptr) break;
|
|
|
|
|
}
|
|
|
|
|
ppVars[i] = nullptr;
|
|
|
|
|
|
|
|
|
|
// creates a variable for the result
|
|
|
|
|
CBotVar* pResult = nullptr; // constructor still void
|
|
|
|
|
|
|
|
|
|
if ( !pClass->ExecuteMethode(m_nMethodeIdent, pClass->GetName(),
|
|
|
|
|
pThis, ppVars,
|
|
|
|
|
pResult, pile2, GetToken())) return false; // interrupt
|
|
|
|
|
|
|
|
|
|
pThis->SetInit(CBotVar::InitType::DEF);
|
|
|
|
|
pThis->ConstructorSet(); // indicates that the constructor has been called
|
|
|
|
|
pile->Return(pile2); // releases a piece of stack
|
|
|
|
|
|
|
|
|
|
// pInstance = pThis->GetPointer();
|
|
|
|
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
// if ( !bIntrincic ) pThis->SetPointer(pInstance); // a pointer to the instance
|
|
|
|
|
|
|
|
|
|
pile->SetState(3); // finished this part
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
if ( pile->IfStep() ) return false;
|
|
|
|
|
|
|
|
|
|
if ( m_next2b != nullptr &&
|
|
|
|
|
!m_next2b->Execute(pile)) return false; // other (s) definition (s)
|
|
|
|
|
|
|
|
|
|
return pj->Return( pile ); // transmits below (further)
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
////////////////////////////////////////////////////////////////////////////////
|
2015-12-31 13:44:19 +00:00
|
|
|
|
void CBotDefClass::RestoreState(CBotStack* &pj, bool bMain)
|
2015-11-11 21:36:18 +00:00
|
|
|
|
{
|
|
|
|
|
CBotVar* pThis = nullptr;
|
|
|
|
|
|
|
|
|
|
CBotStack* pile = pj;
|
|
|
|
|
if ( bMain ) pile = pj->RestoreStack(this);
|
|
|
|
|
if ( pile == nullptr ) return;
|
|
|
|
|
|
|
|
|
|
// creates the variable of type pointer to the object
|
|
|
|
|
{
|
2015-12-20 15:19:10 +00:00
|
|
|
|
std::string name = m_var->m_token.GetString();
|
2015-11-11 21:36:18 +00:00
|
|
|
|
pThis = pile->FindVar(name);
|
|
|
|
|
pThis->SetUniqNum((static_cast<CBotLeftExprVar*>(m_var))->m_nIdent); // its attribute a unique number
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
CBotToken* pt = &m_token;
|
|
|
|
|
CBotClass* pClass = CBotClass::Find(pt);
|
|
|
|
|
bool bIntrincic = pClass->IsIntrinsic();
|
|
|
|
|
|
|
|
|
|
if ( bMain && pile->GetState()<3)
|
|
|
|
|
{
|
|
|
|
|
// is there an assignment or parameters (constructor)
|
|
|
|
|
|
|
|
|
|
// CBotVarClass* pInstance = nullptr;
|
|
|
|
|
|
|
|
|
|
if ( m_expr != nullptr )
|
|
|
|
|
{
|
|
|
|
|
// evaluates the expression for the assignment
|
|
|
|
|
m_expr->RestoreState(pile, bMain);
|
|
|
|
|
return;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
else if ( m_hasParams )
|
|
|
|
|
{
|
|
|
|
|
// evaluates the constructor of an instance
|
|
|
|
|
|
|
|
|
|
if ( !bIntrincic && pile->GetState() == 1)
|
|
|
|
|
{
|
|
|
|
|
return;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
CBotVar* ppVars[1000];
|
|
|
|
|
CBotStack* pile2 = pile;
|
|
|
|
|
|
|
|
|
|
int i = 0;
|
|
|
|
|
|
2015-12-27 15:51:57 +00:00
|
|
|
|
CBotInstr* p = m_parameters;
|
2015-11-11 21:36:18 +00:00
|
|
|
|
// evaluates the parameters
|
|
|
|
|
// and the values an the stack
|
2015-12-31 15:10:47 +00:00
|
|
|
|
// so that it can be interrupted at any time
|
2015-11-11 21:36:18 +00:00
|
|
|
|
|
|
|
|
|
if ( p != nullptr) while ( true )
|
|
|
|
|
{
|
|
|
|
|
pile2 = pile2->RestoreStack(); // place on the stack for the results
|
|
|
|
|
if ( pile2 == nullptr ) return;
|
|
|
|
|
|
|
|
|
|
if ( pile2->GetState() == 0 )
|
|
|
|
|
{
|
|
|
|
|
p->RestoreState(pile2, bMain); // interrupted here?
|
|
|
|
|
return;
|
|
|
|
|
}
|
|
|
|
|
ppVars[i++] = pile2->GetVar();
|
|
|
|
|
p = p->GetNext();
|
|
|
|
|
if ( p == nullptr) break;
|
|
|
|
|
}
|
|
|
|
|
ppVars[i] = nullptr;
|
|
|
|
|
|
|
|
|
|
// creates a variable for the result
|
|
|
|
|
// CBotVar* pResult = nullptr; // constructor still void
|
|
|
|
|
|
|
|
|
|
pClass->RestoreMethode(m_nMethodeIdent, pClass->GetName(), pThis, ppVars, pile2);
|
|
|
|
|
return;
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
if ( m_next2b != nullptr )
|
|
|
|
|
m_next2b->RestoreState(pile, bMain); // other(s) definition(s)
|
|
|
|
|
}
|
2015-12-26 13:19:24 +00:00
|
|
|
|
|
2015-12-31 13:44:19 +00:00
|
|
|
|
std::map<std::string, CBotInstr*> CBotDefClass::GetDebugLinks()
|
2015-12-27 15:51:57 +00:00
|
|
|
|
{
|
|
|
|
|
auto links = CBotInstr::GetDebugLinks();
|
|
|
|
|
links["m_var"] = m_var;
|
|
|
|
|
links["m_parameters"] = m_parameters;
|
|
|
|
|
links["m_expr"] = m_expr;
|
|
|
|
|
return links;
|
|
|
|
|
}
|
|
|
|
|
|
2015-12-26 13:19:24 +00:00
|
|
|
|
} // namespace CBot
|