home *** CD-ROM | disk | FTP | other *** search
/ ftp.mactech.com 2010 / ftp.mactech.com.tar / ftp.mactech.com / challenge / 12.09-Sep96 / Testcode96.09R1.sit.hqx / Testcode96.09R1 / main.c < prev    next >
C/C++ Source or Header  |  1996-08-20  |  8KB  |  312 lines

  1. void JavaMiniVM(
  2.     void *constant_pool,        /* pointer to cp_info array */
  3.     void *fields,                        /* pointer to field_info array */
  4.     void *methods,                        /* pointer to method_info array */
  5.     void *classFile,                /* pointer to class file */
  6.     long methodToExecute,    /* index of method to start executing */
  7.     void *heapSpace,                /* preallocated storage for your use */
  8.     void *returnStack                /* stack where return values are stored */
  9. );
  10.  
  11. #define printConst 0
  12.  
  13. #define kFileName1 "Swarm.class"
  14. #define kTargetClass1 "myRun"
  15. #define kResult1 21111L
  16.  
  17. #define kFileName2 "FibApp.class"
  18. #define kTargetClass2 "Fib"
  19. #define kResult2 102334155L
  20.  
  21. #define kFileName3 "HelloWorld.class"
  22. #define kTargetClass3 "myHello"
  23. #define kResult3 "Hello, World!"
  24.  
  25. #define kFileName4 "MiscByteCodes.class"
  26. #define kTargetClass4 "myTest"
  27. #define kResult4 115
  28.  
  29. #include <stdio.h>
  30. #include <stdlib.h>
  31. #include <string.h>
  32.     
  33.     
  34. #define READLONG(n,x) n=*(unsigned long *)x; x+=sizeof(long);
  35. #define READSHORT(n,x) n=*(unsigned short *)x; x+=sizeof(short);
  36. #define READBYTE(n,x) n=*(unsigned char *)x; x+=sizeof(unsigned char);
  37.  
  38. void **pConstant;
  39. short *constantLength;
  40.  
  41. static unsigned char *ProcessAttribute(unsigned char *p,long j)
  42. {
  43. unsigned short attribute_name,opcodeByte;
  44. unsigned long attribute_length;
  45. char *attr;
  46. long k,i;
  47. short length,max_stack,max_locals,byteLength;
  48. long code_length;
  49.     READSHORT(attribute_name,p);
  50.     READLONG(attribute_length,p);
  51.     length = constantLength[attribute_name];
  52.     attr = 3 + (char *)pConstant[attribute_name]; /* +3 skips tag and length */
  53.     if (0 == strncmp("SourceFile",attr,length)) { 
  54.         ;
  55.     } else if (0 == strncmp("ConstantValue",attr,length)) { 
  56.         ;
  57.     } else if (0 == strncmp("Code",attr,length)) { 
  58.         READSHORT(max_stack,p);
  59.         READSHORT(max_locals,p);
  60.         READLONG(code_length,p);
  61.         p += attribute_length-8;  
  62.         return p;
  63.     } else if (0 == strncmp("Exceptions",attr,length)) { 
  64.         ;
  65.     } else if (0 == strncmp("LineNumberTable",attr,length)) { 
  66.         ;
  67.     } else if (0 == strncmp("LocalVariableTable",attr,length)) { 
  68.         ;
  69.     } else {
  70.         ;
  71.     }
  72.     p += attribute_length;
  73.  
  74.     return p;
  75. }
  76.  
  77. static void DoReadClass(char *fileName, char *targetClass,
  78.     void **p_constant_pool,        /* pointer to cp_info array */
  79.     void **p_fields,                        /* pointer to field_info array */
  80.     void **p_methods,                        /* pointer to method_info array */
  81.     void **p_classFile,                /* pointer to class file */
  82.     long *p_methodToExecute    /* index of method to start executing */
  83. )
  84. {
  85. FILE *inFile;
  86. unsigned char *p,*buf;
  87. unsigned long magic, numBytes;
  88. unsigned long bytes,high_bytes,low_bytes;
  89. unsigned short minor_version,major_version,constant_pool_count;
  90. unsigned short name_index,class_index,name_and_type_index,string_index;
  91. unsigned short signature_index;
  92. unsigned short length;
  93. unsigned short access_flags,this_class,super_class,interfaces_count,interfaces;
  94. unsigned short fields_count,attribute_count,attribute_name;
  95. unsigned short methods_count,attributes_count;
  96. void *constant_pool,*fields,*methods,*classFile;
  97. long methodToExecute;
  98.  
  99. unsigned long attribute_length;
  100. unsigned char tag;
  101. fpos_t pos;
  102. int err;
  103. long i,j,k;
  104.     inFile = fopen(fileName,"rb");
  105.     if (inFile == nil) DebugStr("\p fopen err");
  106.     err = fseek(inFile,0L,SEEK_END);
  107.     if (err != 0) DebugStr("\p fseek err");
  108.     err = fgetpos(inFile,&pos);
  109.     if (err != 0) DebugStr("\p fgetpos err");
  110.     buf = (unsigned char *)NewPtr(pos._Off);
  111.     if (buf == nil) DebugStr("\p NewPtr err");
  112.     fseek(inFile,0L,SEEK_SET);
  113.     numBytes = fread(buf,1,pos._Off,inFile);
  114.     p = buf;
  115.     
  116. /* Header */
  117.     classFile = p;
  118.     
  119.     READLONG(magic,p);
  120.     
  121.     READSHORT(minor_version,p);
  122.     READSHORT(major_version,p);
  123.     
  124. /* Constant pool */
  125.     READSHORT(constant_pool_count,p);
  126.     pConstant = (void **)NewPtrClear(constant_pool_count * sizeof(Ptr));
  127.     constantLength = (short *)NewPtrClear(constant_pool_count * sizeof(short));
  128.     
  129.     constant_pool = p;
  130.     
  131.     for (i=1; i<constant_pool_count; ++i) {
  132.         pConstant[i] = p; READBYTE(tag,p);
  133.         switch (tag) {
  134.             case 7:     /*Constant_Class*/
  135.                 READSHORT(name_index,p);
  136.                 break;
  137.             case 9:     /*Fieldref*/
  138.             case 10:    /*Methodref*/
  139.             case 11:    /*InterfaceMethodref*/
  140.                 READSHORT(class_index,p);
  141.                 READSHORT(name_and_type_index,p);
  142.                 break;
  143.             case 8:     /*Constant_Class*/
  144.                 READSHORT(string_index,p);
  145.                 break;
  146.             case 3:     /*Integer*/
  147.             case 4:     /*Float*/
  148.                 READLONG(bytes,p);
  149.                 break;
  150.             case 5:     /*long*/
  151.             case 6:     /*double*/
  152.                 READLONG(high_bytes,p);
  153.                 READLONG(low_bytes,p);
  154.                 ++i;        // 8 byte constants take 2 slots in constant pool
  155.                 break;
  156.             case 12: /*NameAndType*/
  157.             case 13: /*??*/
  158.                 READSHORT(name_index,p);
  159.                 READSHORT(signature_index,p);
  160.                 break;
  161.             case 1:     /*Utf8*/
  162.             case 2:     /*Unicode*/
  163.                 READSHORT(length,p);
  164.                 constantLength[i] = length;
  165.                 p += length;
  166.                 break;
  167.             default:
  168.                 p -=1 ;
  169.                 break;
  170.         }
  171.     }
  172.     READSHORT(access_flags,p);
  173.     READSHORT(this_class,p);
  174.     READSHORT(super_class,p);
  175.     READSHORT(interfaces_count,p);
  176.     for (i=0; i<interfaces_count; ++i) {
  177.         READSHORT(interfaces,p);
  178.     }
  179.     READSHORT(fields_count,p);
  180.     
  181.     fields = p;
  182.     
  183.     for (i=0; i<fields_count; ++i) {
  184.         READSHORT(access_flags,p);
  185.         READSHORT(name_index,p);  
  186.         READSHORT(signature_index,p);
  187.         READSHORT(attribute_count,p);
  188.         for (j=0; j<attribute_count; ++j) {
  189.             p = ProcessAttribute(p,j);
  190.         }
  191.     }
  192.     READSHORT(methods_count,p);
  193.     
  194.     methods = p;
  195.     
  196.     for (i=0; i<methods_count; ++i) {
  197.         char *theMethodName;
  198.         READSHORT(access_flags,p);
  199.         READSHORT(name_index,p);  
  200.         READSHORT(signature_index,p);
  201.         READSHORT(attribute_count,p);
  202.         theMethodName = 3 + (char *)pConstant[name_index]; /* +3 skips tag and length */
  203.         if (0 == strncmp(targetClass,theMethodName,constantLength[name_index])) {
  204.             methodToExecute = i;
  205.         }
  206.  
  207.         for (j=0; j<attribute_count; ++j) {
  208.             p = ProcessAttribute(p,j);
  209.         }
  210.     }
  211.     READSHORT(attributes_count,p);
  212.     for (j=0; j<attributes_count; ++j) {
  213.         p = ProcessAttribute(p,j);
  214.     }
  215.     
  216.     *p_constant_pool = constant_pool;
  217.     *p_fields = fields;
  218.     *p_methods = methods;
  219.     *p_classFile = classFile;
  220.     *p_methodToExecute = methodToExecute;
  221. }
  222.  
  223. // 
  224. //    Initialize everything for the program, make sure we can run
  225. //
  226.  
  227. static void Initialize(void)
  228. {
  229.     WindowPtr    mainPtr;
  230.     long i;
  231.     
  232.     /* Initialize all the needed managers. */
  233.     InitGraf(&qd.thePort);
  234.     InitFonts();
  235.     InitWindows();
  236.     InitMenus();
  237.     TEInit();
  238.     InitDialogs(nil);
  239.     InitCursor();
  240.  
  241.     GetDateTime((unsigned long*) &qd.randSeed);
  242. }
  243.  
  244. #define RUNCASE(n) \
  245.     if (nil != heapSpace) DisposePtr(heapSpace); \
  246.     if (nil != returnStack) DisposePtr(returnStack); \
  247.     if (nil != classFile) DisposePtr(classFile); \
  248.     heapSpace = NewPtrClear(10*1024L*1024); \
  249.     returnStack = NewPtrClear(1024); \
  250.     methodToExecute = -1; \
  251.     DoReadClass(kFileName##n,kTargetClass##n,&constant_pool,&fields,&methods,&classFile,&methodToExecute);    \
  252.     JavaMiniVM(constant_pool,fields,methods,classFile,methodToExecute,heapSpace,returnStack); \
  253.  
  254. void main(void)
  255. {
  256.     void *constant_pool=nil;        /* pointer to cp_info array */
  257.     void *fields=nil;                /* pointer to field_info array */
  258.     void *methods=nil;                /* pointer to method_info array */
  259.     void *classFile=nil;            /* pointer to class file */
  260.     long methodToExecute=0;            /* index of method to start executing */
  261.     void *heapSpace=nil;
  262.     void *returnStack=nil;
  263.     
  264.     long result;
  265.     char *resultP;
  266.     char *s;
  267.     short len;
  268.  
  269.     Initialize();
  270.  
  271. // Case 1
  272.     RUNCASE(1)
  273.     result = *(long *)returnStack;
  274.     if (result == kResult1)
  275.         printf("Correct result %ld returned.\n",result);
  276.     else
  277.         printf("Inorrect result %ld returned, expected %ld.\n",result,kResult1);
  278.     printf("\n\n");
  279.     
  280.  
  281. // Case 2
  282.     RUNCASE(2)
  283.     result = *(long *)returnStack;
  284.     if (result == kResult2)
  285.         printf("Correct result %ld returned.\n",result);
  286.     else
  287.         printf("Inorrect result %ld returned, expected %ld.\n",result,kResult2);
  288.     printf("\n\n");
  289.  
  290. // Case 3
  291.     RUNCASE(3)
  292. //    If I understand areturn correctly, the stack has a pointer to a CONSTANT_Utf8 object
  293.     resultP = *(char **)returnStack;
  294.     len = *(short *)resultP;
  295.     s = (char *)(2+resultP);
  296.     if ( (len == strlen(kResult3)) && (0 != strncmp(kResult3,s,len) ) )
  297.         printf("Correct result \"%s\" returned.\n",s);
  298.     else
  299.         printf("Inorrect result \"%s\" returned, expected \"%s\".\n",s,kResult3);
  300.     printf("\n\n");
  301.     
  302.  
  303. // Case 4
  304.     RUNCASE(4)
  305.     result = *(long *)returnStack;
  306.     if (result == kResult4)
  307.         printf("Correct result %ld returned.\n",result);
  308.     else
  309.         printf("Inorrect result %ld returned, expected %ld.\n",result,kResult4);
  310.     printf("\n\n");
  311. }
  312.