hprof_class.c
来自「一个小公司要求给写的很简单的任务管理系统。」· C语言 代码 · 共 674 行 · 第 1/2 页
C
674 行
/* * @(#)hprof_class.c 1.35 05/11/17 * * Copyright (c) 2006 Sun Microsystems, Inc. All Rights Reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions are met: * * -Redistribution of source code must retain the above copyright notice, this * list of conditions and the following disclaimer. * * -Redistribution in binary form must reproduce the above copyright notice, * this list of conditions and the following disclaimer in the documentation * and/or other materials provided with the distribution. * * Neither the name of Sun Microsystems, Inc. or the names of contributors may * be used to endorse or promote products derived from this software without * specific prior written permission. * * This software is provided "AS IS," without a warranty of any kind. ALL * EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND WARRANTIES, INCLUDING * ANY IMPLIED WARRANTY OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE * OR NON-INFRINGEMENT, ARE HEREBY EXCLUDED. SUN MIDROSYSTEMS, INC. ("SUN") * AND ITS LICENSORS SHALL NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE * AS A RESULT OF USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR ANY LOST * REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, CONSEQUENTIAL, * INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND REGARDLESS OF THE THEORY * OF LIABILITY, ARISING OUT OF THE USE OF OR INABILITY TO USE THIS SOFTWARE, * EVEN IF SUN HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGES. * * You acknowledge that this software is not designed, licensed or intended * for use in the design, construction, operation or maintenance of any * nuclear facility. *//* Table of class information. * * Each element in this table is identified with a ClassIndex. * Each element is uniquely identified by it's signature and loader. * Every class load has a unique class serial number. * While loaded, each element will have a cache of a global reference * to it's jclass object, plus jmethodID's as needed. * Method signatures and names are obtained via BCI. * Methods can be identified with a ClassIndex and MethodIndex pair, * where the MethodIndex matches the index of the method name and * signature arrays obtained from the BCI pass. * Strings are stored in the string table and a StringIndex is used. * Class Loaders are stored in the loader table and a LoaderIndex is used. * Since the jclass object is an object, at some point an object table * entry may be allocated for the jclass as an ObjectIndex. */#include "hprof.h"/* Effectively represents a jclass object. *//* These table elements are made unique by and sorted by signature name. */typedef struct ClassKey { StringIndex sig_string_index; /* Signature of class */ LoaderIndex loader_index; /* Index for class loader */} ClassKey;/* Each class could contain method information, gotten from BCI callback */typedef struct MethodInfo { StringIndex name_index; /* Method name, index into string table */ StringIndex sig_index; /* Method signature, index into string table */ jmethodID method_id; /* Method ID, possibly NULL at first */} MethodInfo;/* The basic class information we save */typedef struct ClassInfo { jclass classref; /* Global ref to jclass */ MethodInfo *method; /* Array of method data */ int method_count; /* Count of methods */ ObjectIndex object_index; /* Optional object index for jclass */ SerialNumber serial_num; /* Unique to the actual class load */ ClassStatus status; /* Current class status (bit mask) */ ClassIndex super; /* Super class in this table */ StringIndex name; /* Name of class */ jint inst_size; /* #bytes needed for instance fields */ jint field_count; /* Number of all fields */ FieldInfo *field; /* Pointer to all FieldInfo's */} ClassInfo;/* Private interfaces */static ClassKey*get_pkey(ClassIndex index){ void *key_ptr; int key_len; table_get_key(gdata->class_table, index, (void*)&key_ptr, &key_len); HPROF_ASSERT(key_len==sizeof(ClassKey)); HPROF_ASSERT(key_ptr!=NULL); return (ClassKey*)key_ptr;}static voidfillin_pkey(const char *sig, LoaderIndex loader_index, ClassKey *pkey){ static ClassKey empty_key; HPROF_ASSERT(loader_index!=0); *pkey = empty_key; pkey->sig_string_index = string_find_or_create(sig); pkey->loader_index = loader_index;}static ClassInfo *get_info(ClassIndex index){ ClassInfo *info; info = (ClassInfo*)table_get_info(gdata->class_table, index); return info;}static voidfill_info(TableIndex index, ClassKey *pkey){ ClassInfo *info; char *sig; info = get_info(index); info->serial_num = gdata->class_serial_number_counter++; info->method_count = 0; info->inst_size = -1; info->field_count = -1; info->field = NULL; sig = string_get(pkey->sig_string_index); if ( sig[0] != JVM_SIGNATURE_CLASS ) { info->name = pkey->sig_string_index; } else { int len; len = string_get_len(pkey->sig_string_index); if ( len > 2 ) { char *name; /* Class signature looks like "Lname;", we want "name" here. */ name = HPROF_MALLOC(len-1); (void)memcpy(name, sig+1, len-2); name[len-2] = 0; info->name = string_find_or_create(name); HPROF_FREE(name); } else { /* This would be strange, a class signature not in "Lname;" form? */ info->name = pkey->sig_string_index; } }}static ClassIndexfind_entry(ClassKey *pkey){ ClassIndex index; index = table_find_entry(gdata->class_table, (void*)pkey, (int)sizeof(ClassKey)); return index;}static ClassIndexcreate_entry(ClassKey *pkey){ ClassIndex index; index = table_create_entry(gdata->class_table, (void*)pkey, (int)sizeof(ClassKey), NULL); fill_info(index, pkey); return index;}static ClassIndexfind_or_create_entry(ClassKey *pkey){ ClassIndex index; HPROF_ASSERT(pkey!=NULL); HPROF_ASSERT(pkey->loader_index!=0); index = find_entry(pkey); if ( index == 0 ) { index = create_entry(pkey); } return index;}static voiddelete_classref(JNIEnv *env, ClassInfo *info, jclass klass){ jclass ref; int i; HPROF_ASSERT(env!=NULL); HPROF_ASSERT(info!=NULL); for ( i = 0 ; i < info->method_count ; i++ ) { info->method[i].method_id = NULL; } ref = info->classref; if ( klass != NULL ) { info->classref = newGlobalReference(env, klass); } else { info->classref = NULL; } if ( ref != NULL ) { deleteGlobalReference(env, ref); }}static voidcleanup_item(TableIndex index, void *key_ptr, int key_len, void *info_ptr, void *arg){ ClassInfo *info; /* Cleanup any information in this ClassInfo structure. */ HPROF_ASSERT(key_ptr!=NULL); HPROF_ASSERT(key_len==sizeof(ClassKey)); HPROF_ASSERT(info_ptr!=NULL); info = (ClassInfo *)info_ptr; if ( info->method_count > 0 ) { HPROF_FREE((void*)info->method); info->method_count = 0; info->method = NULL; } if ( info->field != NULL ) { HPROF_FREE((void*)info->field); info->field_count = 0; info->field = NULL; }}static voiddelete_ref_item(TableIndex index, void *key_ptr, int key_len, void *info_ptr, void *arg){ delete_classref((JNIEnv*)arg, (ClassInfo*)info_ptr, NULL);}static voidlist_item(TableIndex index, void *key_ptr, int key_len, void *info_ptr, void *arg){ ClassInfo *info; ClassKey key; char *sig; int i; HPROF_ASSERT(key_ptr!=NULL); HPROF_ASSERT(key_len==sizeof(ClassKey)); HPROF_ASSERT(info_ptr!=NULL); key = *((ClassKey*)key_ptr); sig = string_get(key.sig_string_index); info = (ClassInfo *)info_ptr; debug_message( "0x%08x: Class %s, SN=%u, status=0x%08x, ref=%p," " method_count=%d\n", index, (const char *)sig, info->serial_num, info->status, (void*)info->classref, info->method_count); if ( info->method_count > 0 ) { for ( i = 0 ; i < info->method_count ; i++ ) { debug_message( " Method %d: \"%s\", sig=\"%s\", method=%p\n", i, string_get(info->method[i].name_index), string_get(info->method[i].sig_index), (void*)info->method[i].method_id); } }}static voidall_status_remove(TableIndex index, void *key_ptr, int key_len, void *info_ptr, void *arg){ ClassInfo *info; ClassStatus status; HPROF_ASSERT(info_ptr!=NULL); /*LINTED*/ status = (ClassStatus)(long)(ptrdiff_t)arg; info = (ClassInfo *)info_ptr; info->status &= (~status);}static voidunload_walker(TableIndex index, void *key_ptr, int key_len, void *info_ptr, void *arg){ ClassInfo *info; HPROF_ASSERT(info_ptr!=NULL); info = (ClassInfo *)info_ptr; if ( ! ( info->status & CLASS_IN_LOAD_LIST ) ) { if ( ! (info->status & (CLASS_SPECIAL|CLASS_SYSTEM|CLASS_UNLOADED)) ) { io_write_class_unload(info->serial_num, info->object_index); info->status |= CLASS_UNLOADED; delete_classref((JNIEnv*)arg, info, NULL); } }}/* External interfaces */voidclass_init(void){ HPROF_ASSERT(gdata->class_table==NULL); gdata->class_table = table_initialize("Class", 512, 512, 511, (int)sizeof(ClassInfo));}ClassIndexclass_find_or_create(const char *sig, LoaderIndex loader_index){ ClassKey key; fillin_pkey(sig, loader_index, &key); return find_or_create_entry(&key);}ClassIndexclass_create(const char *sig, LoaderIndex loader_index){ ClassKey key; fillin_pkey(sig, loader_index, &key);
⌨️ 快捷键说明
复制代码Ctrl + C
搜索代码Ctrl + F
全屏模式F11
增大字号Ctrl + =
减小字号Ctrl + -
显示快捷键?