# Home    # nevrax.com   
Nevrax
Nevrax.org
#News
#Mailing-list
#Documentation
#CVS
#Bugs
#License
Docs
 
Documentation  
Main Page   Namespace List   Class Hierarchy   Alphabetical List   Compound List   File List   Namespace Members   Compound Members   File Members   Related Pages   Search  

codage.h

Go to the documentation of this file.
00001 
00007 /* Copyright, 2000 Nevrax Ltd.
00008  *
00009  * This file is part of NEVRAX NEL.
00010  * NEVRAX NEL is free software; you can redistribute it and/or modify
00011  * it under the terms of the GNU General Public License as published by
00012  * the Free Software Foundation; either version 2, or (at your option)
00013  * any later version.
00014 
00015  * NEVRAX NEL is distributed in the hope that it will be useful, but
00016  * WITHOUT ANY WARRANTY; without even the implied warranty of
00017  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
00018  * General Public License for more details.
00019 
00020  * You should have received a copy of the GNU General Public License
00021  * along with NEVRAX NEL; see the file COPYING. If not, write to the
00022  * Free Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
00023  * MA 02111-1307, USA.
00024  */
00025 
00026 #ifndef NL_CODAGE_H
00027 #define NL_CODAGE_H
00028 #ifdef NL_OS_WINDOWS
00029 #pragma warning (disable: 4620)
00030 #pragma warning (disable: 4621)
00031 #endif
00032 
00033 
00034 #include "nel/ai/script/virtual_op_code.h"
00035 #include "nel/ai/script/context_debug.h"
00036 
00037 namespace NLAISCRIPT
00038 {
00039 
00040         // ======================================================================================================
00052         class CIndexStackPointer
00053         {
00054         protected:
00056                 int             _Sp;
00057 
00058         private:
00060                 std::list<int> _Marque;
00061 
00062         public:
00063                 CIndexStackPointer():_Sp(0)
00064                 {
00065                 }
00066 
00068                 virtual operator int ()
00069                 {
00070                         return _Sp;
00071                 }
00072 
00074                 virtual void operator ++ ( int )
00075                 {               
00076                         _Sp ++;
00077                 }
00078 
00080                 virtual void operator -- ( int )
00081                 {               
00082                         _Sp --;
00083                 }
00084 
00086                 virtual void operator += (int k)
00087                 {
00088                         _Sp += k;
00089                 }
00090 
00092                 virtual void operator -= (int k)
00093                 {               
00094                         _Sp -= k;
00095                 }
00096 
00098                 virtual void pushMark()
00099                 {
00100                         _Marque.push_back(_Sp);
00101                 }
00102 
00104                 virtual int popMark()
00105                 {
00106                         int i = 0;                      
00107                         i = _Marque.back();
00108                         _Marque.pop_back();             
00109                         return i;
00110                 }
00111 
00112                 virtual int markSize()
00113                 {
00114                         return _Marque.size();
00115                 }
00116 
00118                 virtual int mark()
00119                 {
00120                         return _Marque.back();          
00121                 }
00122 
00124                 void clear()
00125                 {
00126                         _Sp = 0;                        
00127                         _Marque.clear();
00128                 }
00129 
00130                 virtual ~CIndexStackPointer()   
00131                 {
00132                 }
00133 
00134         };
00135 
00136         // ======================================================================================================
00148         class CStackPointer: public CIndexStackPointer
00149         {
00150         private:                                
00152                 int                             _Count;
00154                 int                             _Bp;
00155                 
00157                 int                             _Sh;
00158 
00160                 std::list<int>  _Decalage;
00162                 std::list<int>  _Shift;
00163 
00165                 NLAIAGENT::IObjectIA    **_Stack;       
00166 
00167         public:
00168                 CStackPointer(int count = 1024*8)
00169                 {
00170                         _Count = count;
00171                         _Stack = new NLAIAGENT::IObjectIA *[ count ];
00172                         for(int i = 0; i < _Count; i ++)
00173                         {
00174                                 _Stack[i] = NULL;
00175                         }                       
00176                         _Sp = 0;
00177                         _Bp = 0;
00178                         _Sh = 0;
00179                 }
00180 
00182                 NLAIAGENT::IObjectIA *&operator [] (int i)
00183                 {
00184 #ifdef NL_DEBUG
00185                         if ( (_Sp + _Bp + _Sh) >= _Count )
00186                         {
00187                                 throw NLAIE::CExceptionIndexError();
00188                         }
00189 #endif                  
00190                         return _Stack[i + _Bp + _Sh];
00191                 }
00192 
00194                 operator NLAIAGENT::IObjectIA *()
00195                 {
00196 #ifdef NL_DEBUG
00197                         if ( (_Sp + _Bp + _Sh) >= _Count )
00198                         {
00199                                 throw NLAIE::CExceptionIndexError();
00200                         }
00201 #endif                  
00202                         return _Stack[_Sp + _Bp + _Sh];
00203                 }
00204 
00206                 virtual void operator -- (int)
00207                 {
00208 #ifdef NL_DEBUG
00209                         if ( (_Sp + _Bp + _Sh) >= _Count )
00210                         {
00211                                 throw NLAIE::CExceptionIndexError();
00212                         }
00213 #endif                                          
00214                         int i = _Sp + _Bp  + _Sh;
00215                         if(_Stack[i])
00216                         {                       
00217                                 _Stack[i]->release(); 
00218                                 _Stack[i] = NULL;
00219                         }
00220                         _Sp --;
00221                 }
00222                 
00224                 virtual void operator -= (int k)
00225                 {
00226 #ifdef NL_DEBUG
00227                         if ( (_Sp + _Bp + _Sh) >= _Count )
00228                         {
00229                                 throw NLAIE::CExceptionIndexError();
00230                         }
00231 #endif                                          
00232                         int n = _Sp + _Bp + _Sh;
00233                         for(int i = n - k; i < n; i ++) 
00234                         {
00235                                 if(_Stack[i])
00236                                 {
00237                                         _Stack[i]->release();
00238                                         _Stack[i] = NULL;
00239                                 }
00240                         }
00241                         _Sp -= k;
00242                 }
00243 
00245                 void addStack(int bp)
00246                 {
00247                         _Bp += bp;
00248                         _Sp -= bp;
00249                         _Decalage.push_back(bp);
00250                 }
00251 
00253                 void restoreStack()
00254                 {                       
00255                         int k = _Bp;
00256                         _Bp -= _Decalage.back();
00257                         _Decalage.pop_back();
00258                         _Sp += k;
00259                         
00260                         *this -= k;                             
00261                 }
00262 
00264                 void setShift(int s)
00265                 {
00266                         _Sh += s;
00267                         _Sp -= s;
00268                         _Shift.push_back(s);
00269                 }
00270 
00272                 void restoreShift()
00273                 {                       
00274                         int s = _Shift.back();
00275                         _Shift.pop_back();
00276                         _Sp += s;
00277                         _Sh -= s;
00278                 }
00279 
00280 
00282                 bool restoreStackState()
00283                 {
00284                         return _Decalage.size() != 0;
00285                 }
00286 
00288                 bool restoreShiftState()
00289                 {
00290                         return _Shift.size() != 0;
00291                 }
00292                 
00293                 ~CStackPointer()
00294                 {               
00295                         if(_Stack)
00296                         {
00297                         
00298                                 for(int i = _Bp; i < (_Sp + _Bp); i ++)
00299                                 {
00300                                         if(_Stack[i] != NULL)
00301                                         {
00302                                                 _Stack[i]->release();
00303                                                 _Stack[i] = NULL;
00304                                         }
00305                                 }
00306                                 delete []_Stack;
00307                                 _Stack = NULL;
00308                         }                       
00309                 }
00310         };
00311 
00312 
00313         class CCodeBrancheRun;
00314         typedef CStackPointer   tStackRef;
00315         typedef CCodeBrancheRun tCodeRef;
00316 
00317         // ======================================================================================================
00330         class CCodeContext : public NLAIAGENT::IObjectIA
00331         {               
00332         public:
00333 
00335                 tStackRef                       &Stack;
00337                 tStackRef                       &Heap;
00339                 tCodeRef                        *Code;
00341                 const NLAIAGENT::IObjectIA      *Self;
00343                 NLAIC::IIO                      *InputOutput;
00345                 std::list<NLAIAGENT::IObjectIA	*> Param;
00347                 CContextDebug           ContextDebug;
00348 
00349         public:
00351                 static const NLAIC::CIdentType IdCodeContext;
00352 
00353         public:
00354 
00355                 CCodeContext(tStackRef &stackMem,tStackRef &heapMem,tCodeRef *codeMem,const NLAIAGENT::IObjectIA *thisClass,NLAIC::IIO *io):
00356                 Stack(stackMem),
00357                 Heap(heapMem),          
00358                 Code(codeMem),
00359                 Self(thisClass),
00360                 InputOutput(io)         
00361                 {
00362                         if(InputOutput != NULL) InputOutput->incRef();
00363                 }
00364 
00366                 void init()
00367                 {
00368                         ContextDebug.init();
00369                 }
00370 
00372                 void setIO(NLAIC::IIO *io)
00373                 {
00374                         if(InputOutput != NULL) InputOutput->release();
00375                         InputOutput = io;                       
00376                 }
00377 
00379 
00380                 const NLAIC::CIdentType &getType(void) const
00381                 {
00382                         return IdCodeContext;
00383                 }
00384                 const NLAIC::IBasicType *clone(void) const
00385                 {
00386                         CCodeContext *x = new CCodeContext(Stack,Heap,Code,Self,InputOutput);                   
00387                         return x;
00388                 }
00389                 const NLAIC::IBasicType *newInstance(void) const
00390                 {
00391                         return clone();
00392                 }
00393                 void getDebugString(std::string &t) const
00394                 {
00395                         t = NLAIC::stringGetBuild("CCodeContext");
00396                 }
00397                 void save(NLMISC::IStream &f)
00398                 {                       
00399                 }
00400                 void load(NLMISC::IStream &f)
00401                 {
00402                 }
00404 
00406 
00407                 bool isEqual(const class NLAIAGENT::IBasicObjectIA &) const
00408                 {
00409                         return true;
00410                 }
00412 
00414 
00415                 const NLAIAGENT::IObjectIA::CProcessResult &run(void)
00416                 {
00417                         return NLAIAGENT::IObjectIA::ProcessRun;;
00418                 }
00420 
00421                 ~CCodeContext()
00422                 {
00423                         if(InputOutput != NULL) InputOutput->release();
00424                 }
00425         };
00426 
00427         class IConstraint;
00428 
00429         // ======================================================================================================
00442         class CBagOfCode 
00443         {
00444         private:
00445                 IOpCode *_Opcode;
00446                 std::list<IConstraint *> _Constraint;
00447 
00448         public:
00449                 CBagOfCode(IOpCode *opcode):_Opcode(opcode)
00450                 {
00451                         
00452                 }
00453 
00455                 operator IOpCode *() const
00456                 {
00457                         return _Opcode;
00458                 }
00459 
00461                 void setCode(IOpCode *op)
00462                 {
00463                         _Opcode = op;   
00464                 }
00465 
00467                 void addConstraint(IConstraint *c)
00468                 {                       
00469                         _Constraint.push_back(c);
00470                 }
00471 
00473                 void addConstraint(CBagOfCode *b)
00474                 {       
00475                         std::list<IConstraint *>::iterator it = b->_Constraint.begin();
00476                         while(it != b->_Constraint.end())
00477                         {                               
00478                                 _Constraint.push_back(*it++);
00479                         }                       
00480                 }
00481 
00484                 void setConstraintIndex(int i,CCodeBrancheRun *c);
00485 
00486                 ~CBagOfCode(){}
00487                 
00488 
00489         };
00490 
00491         typedef std::list<CBagOfCode *> tListCode;
00492         typedef std::list<CBagOfCode *>::iterator tListCodeIter;
00493 
00494         // ======================================================================================================
00504         class CCodeBrancheRun: public ICodeBranche
00505         {
00506         public:
00507                 static NLAIC::IIO       *InputOutput;
00508 
00509         protected:
00511                 IOpCode **_TableCode;
00513                 int             _Ip;
00515                 int             _Count;  
00517                 NLAIAGENT::IObjectIA::CProcessResult _RunState;
00518 
00519         protected:
00520 
00522                 void del()
00523                 {
00524                         if(_TableCode != NULL)
00525                         {
00526                                 for(int i = 0 ;i < _Count; i ++)
00527                                 {
00528                                         if(_TableCode[i]) _TableCode[i]->release();
00529                                 }
00530                                 delete []_TableCode;
00531                         }
00532                 }
00533 
00534         public:
00535                 static const NLAIC::CIdentType IdCodeBrancheRun;
00536         public:
00537 
00538                 
00540                 CCodeBrancheRun(const CCodeBrancheRun &l):_TableCode(NULL),_Ip(0),_Count(l._Count)
00541                 {
00542                         _TableCode = new IOpCode * [_Count];
00543                         for(int i = 0 ;i < _Count; i ++) 
00544                         {
00545                                 _TableCode[i] = (IOpCode *)l._TableCode[i];//->clone();                         
00546                                 _TableCode[i]->incRef();
00547                         }
00548                 }
00549 
00551                 CCodeBrancheRun(const tListCode &l):
00552                         _TableCode(NULL),_Ip(0),_Count(l.size())
00553                 {
00554                         initCode(l);    
00555                 }       
00556 
00558                 CCodeBrancheRun(int N,const IOpCode &op);
00560                 CCodeBrancheRun(int N);
00561 
00563                 CCodeBrancheRun(NLMISC::IStream &is):_TableCode(NULL),_Ip(0),_Count(0)
00564                 {
00565                         load(is);
00566                 }
00567 
00568                 virtual ~CCodeBrancheRun()
00569                 {
00570                         del();
00571                 }
00572 
00573                 
00574                 void initCode(const tListCode &l)
00575                 {
00576                         del();
00577                         _Count = l.size();
00578 
00579                         tListCode::const_iterator i;            
00580                         _TableCode = new IOpCode * [l.size()];
00581                         i = l.begin();
00582                         int k = 0;
00583                         while(i != l.end())
00584                         {
00585                                 _TableCode[k ++] = (IOpCode *)*i++;
00586                         }               
00587                 }
00588 
00589                 void initCode(const CCodeBrancheRun &l)
00590                 {
00591                         del();
00592 
00593                         _Ip = 0;
00594                         _Count = l._Count;
00595                         
00596                         _TableCode = new IOpCode * [_Count];            
00597                         for(int i = 0; i < _Count;i ++)
00598                         {
00599                                 _TableCode[i ++] = (IOpCode *)l._TableCode[i]->clone();
00600                         }
00601                 }
00602 
00604                 IOpCode *&operator [] (int i)
00605                 {
00606                         return _TableCode[i];
00607                 }
00608 
00610                 void operator = (uint32 l)
00611                 {
00612                         _Ip = l;
00613                 }
00614 
00616                 void operator += (uint32 l)
00617                 {
00618                         _Ip += l;
00619                 }
00620 
00622                 operator uint32 ()
00623                 {
00624                         return _Ip;
00625                 }
00626 
00627                 void init()
00628                 {
00629                         _Ip = 0;
00630                 }
00631 
00633                 IOpCode &nextCode()
00634                 {
00635                         return *_TableCode[_Ip++];
00636                 }                                       
00637 
00639 
00640                 virtual const NLAIAGENT::IObjectIA::CProcessResult &run(NLAIAGENT::IObjectIA &self);
00641                 virtual const NLAIAGENT::IObjectIA::CProcessResult &run(CCodeContext &);
00642 
00643                 NLAIAGENT::TProcessStatement runOpCode(CCodeContext &context);
00644                 void getDebugResult(std::string &str,CCodeContext &context) const;              
00646 
00648 
00649                 void save(NLMISC::IStream &f);  
00650                 void load(NLMISC::IStream &f);  
00651                 void getDebugString(std::string &) const;
00652                 const NLAIC::CIdentType &getType() const;               
00653                 const NLAIC::IBasicType *clone() const 
00654                 {
00655                         NLAIC::IBasicType *x = new CCodeBrancheRun(*this);                      
00656                         return x;
00657                 }
00658                 const NLAIC::IBasicType *newInstance() const;
00659                 
00661 
00663 
00664                 bool isEqual(const NLAIAGENT::IBasicObjectIA &a) const{ return true;}   
00666 
00668 
00669                 virtual const NLAIAGENT::IObjectIA::CProcessResult &run();              
00671                 
00672         };
00673 }
00674 #include "nel/ai/script/opcode.h"
00675 
00676 #endif
00677