⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 check_code.c

📁 已经移植好的java虚拟机
💻 C
📖 第 1 页 / 共 5 页
字号:
/* * @(#)check_code.c	1.26 02/09/27 * * Copyright 1995-1999 by Sun Microsystems, Inc., * 901 San Antonio Road, Palo Alto, California, 94303, U.S.A. * All rights reserved. *  * This software is the confidential and proprietary information * of Sun Microsystems, Inc. ("Confidential Information").  You * shall not disclose such Confidential Information and shall use * it only in accordance with the terms of the license agreement * you entered into with Sun. * Use is subject to license terms. */ /*========================================================================= * SYSTEM:    Verifier * SUBSYSTEM: Verifies codes within a method block. * FILE:      check_code.c * OVERVIEW:  Verifies that the code within a method block does not *            exploit any security holes. * AUTHOR:    Sheng Liang, Consumer & Embedded  *            Initial implementation based on the Classic VM Verifier. *            Edited by Tasneem Sayeed, Java Consumer Technologies *=======================================================================*//*========================================================================= * Include files *=======================================================================*/#include <check_code.h>#include <opcodes.length>#include <opcodes.in_out>/*========================================================================= * Globals and extern declarations *=======================================================================*/#ifdef DEBUG_VERIFIER    int verify_verbose = 0;    static struct context_type *GlobalContext;#endifvoid rewriteCode(context_type *vcontext, struct methodblock *mb);static void verify_method(context_type *context, struct methodblock *mb);static void verify_field(context_type *context, struct fieldblock *fb);static void verify_opcode_operands (context_type *, int inumber, int offset);static void set_protected(context_type *, int inumber, int key, opcode_type);static bool_t isSuperClass(context_type *, fullinfo_type);static void initialize_exception_table(context_type *);static int instruction_length(unsigned char *iptr);static bool_t isLegalTarget(context_type *, int offset);static void verify_constant_pool_type(context_type *, int, unsigned);static void initialize_dataflow(context_type *);static void run_dataflow(context_type *context);static void check_register_values(context_type *context, int inumber);static void check_flags(context_type *context, int inumber);static void pop_stack(context_type *, int inumber, stack_info_type *);static void update_registers(context_type *, int inumber, register_info_type *);static void update_flags(context_type *, int inumber, 			 flag_type *new_and_flags, flag_type *new_or_flags);static void push_stack(context_type *, int inumber, stack_info_type *stack);static void merge_into_successors(context_type *, int inumber, 				  register_info_type *register_info,				  stack_info_type *stack_info, 				  flag_type and_flags, flag_type or_flags);static void merge_into_one_successor(context_type *context, 				     int from_inumber, int inumber, 				     register_info_type *register_info,				     stack_info_type *stack_info, 				     flag_type and_flags, flag_type or_flags,				     bool_t isException);static void merge_stack(context_type *, int inumber, int to_inumber, 			stack_info_type *);static void merge_registers(context_type *, int inumber, int to_inumber, 			    register_info_type *);static void merge_flags(context_type *context, int from_inumber, int to_inumber,			flag_type new_and_flags, flag_type new_or_flags);static stack_item_type *copy_stack(context_type *, stack_item_type *);static mask_type *copy_masks(context_type *, mask_type *masks, int mask_count);static mask_type *add_to_masks(context_type *, mask_type *, int , int);static fullinfo_type decrement_indirection(fullinfo_type);static fullinfo_type merge_fullinfo_types(context_type *context, 					  fullinfo_type a, fullinfo_type b,					  bool_t assignment);static bool_t isAssignableTo(context_type *,fullinfo_type a, fullinfo_type b);static ClassClass *object_fullinfo_to_classclass(context_type *, fullinfo_type);#define NEW(type, count) \        ((type *)CCalloc(context, (count)*(sizeof(type)), FALSE))#define ZNEW(type, count) \        ((type *)CCalloc(context, (count)*(sizeof(type)), TRUE))static void CCinit(context_type *context);static void CCreinit(context_type *context);static void CCdestroy(context_type *context);static void *CCalloc(context_type *context, int size, bool_t zero);static char *cp_index_to_fieldname(context_type *context, int cp_index);static char *cp_index_to_signature(context_type *context, int cp_index);static fullinfo_type cp_index_to_class_fullinfo(context_type *, int, bool_t);static char signature_to_fieldtype(context_type *context, 				   char **signature_p, fullinfo_type *info);static void CCerror (context_type *, char *format, ...);#ifdef DEBUG_VERIFIERstatic void print_stack (context_type *, stack_info_type *stack_info);static void print_registers(context_type *, register_info_type *register_info);static void print_flags(context_type *, flag_type, flag_type);static void print_formatted_fieldname(context_type *context, int index);#endif/* * Access local hash tables without locking. This extra level * of naming is intended to emphasize the fact that locks are * not held and also to do error handling. Although it is not * strictly necessary, one should always use the "_Local"   * versions of these functions on the verifier's local hash * tables. */#define Str2IDFree_Local(localHashRoot) Str2IDFree(localHashRoot)/*========================================================================= * FUNCTION:      Str2ID_Local  * OVERVIEW:      Access local hash tables without locking *                This extra level of naming is intended to emphasize the *                fact that locks are not held and also to do error handling.  *                These functions could all be macros like Str2IDFree_Local(), *                except that Str2ID() and ID2Str() can run out of memory,  *                and the code in this file makes it inconvenient to check *                for that. As an expedient, rather than throwing exceptions, *                Str2ID_Local() is a function that calls CCerror() if  *                necessary.  *                Returns the index given the string which corresponds to the *                hash table entry. * INTERFACE: *   parameters:  context_type *: context  *                struct StrIDhash **: hash_ptr  *                char *: s *                void ***: param *                int: Copy *                 *   returns:     unsigned short  *=======================================================================*/unsigned shortStr2ID_Local(context_type *context, struct StrIDhash **hash_ptr, char *s,	     void ***param, int Copy) {    unsigned short ret;    if ((ret = Str2ID(hash_ptr, s, param, Copy)) == 0) {	CCerror(context, "Out of memory");    }    return ret;}/*========================================================================= * FUNCTION:      ID2Str_Local  * OVERVIEW:      Access local hash tables without locking *                This extra level of naming is intended to emphasize the *                fact that locks are not held and also to do error handling.  *                These functions could all be macros like Str2IDFree_Local(), *                except that Str2ID() and ID2Str() can run out of memory,  *                and the code in this file makes it inconvenient to check *                for that. As an expedient, rather than throwing exceptions, *                ID2Str_Local() is a function that calls CCerror() if  *                necessary.  *                Returns the string given the index which corresponds to the *                hash table entry. * INTERFACE: *   parameters:  context_type *: context  *                struct StrIDhash *: h  *                unsigned short: ID  *                void ***: param *                 *   returns:     char *  *=======================================================================*/char *ID2Str_Local(context_type *context, struct StrIDhash *h, unsigned short ID, 	     void ***param) {    char *ret;    if ((ret = ID2Str(h, ID, param)) == 0) {	CCerror(context, "Out of memory");    }    return ret;}/*========================================================================= * FUNCTION:      verify_class_codes  * OVERVIEW:      Verifies the code for each of the methods in a class. *                Invoked by verify_class().  *                Returns true if the class codes are ok.  * INTERFACE: *   parameters:  pointer to the ClassClass structure.  *                 *   returns:     boolean type *=======================================================================*/bool_t verify_class_codes(ClassClass *cb) {    context_type context_structure;    context_type *context = &context_structure;    bool_t result = TRUE;    void **addr;    int i;#ifdef DEBUG_VERIFIER    GlobalContext = context;#endif    /* Initialize the class-wide fields of the context. */    context->class = cb;    context->classHash = 0;    /* Zero method block field of the context, in case anyone calls CCerrror */    context->mb = 0;    context->superClasses = NULL;	/* filled in later */    /* Don't call CCerror or anything that can call it above the setjmp! */    if (!setjmp(context->jump_buffer)) {	struct methodblock *mb;	struct fieldblock *fb;	CCinit(context);		/* initialize heap; may throw */	context->object_info = 	    MAKE_CLASSNAME_INFO(context, JAVAPKG "Object", &addr);	*addr = classJavaLangObject;	context->string_info =	    MAKE_CLASSNAME_INFO(context, JAVAPKG "String", &addr);	*addr = classJavaLangString;	context->throwable_info =	    MAKE_CLASSNAME_INFO(context, JAVAPKG "Throwable", &addr);	*addr = classJavaLangThrowable;	context->currentclass_info =	    MAKE_CLASSNAME_INFO_WITH_COPY(context, cbName(cb), &addr);	*addr = cb;	if (cbSuperclass(cb) != 0) {	    ClassClass *super = cbSuperclass(cb);	    context->superclass_info =	        MAKE_CLASSNAME_INFO_WITH_COPY(context, cbName(super), &addr);	    *addr = super;	} else { 	    context->superclass_info = 0;	}    	/* Look at each method */	for (i = cbFieldsCount(cb), fb = cbFields(cb); --i >= 0; fb++) 	    verify_field(context, fb);        unhand(context->class)->new_class_entries = 	    (char **)malloc((cbConstantPoolCount(context->class) * 3 + 100) * sizeof(char *));        unhand(context->class)->n_new_class_entries = 0;	for (i = cbMethodsCount(cb), mb = cbMethods(cb); --i >= 0; mb++) 	    verify_method(context, mb);	unhand(context->class)->new_class_entries = 	    (char **)realloc(unhand(context->class)->new_class_entries,	                     unhand(context->class)->n_new_class_entries * sizeof(char *));	result = TRUE;    } else { 	result = FALSE;    }    /* Cleanup */    Str2IDFree_Local(&context->classHash);#ifdef DEBUG_VERIFIER    GlobalContext = 0;#endif    if (context->superClasses != NULL) {	sysFree(context->superClasses);    }    CCdestroy(context);		/* destroy heap */    return result;}/*========================================================================= * FUNCTION:      verify_field * OVERVIEW:      Verifies the field block within each method of a class *                file. *                Invoked by verify_class_codes().  *                Returns true if the field block is ok.  * INTERFACE: *   parameters:  pointer to the context_type structure.  *                pointer to the field block *                 *   returns:     boolean type *=======================================================================*/static voidverify_field(context_type *context, struct fieldblock *fb){    int access_bits = fb->access;    if (  ((access_bits & ACC_PUBLIC) != 0) && 	  ((access_bits & (ACC_PRIVATE | ACC_PROTECTED)) != 0)) {	if (verbose) { 	    jio_fprintf(stderr, "VERIFIER ERROR %s.%s:\n", 		    cbName(fieldclass(fb)), fb->name);	    jio_fprintf(stderr, "Inconsistent access bits.");	}	longjmp(context->jump_buffer, 1);    } }/*========================================================================= * FUNCTION:      get_type_name * OVERVIEW:      Retrieves the type name information given the item type.  *                Used by get_type_code() which is invoked by verify_method() *                to retrieve the type code for the stack map entries.  * INTERFACE: *   parameters:  pointer to the context_type structure.  *                fullinfo_type: type *                char *: buf *                 *   returns:     nothing *=======================================================================*/static void get_type_name(context_type *context, fullinfo_type type, char *buf){    int i;    int indirection = GET_INDIRECTION(type);    for (i = indirection; i-- > 0; )	*buf++ = '[';    switch (GET_ITEM_TYPE(type)) {        case ITEM_Integer:       	    *buf++ = 'I'; break;	case ITEM_Float:         	    *buf++ = 'F'; break;	case ITEM_Double:        	    *buf++ = 'D'; break;	case ITEM_Long:          	    *buf++ = 'J'; break;	case ITEM_Char:	    *buf++ = 'C'; break;	case ITEM_Short:	    *buf++ = 'S'; break;	case ITEM_Byte:	    *buf++ = 'B'; break;	case ITEM_Boolean:	    *buf++ = 'Z'; break;	case ITEM_Object: {            unsigned short extra = GET_EXTRA_INFO(type);            if (indirection) *buf++ = 'L';

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -