00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017 #ifndef _interp_program_h
00018 #define _interp_program_h
00019
00020 #include <spl/types.h>
00021 #include <spl/Debug.h>
00022 #include <spl/Memory.h>
00023 #include <spl/interp/OpCodes.h>
00024 #include <spl/RefCountPtr.h>
00025 #include <spl/collection/StringTable.h>
00026 #include <spl/Variant.h>
00027 #include <spl/collection/Vector.h>
00028
00029 struct Instruction
00030 {
00031 uint32 opCode : 8;
00032 uint32 argSrc : 4;
00033 uint32 argIdx : 24;
00034 };
00035
00036 inline void ValidateType(const struct Instruction& i)
00037 {
00038 }
00039
00040 class Program : IMemoryValidate
00041 {
00042 private:
00043 Vector<VariantPtr> m_cdata;
00044 Vector<Instruction> m_code;
00045 Instruction m_exitInstr;
00046 int m_argCount;
00047
00048 public:
00049 Program();
00050 Program(const Program& program);
00051 Program& operator =(const Program& program);
00052 virtual ~Program();
00053
00054 void Clear();
00055
00056 inline void NoteArgument() { m_argCount++; }
00057 inline int ArgumentCount() const { return m_argCount; }
00058
00059 int AddToTable(const String& s);
00060 int AddToTable(const int32 i);
00061 int AddToTable(const float64 f);
00062 int AddToTable(const Date& dt);
00063 int AddToTable(const DateTime& dtm);
00064
00065 int AppendCode(enum JsOpCode i, JsOpCodeArgSrc s, int32 idx);
00066 inline int AppendCode(enum JsOpCode c) { return AppendCode(c, JSOPARG_NONE, 0); }
00067
00068 void FixupCode(int pos, int32 idx);
00069
00070 inline bool CanContinue(int pc) const
00071 {
00072 return pc >= 0 && pc < m_code.Count();
00073 }
00074
00075 inline Instruction InstructionAt(int pc) const
00076 {
00077 if (0 > pc || pc >= m_code.Count())
00078 {
00079 return m_exitInstr;
00080 }
00081 return m_code.ElementAt(pc);
00082 }
00083
00084 inline VariantPtr GetArg(Instruction i, Vector<VariantPtr>& stk) const
00085 {
00086 if (JSOPARG_IMM == i.argSrc)
00087 {
00088 return VariantPtr(new Variant((int32)i.argIdx));
00089 }
00090 if (JSOPARG_TAB == i.argSrc)
00091 {
00092 return m_cdata.ElementAt(i.argIdx);
00093 }
00094 if (JSOPARG_STK == i.argSrc)
00095 {
00096 return stk.ElementAt(i.argIdx);
00097 }
00098 throw new Exception("Invalid argument source in Program::GetArg");
00099 }
00100
00101 #if defined(DEBUG) || defined(_DEBUG)
00102 void CheckMem() const;
00103 void ValidateMem() const;
00104 #endif
00105 };
00106
00107 #endif