[BACK]Return to rf_alloclist.c CVS log [TXT][DIR] Up to [local] / sys / dev / raidframe

Annotation of sys/dev/raidframe/rf_alloclist.c, Revision 1.1

1.1     ! nbrk        1: /*     $OpenBSD: rf_alloclist.c,v 1.4 2002/12/16 07:01:03 tdeval Exp $ */
        !             2: /*     $NetBSD: rf_alloclist.c,v 1.4 1999/08/13 03:41:53 oster Exp $   */
        !             3:
        !             4: /*
        !             5:  * Copyright (c) 1995 Carnegie-Mellon University.
        !             6:  * All rights reserved.
        !             7:  *
        !             8:  * Author: Mark Holland
        !             9:  *
        !            10:  * Permission to use, copy, modify and distribute this software and
        !            11:  * its documentation is hereby granted, provided that both the copyright
        !            12:  * notice and this permission notice appear in all copies of the
        !            13:  * software, derivative works or modified versions, and any portions
        !            14:  * thereof, and that both notices appear in supporting documentation.
        !            15:  *
        !            16:  * CARNEGIE MELLON ALLOWS FREE USE OF THIS SOFTWARE IN ITS "AS IS"
        !            17:  * CONDITION.  CARNEGIE MELLON DISCLAIMS ANY LIABILITY OF ANY KIND
        !            18:  * FOR ANY DAMAGES WHATSOEVER RESULTING FROM THE USE OF THIS SOFTWARE.
        !            19:  *
        !            20:  * Carnegie Mellon requests users of this software to return to
        !            21:  *
        !            22:  *  Software Distribution Coordinator  or  Software.Distribution@CS.CMU.EDU
        !            23:  *  School of Computer Science
        !            24:  *  Carnegie Mellon University
        !            25:  *  Pittsburgh PA 15213-3890
        !            26:  *
        !            27:  * any improvements or extensions that they make and grant Carnegie the
        !            28:  * rights to redistribute these changes.
        !            29:  */
        !            30:
        !            31: /****************************************************************************
        !            32:  *
        !            33:  * Alloclist.c -- Code to manipulate allocation lists.
        !            34:  *
        !            35:  * An allocation list is just a list of AllocListElem structures. Each
        !            36:  * such structure contains a fixed-size array of pointers. Calling
        !            37:  * FreeAList() causes each pointer to be freed.
        !            38:  *
        !            39:  ***************************************************************************/
        !            40:
        !            41: #include "rf_types.h"
        !            42: #include "rf_threadstuff.h"
        !            43: #include "rf_alloclist.h"
        !            44: #include "rf_debugMem.h"
        !            45: #include "rf_etimer.h"
        !            46: #include "rf_general.h"
        !            47: #include "rf_shutdown.h"
        !            48:
        !            49: RF_DECLARE_STATIC_MUTEX(alist_mutex);
        !            50: static unsigned int fl_hit_count, fl_miss_count;
        !            51:
        !            52: static RF_AllocListElem_t *al_free_list = NULL;
        !            53: static int al_free_list_count;
        !            54:
        !            55: #define        RF_AL_FREELIST_MAX      256
        !            56:
        !            57: #define        DO_FREE(_p,_sz)         RF_Free((_p), (_sz))
        !            58:
        !            59: void rf_ShutdownAllocList(void *);
        !            60:
        !            61: void
        !            62: rf_ShutdownAllocList(void *ignored)
        !            63: {
        !            64:        RF_AllocListElem_t *p, *pt;
        !            65:
        !            66:        for (p = al_free_list; p;) {
        !            67:                pt = p;
        !            68:                p = p->next;
        !            69:                DO_FREE(pt, sizeof(*pt));
        !            70:        }
        !            71:        rf_mutex_destroy(&alist_mutex);
        !            72:        /*
        !            73:         * printf("Alloclist: Free list hit count %lu (%lu %%) miss count %lu"
        !            74:         *     " (%lu %%).\n", fl_hit_count,
        !            75:         *     (100*fl_hit_count)/(fl_hit_count+fl_miss_count),
        !            76:         *     fl_miss_count, (100*fl_miss_count)/(fl_hit_count+fl_miss_count));
        !            77:         */
        !            78: }
        !            79:
        !            80: int
        !            81: rf_ConfigureAllocList(RF_ShutdownList_t **listp)
        !            82: {
        !            83:        int rc;
        !            84:
        !            85:        rc = rf_mutex_init(&alist_mutex);
        !            86:        if (rc) {
        !            87:                RF_ERRORMSG3("Unable to init mutex file %s line %d rc=%d.\n",
        !            88:                    __FILE__, __LINE__, rc);
        !            89:                return (rc);
        !            90:        }
        !            91:        al_free_list = NULL;
        !            92:        fl_hit_count = fl_miss_count = al_free_list_count = 0;
        !            93:        rc = rf_ShutdownCreate(listp, rf_ShutdownAllocList, NULL);
        !            94:        if (rc) {
        !            95:                RF_ERRORMSG3("Unable to add to shutdown list file %s line %d"
        !            96:                    " rc=%d.\n", __FILE__, __LINE__, rc);
        !            97:                rf_mutex_destroy(&alist_mutex);
        !            98:                return (rc);
        !            99:        }
        !           100:        return (0);
        !           101: }
        !           102:
        !           103:
        !           104: /*
        !           105:  * We expect the lists to have at most one or two elements, so we're willing
        !           106:  * to search for the end. If you ever observe the lists growing longer,
        !           107:  * increase POINTERS_PER_ALLOC_LIST_ELEMENT.
        !           108:  */
        !           109: void
        !           110: rf_real_AddToAllocList(RF_AllocListElem_t *l, void *p, int size, int lockflag)
        !           111: {
        !           112:        RF_AllocListElem_t *newelem;
        !           113:
        !           114:        for (; l->next; l = l->next)
        !           115:                RF_ASSERT(l->numPointers == RF_POINTERS_PER_ALLOC_LIST_ELEMENT);        /* Find end of list. */
        !           116:
        !           117:        RF_ASSERT(l->numPointers >= 0 &&
        !           118:            l->numPointers <= RF_POINTERS_PER_ALLOC_LIST_ELEMENT);
        !           119:        if (l->numPointers == RF_POINTERS_PER_ALLOC_LIST_ELEMENT) {
        !           120:                newelem = rf_real_MakeAllocList(lockflag);
        !           121:                l->next = newelem;
        !           122:                l = newelem;
        !           123:        }
        !           124:        l->pointers[l->numPointers] = p;
        !           125:        l->sizes[l->numPointers] = size;
        !           126:        l->numPointers++;
        !           127:
        !           128: }
        !           129:
        !           130:
        !           131: /*
        !           132:  * We use the debug_mem_mutex here because we need to lock it anyway to call
        !           133:  * free. This is probably a bug somewhere else in the code, but when I call
        !           134:  * malloc/free outside of any lock, I have endless trouble with malloc
        !           135:  * appearing to return the same pointer twice. Since we have to lock it
        !           136:  * anyway, we might as well use it as the lock around the al_free_list.
        !           137:  * Note that we can't call Free with the debug_mem_mutex locked.
        !           138:  */
        !           139: void
        !           140: rf_FreeAllocList(RF_AllocListElem_t *l)
        !           141: {
        !           142:        int i;
        !           143:        RF_AllocListElem_t *temp, *p;
        !           144:
        !           145:        for (p = l; p; p = p->next) {
        !           146:                RF_ASSERT(p->numPointers >= 0 &&
        !           147:                    p->numPointers <= RF_POINTERS_PER_ALLOC_LIST_ELEMENT);
        !           148:                for (i = 0; i < p->numPointers; i++) {
        !           149:                        RF_ASSERT(p->pointers[i]);
        !           150:                        RF_Free(p->pointers[i], p->sizes[i]);
        !           151:                }
        !           152:        }
        !           153:        while (l) {
        !           154:                temp = l;
        !           155:                l = l->next;
        !           156:                if (al_free_list_count > RF_AL_FREELIST_MAX) {
        !           157:                        DO_FREE(temp, sizeof(*temp));
        !           158:                } else {
        !           159:                        temp->next = al_free_list;
        !           160:                        al_free_list = temp;
        !           161:                        al_free_list_count++;
        !           162:                }
        !           163:        }
        !           164: }
        !           165:
        !           166: RF_AllocListElem_t *
        !           167: rf_real_MakeAllocList(int lockflag)
        !           168: {
        !           169:        RF_AllocListElem_t *p;
        !           170:
        !           171:        if (al_free_list) {
        !           172:                fl_hit_count++;
        !           173:                p = al_free_list;
        !           174:                al_free_list = p->next;
        !           175:                al_free_list_count--;
        !           176:        } else {
        !           177:                fl_miss_count++;
        !           178:                RF_Malloc(p, sizeof(RF_AllocListElem_t),
        !           179:                    (RF_AllocListElem_t *));    /*
        !           180:                                                 * No allocation locking
        !           181:                                                 * in kernel, so this is
        !           182:                                                 * fine.
        !           183:                                                 */
        !           184:        }
        !           185:        if (p == NULL) {
        !           186:                return (NULL);
        !           187:        }
        !           188:        bzero((char *) p, sizeof(RF_AllocListElem_t));
        !           189:        return (p);
        !           190: }

CVSweb