ViewVC Help
View File | Revision Log | Show Annotations | Download File | Root Listing
root/radiance/ray/src/hd/sm_list.c
Revision: 3.8
Committed: Sat Feb 22 02:07:25 2003 UTC (21 years, 2 months ago) by greg
Content type: text/plain
Branch: MAIN
CVS Tags: rad3R6P1, rad3R5, rad3R6
Changes since 3.7: +1 -4 lines
Log Message:
Changes and check-in for 3.5 release
Includes new source files and modifications not recorded for many years
See ray/doc/notes/ReleaseNotes for notes between 3.1 and 3.5 release

File Contents

# Content
1 #ifndef lint
2 static const char RCSid[] = "$Id$";
3 #endif
4 /*
5 * sm_list.c
6 * Routines for handling linked generic linked lists, stack, and
7 * circular lists. Data element is an int (can be cast to hold
8 * pointer to more general data element)
9 */
10
11 #include "standard.h"
12 #include "sm_list.h"
13
14 /* List of available edges */
15 static LIST *free_lists = NULL;
16 #ifdef DEBUG
17 extern int Malloc_cnt;
18 #endif
19 LIST
20 /* NOTE: Memory is not initialized */
21 *new_list()
22 {
23 LIST *l;
24
25 /* check free list for available edges */
26 if( free_lists )
27 {
28 l = free_lists;
29 free_lists = LIST_NEXT(free_lists);
30 }
31 /* if no free edges- allocate the memory */
32 else
33 {
34 if( !(l = (LIST *)malloc(sizeof(LIST))))
35 error(SYSTEM,"new_list():Unable to allocate memory");
36 }
37 return(l);
38 }
39
40
41 /* attaches list a at the end of list b */
42 LIST
43 *append_list(a,b)
44 LIST *a,*b;
45 {
46 LIST * l;
47
48 if(!b)
49 return(a);
50
51 l = b;
52 while(LIST_NEXT(l) && LIST_NEXT(l) != b)
53 l = LIST_NEXT(l);
54
55 SET_LIST_NEXT(l,a);
56
57 return(b);
58 }
59
60 /* attaches list a at the end of list b */
61 LIST
62 *add_data(l,d,end)
63 LIST *l;
64 int d;
65 LIST **end;
66
67 {
68 LIST *list,*lptr;
69
70 list = new_list();
71 SET_LIST_DATA(list,d);
72 SET_LIST_NEXT(list,NULL);
73 if(!l)
74 {
75 if(end)
76 *end = list;
77 return(list);
78 }
79 if(end)
80 lptr = *end;
81 else
82 {
83 lptr = l;
84 while(LIST_NEXT(lptr))
85 lptr = LIST_NEXT(lptr);
86 }
87 LIST_NEXT(lptr) = list;
88 if(end)
89 *end = list;
90
91 return(l);
92 }
93
94 /* Adds data to the end of a circular list. If set, "end"
95 * is a pointer to the last element in the list
96 */
97 LIST
98 *add_data_to_circular_list(l,end,d)
99 LIST *l,**end;
100 int d;
101 {
102 LIST *list;
103
104 list = new_list();
105 SET_LIST_DATA(list,d);
106
107 if(!l)
108 l = list;
109 else
110 {
111 if(*end)
112 SET_LIST_NEXT(*end,list);
113 else
114 l = append_list(list,l);
115 }
116
117 *end = list;
118 SET_LIST_NEXT(list,l);
119 return(l);
120 }
121
122
123
124 /* frees the list */
125 LIST
126 *free_list(l)
127 LIST * l;
128 {
129 if(!l)
130 return(NULL);
131
132 free_lists = append_list(free_lists,l);
133
134 return(NULL);
135 }
136
137 /* Pushes data element d at the top of the list- returns pointer
138 to new top of list
139 */
140 LIST
141 *push_data(l,d)
142 LIST *l;
143 int d;
144 {
145 LIST *list;
146
147 list = new_list();
148 SET_LIST_DATA(list,d);
149 SET_LIST_NEXT(list,l);
150 return(list);
151 }
152 /* Returns data element d at the top of the list- returns pointer
153 to new top of list
154 */
155 int
156 pop_list(l)
157 LIST **l;
158 {
159 LIST *p;
160 int d;
161
162 if(!l)
163 return(NULL);
164 if(!(p = *l))
165 return(NULL);
166
167 d = LIST_DATA(p);
168
169 *l = LIST_NEXT(p);
170
171 LIST_NEXT(p) =NULL;
172 free_list(p);
173
174 return(d);
175 }
176
177 /* Search through list for data element "d", and remove from
178 * list: Returns TRUE if found, false otherwise
179 */
180 int
181 remove_from_list(d,list)
182 int d;
183 LIST **list;
184 {
185 LIST *l,*prev;
186
187 l = *list;
188 prev = NULL;
189
190 while(l)
191 {
192 if(LIST_DATA(l) == d)
193 {
194 if(l == *list)
195 *list = LIST_NEXT(*list);
196 else
197 SET_LIST_NEXT(prev,LIST_NEXT(l));
198
199 SET_LIST_NEXT(l,NULL);
200 free_list(l);
201 return(TRUE);
202 }
203 prev = l;
204 l = LIST_NEXT(l);
205 }
206 return(FALSE);
207 }
208
209
210
211
212
213
214
215
216
217
218
219
220
221