Annotation of objc/objc-utils.m, revision 1.1

1.1     ! root        1: /*
        !             2:  * Copyright (c) 1999 Apple Computer, Inc. All rights reserved.
        !             3:  *
        !             4:  * @APPLE_LICENSE_HEADER_START@
        !             5:  * 
        !             6:  * "Portions Copyright (c) 1999 Apple Computer, Inc.  All Rights
        !             7:  * Reserved.  This file contains Original Code and/or Modifications of
        !             8:  * Original Code as defined in and that are subject to the Apple Public
        !             9:  * Source License Version 1.0 (the 'License').  You may not use this file
        !            10:  * except in compliance with the License.  Please obtain a copy of the
        !            11:  * License at http://www.apple.com/publicsource and read it before using
        !            12:  * this file.
        !            13:  * 
        !            14:  * The Original Code and all software distributed under the License are
        !            15:  * distributed on an 'AS IS' basis, WITHOUT WARRANTY OF ANY KIND, EITHER
        !            16:  * EXPRESS OR IMPLIED, AND APPLE HEREBY DISCLAIMS ALL SUCH WARRANTIES,
        !            17:  * INCLUDING WITHOUT LIMITATION, ANY WARRANTIES OF MERCHANTABILITY,
        !            18:  * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT.  Please see the
        !            19:  * License for the specific language governing rights and limitations
        !            20:  * under the License."
        !            21:  * 
        !            22:  * @APPLE_LICENSE_HEADER_END@
        !            23:  */
        !            24: /*
        !            25:  *     objc-utils.m
        !            26:  *     Copyright 1988, NeXT, Inc.
        !            27:  *     Author: s. naroff
        !            28:  */
        !            29: #ifdef SHLIB
        !            30: #import "shlib.h"
        !            31: #endif
        !            32: 
        !            33: #import "objc-private.h"
        !            34: 
        !            35: #include <sys/time.h>
        !            36: #include <sys/resource.h>
        !            37: #include <stdio.h>
        !            38: #include <time.h>
        !            39: #include "objc-dispatch.h"
        !            40: 
        !            41: #import "HashTable.h"
        !            42: 
        !            43: 
        !            44: /* Return time used so far, in microseconds.  */
        !            45: 
        !            46: int gettime (void)
        !            47: {
        !            48:   struct rusage rusage;
        !            49: 
        !            50:   getrusage (0, &rusage);
        !            51:   return (rusage.ru_utime.tv_sec * 1000000 + rusage.ru_utime.tv_usec
        !            52:          + rusage.ru_stime.tv_sec * 1000000 + rusage.ru_stime.tv_usec);
        !            53: }
        !            54: 
        !            55: void print_time (const char *str, int total, struct timeval *tv)
        !            56: {
        !            57:   extern char **NXArgv;
        !            58: 
        !            59:   fprintf (stderr,
        !            60:           "time to `%s' for `%s':\n\t%7d.%06d (sys+usr)"
        !            61:                "\t%7ld.%01ld (real).\n", str, NXArgv[0],
        !            62:           total / 1000000, total % 1000000, 
        !            63:                tv->tv_sec, tv->tv_usec/100000);
        !            64: }
        !            65: 
        !            66: static int cacheHits = 0;
        !            67: static int cacheMisses = 0;
        !            68: static int supercacheHits = 0;
        !            69: static int supercacheMisses = 0;
        !            70: 
        !            71: void _objc_msgCollectStats(MSG stackframe, int fromsuper, int cacheHit)
        !            72: {
        !            73:        if (fromsuper)
        !            74:          cacheHit ? supercacheHits++ : supercacheMisses++;
        !            75:        else
        !            76:          cacheHit ? cacheHits++ : cacheMisses++;
        !            77: }
        !            78: 
        !            79: void _objc_msgPrintStats(void)
        !            80: {
        !            81:        time_t tm = time(0);
        !            82: 
        !            83:        fprintf (stderr, "%s", ctime(&tm));
        !            84:        fprintf (stderr, "maxSelector: %d\n", (int) _sel_getMaxUid());
        !            85:        fprintf (stderr, "  _msg:      sent = %6d, %6d hits %6d misses",
        !            86:           cacheHits+cacheMisses, cacheHits,cacheMisses);
        !            87:        fprintf (stderr, "  (%3.2f%%)\n",
        !            88: 
        !            89:           (float)cacheHits/(cacheHits+cacheMisses) * 100);
        !            90:        fprintf (stderr, "  _msgSuper: sent = %6d, %6d hits %6d misses",
        !            91:           supercacheHits+supercacheMisses, supercacheHits,supercacheMisses);
        !            92:        fprintf (stderr, "  (%3.2f%%)\n",
        !            93:           (float)supercacheHits/(supercacheHits+supercacheMisses) * 100);
        !            94: 
        !            95:        // reset
        !            96:        cacheHits = cacheMisses = supercacheHits = supercacheMisses = 0;
        !            97: }
        !            98: 
        !            99: int _objc_class_respondsTo(Class class)
        !           100: {
        !           101:        Class super;
        !           102:        int nMethods = 0;
        !           103: 
        !           104:        if (class->methods) {
        !           105:                struct objc_method_list *catmethods = class->methods->method_next;
        !           106:                if (catmethods) {
        !           107:                        do {
        !           108:                                nMethods += catmethods->method_count; 
        !           109:                                catmethods = catmethods->method_next;
        !           110:                        } while (catmethods);
        !           111:                } else {
        !           112:                  nMethods += class->methods->method_count; 
        !           113:                }
        !           114:        }
        !           115: 
        !           116:        for (super = class->super_class; super; super = super->super_class)
        !           117:                if (super->methods) {
        !           118:                struct objc_method_list *catmethods = super->methods->method_next;
        !           119:                if (catmethods) {
        !           120:                        do {
        !           121:                                nMethods += catmethods->method_count; 
        !           122:                                catmethods = catmethods->method_next;
        !           123:                        } while (catmethods);
        !           124:                } else {
        !           125:                  nMethods += super->methods->method_count; 
        !           126:                }
        !           127:                }
        !           128:        return nMethods;
        !           129: }
        !           130: 
        !           131: /*
        !           132:  *     Purpose:        debug/analysis.
        !           133:  */
        !           134: void _objc_classPrintStats(int detail)
        !           135: {
        !           136:        int n_meta = 0, b_meta = 0, n_class = 0, b_class = 0;
        !           137:        int n_classes = 0, n_classes_used = 0;
        !           138:        int n_class_responds = 0, n_meta_responds = 0;
        !           139:        int class_responds = 0, meta_responds = 0;
        !           140:        int n_class_implements = 0, n_meta_implements = 0;
        !           141:        int class_implements = 0, meta_implements = 0;
        !           142:        int n_categories = 0;
        !           143:        Class cls, oldvalue;
        !           144:        NXHashTable *class_hash;
        !           145:        NXHashState state;
        !           146:        void *page;
        !           147:        HashTable *pagehash = [HashTable newKeyDesc:"i"];
        !           148:        
        !           149:        class_hash = objc_getClasses();
        !           150:         state = NXInitHashState(class_hash);
        !           151: 
        !           152:        while (NXNextHashState(class_hash, &state, (void **)&cls)) {
        !           153: 
        !           154:            Class meta = cls->isa;
        !           155: 
        !           156:            n_classes++;
        !           157: 
        !           158: //         if (CLS_GETINFO(meta, CLS_INITIALIZED))
        !           159:              {
        !           160:              if (CLS_GETINFO(meta, CLS_INITIALIZED))
        !           161:                n_classes_used++;
        !           162: 
        !           163:              page = (void *)((unsigned int)cls - ((unsigned int)cls % 0x2000));
        !           164:              oldvalue = [pagehash insertKey:page value:cls];
        !           165: 
        !           166:              if (detail)
        !           167:                printf("`%s' (%p,page #%p):\n", cls->name, 
        !           168:                                        cls, page);
        !           169: 
        !           170:              if (cls->methods) {
        !           171:                struct objc_method_list *catmethods;
        !           172: 
        !           173:                class_implements = cls->methods->method_count;
        !           174:                catmethods = cls->methods->method_next;
        !           175:                if (catmethods) {
        !           176:                        n_categories = 0;
        !           177:                        do {
        !           178:                                class_implements += catmethods->method_count; 
        !           179:                                catmethods = catmethods->method_next;
        !           180:                                if (catmethods)
        !           181:                                        n_categories++;
        !           182:                        } while (catmethods);
        !           183:                }
        !           184:              } else {
        !           185:                class_implements = 0;
        !           186:              }
        !           187: 
        !           188:              //printf("n_categories = %d\n",n_categories);
        !           189: 
        !           190:              if (meta->methods) {
        !           191:                struct objc_method_list *catmethods;
        !           192: 
        !           193:                meta_implements = meta->methods->method_count; 
        !           194:                catmethods = meta->methods->method_next;
        !           195:                if (catmethods) {
        !           196:                        do {
        !           197:                                meta_implements += catmethods->method_count; 
        !           198:                                catmethods = catmethods->method_next;
        !           199:                        } while (catmethods);
        !           200:                }
        !           201:              } else {
        !           202:                meta_implements = 0;
        !           203:              }
        !           204: 
        !           205:              if (detail)
        !           206:                printf("  implements %d instance methods, %d class methods\n",
        !           207:                        class_implements, meta_implements);
        !           208: 
        !           209:              n_class_implements += class_implements;
        !           210:              n_meta_implements += meta_implements;
        !           211: 
        !           212:              class_responds = _objc_class_respondsTo(cls);
        !           213:              meta_responds = _objc_class_respondsTo(meta);
        !           214:              
        !           215:              if (detail)
        !           216:                printf("  responds to %d instance methods, %d class methods\n",
        !           217:                        class_responds, meta_responds);
        !           218: 
        !           219:              n_class_responds += class_responds;
        !           220:              n_meta_responds += meta_responds;
        !           221: 
        !           222:               if (cls->cache)
        !           223:                 {
        !           224:                if (detail) {
        !           225:                  printf("  using %u instance methods\n", cls->cache->occupied);
        !           226:                  printf("  instance cache has %u slots, it is %3.2f%% full.\n",
        !           227:                        cls->cache->mask+1, 
        !           228:                        (float)cls->cache->occupied/(cls->cache->mask+1) * 100);
        !           229:                }
        !           230:                b_class += sizeof(struct objc_cache) + 
        !           231:                        ((cls->cache->mask+1) * sizeof(Method));
        !           232:                n_class++;
        !           233:                 }
        !           234:              if (meta->cache)
        !           235:                 {
        !           236:                if (detail) {
        !           237:                  printf("  using %u class methods\n", meta->cache->occupied);
        !           238:                  printf("  class cache has %u slots, it is %3.2f%% full.\n",
        !           239:                       meta->cache->mask+1, 
        !           240:                       (float)meta->cache->occupied/(meta->cache->mask+1) * 100);
        !           241:                }
        !           242:                b_meta += sizeof(struct objc_cache) + 
        !           243:                        ((meta->cache->mask+1) * sizeof(Method));
        !           244:                n_meta++;
        !           245:                }
        !           246:              }
        !           247:          }
        !           248:        {
        !           249:        Module *mods = objc_getModules();
        !           250:        int catcnt = 0;
        !           251: 
        !           252:        while (*mods) {
        !           253:                int i, total = (*mods)->symtab->cls_def_cnt + 
        !           254:                                (*mods)->symtab->cat_def_cnt; 
        !           255: 
        !           256:                catcnt += (*mods)->symtab->cat_def_cnt; 
        !           257: 
        !           258:                /* add categories */
        !           259:                for (i = (*mods)->symtab->cls_def_cnt;  i < total; i++) {
        !           260:                        //Category cat = (*mods)->symtab->defs[i];
        !           261:                        //printf("Category `%s' for Class `%s'.\n", cat->category_name, cat->class_name);
        !           262:                }
        !           263:                mods++; 
        !           264:        }
        !           265:        printf("\nClass Info:\n\n");
        !           266:        printf("%d classes (%d categories) - class descriptors spread across %u pages.\n", 
        !           267:                        n_classes, catcnt, [pagehash count]);
        !           268:        }
        !           269:        printf("%d classes currently in use\n", n_classes_used);
        !           270:        printf("%d instance methods, ",n_class_implements);
        !           271:        printf("%d instance responders\n",n_class_responds);
        !           272:        printf("%d class methods, ",n_meta_implements);
        !           273:        printf("%d class responders\n",n_meta_responds);
        !           274: 
        !           275:        if (n_class) {
        !           276:                printf("%d bytes allocated to cache instance methods ",b_class);
        !           277:                printf("(%d bytes per class)\n",
        !           278:                                b_class/n_class);
        !           279:        }
        !           280:        if (n_meta) {
        !           281:                printf("%d bytes allocated to cache class methods ",b_meta);
        !           282:                printf("(%d bytes per meta class)\n",
        !           283:                                b_meta/n_meta);
        !           284:        }
        !           285: 
        !           286:        {
        !           287:        Module *mods = objc_getModules();
        !           288:        int selrefs = 0;
        !           289: 
        !           290:        while (*mods) {
        !           291:                int nsels = (*mods)->symtab->sel_ref_cnt;
        !           292: #if 0
        !           293:                int i;
        !           294:                for (i = 0; i < nsels; i++)
        !           295:                        printf("refs[%d] = %s\n",i, 
        !           296:                                sel_getName((*mods)->symtab->refs[i]));
        !           297: #endif
        !           298:                selrefs += nsels; 
        !           299:                mods++;
        !           300:        }
        !           301: 
        !           302:        printf("\nSelector Info:\n\n");
        !           303:        printf("%d selector references\n", selrefs);
        !           304:        printf("%d unique selectors\n", (int) _sel_getMaxUid());
        !           305:        }
        !           306: }

unix.superglobalmegacorp.com

This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.