root/src/VM/cil/cilVM.cpp

Revision 195, 13.7 kB (checked in by hak, 2 months ago)

Ver.0.91.0.137
- Added OSX/GCC support!
- Can compile in XCode 3.1/GCC 4.0.1 & Visual Studio 2005.
- Runs in OSX 10.5.4 & Windows XP/Vista
- Number::toString support a radix.
- BRFALSE bug fix
- Minor code clean up

Line 
1 /****************************************************************************
2  *
3  * CRI Middleware SDK
4  *
5  * Copyright (c) 2008 CRI Middleware, Inc. All rights reserved.
6  *
7  * Use, modification and distribution are subject to the CRI Script Software
8  * License, Version 1.0(see accompanying file "CriScript_License_1_0.txt" or
9  * copy at www.criscript.com/trac/wiki/CRI%20Script%20Software%20License%201.0 ).
10  *
11  *
12  * Library  : CRIScript
13  * Module   : cil Virtual Machine
14  * File     : CCilVm.cpp
15  * Date     :
16  * Version  :
17  *
18  ****************************************************************************/
19
20 /***************************************************************************
21  *      Include file
22  ***************************************************************************/
23 #include "stdafx.h"
24 #include "criscript.h"
25 #include "cilVm.h"
26 namespace cri {
27 /***************************************************************************
28  *      Variables
29  ***************************************************************************/
30
31 /***************************************************************************
32  *      Methods
33  ***************************************************************************/
34
35 /***************************************************************************
36  * VM main execution routine
37  ***************************************************************************/
38 #ifdef VM_DISPATCH_SWITCH
39 VM_STATUS_TYPE CCilVm::execute()
40 {
41         if( m_status != VM_EXECUTE_INITIALIZED
42                 && m_status != VM_EXECUTE_EXECUTING             //Canbe executing while InvokeMethod() call
43                 && m_status != VM_EXECUTE_SUSPENDED
44                 && m_status != VM_EXECUTE_SWAPPEDOUT )
45                 return m_status;
46
47         m_status = VM_EXECUTE_EXECUTING;
48
49         bool bExecute = true;
50         uint8_t bIL;
51
52         m_stopwatch.Start();
53        
54         while( 1 )
55         {
56                 m_iTickCount ++;
57                 bIL = getNextBytecode();
58
59                 switch( bIL )
60                 {
61                 case CEE_NOP:
62                         //No operation
63                         break;
64                 case CEE_BREAK:
65                         //If debugger is attached, do some debugger staff here.
66                         //No operation
67                         break;
68                 //---------------------------------------------------------------
69                 //Exception handlers
70                 //---------------------------------------------------------------
71                 case CEE_EXT_ENTER:
72                         EnterOperator();
73                         break;
74                 case CEE_EXT_LEAVE:
75                         LeaveOperator();
76                         break;
77                 case CEE_EXT_FINALLY:
78                         FinallyOperator();      //execute Finally clause but not adjust Instruction pointer
79                         break;
80                 case CEE_THROW:
81                         //Take variable from eval stack and throw exception
82                         ThrowOperator();
83                         break;
84                 //---------------------------------------------------------------
85                 //Type conversion
86                 //---------------------------------------------------------------
87                 case CEE_EXT_CONV_B:
88                         convertToBoolean();
89                         break;
90                 //---------------------------------------------------------------
91                 //Branch instructions
92                 //---------------------------------------------------------------
93                 case CEE_CALL:
94                         CallOperator();
95                         break;
96                 case CEE_EXT_CALLI:
97                         {
98                         //Note:
99                         //CallI oprator is expanded for generic argument
100                         CVariable& var = getEvalStackFirstEntry();
101                         if( OperandType( var.iOperandType ) != OPERAND_OBJECTREF )
102                         {
103                                 ThrowExceptionFromVm( &wstring( ERRORSTRING_ILLEGALCALL ),
104                                         &wstring( NAME_BUILTIN_ERROR_OBJECT ),
105                                         ERROR_ILLEGALCALL );
106                                 //Pop illegal function reference
107                                 popEvalStack();
108
109                                 //Push undefined return value for later operations
110                                 pushEvalStackUndefined();
111                                 break;
112                         }
113                         RID ridCall = var.refObject->getCall();
114                         CVariable& varParent = var.refObject->getParentVariable();
115                         popEvalStack();
116                         CallOperator( &varParent, ridCall );
117                         }
118                         break;
119                 case CEE_RET:
120                         bExecute = RetOperator();
121                         if( !bExecute ) goto END_PROGRAM;
122                         break;
123                 case CEE_JMP:
124                 /*
125                 for Jump, scope check need to be done at a compile time. Opcode works just as same as CEE_BR
126                 */
127                 //No break here;
128                 case CEE_BR:            //Unconditional branch
129                         {
130                                 int32_t* pOffset = (int32_t*)m_pCurrentInstruction;
131                                 m_pCurrentInstruction += *pOffset + LONGBR_ADJUST;
132                         }
133                         break;
134                 case CEE_BR_S:          //Unconditional branch/s
135                         {
136                                 int8_t* pOffset = (int8_t*)m_pCurrentInstruction;
137                                 m_pCurrentInstruction += *pOffset + SHORTBR_ADJUST;
138                         }
139                         break;
140                 case CEE_REM:
141                         reminderOperator();
142                         break;
143                 case CEE_BRFALSE:
144                         BrFalseOperator();
145                         break;
146                 case CEE_BRFALSE_S:
147                         BrFalseShortOperator();
148                         break;
149                 case CEE_BRTRUE:
150                         BrTrueOperator();
151                         break;
152                 case CEE_BRTRUE_S:
153                         BrTrueShortOperator();
154                         break;
155                 case CEE_BEQ:
156                         BeqOperator();
157                         break;
158                 case CEE_BEQ_S:
159                         BeqShortOperator();
160                         break;
161                 case CEE_BNE_UN:
162                         BneOperator();
163                         break;
164                 case CEE_BNE_UN_S:
165                         BneShortOperator();
166                         break;
167                 case CEE_EXT_BNGE:
168                         BngeOperator();
169                         break;
170                 case CEE_EXT_BNGE_S:
171                         BngeShortOperator();
172                         break;
173                 case CEE_EXT_BNGT:
174                         BngtOperator();
175                         break;
176                 case CEE_EXT_BNGT_S:
177                         BngtShortOperator();
178                         break;
179                 case CEE_EXT_BNLE:
180                         BnleOperator();
181                         break;
182                 case CEE_EXT_BNLE_S:
183                         BnleShortOperator();
184                         break;
185                 case CEE_EXT_BNLT:
186                         BnltOperator();
187                         break;
188                 case CEE_EXT_BNLT_S:
189                         BnltShortOperator();
190                         break;
191                 //---------------------------------------------------------------
192                 //Stack management
193                 //---------------------------------------------------------------
194                 case CEE_DUP:
195                         assert( isEvalStackEmpty() );
196                         dupEvalStack();
197                         break;
198                 case CEE_POP:
199                         assert( isEvalStackEmpty() );
200                         popEvalStack();
201                         break;
202                 //---------------------------------------------------------------
203                 //Object management
204                 //---------------------------------------------------------------
205                 case CEE_NEWOBJ:
206                         CreateNewObject();
207                         break;
208                 case CEE_LDSTR:
209                         CreateNewStringValue();
210                         break;
211                 //---------------------------------------------------------------
212                 //Load/store instructions
213                 //---------------------------------------------------------------
214                 case CEE_LDNULL:
215                         //Load NULL to eval stack
216                         pushEvalStackNull();
217                         break;
218                 case CEE_LDC_I4:
219                         {
220                                 int32_t i = getNextInt32();
221                                 pushEvalStack( i );
222                         }
223                         break;
224                 case CEE_LDC_I4_S:
225                         {
226                                 int8_t c = getNextInt8();
227                                 pushEvalStack( (int32_t)c );
228                         }
229                         break;
230                 case CEE_LDC_I4_M1:
231                         pushEvalStack( -1 );
232                         break;
233                 case CEE_LDC_I4_0:
234                         pushEvalStack( 0 );
235                         break;
236                 case CEE_LDC_I4_1:
237                         pushEvalStack( 1 );
238                         break;
239                 case CEE_LDC_I4_2:
240                         pushEvalStack( 2 );
241                         break;
242                 case CEE_LDC_I4_3:
243                         pushEvalStack( 3 );
244                         break;
245                 case CEE_LDC_I4_4:
246                         pushEvalStack( 4 );
247                         break;
248                 case CEE_LDC_I4_5:
249                         pushEvalStack( 5 );
250                         break;
251                 case CEE_LDC_I4_6:
252                         pushEvalStack( 6 );
253                         break;
254                 case CEE_LDC_I4_7:
255                         pushEvalStack( 7 );
256                         break;
257                 case CEE_LDC_I4_8:
258                         pushEvalStack( 8 );
259                         break;
260                 case CEE_LDC_I8:
261                         {
262                                 int64_t i = getNextInt64();
263                                 pushEvalStack( i );
264                         }
265                         break;
266                 case CEE_LDC_R4:
267                         {
268                                 float f = getNextFloat();
269                                 pushEvalStack( f );
270                         }
271                         break;
272                 case CEE_LDC_R8:
273                         {
274                                 double d = getNextDouble();
275                                 pushEvalStack( d );
276                         }
277                         break;
278                 case CEE_LDSFLD:
279                         loadStaticField( getNextToken() );
280                         break;
281                 case CEE_STSFLD:
282                         storeStaticField( getNextToken() );
283                         break;
284                 case CEE_LDLOC_0:
285                         loadLocalVariable( 0 );
286                         break;
287                 case CEE_LDLOC_1:
288                         loadLocalVariable( 1 );
289                         break;
290                 case CEE_LDLOC_2:
291                         loadLocalVariable( 2 );
292                         break;
293                 case CEE_LDLOC_3:
294                         loadLocalVariable( 3 );
295                         break;
296                 case CEE_LDLOC_S:
297                         loadLocalVariable( getNextInt8() );
298                         break;
299                 case CEE_STLOC_0:
300                         storeLocalVariable( 0 );
301                         break;
302                 case CEE_STLOC_1:
303                         storeLocalVariable( 1 );
304                         break;
305                 case CEE_STLOC_2:
306                         storeLocalVariable( 2 );
307                         break;
308                 case CEE_STLOC_3:
309                         storeLocalVariable( 3 );
310                         break;
311                 case CEE_STLOC_S:
312                         storeLocalVariable( getNextInt8() );
313                         break;
314                 //---------------------------------------------------------------
315                 //Arithmetical instructions
316                 //---------------------------------------------------------------
317                 case CEE_EXT_INCSFLD:
318                         incStaticFieldOperator( getNextToken() );
319                         break;
320                 case CEE_EXT_INC:
321                         incOperator();
322                         break;
323                 case CEE_EXT_DEC:
324                         decOperator();
325                         break;
326                 case CEE_ADD:
327                         addOperator();
328                         break;
329                 case CEE_SUB:
330                         subtractOperator();
331                         break;
332                 case CEE_MUL:
333                         multiplyOperator();
334                         break;
335                 case CEE_DIV:
336                         divisionOperator();
337                         break;
338                 case CEE_AND:
339                         bitwiseAndOperator();
340                         break;
341                 case CEE_OR:
342                         bitwiseOrOperator();
343                         break;
344                 case CEE_XOR:
345                         bitwiseXorOperator();
346                         break;
347                 case CEE_NOT:
348                         bitwiseNotOperator();
349                         break;
350                 case CEE_SHL:
351                         ShlOperator();
352                         break;
353                 case CEE_SHR:
354                         ShrOperator();
355                         break;
356                 case CEE_SHR_UN:
357                         ShrUnOperator();
358                         break;
359                 case CEE_NEG:
360                         negOperator();
361                         break;
362                 //---------------------------------------------------------------
363                 //Argument list related one
364                 //---------------------------------------------------------------
365                 case CEE_EXT_STARGLIST_S:
366                         storeArgumentListWithThisPointer( getNextUint8() );
367                         break;
368                 case CEE_EXT_STARGLIST:
369                         storeArgumentListWithThisPointer( getNextInt32() );
370                         break;
371                 case CEE_LDARG_0:
372                         //Dedicated to load this pointer
373                         loadArgument( 0 );
374                         break;
375                 case CEE_LDARG_1:
376                         loadArgument( 1 );
377                         break;
378                 case CEE_LDARG_2:
379                         loadArgument( 2 );
380                         break;
381                 case CEE_LDARG_3:
382                         loadArgument( 3 );
383                         break;
384                 case CEE_LDARG_S:
385                         loadArgument( getNextInt8() );
386                         break;
387                 case CEE_STARG_S:
388                         storeArgument( getNextInt8() );
389                         break;
390
391                 //---------------------------------------------------------------
392                 //Not implemented
393                 //---------------------------------------------------------------
394                 case CEE_BGE:
395                 case CEE_BGE_S:
396                 case CEE_BGT:
397                 case CEE_BGT_S:
398                 case CEE_BLE:
399                 case CEE_BLE_S:
400                 case CEE_BLT:
401                 case CEE_BLT_S:
402                 case CEE_CALLI:
403                 case CEE_SWITCH:
404                 case CEE_LDARGA_S:
405                 case CEE_LDLOCA_S:
406                 case CEE_LDIND_I1:
407                 case CEE_LDIND_U1:
408                 case CEE_LDIND_I2:
409                 case CEE_LDIND_U2:
410                 case CEE_LDIND_I4:
411                 case CEE_LDIND_U4:
412                 case CEE_LDIND_I8:
413                 case CEE_LDIND_I:
414                 case CEE_LDIND_R4:
415                 case CEE_LDIND_R8:
416                 case CEE_LDIND_REF:
417                 case CEE_STIND_REF:
418                 case CEE_STIND_I1:
419                 case CEE_STIND_I2:
420                 case CEE_STIND_I4:
421                 case CEE_STIND_I8:
422                 case CEE_STIND_R4:
423                 case CEE_STIND_R8:
424                 case CEE_DIV_UN:
425                 case CEE_REM_UN:
426                 case CEE_CONV_I1:
427                 case CEE_CONV_I2:
428                 case CEE_CONV_I4:
429                 case CEE_CONV_I8:
430                 case CEE_CONV_R4:
431                 case CEE_CONV_R8:
432                 case CEE_CONV_U4:
433                 case CEE_CONV_U8:
434                 case CEE_CALLVIRT:
435                 case CEE_CPOBJ:
436                 case CEE_LDOBJ:
437                 case CEE_CASTCLASS:
438                 case CEE_ISINST:
439                 case CEE_CONV_R_UN:
440                 case CEE_UNBOX:
441                 case CEE_LDFLD:
442                 case CEE_LDFLDA:
443                 case CEE_STFLD:
444                 case CEE_LDSFLDA:
445                 case CEE_STOBJ:
446                 case CEE_CONV_OVF_I1_UN:
447                 case CEE_CONV_OVF_I2_UN:
448                 case CEE_CONV_OVF_I4_UN:
449                 case CEE_CONV_OVF_I8_UN:
450                 case CEE_CONV_OVF_U1_UN:
451                 case CEE_CONV_OVF_U2_UN:
452                 case CEE_CONV_OVF_U4_UN:
453                 case CEE_CONV_OVF_U8_UN:
454                 case CEE_CONV_OVF_I_UN:
455                 case CEE_CONV_OVF_U_UN:
456                 case CEE_BOX:
457                 case CEE_NEWARR:
458                 case CEE_LDLEN:
459                 case CEE_LDELEMA:
460                 case CEE_LDELEM_I1:
461                 case CEE_LDELEM_U1:
462                 case CEE_LDELEM_I2:
463                 case CEE_LDELEM_U2:
464                 case CEE_LDELEM_I4:
465                 case CEE_LDELEM_U4:
466                 case CEE_LDELEM_I8:
467                 case CEE_LDELEM_I:
468                 case CEE_LDELEM_R4:
469                 case CEE_LDELEM_R8:
470                 case CEE_LDELEM_REF:
471                 case CEE_STELEM_I:
472                 case CEE_STELEM_I1:
473                 case CEE_STELEM_I2:
474                 case CEE_STELEM_I4:
475                 case CEE_STELEM_I8:
476                 case CEE_STELEM_R4:
477                 case CEE_STELEM_R8:
478                 case CEE_STELEM_REF:
479                 case CEE_LDELEM:
480                 case CEE_STELEM:
481                 case CEE_UNBOX_ANY:
482                 case CEE_CONV_OVF_I1:
483                 case CEE_CONV_OVF_U1:
484                 case CEE_CONV_OVF_I2:
485                 case CEE_CONV_OVF_U2:
486                 case CEE_CONV_OVF_I4:
487                 case CEE_CONV_OVF_U4:
488                 case CEE_CONV_OVF_I8:
489                 case CEE_CONV_OVF_U8:
490                 case CEE_REFANYVAL:
491                 case CEE_CKFINITE:
492                 case CEE_MKREFANY:
493                 case CEE_LDTOKEN:
494                 case CEE_CONV_U2:
495                 case CEE_CONV_U1:
496                 case CEE_CONV_I:
497                 case CEE_CONV_OVF_I:
498                 case CEE_CONV_OVF_U:
499                 case CEE_ADD_OVF:
500                 case CEE_ADD_OVF_UN:
501                 case CEE_MUL_OVF:
502                 case CEE_MUL_OVF_UN:
503                 case CEE_SUB_OVF:
504                 case CEE_SUB_OVF_UN:
505                 case CEE_ENDFINALLY:
506                 case CEE_LEAVE:
507                 case CEE_LEAVE_S:
508                 case CEE_STIND_I:
509                 case CEE_CONV_U:
510                 case CEE_PREFIX6:
511                 case CEE_PREFIX5:
512                 case CEE_PREFIX4:
513                 case CEE_PREFIX3:
514                 case CEE_PREFIX2:
515                 case CEE_PREFIXREF:
516
517                         Debug_Fatal( "Not implemented yet" );
518                         break;
519                 case CEE_PREFIX1:       //2 bytes instructions
520                         bIL = getNextBytecode();
521                         switch( bIL )
522                         {
523                         case CEE_CODE_LABEL & 0xff:
524                                 //Just ingnore it
525                                 getNextToken();
526                                 break;
527                         //---------------------------------------------------------------
528                         //Compare
529                         //---------------------------------------------------------------
530                         case CEE_CEQ  & 0xff:
531                                 CeqOperator();
532                                 break;
533                         case CEE_EXT_CNE  & 0xff:
534                                 CneOperator();
535                                 break;
536                         case CEE_CGT  & 0xff:
537                                 CgtOperator();
538                                 break;
539                         case CEE_CLT  & 0xff:
540                                 CltOperator();
541                                 break;
542                         case CEE_EXT_CGE  & 0xff: