You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@harmony.apache.org by dl...@apache.org on 2007/08/12 22:46:13 UTC
svn commit: r565142 -
/harmony/enhanced/sandbox/bootjvm/bootJVM/jvm/src/class.c
Author: dlydick
Date: Sun Aug 12 13:46:12 2007
New Revision: 565142
URL: http://svn.apache.org/viewvc?view=rev&rev=565142
Log:
Disallow in class_find_by_cp_entry() all constant_pool
entries except UTF8.
Added support for reading class info from Java
archives as well as explicit class files.
Added test for an abstract method in class_load_resolve_clinit()
with same arbitrary decision as for when non 'clinit' method
was available, and marked as a to-do item.
Mark JVM for shutdown if no previous thread to revive.
Modified:
harmony/enhanced/sandbox/bootjvm/bootJVM/jvm/src/class.c
Modified: harmony/enhanced/sandbox/bootjvm/bootJVM/jvm/src/class.c
URL: http://svn.apache.org/viewvc/harmony/enhanced/sandbox/bootjvm/bootJVM/jvm/src/class.c?view=diff&rev=565142&r1=565141&r2=565142
==============================================================================
--- harmony/enhanced/sandbox/bootjvm/bootJVM/jvm/src/class.c (original)
+++ harmony/enhanced/sandbox/bootjvm/bootJVM/jvm/src/class.c Sun Aug 12 13:46:12 2007
@@ -53,6 +53,7 @@
#include "exit.h"
#include "field.h"
#include "gc.h"
+#include "jar.h"
#include "jvm.h"
#include "jvmclass.h"
#include "linkage.h"
@@ -276,7 +277,7 @@
/*!
- * @brief Load a class into ad class table slot and load up its
+ * @brief Load a class into a class table slot and load up its
* associated class definition object.
*
* Create a Java class itself (and NOT a @c @b new instance
@@ -895,6 +896,15 @@
jvm_class_index clsidx;
+ /* Disallow all but UTF8 @c @b constant_pool entries */
+ if (CONSTANT_Utf8 != PTR_THIS_CP_Utf8(clsname)->tag)
+ {
+ /* Somebody goofed */
+ exit_throw_exception(EXIT_JVM_INTERNAL,
+ JVMCLASS_JAVA_LANG_INTERNALERROR);
+/*NOTREACHED*/
+ }
+
jvm_array_dim arraydims =
utf_get_utf_arraydims(PTR_THIS_CP_Utf8(clsname));
@@ -1035,7 +1045,7 @@
*
* where @b name is a null-terminated string passed as the only parm,
* and @b b is the byte array read in by classfile_read_classfile()
- * or classfile_read_jarfile(), and @b off is zero, and @b len being
+ * or jarutil_read_member(), and @b off is zero, and @b len being
* discovered by classfile_read_XXXfile().
*
* @todo HARMONY-6-jvm-class.c-7 Spec section 5.3.4
@@ -1197,10 +1207,10 @@
* the class. All array class file pointers will point
* to this class file structure.
*/
- u1 *pcfd;
- ClassFile *pcfs;
- rchar *pcname;
- jvm_class_index clsidx;
+ u1 *pcfd;
+ ClassFile *pcfs;
+ classpath_search *pcname;
+ jvm_class_index clsidx;
if (LOCAL_CONSTANT_NO_ARRAY_DIMS < arraydims)
{
@@ -1237,40 +1247,33 @@
pcname = classpath_get_from_cp_entry_utf(pnofmt);
- HEAP_FREE_DATA(pnofmt);
-
- GENERIC_FAILURE1_THROWERROR((rnull == pcname),
- DMLNORM,
- arch_function_name,
- "Cannot locate class %s",
- clsname,
- EXIT_JVM_CLASS,
+ GENERIC_FAILURECP1_THROWERROR((rnull == pcname),
+ DMLNORM,
+ arch_function_name,
+ "Cannot locate class %*.*s",
+ pnofmt,
+ EXIT_JVM_CLASS,
JVMCLASS_JAVA_LANG_NOCLASSDEFFOUNDERROR,
- pcname,
- rnull);
+ rnull,
+ pnofmt);
/*
- * Check if JAR file or class file and read in the class
- * file data stream as a simple binary image.
+ * Read in the class from wherever it was found, either
+ * in a Java archive or a class file. Return a simple
+ * binary image of that data
*/
- if (rtrue == classpath_isjar(pcname))
- {
- pcfd = classfile_read_jarfile(pcname);
- }
- else
- {
- pcfd = classfile_read_classfile(pcname);
- }
+ pcfd = classfile_read(pcname, rtrue);
- GENERIC_FAILURE1_THROWERROR((rnull == pcfd),
- DMLNORM,
- arch_function_name,
- "Cannot read file %s",
- pcname,
- EXIT_JVM_CLASS,
+ GENERIC_FAILURECP1_THROWERROR((rnull == pcfd),
+ DMLNORM,
+ arch_function_name,
+ "Cannot read file %*.*s",
+ pnofmt,
+ EXIT_JVM_CLASS,
JVMCLASS_JAVA_LANG_CLASSFORMATERROR,
- pcfd,
- pcname);
+ rnull,
+ pnofmt);
+
/*!
* @todo HARMONY-6-jvm-class.c-9 Throw
@@ -1290,18 +1293,18 @@
/* Don't need file image any more */
HEAP_FREE_DATA(pcfd);
- GENERIC_FAILURE1_THROWERROR((rnull == pcfs),
- DMLNORM,
- arch_function_name,
- "Invalid class file %s",
- pcname,
- EXIT_JVM_CLASS,
+ GENERIC_FAILURECP1_THROWERROR((rnull == pcfs),
+ DMLNORM,
+ arch_function_name,
+ "Invalid class file %*.*s",
+ pnofmt,
+ EXIT_JVM_CLASS,
JVMCLASS_JAVA_LANG_CLASSFORMATERROR,
- pcname,
- rnull);
+ rnull,
+ pnofmt);
- /* Don't need absolute path name any more, either */
- HEAP_FREE_DATA(pcname);
+ /* Don't need unformatted class name any more, either */
+ HEAP_FREE_DATA(pnofmt);
/*!
* @internal Load superclass
@@ -1311,7 +1314,7 @@
* execution engine moves a new class from the
* START state into the RUNNABLE state.)
*/
- if (jvm_class_index_null != pcfs->super_class)
+ if (jvm_constant_pool_index_null != pcfs->super_class)
{
CONSTANT_Utf8_info *name = PTR_CP1_CLASS_NAME(pcfs,
pcfs->super_class);
@@ -1348,7 +1351,7 @@
*/
(rvoid) class_load_resolve_clinit(super_name,
jvm_thread_index_null,
- rfalse,
+ (rtrue == jvm_completely_initialized) ? rfalse : rtrue,
find_registerNatives);
/*
@@ -1438,7 +1441,7 @@
/*!
- * @brief All-purpose class loading, load, resolve, @c @b \<clinit\> ,
+ * @brief All-purpose class linking, load, resolve, @c @b \<clinit\> ,
* each step only run if needed.
*
* Load a class into the JVM, resolve its linkages, and run its
@@ -1529,6 +1532,8 @@
{
ARCH_FUNCTION_NAME(class_load_resolve_clinit);
+ rboolean shutdown_jvm = rfalse;
+
jvm_class_index clsidx = class_load_from_prchar(clsname,
find_registerNatives,
(jint *) rnull);
@@ -1558,122 +1563,141 @@
LOCAL_CONSTANT_UTF8_CLASS_CONSTRUCTOR_PARMS);
if (jvm_method_index_bad == mthidx)
{
- /*
- * Return valid class index even if no @c @b \<clinit\>
- * was available
+ /*!
+ * @todo HARMONY-6-jvm-class.c-21 Currently, return
+ * valid class index even if no @c @b \<clinit\>
+ * was available. Is this the proper thing to do?
+ *
*/
return(clsidx);
}
- else
- {
- jvm_thread_index thridxLOAD;
- if (jvm_thread_index_null != thridx)
- {
- thridxLOAD = thridx;
+ jvm_thread_index thridxLOAD;
- /*!
- * @internal see similar logic for loading a new stack
- * frame and PC in thread_new_common()
- *
- */
+ if (jvm_thread_index_null != thridx)
+ {
+ thridxLOAD = thridx;
- ClassFile *pcfs = CLASS_OBJECT_LINKAGE(clsidx)->pcfs;
+ /*!
+ * @internal see similar logic for loading a new stack
+ * frame and PC in thread_new_common()
+ *
+ */
- jvm_attribute_index codeatridx =
- pcfs
- ->methods[mthidx]
- ->LOCAL_method_binding
- .codeatridxJVM;
+ ClassFile *pcfs = CLASS_OBJECT_LINKAGE(clsidx)->pcfs;
- if (jvm_attribute_index_bad == codeatridx)
- {
- /*!
- * @todo HARMONY-6-jvm-class.c-13 Currently, return
- * valid class index even if no @c @b \<clinit\>
- * was available. Is this correct? Or should it
- * throw a @b VerifyError since a method was
- * declared, yet had no code area? Take the
- * easy way out for now, evaluate and maybe fix
- * later.
- */
- return(clsidx);
- }
+ jvm_attribute_index codeatridx =
+ pcfs
+ ->methods[mthidx]
+ ->LOCAL_method_binding
+ .codeatridxJVM;
- jvm_attribute_index excpatridx =
- pcfs
- ->methods[mthidx]
- ->LOCAL_method_binding
- .excpatridxJVM;
-
- Code_attribute *pca =
- (Code_attribute *)
- &pcfs->methods[mthidx]->attributes[codeatridx]->ai;
-
- /* Check for stack overflow if this frame is loaded */
- if (JVMCFG_MAX_SP <= GET_SP(thridx) +
- JVMREG_STACK_MIN_FRAME_HEIGHT +
- JVMREG_STACK_PC_HEIGHT +
- pca->max_stack +
- pca->max_locals)
- {
- exit_throw_exception(EXIT_JVM_CLASS,
- JVMCLASS_JAVA_LANG_OUTOFMEMORYERROR);
-/*NOTLOADED*/
- }
-
- /*
- * Save old stack frame for @b RETURN from @c b \<clinit\>
+ if (jvm_attribute_index_bad == codeatridx)
+ {
+ /*!
+ * @todo HARMONY-6-jvm-class.c-13 Currently, return
+ * valid class index even if no @c @b \<clinit\>
+ * was available. Is this correct? Or should it
+ * throw a @b VerifyError since a method was
+ * declared, yet had no code area? Take the
+ * easy way out for now, evaluate and maybe fix
+ * later.
*/
- PUSH_FRAME(thridx, pca->max_locals);
-
- /* Load PC of @c @b \<clinit\> method */
- PUT_PC_IMMEDIATE(thridx,
- clsidx,
- mthidx,
- codeatridx,
- excpatridx,
- CODE_CONSTRAINT_START_PC);
+ return(clsidx);
}
- else
+
+ if (jvm_attribute_index_abstract == codeatridx)
{
- /*
- * Class is now known to be available,
- * so start it on the system thread.
- *
- * There is no old stack frame to save for @b RETURN
- * from @c @b \<clinit\> because this a new thread. The
- * starting stack frame is set up by thread_class_load()
- * and returning to it will @b COMPLETE the thread.
+ /*!
+ * @todo HARMONY-6-jvm-class.c-21 Same issue as with
+ * test for @link #jvm_attribute_index_bad
+ * jvm_attribute_index_bad@endlink above.
*/
- thridxLOAD =
- thread_class_load(clsname,
- LOCAL_CONSTANT_UTF8_CLASS_CONSTRUCTOR,
- LOCAL_CONSTANT_UTF8_CLASS_CONSTRUCTOR_PARMS,
- THREAD_PRIORITY_MAX,
- rfalse,
- usesystemthread,
- find_registerNatives);
+ return(clsidx);
}
- jvm_manual_thread_run(thridxLOAD,
- ((rtrue == usesystemthread) ||
- (jvm_thread_index_null == thridx))
- ? rtrue /* Die if not prev @b RUN */
- : rfalse,
- clsname,
- LOCAL_CONSTANT_UTF8_CLASS_CONSTRUCTOR,
- LOCAL_CONSTANT_UTF8_CLASS_CONSTRUCTOR_PARMS);
+ jvm_attribute_index excpatridx =
+ pcfs
+ ->methods[mthidx]
+ ->LOCAL_method_binding
+ .excpatridxJVM;
+
+ Code_attribute *pca =
+ (Code_attribute *)
+ &pcfs->methods[mthidx]->attributes[codeatridx]->ai;
+
+ /* Check for stack overflow if this frame is loaded */
+ if (JVMCFG_MAX_SP <= GET_SP(thridx) +
+ JVMREG_STACK_MIN_FRAME_HEIGHT +
+ JVMREG_STACK_PC_HEIGHT +
+ pca->max_stack +
+ pca->max_locals)
+ {
+ exit_throw_exception(EXIT_JVM_CLASS,
+ JVMCLASS_JAVA_LANG_OUTOFMEMORYERROR);
+/*NOTREACHED*/
+ }
- /* Class @c @b \<clinit\> has been completed (manually) */
- CLASS(clsidx).status &= ~CLASS_STATUS_DOCLINIT;
- CLASS(clsidx).status |= CLASS_STATUS_CLINIT;
+ /*
+ * Save old stack frame for @b RETURN from @c b \<clinit\>
+ */
+ PUSH_FRAME(thridx, pca->max_locals);
+ /* Load PC of @c @b \<clinit\> method */
+ PUT_PC_IMMEDIATE(thridx,
+ clsidx,
+ mthidx,
+ codeatridx,
+ excpatridx,
+ CODE_CONSTRAINT_START_PC);
+ }
+ else
+ {
+ /*
+ * Class is now known to be available,
+ * so start it on the system thread.
+ *
+ * There is no old stack frame to save for @b RETURN
+ * from @c @b \<clinit\> because this a new thread. The
+ * starting stack frame is set up by thread_class_load()
+ * and returning to it will @b COMPLETE the thread.
+ */
+ thridxLOAD =
+ thread_class_load(clsname,
+ LOCAL_CONSTANT_UTF8_CLASS_CONSTRUCTOR,
+ LOCAL_CONSTANT_UTF8_CLASS_CONSTRUCTOR_PARMS,
+ THREAD_PRIORITY_MAX,
+ rfalse,
+ usesystemthread,
+ find_registerNatives);
- /*Return class index of class loaded,resolved,and ready to use*/
- return(clsidx);
+ /*
+ * Die if not previous thread in @b RUN state
+ * or if requesting system thread, but that
+ * thread is already in use.
+ */
+ if ((rfalse == usesystemthread) ||
+ (!(THREAD(JVMCFG_SYSTEM_THREAD).status &
+ THREAD_STATUS_INUSE)))
+ {
+ shutdown_jvm = rtrue;
+ }
}
+ jvm_manual_thread_run(thridxLOAD,
+ shutdown_jvm,
+ clsname,
+ LOCAL_CONSTANT_UTF8_CLASS_CONSTRUCTOR,
+ LOCAL_CONSTANT_UTF8_CLASS_CONSTRUCTOR_PARMS);
+
+ /* Class @c @b \<clinit\> has been completed (manually) */
+ CLASS(clsidx).status &= ~CLASS_STATUS_DOCLINIT;
+ CLASS(clsidx).status |= CLASS_STATUS_CLINIT;
+
+
+ /*Return class index of class loaded,resolved,and ready to use*/
+ return(clsidx);
+
} /* END of class_load_resolve_clinit() */
@@ -1971,7 +1995,7 @@
/*!
- * @brief Report number of class static fields are in a class file.
+ * @brief Report number of class static fields in a class file.
*
*
* @param pcfs Pointer to ClassFile area
@@ -2110,7 +2134,7 @@
/*!
- * @brief Report number of object instance fields are in a class file.
+ * @brief Report number of object instance fields in a class file.
*
*
* @param pcfs Pointer to ClassFile area