X-Git-Url: http://wien.tomnetworks.com/gitweb/?a=blobdiff_plain;f=src%2Fvm%2Fresolve.h;h=b38b80b7606a3a35117920be3c0f02c3caab607d;hb=b6fbb1958c8971b06e87ea3c37be0deaff131768;hp=b3b20faa9d153c63fd3a66b8ae58c29c574dbe14;hpb=80675af1e145f5102b7831f9a086c2fe07c80155;p=cacao.git diff --git a/src/vm/resolve.h b/src/vm/resolve.h index b3b20faa9..b38b80b76 100644 --- a/src/vm/resolve.h +++ b/src/vm/resolve.h @@ -1,9 +1,9 @@ -/* vm/resolve.h - resolving classes/interfaces/fields/methods +/* src/vm/resolve.h - resolving classes/interfaces/fields/methods - Copyright (C) 1996-2005 R. Grafl, A. Krall, C. Kruegel, C. Oates, - R. Obermaisser, M. Platter, M. Probst, S. Ring, E. Steiner, - C. Thalinger, D. Thuernbeck, P. Tomsich, C. Ullrich, J. Wenninger, - Institut f. Computersprachen - TU Wien + Copyright (C) 1996-2005, 2006, 2007 R. Grafl, A. Krall, C. Kruegel, + C. Oates, R. Obermaisser, M. Platter, M. Probst, S. Ring, + E. Steiner, C. Thalinger, D. Thuernbeck, P. Tomsich, C. Ullrich, + J. Wenninger, Institut f. Computersprachen - TU Wien This file is part of CACAO. @@ -19,16 +19,8 @@ You should have received a copy of the GNU General Public License along with this program; if not, write to the Free Software - Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA - 02111-1307, USA. - - Contact: cacao@complang.tuwien.ac.at - - Authors: Edwin Steiner - - Changes: - - $Id: resolve.h 2112 2005-03-29 21:29:08Z twisti $ + Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA + 02110-1301, USA. */ @@ -38,20 +30,32 @@ /* forward declarations *******************************************************/ +typedef struct unresolved_class unresolved_class; typedef struct unresolved_field unresolved_field; typedef struct unresolved_method unresolved_method; typedef struct unresolved_subtype_set unresolved_subtype_set; +#include "config.h" +#include "vm/types.h" + #include "vm/global.h" -#include "vm/loader.h" + #include "vm/jit/jit.h" +#include "vm/jit/reg.h" +#include "vm/jit/verify/typeinfo.h" + +#include "vmcore/class.h" +#include "vmcore/field.h" +#include "vmcore/method.h" +#include "vmcore/references.h" /* constants ******************************************************************/ -#define RESOLVE_STATIC 0x0001 -#define RESOLVE_PUTFIELD 0x0002 +#define RESOLVE_STATIC 0x0001 /* ref to static fields/methods */ +#define RESOLVE_PUTFIELD 0x0002 /* field ref inside a PUT{FIELD,STATIC}... */ +#define RESOLVE_SPECIAL 0x0004 /* method ref inside INVOKESPECIAL */ /* enums **********************************************************************/ @@ -61,21 +65,16 @@ typedef enum { resolveEager } resolve_mode_t; - typedef enum { resolveLinkageError, resolveIllegalAccessError } resolve_err_t; - -/* classref_or_classinfo ******************************************************/ - -typedef union { - constant_classref *ref; /* a symbolic class reference */ - classinfo *cls; /* an already loaded class */ - void *any; /* used for general access (x != NULL,...) */ -} classref_or_classinfo; - +typedef enum { + resolveFailed = false, /* this must be a false value */ + resolveDeferred = true, /* this must be a true value */ + resolveSucceeded +} resolve_result_t; /* structs ********************************************************************/ @@ -83,6 +82,11 @@ struct unresolved_subtype_set { classref_or_classinfo *subtyperefs; /* NULL terminated list */ }; +struct unresolved_class { + constant_classref *classref; + methodinfo *referermethod; + unresolved_subtype_set subtypeconstraints; +}; /* XXX unify heads of unresolved_field and unresolved_method? */ @@ -110,298 +114,147 @@ struct unresolved_method { #define UNRESOLVED_SUBTYPE_SET_EMTPY(stset) \ do { (stset).subtyperefs = NULL; } while(0) -/* a value that never occurrs in classinfo.header.vftbl */ -#define CLASSREF_PSEUDO_VFTBL ((vftbl_t *) 1) - -/* macro for testing if a classref_or_classinfo is a classref */ -/* `reforinfo` is only evaluated once */ -#define IS_CLASSREF(reforinfo) \ - ((reforinfo).ref->pseudo_vftbl == CLASSREF_PSEUDO_VFTBL) +/* function prototypes ********************************************************/ -/* macro for casting a classref/classinfo * to a classref_or_classinfo */ -#define CLASSREF_OR_CLASSINFO(value) \ - (*((classref_or_classinfo *)(&(value)))) +bool resolve_class_from_name(classinfo* referer,methodinfo *refmethod, + utf *classname, + resolve_mode_t mode, + bool checkaccess, + bool link, + classinfo **result); + +bool resolve_classref(methodinfo *refmethod, + constant_classref *ref, + resolve_mode_t mode, + bool checkaccess, + bool link, + classinfo **result); + +bool resolve_classref_or_classinfo(methodinfo *refmethod, + classref_or_classinfo cls, + resolve_mode_t mode, + bool checkaccess, + bool link, + classinfo **result); +classinfo *resolve_classref_or_classinfo_eager(classref_or_classinfo cls, bool checkaccess); -/* function prototypes ********************************************************/ +bool resolve_class_from_typedesc(typedesc *d,bool checkaccess,bool link,classinfo **result); -/* resolve_class *************************************************************** - - Resolve a symbolic class reference - - IN: - referer..........the class containing the reference - refmethod........the method from which resolution was triggered - (may be NULL if not applicable) - classname........class name to resolve - mode.............mode of resolution: - resolveLazy...only resolve if it does not - require loading classes - resolveEager..load classes if necessary - - OUT: - *result..........set to result of resolution, or to NULL if - the reference has not been resolved - In the case of an exception, *result is - guaranteed to be set to NULL. - - RETURN VALUE: - true.............everything ok - (*result may still be NULL for resolveLazy) - false............an exception has been thrown - - NOTE: - The returned class is *not* guaranteed to be linked! - (It is guaranteed to be loaded, though.) - -*******************************************************************************/ - -bool -resolve_class(classinfo *referer,methodinfo *refmethod, - utf *classname, +#ifdef ENABLE_VERIFIER +bool resolve_class(unresolved_class *ref, resolve_mode_t mode, + bool checkaccess, classinfo **result); -/* resolve_classref_or_classinfo *********************************************** - - Resolve a symbolic class reference if necessary - - IN: - refmethod........the method from which resolution was triggered - (may be NULL if not applicable) - cls..............class reference or classinfo - mode.............mode of resolution: - resolveLazy...only resolve if it does not - require loading classes - resolveEager..load classes if necessary - link.............if true, guarantee that the returned class, if any, - has been linked - - OUT: - *result..........set to result of resolution, or to NULL if - the reference has not been resolved - In the case of an exception, *result is - guaranteed to be set to NULL. - - RETURN VALUE: - true.............everything ok - (*result may still be NULL for resolveLazy) - false............an exception has been thrown - -*******************************************************************************/ - -bool -resolve_classref_or_classinfo(methodinfo *refmethod, - classref_or_classinfo cls, - resolve_mode_t mode, - bool link, - classinfo **result); +classinfo * resolve_class_eager(unresolved_class *ref); +classinfo * resolve_class_eager_no_access_check(unresolved_class *ref); +#endif /* ENABLE_VERIFIER */ -/* resolve_field *************************************************************** - - Resolve an unresolved field reference - - IN: - ref..............struct containing the reference - mode.............mode of resolution: - resolveLazy...only resolve if it does not - require loading classes - resolveEager..load classes if necessary - - OUT: - *result..........set to the result of resolution, or to NULL if - the reference has not been resolved - In the case of an exception, *result is - guaranteed to be set to NULL. - - RETURN VALUE: - true.............everything ok - (*result may still be NULL for resolveLazy) XXX implement - false............an exception has been thrown - -*******************************************************************************/ - -bool -resolve_field(unresolved_field *ref, +bool resolve_field(unresolved_field *ref, resolve_mode_t mode, fieldinfo **result); -/* resolve_method ************************************************************** - - Resolve an unresolved method reference - - IN: - ref..............struct containing the reference - mode.............mode of resolution: - resolveLazy...only resolve if it does not - require loading classes - resolveEager..load classes if necessary - - OUT: - *result..........set to the result of resolution, or to NULL if - the reference has not been resolved - In the case of an exception, *result is - guaranteed to be set to NULL. - - RETURN VALUE: - true.............everything ok - (*result may still be NULL for resolveLazy) XXX implement - false............an exception has been thrown - -*******************************************************************************/ - -bool -resolve_method(unresolved_method *ref, +bool resolve_method(unresolved_method *ref, resolve_mode_t mode, methodinfo **result); -/* resolve_and_check_subtype_set *********************************************** - - Resolve the references in the given set and test subtype relationships - - IN: - referer..........the class containing the references - refmethod........the method triggering the resolution - ref..............a set of class/interface references - (may be empty) - type.............the type to test against the set - reversed.........if true, test if type is a subtype of - the set members, instead of the other - way round - mode.............mode of resolution: - resolveLazy...only resolve if it does not - require loading classes - resolveEager..load classes if necessary - error............which type of exception to throw if - the test fails. May be: - resolveLinkageError, or - resolveIllegalAccessError - - OUT: - *checked.........set to true if all checks were performed, - otherwise set to false - (This is guaranteed to be true if mode was - resolveEager and no exception occured.) - If checked == NULL, this parameter is not used. - - RETURN VALUE: - true.............the check succeeded - false............the check failed. An exception has been - thrown. - - NOTE: - The references in the set are resolved first, so any - exception which may occurr during resolution may - be thrown by this function. - -*******************************************************************************/ - -bool -resolve_and_check_subtype_set(classinfo *referer,methodinfo *refmethod, - unresolved_subtype_set *ref, - classref_or_classinfo type, - bool reversed, - resolve_mode_t mode, - resolve_err_t error, - bool *checked); - -/* create_unresolved_field ***************************************************** - - Create an unresolved_field struct for the given field access instruction - - IN: - referer..........the class containing the reference - refmethod........the method triggering the resolution (if any) - iptr.............the {GET,PUT}{FIELD,STATIC}{,CONST} instruction - stack............the input stack of the instruction - - RETURN VALUE: - a pointer to a new unresolved_field struct - -*******************************************************************************/ - -unresolved_field * -create_unresolved_field(classinfo *referer,methodinfo *refmethod, - instruction *iptr, - stackelement *stack); - -/* create_unresolved_method **************************************************** - - Create an unresolved_method struct for the given method invocation - - IN: - referer..........the class containing the reference - refmethod........the method triggering the resolution (if any) - iptr.............the INVOKE* instruction - stack............the input stack of the instruction - - RETURN VALUE: - a pointer to a new unresolved_method struct - -*******************************************************************************/ - -unresolved_method * -create_unresolved_method(classinfo *referer,methodinfo *refmethod, - instruction *iptr, - stackelement *stack); - -/* unresolved_field_free ******************************************************* - - Free the memory used by an unresolved_field - - IN: - ref..............the unresolved_field - -*******************************************************************************/ +classinfo * resolve_classref_eager(constant_classref *ref); +classinfo * resolve_classref_eager_nonabstract(constant_classref *ref); +fieldinfo * resolve_field_eager(unresolved_field *ref); +methodinfo * resolve_method_eager(unresolved_method *ref); -void unresolved_field_free(unresolved_field *ref); +#ifdef ENABLE_VERIFIER +unresolved_class * create_unresolved_class(methodinfo *refmethod, + constant_classref *classref, + typeinfo *valuetype); +#endif -/* unresolved_method_free ****************************************************** - - Free the memory used by an unresolved_method - - IN: - ref..............the unresolved_method +unresolved_field *resolve_create_unresolved_field(classinfo *referer, + methodinfo *refmethod, + instruction *iptr); -*******************************************************************************/ +unresolved_method * resolve_create_unresolved_method(classinfo *referer, + methodinfo *refmethod, + constant_FMIref *methodref, + bool invokestatic, + bool invokespecial); +void unresolved_class_free(unresolved_class *ref); +void unresolved_field_free(unresolved_field *ref); void unresolved_method_free(unresolved_method *ref); -/* unresolved_field_debug_dump ************************************************* - - Print debug info for unresolved_field to stream - - IN: - ref..............the unresolved_field - file.............the stream - -*******************************************************************************/ - +resolve_result_t resolve_method_lazy(methodinfo *refmethod, + constant_FMIref *methodref, + bool invokespecial); + +resolve_result_t resolve_field_lazy(methodinfo *refmethod, + constant_FMIref *fieldref); + +#if defined(ENABLE_VERIFIER) +resolve_result_t resolve_field_verifier_checks(methodinfo *refmethod, + constant_FMIref *fieldref, + classinfo *container, + fieldinfo *fi, + typeinfo *instanceti, + typeinfo *valueti, + bool isstatic, + bool isput); + +bool resolve_constrain_unresolved_field(unresolved_field *ref, + classinfo *referer, + methodinfo *refmethod, + typeinfo *instanceti, + typeinfo *valueti); + +resolve_result_t resolve_method_verifier_checks(methodinfo *refmethod, + constant_FMIref *methodref, + methodinfo *mi, + bool invokestatic); + +resolve_result_t resolve_method_instance_type_checks(methodinfo *refmethod, + methodinfo *mi, + typeinfo *instanceti, + bool invokespecial); + +resolve_result_t resolve_method_param_type_checks(jitdata *jd, + methodinfo *refmethod, + instruction *iptr, + methodinfo *mi, + bool invokestatic); + +resolve_result_t resolve_method_param_type_checks_stackbased( + methodinfo *refmethod, + methodinfo *mi, + bool invokestatic, + typedescriptor *stack); + +bool resolve_method_loading_constraints(classinfo *referer, + methodinfo *mi); + +bool resolve_constrain_unresolved_method_instance(unresolved_method *ref, + methodinfo *refmethod, + typeinfo *instanceti, + bool invokespecial); + +bool resolve_constrain_unresolved_method_params(jitdata *jd, + unresolved_method *ref, + methodinfo *refmethod, + instruction *iptr); + +bool resolve_constrain_unresolved_method_params_stackbased( + unresolved_method *ref, + methodinfo *refmethod, + typedescriptor *stack); + +#endif /* defined(ENABLE_VERIFIER) */ + +#ifndef NDEBUG +void unresolved_class_debug_dump(unresolved_class *ref,FILE *file); void unresolved_field_debug_dump(unresolved_field *ref,FILE *file); - -/* unresolved_method_debug_dump ************************************************ - - Print debug info for unresolved_method to stream - - IN: - ref..............the unresolved_method - file.............the stream - -*******************************************************************************/ - void unresolved_method_debug_dump(unresolved_method *ref,FILE *file); - -/* unresolved_subtype_set_debug_dump ******************************************* - - Print debug info for unresolved_subtype_set to stream - - IN: - stset............the unresolved_subtype_set - file.............the stream - -*******************************************************************************/ - void unresolved_subtype_set_debug_dump(unresolved_subtype_set *stset,FILE *file); +#endif #endif /* _RESOLVE_H */