271 lines
8.9 KiB
C
271 lines
8.9 KiB
C
![]() |
/*
|
||
|
* This file is part of the Colobot: Gold Edition source code
|
||
|
* Copyright (C) 2001-2015, Daniel Roux, EPSITEC SA & TerranovaTeam
|
||
|
* 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
|
||
|
*/
|
||
|
|
||
|
#pragma once
|
||
|
|
||
|
// Modules inlcude
|
||
|
#include "CBot.h"
|
||
|
|
||
|
// Local include
|
||
|
|
||
|
// Global include
|
||
|
|
||
|
|
||
|
/*!
|
||
|
* \class CBotStack
|
||
|
* \brief The CBotStack class Management of the execution stack. Actually the
|
||
|
* only thing it can do is to create an instance of a stack. To use for routine
|
||
|
* CBotProgram :: Execute(CBotStack)
|
||
|
*/
|
||
|
class CBotStack
|
||
|
{
|
||
|
public:
|
||
|
#if STACKMEM
|
||
|
/**
|
||
|
* \brief FirstStack Allocate first stack
|
||
|
* \return pointer to created stack
|
||
|
*/
|
||
|
static CBotStack * FirstStack();
|
||
|
|
||
|
/** \brief Delete Remove current stack */
|
||
|
void Delete();
|
||
|
#endif
|
||
|
|
||
|
/**
|
||
|
* \brief CBotStack Constructor of the stack
|
||
|
* \param ppapa Not used.
|
||
|
*/
|
||
|
CBotStack(CBotStack* ppapa);
|
||
|
|
||
|
|
||
|
/** \brief ~CBotStack Destructor */
|
||
|
~CBotStack();
|
||
|
|
||
|
/**
|
||
|
* \brief StackOver Check if end of stack is reached
|
||
|
* \return true if end of stack
|
||
|
*/
|
||
|
bool StackOver();
|
||
|
|
||
|
/**
|
||
|
* \brief GetError Get error number of the stack
|
||
|
* \param [out] start beginning of the stack
|
||
|
* \param [out] end end of stack
|
||
|
* \return error number
|
||
|
*/
|
||
|
int GetError(int& start, int& end);
|
||
|
|
||
|
/**
|
||
|
* \brief GetError Get error number
|
||
|
* \return eror number
|
||
|
*/
|
||
|
int GetError();// rend le numéro d'erreur retourné
|
||
|
|
||
|
/**
|
||
|
* \brief Reset Reset error at and set user
|
||
|
* \param [in] pUser User of stack
|
||
|
*/
|
||
|
void Reset(void* pUser);
|
||
|
|
||
|
/**
|
||
|
* \brief SetType Determines the type.
|
||
|
* \param type Type of instruction on the stack.
|
||
|
*/
|
||
|
void SetType(CBotTypResult& type);
|
||
|
|
||
|
/**
|
||
|
* \brief GetType Get the type of value on the stack.
|
||
|
* \param [in] mode Used when getting class type (1 gives pointer, 2 gives intrinsic).
|
||
|
* \return Type number.
|
||
|
*/
|
||
|
int GetType(int mode = 0);
|
||
|
|
||
|
/**
|
||
|
* \brief Getes the type of complete value on the stack.
|
||
|
* \param [in] mode Used when getting class type (1 gives pointer, 2 gives intrinsic).
|
||
|
* \return Type of an element.
|
||
|
*/
|
||
|
CBotTypResult GetTypResult(int mode = 0);
|
||
|
|
||
|
/**
|
||
|
* \brief Adds a local variable.
|
||
|
* \param [in] p Variable to be added.
|
||
|
*/
|
||
|
void AddVar(CBotVar* p);
|
||
|
|
||
|
/**
|
||
|
* \brief Fetch a variable by its token.
|
||
|
* \brief This may be a composite variable
|
||
|
* \param [in] pToken Token upon which search is performed
|
||
|
* \param [in] bUpdate Not used. Probably need to be removed
|
||
|
* \param [in] bModif Not used. Probably need to be removed
|
||
|
* \return Found variable
|
||
|
*/
|
||
|
CBotVar* FindVar(CBotToken* &pToken, bool bUpdate = false,
|
||
|
bool bModif = false);
|
||
|
|
||
|
/**
|
||
|
* \brief Fetch a variable by its token.
|
||
|
* \brief This may be a composite variable
|
||
|
* \param [in] pToken Token upon which search is performed
|
||
|
* \param [in] bUpdate Not used. Probably need to be removed
|
||
|
* \param [in] bModif Not used. Probably need to be removed
|
||
|
* \return Found variable
|
||
|
*/
|
||
|
CBotVar* FindVar(CBotToken& pToken, bool bUpdate = false,
|
||
|
bool bModif = false);
|
||
|
|
||
|
/**
|
||
|
* \brief Fetch variable by its name
|
||
|
* \param [in] name Name of variable to find
|
||
|
* \return Found variable
|
||
|
*/
|
||
|
CBotVar* FindVar(const char* name);
|
||
|
|
||
|
/**
|
||
|
* \brief Fetch a variable on the stack according to its identification number
|
||
|
* \brief This is faster than comparing names
|
||
|
* \param [in] ident Identifier of a variable
|
||
|
* \param [in] bUpdate Not used. Probably need to be removed
|
||
|
* \param [in] bModif Not used. Probably need to be removed
|
||
|
* \return Found variable
|
||
|
*/
|
||
|
CBotVar* FindVar(long ident, bool bUpdate = false,
|
||
|
bool bModif = false);
|
||
|
|
||
|
/**
|
||
|
* \brief Find variable by its token and returns a copy of it.
|
||
|
* \param Token Token upon which search is performed
|
||
|
* \param bUpdate Not used.
|
||
|
* \return Found variable, nullptr if not found
|
||
|
*/
|
||
|
CBotVar* CopyVar(CBotToken& Token, bool bUpdate = false);
|
||
|
|
||
|
|
||
|
CBotStack* AddStack(CBotInstr* instr = nullptr, bool bBlock = false); // extends the stack
|
||
|
CBotStack* AddStackEOX(CBotCall* instr = nullptr, bool bBlock = false); // extends the stack
|
||
|
CBotStack* RestoreStack(CBotInstr* instr = nullptr);
|
||
|
CBotStack* RestoreStackEOX(CBotCall* instr = nullptr);
|
||
|
|
||
|
CBotStack* AddStack2(bool bBlock = false); // extends the stack
|
||
|
bool Return(CBotStack* pFils); // transmits the result over
|
||
|
bool ReturnKeep(CBotStack* pFils); // transmits the result without reducing the stack
|
||
|
bool BreakReturn(CBotStack* pfils, const char* name = nullptr);
|
||
|
// in case of eventual break
|
||
|
bool IfContinue(int state, const char* name);
|
||
|
// or "continue"
|
||
|
|
||
|
bool IsOk();
|
||
|
|
||
|
bool SetState(int n, int lim = -10); // select a state
|
||
|
int GetState(); // in what state am I?
|
||
|
bool IncState(int lim = -10); // passes to the next state
|
||
|
bool IfStep(); // do step by step
|
||
|
bool Execute();
|
||
|
|
||
|
void SetVar( CBotVar* var );
|
||
|
void SetCopyVar( CBotVar* var );
|
||
|
CBotVar* GetVar();
|
||
|
CBotVar* GetCopyVar();
|
||
|
CBotVar* GetPtVar();
|
||
|
bool GetRetVar(bool bRet);
|
||
|
long GetVal();
|
||
|
|
||
|
void SetError(int n, CBotToken* token = nullptr);
|
||
|
void SetPosError(CBotToken* token);
|
||
|
void ResetError(int n, int start, int end);
|
||
|
void SetBreak(int val, const char* name);
|
||
|
|
||
|
void SetBotCall(CBotProgram* p);
|
||
|
CBotProgram* GetBotCall(bool bFirst = false);
|
||
|
void* GetPUser();
|
||
|
bool GetBlock();
|
||
|
|
||
|
|
||
|
bool ExecuteCall(long& nIdent, CBotToken* token, CBotVar** ppVar, CBotTypResult& rettype);
|
||
|
void RestoreCall(long& nIdent, CBotToken* token, CBotVar** ppVar);
|
||
|
|
||
|
bool SaveState(FILE* pf);
|
||
|
bool RestoreState(FILE* pf, CBotStack* &pStack);
|
||
|
|
||
|
static
|
||
|
void SetTimer(int n);
|
||
|
|
||
|
void GetRunPos(const char* &FunctionName, int &start, int &end);
|
||
|
CBotVar* GetStackVars(const char* &FunctionName, int level);
|
||
|
|
||
|
int m_temp;
|
||
|
|
||
|
private:
|
||
|
CBotStack* m_next;
|
||
|
CBotStack* m_next2;
|
||
|
CBotStack* m_prev;
|
||
|
friend class CBotInstArray;
|
||
|
|
||
|
#ifdef _DEBUG
|
||
|
int m_index;
|
||
|
#endif
|
||
|
int m_state;
|
||
|
int m_step;
|
||
|
static int m_error;
|
||
|
static int m_start;
|
||
|
static int m_end;
|
||
|
static
|
||
|
CBotVar* m_retvar; // result of a return
|
||
|
|
||
|
CBotVar* m_var; // result of the operations
|
||
|
CBotVar* m_listVar; // variables declared at this level
|
||
|
|
||
|
bool m_bBlock; // is part of a block (variables are local to this block)
|
||
|
bool m_bOver; // stack limits?
|
||
|
// bool m_bDontDelete; // special, not to destroy the variable during delete
|
||
|
CBotProgram* m_prog; // user-defined functions
|
||
|
|
||
|
static
|
||
|
int m_initimer;
|
||
|
static
|
||
|
int m_timer;
|
||
|
static
|
||
|
CBotString m_labelBreak;
|
||
|
static
|
||
|
void* m_pUser;
|
||
|
|
||
|
CBotInstr* m_instr; // the corresponding instruction
|
||
|
bool m_bFunc; // an input of a function?
|
||
|
CBotCall* m_call; // recovery point in a extern call
|
||
|
friend class CBotTry;
|
||
|
};
|
||
|
|
||
|
// inline routinees must be declared in file.h
|
||
|
|
||
|
inline bool CBotStack::IsOk()
|
||
|
{
|
||
|
return (m_error == 0);
|
||
|
}
|
||
|
|
||
|
inline int CBotStack::GetState()
|
||
|
{
|
||
|
return m_state;
|
||
|
}
|
||
|
|
||
|
inline int CBotStack::GetError()
|
||
|
{
|
||
|
return m_error;
|
||
|
}
|