xref: /aosp_15_r20/external/libdrm/xf86drmSL.c (revision 7688df22e49036ff52a766b7101da3a49edadb8c)
1*7688df22SAndroid Build Coastguard Worker /* xf86drmSL.c -- Skip list support
2*7688df22SAndroid Build Coastguard Worker  * Created: Mon May 10 09:28:13 1999 by [email protected]
3*7688df22SAndroid Build Coastguard Worker  *
4*7688df22SAndroid Build Coastguard Worker  * Copyright 1999 Precision Insight, Inc., Cedar Park, Texas.
5*7688df22SAndroid Build Coastguard Worker  * All Rights Reserved.
6*7688df22SAndroid Build Coastguard Worker  *
7*7688df22SAndroid Build Coastguard Worker  * Permission is hereby granted, free of charge, to any person obtaining a
8*7688df22SAndroid Build Coastguard Worker  * copy of this software and associated documentation files (the "Software"),
9*7688df22SAndroid Build Coastguard Worker  * to deal in the Software without restriction, including without limitation
10*7688df22SAndroid Build Coastguard Worker  * the rights to use, copy, modify, merge, publish, distribute, sublicense,
11*7688df22SAndroid Build Coastguard Worker  * and/or sell copies of the Software, and to permit persons to whom the
12*7688df22SAndroid Build Coastguard Worker  * Software is furnished to do so, subject to the following conditions:
13*7688df22SAndroid Build Coastguard Worker  *
14*7688df22SAndroid Build Coastguard Worker  * The above copyright notice and this permission notice (including the next
15*7688df22SAndroid Build Coastguard Worker  * paragraph) shall be included in all copies or substantial portions of the
16*7688df22SAndroid Build Coastguard Worker  * Software.
17*7688df22SAndroid Build Coastguard Worker  *
18*7688df22SAndroid Build Coastguard Worker  * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
19*7688df22SAndroid Build Coastguard Worker  * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
20*7688df22SAndroid Build Coastguard Worker  * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.  IN NO EVENT SHALL
21*7688df22SAndroid Build Coastguard Worker  * PRECISION INSIGHT AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM, DAMAGES OR
22*7688df22SAndroid Build Coastguard Worker  * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
23*7688df22SAndroid Build Coastguard Worker  * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
24*7688df22SAndroid Build Coastguard Worker  * DEALINGS IN THE SOFTWARE.
25*7688df22SAndroid Build Coastguard Worker  *
26*7688df22SAndroid Build Coastguard Worker  * Authors: Rickard E. (Rik) Faith <[email protected]>
27*7688df22SAndroid Build Coastguard Worker  *
28*7688df22SAndroid Build Coastguard Worker  * DESCRIPTION
29*7688df22SAndroid Build Coastguard Worker  *
30*7688df22SAndroid Build Coastguard Worker  * This file contains a straightforward skip list implementation.n
31*7688df22SAndroid Build Coastguard Worker  *
32*7688df22SAndroid Build Coastguard Worker  * FUTURE ENHANCEMENTS
33*7688df22SAndroid Build Coastguard Worker  *
34*7688df22SAndroid Build Coastguard Worker  * REFERENCES
35*7688df22SAndroid Build Coastguard Worker  *
36*7688df22SAndroid Build Coastguard Worker  * [Pugh90] William Pugh.  Skip Lists: A Probabilistic Alternative to
37*7688df22SAndroid Build Coastguard Worker  * Balanced Trees. CACM 33(6), June 1990, pp. 668-676.
38*7688df22SAndroid Build Coastguard Worker  *
39*7688df22SAndroid Build Coastguard Worker  */
40*7688df22SAndroid Build Coastguard Worker 
41*7688df22SAndroid Build Coastguard Worker #include <stdio.h>
42*7688df22SAndroid Build Coastguard Worker #include <stdlib.h>
43*7688df22SAndroid Build Coastguard Worker 
44*7688df22SAndroid Build Coastguard Worker #include "libdrm_macros.h"
45*7688df22SAndroid Build Coastguard Worker #include "xf86drm.h"
46*7688df22SAndroid Build Coastguard Worker 
47*7688df22SAndroid Build Coastguard Worker #define SL_LIST_MAGIC  0xfacade00LU
48*7688df22SAndroid Build Coastguard Worker #define SL_ENTRY_MAGIC 0x00fab1edLU
49*7688df22SAndroid Build Coastguard Worker #define SL_FREED_MAGIC 0xdecea5edLU
50*7688df22SAndroid Build Coastguard Worker #define SL_MAX_LEVEL   16
51*7688df22SAndroid Build Coastguard Worker #define SL_RANDOM_SEED 0xc01055a1LU
52*7688df22SAndroid Build Coastguard Worker 
53*7688df22SAndroid Build Coastguard Worker #define SL_RANDOM_DECL        static void *state = NULL
54*7688df22SAndroid Build Coastguard Worker #define SL_RANDOM_INIT(seed)  if (!state) state = drmRandomCreate(seed)
55*7688df22SAndroid Build Coastguard Worker #define SL_RANDOM             drmRandom(state)
56*7688df22SAndroid Build Coastguard Worker 
57*7688df22SAndroid Build Coastguard Worker typedef struct SLEntry {
58*7688df22SAndroid Build Coastguard Worker     unsigned long     magic;	   /* SL_ENTRY_MAGIC */
59*7688df22SAndroid Build Coastguard Worker     unsigned long     key;
60*7688df22SAndroid Build Coastguard Worker     void              *value;
61*7688df22SAndroid Build Coastguard Worker     int               levels;
62*7688df22SAndroid Build Coastguard Worker     struct SLEntry    *forward[1]; /* variable sized array */
63*7688df22SAndroid Build Coastguard Worker } SLEntry, *SLEntryPtr;
64*7688df22SAndroid Build Coastguard Worker 
65*7688df22SAndroid Build Coastguard Worker typedef struct SkipList {
66*7688df22SAndroid Build Coastguard Worker     unsigned long    magic;	/* SL_LIST_MAGIC */
67*7688df22SAndroid Build Coastguard Worker     int              level;
68*7688df22SAndroid Build Coastguard Worker     int              count;
69*7688df22SAndroid Build Coastguard Worker     SLEntryPtr       head;
70*7688df22SAndroid Build Coastguard Worker     SLEntryPtr       p0;	/* Position for iteration */
71*7688df22SAndroid Build Coastguard Worker } SkipList, *SkipListPtr;
72*7688df22SAndroid Build Coastguard Worker 
SLCreateEntry(int max_level,unsigned long key,void * value)73*7688df22SAndroid Build Coastguard Worker static SLEntryPtr SLCreateEntry(int max_level, unsigned long key, void *value)
74*7688df22SAndroid Build Coastguard Worker {
75*7688df22SAndroid Build Coastguard Worker     SLEntryPtr entry;
76*7688df22SAndroid Build Coastguard Worker 
77*7688df22SAndroid Build Coastguard Worker     if (max_level < 0 || max_level > SL_MAX_LEVEL) max_level = SL_MAX_LEVEL;
78*7688df22SAndroid Build Coastguard Worker 
79*7688df22SAndroid Build Coastguard Worker     entry         = drmMalloc(sizeof(*entry)
80*7688df22SAndroid Build Coastguard Worker 			     + (max_level + 1) * sizeof(entry->forward[0]));
81*7688df22SAndroid Build Coastguard Worker     if (!entry) return NULL;
82*7688df22SAndroid Build Coastguard Worker     entry->magic  = SL_ENTRY_MAGIC;
83*7688df22SAndroid Build Coastguard Worker     entry->key    = key;
84*7688df22SAndroid Build Coastguard Worker     entry->value  = value;
85*7688df22SAndroid Build Coastguard Worker     entry->levels = max_level + 1;
86*7688df22SAndroid Build Coastguard Worker 
87*7688df22SAndroid Build Coastguard Worker     return entry;
88*7688df22SAndroid Build Coastguard Worker }
89*7688df22SAndroid Build Coastguard Worker 
SLRandomLevel(void)90*7688df22SAndroid Build Coastguard Worker static int SLRandomLevel(void)
91*7688df22SAndroid Build Coastguard Worker {
92*7688df22SAndroid Build Coastguard Worker     int level = 1;
93*7688df22SAndroid Build Coastguard Worker     SL_RANDOM_DECL;
94*7688df22SAndroid Build Coastguard Worker 
95*7688df22SAndroid Build Coastguard Worker     SL_RANDOM_INIT(SL_RANDOM_SEED);
96*7688df22SAndroid Build Coastguard Worker 
97*7688df22SAndroid Build Coastguard Worker     while ((SL_RANDOM & 0x01) && level < SL_MAX_LEVEL) ++level;
98*7688df22SAndroid Build Coastguard Worker     return level;
99*7688df22SAndroid Build Coastguard Worker }
100*7688df22SAndroid Build Coastguard Worker 
drmSLCreate(void)101*7688df22SAndroid Build Coastguard Worker drm_public void *drmSLCreate(void)
102*7688df22SAndroid Build Coastguard Worker {
103*7688df22SAndroid Build Coastguard Worker     SkipListPtr  list;
104*7688df22SAndroid Build Coastguard Worker     int          i;
105*7688df22SAndroid Build Coastguard Worker 
106*7688df22SAndroid Build Coastguard Worker     list           = drmMalloc(sizeof(*list));
107*7688df22SAndroid Build Coastguard Worker     if (!list) return NULL;
108*7688df22SAndroid Build Coastguard Worker     list->magic    = SL_LIST_MAGIC;
109*7688df22SAndroid Build Coastguard Worker     list->level    = 0;
110*7688df22SAndroid Build Coastguard Worker     list->head     = SLCreateEntry(SL_MAX_LEVEL, 0, NULL);
111*7688df22SAndroid Build Coastguard Worker     list->count    = 0;
112*7688df22SAndroid Build Coastguard Worker 
113*7688df22SAndroid Build Coastguard Worker     for (i = 0; i <= SL_MAX_LEVEL; i++) list->head->forward[i] = NULL;
114*7688df22SAndroid Build Coastguard Worker 
115*7688df22SAndroid Build Coastguard Worker     return list;
116*7688df22SAndroid Build Coastguard Worker }
117*7688df22SAndroid Build Coastguard Worker 
drmSLDestroy(void * l)118*7688df22SAndroid Build Coastguard Worker drm_public int drmSLDestroy(void *l)
119*7688df22SAndroid Build Coastguard Worker {
120*7688df22SAndroid Build Coastguard Worker     SkipListPtr   list  = (SkipListPtr)l;
121*7688df22SAndroid Build Coastguard Worker     SLEntryPtr    entry;
122*7688df22SAndroid Build Coastguard Worker     SLEntryPtr    next;
123*7688df22SAndroid Build Coastguard Worker 
124*7688df22SAndroid Build Coastguard Worker     if (list->magic != SL_LIST_MAGIC) return -1; /* Bad magic */
125*7688df22SAndroid Build Coastguard Worker 
126*7688df22SAndroid Build Coastguard Worker     for (entry = list->head; entry; entry = next) {
127*7688df22SAndroid Build Coastguard Worker 	if (entry->magic != SL_ENTRY_MAGIC) return -1; /* Bad magic */
128*7688df22SAndroid Build Coastguard Worker 	next         = entry->forward[0];
129*7688df22SAndroid Build Coastguard Worker 	entry->magic = SL_FREED_MAGIC;
130*7688df22SAndroid Build Coastguard Worker 	drmFree(entry);
131*7688df22SAndroid Build Coastguard Worker     }
132*7688df22SAndroid Build Coastguard Worker 
133*7688df22SAndroid Build Coastguard Worker     list->magic = SL_FREED_MAGIC;
134*7688df22SAndroid Build Coastguard Worker     drmFree(list);
135*7688df22SAndroid Build Coastguard Worker     return 0;
136*7688df22SAndroid Build Coastguard Worker }
137*7688df22SAndroid Build Coastguard Worker 
SLLocate(void * l,unsigned long key,SLEntryPtr * update)138*7688df22SAndroid Build Coastguard Worker static SLEntryPtr SLLocate(void *l, unsigned long key, SLEntryPtr *update)
139*7688df22SAndroid Build Coastguard Worker {
140*7688df22SAndroid Build Coastguard Worker     SkipListPtr   list  = (SkipListPtr)l;
141*7688df22SAndroid Build Coastguard Worker     SLEntryPtr    entry;
142*7688df22SAndroid Build Coastguard Worker     int           i;
143*7688df22SAndroid Build Coastguard Worker 
144*7688df22SAndroid Build Coastguard Worker     if (list->magic != SL_LIST_MAGIC) return NULL;
145*7688df22SAndroid Build Coastguard Worker 
146*7688df22SAndroid Build Coastguard Worker     for (i = list->level, entry = list->head; i >= 0; i--) {
147*7688df22SAndroid Build Coastguard Worker 	while (entry->forward[i] && entry->forward[i]->key < key)
148*7688df22SAndroid Build Coastguard Worker 	    entry = entry->forward[i];
149*7688df22SAndroid Build Coastguard Worker 	update[i] = entry;
150*7688df22SAndroid Build Coastguard Worker     }
151*7688df22SAndroid Build Coastguard Worker 
152*7688df22SAndroid Build Coastguard Worker     return entry->forward[0];
153*7688df22SAndroid Build Coastguard Worker }
154*7688df22SAndroid Build Coastguard Worker 
drmSLInsert(void * l,unsigned long key,void * value)155*7688df22SAndroid Build Coastguard Worker drm_public int drmSLInsert(void *l, unsigned long key, void *value)
156*7688df22SAndroid Build Coastguard Worker {
157*7688df22SAndroid Build Coastguard Worker     SkipListPtr   list  = (SkipListPtr)l;
158*7688df22SAndroid Build Coastguard Worker     SLEntryPtr    entry;
159*7688df22SAndroid Build Coastguard Worker     SLEntryPtr    update[SL_MAX_LEVEL + 1];
160*7688df22SAndroid Build Coastguard Worker     int           level;
161*7688df22SAndroid Build Coastguard Worker     int           i;
162*7688df22SAndroid Build Coastguard Worker 
163*7688df22SAndroid Build Coastguard Worker     if (list->magic != SL_LIST_MAGIC) return -1; /* Bad magic */
164*7688df22SAndroid Build Coastguard Worker 
165*7688df22SAndroid Build Coastguard Worker     entry = SLLocate(list, key, update);
166*7688df22SAndroid Build Coastguard Worker 
167*7688df22SAndroid Build Coastguard Worker     if (entry && entry->key == key) return 1; /* Already in list */
168*7688df22SAndroid Build Coastguard Worker 
169*7688df22SAndroid Build Coastguard Worker 
170*7688df22SAndroid Build Coastguard Worker     level = SLRandomLevel();
171*7688df22SAndroid Build Coastguard Worker     if (level > list->level) {
172*7688df22SAndroid Build Coastguard Worker 	level = ++list->level;
173*7688df22SAndroid Build Coastguard Worker 	update[level] = list->head;
174*7688df22SAndroid Build Coastguard Worker     }
175*7688df22SAndroid Build Coastguard Worker 
176*7688df22SAndroid Build Coastguard Worker     entry = SLCreateEntry(level, key, value);
177*7688df22SAndroid Build Coastguard Worker 
178*7688df22SAndroid Build Coastguard Worker 				/* Fix up forward pointers */
179*7688df22SAndroid Build Coastguard Worker     for (i = 0; i <= level; i++) {
180*7688df22SAndroid Build Coastguard Worker 	entry->forward[i]     = update[i]->forward[i];
181*7688df22SAndroid Build Coastguard Worker 	update[i]->forward[i] = entry;
182*7688df22SAndroid Build Coastguard Worker     }
183*7688df22SAndroid Build Coastguard Worker 
184*7688df22SAndroid Build Coastguard Worker     ++list->count;
185*7688df22SAndroid Build Coastguard Worker     return 0;			/* Added to table */
186*7688df22SAndroid Build Coastguard Worker }
187*7688df22SAndroid Build Coastguard Worker 
drmSLDelete(void * l,unsigned long key)188*7688df22SAndroid Build Coastguard Worker drm_public int drmSLDelete(void *l, unsigned long key)
189*7688df22SAndroid Build Coastguard Worker {
190*7688df22SAndroid Build Coastguard Worker     SkipListPtr   list = (SkipListPtr)l;
191*7688df22SAndroid Build Coastguard Worker     SLEntryPtr    update[SL_MAX_LEVEL + 1];
192*7688df22SAndroid Build Coastguard Worker     SLEntryPtr    entry;
193*7688df22SAndroid Build Coastguard Worker     int           i;
194*7688df22SAndroid Build Coastguard Worker 
195*7688df22SAndroid Build Coastguard Worker     if (list->magic != SL_LIST_MAGIC) return -1; /* Bad magic */
196*7688df22SAndroid Build Coastguard Worker 
197*7688df22SAndroid Build Coastguard Worker     entry = SLLocate(list, key, update);
198*7688df22SAndroid Build Coastguard Worker 
199*7688df22SAndroid Build Coastguard Worker     if (!entry || entry->key != key) return 1; /* Not found */
200*7688df22SAndroid Build Coastguard Worker 
201*7688df22SAndroid Build Coastguard Worker 				/* Fix up forward pointers */
202*7688df22SAndroid Build Coastguard Worker     for (i = 0; i <= list->level; i++) {
203*7688df22SAndroid Build Coastguard Worker 	if (update[i]->forward[i] == entry)
204*7688df22SAndroid Build Coastguard Worker 	    update[i]->forward[i] = entry->forward[i];
205*7688df22SAndroid Build Coastguard Worker     }
206*7688df22SAndroid Build Coastguard Worker 
207*7688df22SAndroid Build Coastguard Worker     entry->magic = SL_FREED_MAGIC;
208*7688df22SAndroid Build Coastguard Worker     drmFree(entry);
209*7688df22SAndroid Build Coastguard Worker 
210*7688df22SAndroid Build Coastguard Worker     while (list->level && !list->head->forward[list->level]) --list->level;
211*7688df22SAndroid Build Coastguard Worker     --list->count;
212*7688df22SAndroid Build Coastguard Worker     return 0;
213*7688df22SAndroid Build Coastguard Worker }
214*7688df22SAndroid Build Coastguard Worker 
drmSLLookup(void * l,unsigned long key,void ** value)215*7688df22SAndroid Build Coastguard Worker drm_public int drmSLLookup(void *l, unsigned long key, void **value)
216*7688df22SAndroid Build Coastguard Worker {
217*7688df22SAndroid Build Coastguard Worker     SkipListPtr   list = (SkipListPtr)l;
218*7688df22SAndroid Build Coastguard Worker     SLEntryPtr    update[SL_MAX_LEVEL + 1];
219*7688df22SAndroid Build Coastguard Worker     SLEntryPtr    entry;
220*7688df22SAndroid Build Coastguard Worker 
221*7688df22SAndroid Build Coastguard Worker     entry = SLLocate(list, key, update);
222*7688df22SAndroid Build Coastguard Worker 
223*7688df22SAndroid Build Coastguard Worker     if (entry && entry->key == key) {
224*7688df22SAndroid Build Coastguard Worker 	*value = entry;
225*7688df22SAndroid Build Coastguard Worker 	return 0;
226*7688df22SAndroid Build Coastguard Worker     }
227*7688df22SAndroid Build Coastguard Worker     *value = NULL;
228*7688df22SAndroid Build Coastguard Worker     return -1;
229*7688df22SAndroid Build Coastguard Worker }
230*7688df22SAndroid Build Coastguard Worker 
drmSLLookupNeighbors(void * l,unsigned long key,unsigned long * prev_key,void ** prev_value,unsigned long * next_key,void ** next_value)231*7688df22SAndroid Build Coastguard Worker drm_public int drmSLLookupNeighbors(void *l, unsigned long key,
232*7688df22SAndroid Build Coastguard Worker                                     unsigned long *prev_key, void **prev_value,
233*7688df22SAndroid Build Coastguard Worker                                     unsigned long *next_key, void **next_value)
234*7688df22SAndroid Build Coastguard Worker {
235*7688df22SAndroid Build Coastguard Worker     SkipListPtr   list = (SkipListPtr)l;
236*7688df22SAndroid Build Coastguard Worker     SLEntryPtr    update[SL_MAX_LEVEL + 1] = {0};
237*7688df22SAndroid Build Coastguard Worker     int           retcode = 0;
238*7688df22SAndroid Build Coastguard Worker 
239*7688df22SAndroid Build Coastguard Worker     SLLocate(list, key, update);
240*7688df22SAndroid Build Coastguard Worker 
241*7688df22SAndroid Build Coastguard Worker     *prev_key   = *next_key   = key;
242*7688df22SAndroid Build Coastguard Worker     *prev_value = *next_value = NULL;
243*7688df22SAndroid Build Coastguard Worker 
244*7688df22SAndroid Build Coastguard Worker     if (update[0]) {
245*7688df22SAndroid Build Coastguard Worker 	*prev_key   = update[0]->key;
246*7688df22SAndroid Build Coastguard Worker 	*prev_value = update[0]->value;
247*7688df22SAndroid Build Coastguard Worker 	++retcode;
248*7688df22SAndroid Build Coastguard Worker 	if (update[0]->forward[0]) {
249*7688df22SAndroid Build Coastguard Worker 	    *next_key   = update[0]->forward[0]->key;
250*7688df22SAndroid Build Coastguard Worker 	    *next_value = update[0]->forward[0]->value;
251*7688df22SAndroid Build Coastguard Worker 	    ++retcode;
252*7688df22SAndroid Build Coastguard Worker 	}
253*7688df22SAndroid Build Coastguard Worker     }
254*7688df22SAndroid Build Coastguard Worker     return retcode;
255*7688df22SAndroid Build Coastguard Worker }
256*7688df22SAndroid Build Coastguard Worker 
drmSLNext(void * l,unsigned long * key,void ** value)257*7688df22SAndroid Build Coastguard Worker drm_public int drmSLNext(void *l, unsigned long *key, void **value)
258*7688df22SAndroid Build Coastguard Worker {
259*7688df22SAndroid Build Coastguard Worker     SkipListPtr   list = (SkipListPtr)l;
260*7688df22SAndroid Build Coastguard Worker     SLEntryPtr    entry;
261*7688df22SAndroid Build Coastguard Worker 
262*7688df22SAndroid Build Coastguard Worker     if (list->magic != SL_LIST_MAGIC) return -1; /* Bad magic */
263*7688df22SAndroid Build Coastguard Worker 
264*7688df22SAndroid Build Coastguard Worker     entry    = list->p0;
265*7688df22SAndroid Build Coastguard Worker 
266*7688df22SAndroid Build Coastguard Worker     if (entry) {
267*7688df22SAndroid Build Coastguard Worker 	list->p0 = entry->forward[0];
268*7688df22SAndroid Build Coastguard Worker 	*key     = entry->key;
269*7688df22SAndroid Build Coastguard Worker 	*value   = entry->value;
270*7688df22SAndroid Build Coastguard Worker 	return 1;
271*7688df22SAndroid Build Coastguard Worker     }
272*7688df22SAndroid Build Coastguard Worker     list->p0 = NULL;
273*7688df22SAndroid Build Coastguard Worker     return 0;
274*7688df22SAndroid Build Coastguard Worker }
275*7688df22SAndroid Build Coastguard Worker 
drmSLFirst(void * l,unsigned long * key,void ** value)276*7688df22SAndroid Build Coastguard Worker drm_public int drmSLFirst(void *l, unsigned long *key, void **value)
277*7688df22SAndroid Build Coastguard Worker {
278*7688df22SAndroid Build Coastguard Worker     SkipListPtr   list = (SkipListPtr)l;
279*7688df22SAndroid Build Coastguard Worker 
280*7688df22SAndroid Build Coastguard Worker     if (list->magic != SL_LIST_MAGIC) return -1; /* Bad magic */
281*7688df22SAndroid Build Coastguard Worker 
282*7688df22SAndroid Build Coastguard Worker     list->p0 = list->head->forward[0];
283*7688df22SAndroid Build Coastguard Worker     return drmSLNext(list, key, value);
284*7688df22SAndroid Build Coastguard Worker }
285*7688df22SAndroid Build Coastguard Worker 
286*7688df22SAndroid Build Coastguard Worker /* Dump internal data structures for debugging. */
drmSLDump(void * l)287*7688df22SAndroid Build Coastguard Worker drm_public void drmSLDump(void *l)
288*7688df22SAndroid Build Coastguard Worker {
289*7688df22SAndroid Build Coastguard Worker     SkipListPtr   list = (SkipListPtr)l;
290*7688df22SAndroid Build Coastguard Worker     SLEntryPtr    entry;
291*7688df22SAndroid Build Coastguard Worker     int           i;
292*7688df22SAndroid Build Coastguard Worker 
293*7688df22SAndroid Build Coastguard Worker     if (list->magic != SL_LIST_MAGIC) {
294*7688df22SAndroid Build Coastguard Worker 	printf("Bad magic: 0x%08lx (expected 0x%08lx)\n",
295*7688df22SAndroid Build Coastguard Worker 	       list->magic, SL_LIST_MAGIC);
296*7688df22SAndroid Build Coastguard Worker 	return;
297*7688df22SAndroid Build Coastguard Worker     }
298*7688df22SAndroid Build Coastguard Worker 
299*7688df22SAndroid Build Coastguard Worker     printf("Level = %d, count = %d\n", list->level, list->count);
300*7688df22SAndroid Build Coastguard Worker     for (entry = list->head; entry; entry = entry->forward[0]) {
301*7688df22SAndroid Build Coastguard Worker 	if (entry->magic != SL_ENTRY_MAGIC) {
302*7688df22SAndroid Build Coastguard Worker 	    printf("Bad magic: 0x%08lx (expected 0x%08lx)\n",
303*7688df22SAndroid Build Coastguard Worker 		   list->magic, SL_ENTRY_MAGIC);
304*7688df22SAndroid Build Coastguard Worker 	}
305*7688df22SAndroid Build Coastguard Worker 	printf("\nEntry %p <0x%08lx, %p> has %2d levels\n",
306*7688df22SAndroid Build Coastguard Worker 	       entry, entry->key, entry->value, entry->levels);
307*7688df22SAndroid Build Coastguard Worker 	for (i = 0; i < entry->levels; i++) {
308*7688df22SAndroid Build Coastguard Worker 	    if (entry->forward[i]) {
309*7688df22SAndroid Build Coastguard Worker 		printf("   %2d: %p <0x%08lx, %p>\n",
310*7688df22SAndroid Build Coastguard Worker 		       i,
311*7688df22SAndroid Build Coastguard Worker 		       entry->forward[i],
312*7688df22SAndroid Build Coastguard Worker 		       entry->forward[i]->key,
313*7688df22SAndroid Build Coastguard Worker 		       entry->forward[i]->value);
314*7688df22SAndroid Build Coastguard Worker 	    } else {
315*7688df22SAndroid Build Coastguard Worker 		printf("   %2d: %p\n", i, entry->forward[i]);
316*7688df22SAndroid Build Coastguard Worker 	    }
317*7688df22SAndroid Build Coastguard Worker 	}
318*7688df22SAndroid Build Coastguard Worker     }
319*7688df22SAndroid Build Coastguard Worker }
320