File: | nsprpub/pr/src/io/prlayer.c |
Location: | line 151, column 5 |
Description: | Access to field 'lower' results in a dereference of a null pointer (loaded from variable 'fd') |
1 | /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 2 -*- */ | |||||
2 | /* This Source Code Form is subject to the terms of the Mozilla Public | |||||
3 | * License, v. 2.0. If a copy of the MPL was not distributed with this | |||||
4 | * file, You can obtain one at http://mozilla.org/MPL/2.0/. */ | |||||
5 | ||||||
6 | /* | |||||
7 | ** File: prlayer.c | |||||
8 | ** Description: Routines for handling pushable protocol modules on sockets. | |||||
9 | */ | |||||
10 | ||||||
11 | #include "primpl.h" | |||||
12 | #include "prerror.h" | |||||
13 | #include "prmem.h" | |||||
14 | #include "prlock.h" | |||||
15 | #include "prlog.h" | |||||
16 | #include "prio.h" | |||||
17 | ||||||
18 | #include <string.h> /* for memset() */ | |||||
19 | static PRStatus _PR_DestroyIOLayer(PRFileDesc *stack); | |||||
20 | ||||||
21 | void PR_CALLBACK pl_FDDestructor(PRFileDesc *fd) | |||||
22 | { | |||||
23 | PR_ASSERT(fd != NULL)((fd != ((void*)0))?((void)0):PR_Assert("fd != NULL","/home/sylvestre/dev/mozilla/ff/firefox.hg/nsprpub/pr/src/io/prlayer.c" ,23)); | |||||
24 | if (NULL((void*)0) != fd->lower) fd->lower->higher = fd->higher; | |||||
25 | if (NULL((void*)0) != fd->higher) fd->higher->lower = fd->lower; | |||||
26 | PR_DELETE(fd){ PR_Free(fd); (fd) = ((void*)0); }; | |||||
27 | } | |||||
28 | ||||||
29 | /* | |||||
30 | ** Default methods that just call down to the next fd. | |||||
31 | */ | |||||
32 | static PRStatus PR_CALLBACK pl_TopClose (PRFileDesc *fd) | |||||
33 | { | |||||
34 | PRFileDesc *top, *lower; | |||||
35 | PRStatus rv; | |||||
36 | ||||||
37 | PR_ASSERT(fd != NULL)((fd != ((void*)0))?((void)0):PR_Assert("fd != NULL","/home/sylvestre/dev/mozilla/ff/firefox.hg/nsprpub/pr/src/io/prlayer.c" ,37)); | |||||
38 | PR_ASSERT(fd->lower != NULL)((fd->lower != ((void*)0))?((void)0):PR_Assert("fd->lower != NULL" ,"/home/sylvestre/dev/mozilla/ff/firefox.hg/nsprpub/pr/src/io/prlayer.c" ,38)); | |||||
39 | PR_ASSERT(fd->secret == NULL)((fd->secret == ((void*)0))?((void)0):PR_Assert("fd->secret == NULL" ,"/home/sylvestre/dev/mozilla/ff/firefox.hg/nsprpub/pr/src/io/prlayer.c" ,39)); | |||||
40 | PR_ASSERT(fd->methods->file_type == PR_DESC_LAYERED)((fd->methods->file_type == PR_DESC_LAYERED)?((void)0): PR_Assert("fd->methods->file_type == PR_DESC_LAYERED","/home/sylvestre/dev/mozilla/ff/firefox.hg/nsprpub/pr/src/io/prlayer.c" ,40)); | |||||
41 | ||||||
42 | if (PR_IO_LAYER_HEAD(PRDescIdentity)-3 == fd->identity) { | |||||
43 | /* | |||||
44 | * new style stack; close all the layers, before deleting the | |||||
45 | * stack head | |||||
46 | */ | |||||
47 | rv = fd->lower->methods->close(fd->lower); | |||||
48 | _PR_DestroyIOLayer(fd); | |||||
49 | return rv; | |||||
50 | } else if ((fd->higher) && (PR_IO_LAYER_HEAD(PRDescIdentity)-3 == fd->higher->identity)) { | |||||
51 | /* | |||||
52 | * lower layers of new style stack | |||||
53 | */ | |||||
54 | lower = fd->lower; | |||||
55 | /* | |||||
56 | * pop and cleanup current layer | |||||
57 | */ | |||||
58 | top = PR_PopIOLayer(fd->higher, PR_TOP_IO_LAYER(PRDescIdentity)-2); | |||||
59 | top->dtor(top); | |||||
60 | /* | |||||
61 | * then call lower layer | |||||
62 | */ | |||||
63 | return (lower->methods->close(lower)); | |||||
64 | } else { | |||||
65 | /* old style stack */ | |||||
66 | top = PR_PopIOLayer(fd, PR_TOP_IO_LAYER(PRDescIdentity)-2); | |||||
67 | top->dtor(top); | |||||
68 | return (fd->methods->close)(fd); | |||||
69 | } | |||||
70 | } | |||||
71 | ||||||
72 | static PRInt32 PR_CALLBACK pl_DefRead (PRFileDesc *fd, void *buf, PRInt32 amount) | |||||
73 | { | |||||
74 | PR_ASSERT(fd != NULL)((fd != ((void*)0))?((void)0):PR_Assert("fd != NULL","/home/sylvestre/dev/mozilla/ff/firefox.hg/nsprpub/pr/src/io/prlayer.c" ,74)); | |||||
75 | PR_ASSERT(fd->lower != NULL)((fd->lower != ((void*)0))?((void)0):PR_Assert("fd->lower != NULL" ,"/home/sylvestre/dev/mozilla/ff/firefox.hg/nsprpub/pr/src/io/prlayer.c" ,75)); | |||||
76 | ||||||
77 | return (fd->lower->methods->read)(fd->lower, buf, amount); | |||||
78 | } | |||||
79 | ||||||
80 | static PRInt32 PR_CALLBACK pl_DefWrite ( | |||||
81 | PRFileDesc *fd, const void *buf, PRInt32 amount) | |||||
82 | { | |||||
83 | PR_ASSERT(fd != NULL)((fd != ((void*)0))?((void)0):PR_Assert("fd != NULL","/home/sylvestre/dev/mozilla/ff/firefox.hg/nsprpub/pr/src/io/prlayer.c" ,83)); | |||||
84 | PR_ASSERT(fd->lower != NULL)((fd->lower != ((void*)0))?((void)0):PR_Assert("fd->lower != NULL" ,"/home/sylvestre/dev/mozilla/ff/firefox.hg/nsprpub/pr/src/io/prlayer.c" ,84)); | |||||
85 | ||||||
86 | return (fd->lower->methods->write)(fd->lower, buf, amount); | |||||
87 | } | |||||
88 | ||||||
89 | static PRInt32 PR_CALLBACK pl_DefAvailable (PRFileDesc *fd) | |||||
90 | { | |||||
91 | PR_ASSERT(fd != NULL)((fd != ((void*)0))?((void)0):PR_Assert("fd != NULL","/home/sylvestre/dev/mozilla/ff/firefox.hg/nsprpub/pr/src/io/prlayer.c" ,91)); | |||||
92 | PR_ASSERT(fd->lower != NULL)((fd->lower != ((void*)0))?((void)0):PR_Assert("fd->lower != NULL" ,"/home/sylvestre/dev/mozilla/ff/firefox.hg/nsprpub/pr/src/io/prlayer.c" ,92)); | |||||
93 | ||||||
94 | return (fd->lower->methods->available)(fd->lower); | |||||
95 | } | |||||
96 | ||||||
97 | static PRInt64 PR_CALLBACK pl_DefAvailable64 (PRFileDesc *fd) | |||||
98 | { | |||||
99 | PR_ASSERT(fd != NULL)((fd != ((void*)0))?((void)0):PR_Assert("fd != NULL","/home/sylvestre/dev/mozilla/ff/firefox.hg/nsprpub/pr/src/io/prlayer.c" ,99)); | |||||
100 | PR_ASSERT(fd->lower != NULL)((fd->lower != ((void*)0))?((void)0):PR_Assert("fd->lower != NULL" ,"/home/sylvestre/dev/mozilla/ff/firefox.hg/nsprpub/pr/src/io/prlayer.c" ,100)); | |||||
101 | ||||||
102 | return (fd->lower->methods->available64)(fd->lower); | |||||
103 | } | |||||
104 | ||||||
105 | static PRStatus PR_CALLBACK pl_DefFsync (PRFileDesc *fd) | |||||
106 | { | |||||
107 | PR_ASSERT(fd != NULL)((fd != ((void*)0))?((void)0):PR_Assert("fd != NULL","/home/sylvestre/dev/mozilla/ff/firefox.hg/nsprpub/pr/src/io/prlayer.c" ,107)); | |||||
108 | PR_ASSERT(fd->lower != NULL)((fd->lower != ((void*)0))?((void)0):PR_Assert("fd->lower != NULL" ,"/home/sylvestre/dev/mozilla/ff/firefox.hg/nsprpub/pr/src/io/prlayer.c" ,108)); | |||||
109 | ||||||
110 | return (fd->lower->methods->fsync)(fd->lower); | |||||
111 | } | |||||
112 | ||||||
113 | static PRInt32 PR_CALLBACK pl_DefSeek ( | |||||
114 | PRFileDesc *fd, PRInt32 offset, PRSeekWhence how) | |||||
115 | { | |||||
116 | PR_ASSERT(fd != NULL)((fd != ((void*)0))?((void)0):PR_Assert("fd != NULL","/home/sylvestre/dev/mozilla/ff/firefox.hg/nsprpub/pr/src/io/prlayer.c" ,116)); | |||||
117 | PR_ASSERT(fd->lower != NULL)((fd->lower != ((void*)0))?((void)0):PR_Assert("fd->lower != NULL" ,"/home/sylvestre/dev/mozilla/ff/firefox.hg/nsprpub/pr/src/io/prlayer.c" ,117)); | |||||
118 | ||||||
119 | return (fd->lower->methods->seek)(fd->lower, offset, how); | |||||
120 | } | |||||
121 | ||||||
122 | static PRInt64 PR_CALLBACK pl_DefSeek64 ( | |||||
123 | PRFileDesc *fd, PRInt64 offset, PRSeekWhence how) | |||||
124 | { | |||||
125 | PR_ASSERT(fd != NULL)((fd != ((void*)0))?((void)0):PR_Assert("fd != NULL","/home/sylvestre/dev/mozilla/ff/firefox.hg/nsprpub/pr/src/io/prlayer.c" ,125)); | |||||
126 | PR_ASSERT(fd->lower != NULL)((fd->lower != ((void*)0))?((void)0):PR_Assert("fd->lower != NULL" ,"/home/sylvestre/dev/mozilla/ff/firefox.hg/nsprpub/pr/src/io/prlayer.c" ,126)); | |||||
127 | ||||||
128 | return (fd->lower->methods->seek64)(fd->lower, offset, how); | |||||
129 | } | |||||
130 | ||||||
131 | static PRStatus PR_CALLBACK pl_DefFileInfo (PRFileDesc *fd, PRFileInfo *info) | |||||
132 | { | |||||
133 | PR_ASSERT(fd != NULL)((fd != ((void*)0))?((void)0):PR_Assert("fd != NULL","/home/sylvestre/dev/mozilla/ff/firefox.hg/nsprpub/pr/src/io/prlayer.c" ,133)); | |||||
134 | PR_ASSERT(fd->lower != NULL)((fd->lower != ((void*)0))?((void)0):PR_Assert("fd->lower != NULL" ,"/home/sylvestre/dev/mozilla/ff/firefox.hg/nsprpub/pr/src/io/prlayer.c" ,134)); | |||||
135 | ||||||
136 | return (fd->lower->methods->fileInfo)(fd->lower, info); | |||||
137 | } | |||||
138 | ||||||
139 | static PRStatus PR_CALLBACK pl_DefFileInfo64 (PRFileDesc *fd, PRFileInfo64 *info) | |||||
140 | { | |||||
141 | PR_ASSERT(fd != NULL)((fd != ((void*)0))?((void)0):PR_Assert("fd != NULL","/home/sylvestre/dev/mozilla/ff/firefox.hg/nsprpub/pr/src/io/prlayer.c" ,141)); | |||||
142 | PR_ASSERT(fd->lower != NULL)((fd->lower != ((void*)0))?((void)0):PR_Assert("fd->lower != NULL" ,"/home/sylvestre/dev/mozilla/ff/firefox.hg/nsprpub/pr/src/io/prlayer.c" ,142)); | |||||
143 | ||||||
144 | return (fd->lower->methods->fileInfo64)(fd->lower, info); | |||||
145 | } | |||||
146 | ||||||
147 | static PRInt32 PR_CALLBACK pl_DefWritev (PRFileDesc *fd, const PRIOVec *iov, | |||||
148 | PRInt32 size, PRIntervalTime timeout) | |||||
149 | { | |||||
150 | PR_ASSERT(fd != NULL)((fd != ((void*)0))?((void)0):PR_Assert("fd != NULL","/home/sylvestre/dev/mozilla/ff/firefox.hg/nsprpub/pr/src/io/prlayer.c" ,150)); | |||||
| ||||||
151 | PR_ASSERT(fd->lower != NULL)((fd->lower != ((void*)0))?((void)0):PR_Assert("fd->lower != NULL" ,"/home/sylvestre/dev/mozilla/ff/firefox.hg/nsprpub/pr/src/io/prlayer.c" ,151)); | |||||
| ||||||
152 | ||||||
153 | return (fd->lower->methods->writev)(fd->lower, iov, size, timeout); | |||||
154 | } | |||||
155 | ||||||
156 | static PRStatus PR_CALLBACK pl_DefConnect ( | |||||
157 | PRFileDesc *fd, const PRNetAddr *addr, PRIntervalTime timeout) | |||||
158 | { | |||||
159 | PR_ASSERT(fd != NULL)((fd != ((void*)0))?((void)0):PR_Assert("fd != NULL","/home/sylvestre/dev/mozilla/ff/firefox.hg/nsprpub/pr/src/io/prlayer.c" ,159)); | |||||
160 | PR_ASSERT(fd->lower != NULL)((fd->lower != ((void*)0))?((void)0):PR_Assert("fd->lower != NULL" ,"/home/sylvestre/dev/mozilla/ff/firefox.hg/nsprpub/pr/src/io/prlayer.c" ,160)); | |||||
161 | ||||||
162 | return (fd->lower->methods->connect)(fd->lower, addr, timeout); | |||||
163 | } | |||||
164 | ||||||
165 | static PRStatus PR_CALLBACK pl_DefConnectcontinue ( | |||||
166 | PRFileDesc *fd, PRInt16 out_flags) | |||||
167 | { | |||||
168 | PR_ASSERT(fd != NULL)((fd != ((void*)0))?((void)0):PR_Assert("fd != NULL","/home/sylvestre/dev/mozilla/ff/firefox.hg/nsprpub/pr/src/io/prlayer.c" ,168)); | |||||
169 | PR_ASSERT(fd->lower != NULL)((fd->lower != ((void*)0))?((void)0):PR_Assert("fd->lower != NULL" ,"/home/sylvestre/dev/mozilla/ff/firefox.hg/nsprpub/pr/src/io/prlayer.c" ,169)); | |||||
170 | ||||||
171 | return (fd->lower->methods->connectcontinue)(fd->lower, out_flags); | |||||
172 | } | |||||
173 | ||||||
174 | static PRFileDesc* PR_CALLBACK pl_TopAccept ( | |||||
175 | PRFileDesc *fd, PRNetAddr *addr, PRIntervalTime timeout) | |||||
176 | { | |||||
177 | PRStatus rv; | |||||
178 | PRFileDesc *newfd, *layer = fd; | |||||
179 | PRFileDesc *newstack; | |||||
180 | PRBool newstyle_stack = PR_FALSE0; | |||||
181 | ||||||
182 | PR_ASSERT(fd != NULL)((fd != ((void*)0))?((void)0):PR_Assert("fd != NULL","/home/sylvestre/dev/mozilla/ff/firefox.hg/nsprpub/pr/src/io/prlayer.c" ,182)); | |||||
183 | PR_ASSERT(fd->lower != NULL)((fd->lower != ((void*)0))?((void)0):PR_Assert("fd->lower != NULL" ,"/home/sylvestre/dev/mozilla/ff/firefox.hg/nsprpub/pr/src/io/prlayer.c" ,183)); | |||||
184 | ||||||
185 | /* test for new style stack */ | |||||
186 | while (NULL((void*)0) != layer->higher) | |||||
187 | layer = layer->higher; | |||||
188 | newstyle_stack = (PR_IO_LAYER_HEAD(PRDescIdentity)-3 == layer->identity) ? PR_TRUE1 : PR_FALSE0; | |||||
189 | newstack = PR_NEW(PRFileDesc)((PRFileDesc *) (PR_Malloc((sizeof(PRFileDesc))))); | |||||
190 | if (NULL((void*)0) == newstack) | |||||
191 | { | |||||
192 | PR_SetError(PR_OUT_OF_MEMORY_ERROR(-6000L), 0); | |||||
193 | return NULL((void*)0); | |||||
194 | } | |||||
195 | *newstack = *fd; /* make a copy of the accepting layer */ | |||||
196 | ||||||
197 | newfd = (fd->lower->methods->accept)(fd->lower, addr, timeout); | |||||
198 | if (NULL((void*)0) == newfd) | |||||
199 | { | |||||
200 | PR_DELETE(newstack){ PR_Free(newstack); (newstack) = ((void*)0); }; | |||||
201 | return NULL((void*)0); | |||||
202 | } | |||||
203 | ||||||
204 | if (newstyle_stack) { | |||||
205 | newstack->lower = newfd; | |||||
206 | newfd->higher = newstack; | |||||
207 | return newstack; | |||||
208 | } else { | |||||
209 | /* this PR_PushIOLayer call cannot fail */ | |||||
210 | rv = PR_PushIOLayer(newfd, PR_TOP_IO_LAYER(PRDescIdentity)-2, newstack); | |||||
211 | PR_ASSERT(PR_SUCCESS == rv)((PR_SUCCESS == rv)?((void)0):PR_Assert("PR_SUCCESS == rv","/home/sylvestre/dev/mozilla/ff/firefox.hg/nsprpub/pr/src/io/prlayer.c" ,211)); | |||||
212 | return newfd; /* that's it */ | |||||
213 | } | |||||
214 | } | |||||
215 | ||||||
216 | static PRStatus PR_CALLBACK pl_DefBind (PRFileDesc *fd, const PRNetAddr *addr) | |||||
217 | { | |||||
218 | PR_ASSERT(fd != NULL)((fd != ((void*)0))?((void)0):PR_Assert("fd != NULL","/home/sylvestre/dev/mozilla/ff/firefox.hg/nsprpub/pr/src/io/prlayer.c" ,218)); | |||||
219 | PR_ASSERT(fd->lower != NULL)((fd->lower != ((void*)0))?((void)0):PR_Assert("fd->lower != NULL" ,"/home/sylvestre/dev/mozilla/ff/firefox.hg/nsprpub/pr/src/io/prlayer.c" ,219)); | |||||
220 | ||||||
221 | return (fd->lower->methods->bind)(fd->lower, addr); | |||||
222 | } | |||||
223 | ||||||
224 | static PRStatus PR_CALLBACK pl_DefListen (PRFileDesc *fd, PRIntn backlog) | |||||
225 | { | |||||
226 | PR_ASSERT(fd != NULL)((fd != ((void*)0))?((void)0):PR_Assert("fd != NULL","/home/sylvestre/dev/mozilla/ff/firefox.hg/nsprpub/pr/src/io/prlayer.c" ,226)); | |||||
227 | PR_ASSERT(fd->lower != NULL)((fd->lower != ((void*)0))?((void)0):PR_Assert("fd->lower != NULL" ,"/home/sylvestre/dev/mozilla/ff/firefox.hg/nsprpub/pr/src/io/prlayer.c" ,227)); | |||||
228 | ||||||
229 | return (fd->lower->methods->listen)(fd->lower, backlog); | |||||
230 | } | |||||
231 | ||||||
232 | static PRStatus PR_CALLBACK pl_DefShutdown (PRFileDesc *fd, PRIntn how) | |||||
233 | { | |||||
234 | PR_ASSERT(fd != NULL)((fd != ((void*)0))?((void)0):PR_Assert("fd != NULL","/home/sylvestre/dev/mozilla/ff/firefox.hg/nsprpub/pr/src/io/prlayer.c" ,234)); | |||||
235 | PR_ASSERT(fd->lower != NULL)((fd->lower != ((void*)0))?((void)0):PR_Assert("fd->lower != NULL" ,"/home/sylvestre/dev/mozilla/ff/firefox.hg/nsprpub/pr/src/io/prlayer.c" ,235)); | |||||
236 | ||||||
237 | return (fd->lower->methods->shutdown)(fd->lower, how); | |||||
238 | } | |||||
239 | ||||||
240 | static PRInt32 PR_CALLBACK pl_DefRecv ( | |||||
241 | PRFileDesc *fd, void *buf, PRInt32 amount, | |||||
242 | PRIntn flags, PRIntervalTime timeout) | |||||
243 | { | |||||
244 | PR_ASSERT(fd != NULL)((fd != ((void*)0))?((void)0):PR_Assert("fd != NULL","/home/sylvestre/dev/mozilla/ff/firefox.hg/nsprpub/pr/src/io/prlayer.c" ,244)); | |||||
245 | PR_ASSERT(fd->lower != NULL)((fd->lower != ((void*)0))?((void)0):PR_Assert("fd->lower != NULL" ,"/home/sylvestre/dev/mozilla/ff/firefox.hg/nsprpub/pr/src/io/prlayer.c" ,245)); | |||||
246 | ||||||
247 | return (fd->lower->methods->recv)( | |||||
248 | fd->lower, buf, amount, flags, timeout); | |||||
249 | } | |||||
250 | ||||||
251 | static PRInt32 PR_CALLBACK pl_DefSend ( | |||||
252 | PRFileDesc *fd, const void *buf, | |||||
253 | PRInt32 amount, PRIntn flags, PRIntervalTime timeout) | |||||
254 | { | |||||
255 | PR_ASSERT(fd != NULL)((fd != ((void*)0))?((void)0):PR_Assert("fd != NULL","/home/sylvestre/dev/mozilla/ff/firefox.hg/nsprpub/pr/src/io/prlayer.c" ,255)); | |||||
256 | PR_ASSERT(fd->lower != NULL)((fd->lower != ((void*)0))?((void)0):PR_Assert("fd->lower != NULL" ,"/home/sylvestre/dev/mozilla/ff/firefox.hg/nsprpub/pr/src/io/prlayer.c" ,256)); | |||||
257 | ||||||
258 | return (fd->lower->methods->send)(fd->lower, buf, amount, flags, timeout); | |||||
259 | } | |||||
260 | ||||||
261 | static PRInt32 PR_CALLBACK pl_DefRecvfrom ( | |||||
262 | PRFileDesc *fd, void *buf, PRInt32 amount, | |||||
263 | PRIntn flags, PRNetAddr *addr, PRIntervalTime timeout) | |||||
264 | { | |||||
265 | PR_ASSERT(fd != NULL)((fd != ((void*)0))?((void)0):PR_Assert("fd != NULL","/home/sylvestre/dev/mozilla/ff/firefox.hg/nsprpub/pr/src/io/prlayer.c" ,265)); | |||||
266 | PR_ASSERT(fd->lower != NULL)((fd->lower != ((void*)0))?((void)0):PR_Assert("fd->lower != NULL" ,"/home/sylvestre/dev/mozilla/ff/firefox.hg/nsprpub/pr/src/io/prlayer.c" ,266)); | |||||
267 | ||||||
268 | return (fd->lower->methods->recvfrom)( | |||||
269 | fd->lower, buf, amount, flags, addr, timeout); | |||||
270 | } | |||||
271 | ||||||
272 | static PRInt32 PR_CALLBACK pl_DefSendto ( | |||||
273 | PRFileDesc *fd, const void *buf, PRInt32 amount, PRIntn flags, | |||||
274 | const PRNetAddr *addr, PRIntervalTime timeout) | |||||
275 | { | |||||
276 | PR_ASSERT(fd != NULL)((fd != ((void*)0))?((void)0):PR_Assert("fd != NULL","/home/sylvestre/dev/mozilla/ff/firefox.hg/nsprpub/pr/src/io/prlayer.c" ,276)); | |||||
277 | PR_ASSERT(fd->lower != NULL)((fd->lower != ((void*)0))?((void)0):PR_Assert("fd->lower != NULL" ,"/home/sylvestre/dev/mozilla/ff/firefox.hg/nsprpub/pr/src/io/prlayer.c" ,277)); | |||||
278 | ||||||
279 | return (fd->lower->methods->sendto)( | |||||
280 | fd->lower, buf, amount, flags, addr, timeout); | |||||
281 | } | |||||
282 | ||||||
283 | static PRInt16 PR_CALLBACK pl_DefPoll ( | |||||
284 | PRFileDesc *fd, PRInt16 in_flags, PRInt16 *out_flags) | |||||
285 | { | |||||
286 | PR_ASSERT(fd != NULL)((fd != ((void*)0))?((void)0):PR_Assert("fd != NULL","/home/sylvestre/dev/mozilla/ff/firefox.hg/nsprpub/pr/src/io/prlayer.c" ,286)); | |||||
287 | PR_ASSERT(fd->lower != NULL)((fd->lower != ((void*)0))?((void)0):PR_Assert("fd->lower != NULL" ,"/home/sylvestre/dev/mozilla/ff/firefox.hg/nsprpub/pr/src/io/prlayer.c" ,287)); | |||||
288 | ||||||
289 | return (fd->lower->methods->poll)(fd->lower, in_flags, out_flags); | |||||
290 | } | |||||
291 | ||||||
292 | static PRInt32 PR_CALLBACK pl_DefAcceptread ( | |||||
293 | PRFileDesc *sd, PRFileDesc **nd, PRNetAddr **raddr, void *buf, | |||||
294 | PRInt32 amount, PRIntervalTime t) | |||||
295 | { | |||||
296 | PRInt32 nbytes; | |||||
297 | PRStatus rv; | |||||
298 | PRFileDesc *newstack; | |||||
299 | PRFileDesc *layer = sd; | |||||
300 | PRBool newstyle_stack = PR_FALSE0; | |||||
301 | ||||||
302 | PR_ASSERT(sd != NULL)((sd != ((void*)0))?((void)0):PR_Assert("sd != NULL","/home/sylvestre/dev/mozilla/ff/firefox.hg/nsprpub/pr/src/io/prlayer.c" ,302)); | |||||
303 | PR_ASSERT(sd->lower != NULL)((sd->lower != ((void*)0))?((void)0):PR_Assert("sd->lower != NULL" ,"/home/sylvestre/dev/mozilla/ff/firefox.hg/nsprpub/pr/src/io/prlayer.c" ,303)); | |||||
304 | ||||||
305 | /* test for new style stack */ | |||||
306 | while (NULL((void*)0) != layer->higher) | |||||
307 | layer = layer->higher; | |||||
308 | newstyle_stack = (PR_IO_LAYER_HEAD(PRDescIdentity)-3 == layer->identity) ? PR_TRUE1 : PR_FALSE0; | |||||
309 | newstack = PR_NEW(PRFileDesc)((PRFileDesc *) (PR_Malloc((sizeof(PRFileDesc))))); | |||||
310 | if (NULL((void*)0) == newstack) | |||||
311 | { | |||||
312 | PR_SetError(PR_OUT_OF_MEMORY_ERROR(-6000L), 0); | |||||
313 | return -1; | |||||
314 | } | |||||
315 | *newstack = *sd; /* make a copy of the accepting layer */ | |||||
316 | ||||||
317 | nbytes = sd->lower->methods->acceptread( | |||||
318 | sd->lower, nd, raddr, buf, amount, t); | |||||
319 | if (-1 == nbytes) | |||||
320 | { | |||||
321 | PR_DELETE(newstack){ PR_Free(newstack); (newstack) = ((void*)0); }; | |||||
322 | return nbytes; | |||||
323 | } | |||||
324 | if (newstyle_stack) { | |||||
325 | newstack->lower = *nd; | |||||
326 | (*nd)->higher = newstack; | |||||
327 | *nd = newstack; | |||||
328 | return nbytes; | |||||
329 | } else { | |||||
330 | /* this PR_PushIOLayer call cannot fail */ | |||||
331 | rv = PR_PushIOLayer(*nd, PR_TOP_IO_LAYER(PRDescIdentity)-2, newstack); | |||||
332 | PR_ASSERT(PR_SUCCESS == rv)((PR_SUCCESS == rv)?((void)0):PR_Assert("PR_SUCCESS == rv","/home/sylvestre/dev/mozilla/ff/firefox.hg/nsprpub/pr/src/io/prlayer.c" ,332)); | |||||
333 | return nbytes; | |||||
334 | } | |||||
335 | } | |||||
336 | ||||||
337 | static PRInt32 PR_CALLBACK pl_DefTransmitfile ( | |||||
338 | PRFileDesc *sd, PRFileDesc *fd, const void *headers, PRInt32 hlen, | |||||
339 | PRTransmitFileFlags flags, PRIntervalTime t) | |||||
340 | { | |||||
341 | PR_ASSERT(sd != NULL)((sd != ((void*)0))?((void)0):PR_Assert("sd != NULL","/home/sylvestre/dev/mozilla/ff/firefox.hg/nsprpub/pr/src/io/prlayer.c" ,341)); | |||||
342 | PR_ASSERT(sd->lower != NULL)((sd->lower != ((void*)0))?((void)0):PR_Assert("sd->lower != NULL" ,"/home/sylvestre/dev/mozilla/ff/firefox.hg/nsprpub/pr/src/io/prlayer.c" ,342)); | |||||
343 | ||||||
344 | return sd->lower->methods->transmitfile( | |||||
345 | sd->lower, fd, headers, hlen, flags, t); | |||||
346 | } | |||||
347 | ||||||
348 | static PRStatus PR_CALLBACK pl_DefGetsockname (PRFileDesc *fd, PRNetAddr *addr) | |||||
349 | { | |||||
350 | PR_ASSERT(fd != NULL)((fd != ((void*)0))?((void)0):PR_Assert("fd != NULL","/home/sylvestre/dev/mozilla/ff/firefox.hg/nsprpub/pr/src/io/prlayer.c" ,350)); | |||||
351 | PR_ASSERT(fd->lower != NULL)((fd->lower != ((void*)0))?((void)0):PR_Assert("fd->lower != NULL" ,"/home/sylvestre/dev/mozilla/ff/firefox.hg/nsprpub/pr/src/io/prlayer.c" ,351)); | |||||
352 | ||||||
353 | return (fd->lower->methods->getsockname)(fd->lower, addr); | |||||
354 | } | |||||
355 | ||||||
356 | static PRStatus PR_CALLBACK pl_DefGetpeername (PRFileDesc *fd, PRNetAddr *addr) | |||||
357 | { | |||||
358 | PR_ASSERT(fd != NULL)((fd != ((void*)0))?((void)0):PR_Assert("fd != NULL","/home/sylvestre/dev/mozilla/ff/firefox.hg/nsprpub/pr/src/io/prlayer.c" ,358)); | |||||
359 | PR_ASSERT(fd->lower != NULL)((fd->lower != ((void*)0))?((void)0):PR_Assert("fd->lower != NULL" ,"/home/sylvestre/dev/mozilla/ff/firefox.hg/nsprpub/pr/src/io/prlayer.c" ,359)); | |||||
360 | ||||||
361 | return (fd->lower->methods->getpeername)(fd->lower, addr); | |||||
362 | } | |||||
363 | ||||||
364 | static PRStatus PR_CALLBACK pl_DefGetsocketoption ( | |||||
365 | PRFileDesc *fd, PRSocketOptionData *data) | |||||
366 | { | |||||
367 | PR_ASSERT(fd != NULL)((fd != ((void*)0))?((void)0):PR_Assert("fd != NULL","/home/sylvestre/dev/mozilla/ff/firefox.hg/nsprpub/pr/src/io/prlayer.c" ,367)); | |||||
368 | PR_ASSERT(fd->lower != NULL)((fd->lower != ((void*)0))?((void)0):PR_Assert("fd->lower != NULL" ,"/home/sylvestre/dev/mozilla/ff/firefox.hg/nsprpub/pr/src/io/prlayer.c" ,368)); | |||||
369 | ||||||
370 | return (fd->lower->methods->getsocketoption)(fd->lower, data); | |||||
371 | } | |||||
372 | ||||||
373 | static PRStatus PR_CALLBACK pl_DefSetsocketoption ( | |||||
374 | PRFileDesc *fd, const PRSocketOptionData *data) | |||||
375 | { | |||||
376 | PR_ASSERT(fd != NULL)((fd != ((void*)0))?((void)0):PR_Assert("fd != NULL","/home/sylvestre/dev/mozilla/ff/firefox.hg/nsprpub/pr/src/io/prlayer.c" ,376)); | |||||
377 | PR_ASSERT(fd->lower != NULL)((fd->lower != ((void*)0))?((void)0):PR_Assert("fd->lower != NULL" ,"/home/sylvestre/dev/mozilla/ff/firefox.hg/nsprpub/pr/src/io/prlayer.c" ,377)); | |||||
378 | ||||||
379 | return (fd->lower->methods->setsocketoption)(fd->lower, data); | |||||
380 | } | |||||
381 | ||||||
382 | static PRInt32 PR_CALLBACK pl_DefSendfile ( | |||||
383 | PRFileDesc *sd, PRSendFileData *sfd, | |||||
384 | PRTransmitFileFlags flags, PRIntervalTime timeout) | |||||
385 | { | |||||
386 | PR_ASSERT(sd != NULL)((sd != ((void*)0))?((void)0):PR_Assert("sd != NULL","/home/sylvestre/dev/mozilla/ff/firefox.hg/nsprpub/pr/src/io/prlayer.c" ,386)); | |||||
387 | PR_ASSERT(sd->lower != NULL)((sd->lower != ((void*)0))?((void)0):PR_Assert("sd->lower != NULL" ,"/home/sylvestre/dev/mozilla/ff/firefox.hg/nsprpub/pr/src/io/prlayer.c" ,387)); | |||||
388 | ||||||
389 | return sd->lower->methods->sendfile( | |||||
390 | sd->lower, sfd, flags, timeout); | |||||
391 | } | |||||
392 | ||||||
393 | /* Methods for the top of the stack. Just call down to the next fd. */ | |||||
394 | static PRIOMethods pl_methods = { | |||||
395 | PR_DESC_LAYERED, | |||||
396 | pl_TopClose, | |||||
397 | pl_DefRead, | |||||
398 | pl_DefWrite, | |||||
399 | pl_DefAvailable, | |||||
400 | pl_DefAvailable64, | |||||
401 | pl_DefFsync, | |||||
402 | pl_DefSeek, | |||||
403 | pl_DefSeek64, | |||||
404 | pl_DefFileInfo, | |||||
405 | pl_DefFileInfo64, | |||||
406 | pl_DefWritev, | |||||
407 | pl_DefConnect, | |||||
408 | pl_TopAccept, | |||||
409 | pl_DefBind, | |||||
410 | pl_DefListen, | |||||
411 | pl_DefShutdown, | |||||
412 | pl_DefRecv, | |||||
413 | pl_DefSend, | |||||
414 | pl_DefRecvfrom, | |||||
415 | pl_DefSendto, | |||||
416 | pl_DefPoll, | |||||
417 | pl_DefAcceptread, | |||||
418 | pl_DefTransmitfile, | |||||
419 | pl_DefGetsockname, | |||||
420 | pl_DefGetpeername, | |||||
421 | (PRReservedFN)_PR_InvalidInt, | |||||
422 | (PRReservedFN)_PR_InvalidInt, | |||||
423 | pl_DefGetsocketoption, | |||||
424 | pl_DefSetsocketoption, | |||||
425 | pl_DefSendfile, | |||||
426 | pl_DefConnectcontinue, | |||||
427 | (PRReservedFN)_PR_InvalidInt, | |||||
428 | (PRReservedFN)_PR_InvalidInt, | |||||
429 | (PRReservedFN)_PR_InvalidInt, | |||||
430 | (PRReservedFN)_PR_InvalidInt | |||||
431 | }; | |||||
432 | ||||||
433 | PR_IMPLEMENT(const PRIOMethods*)__attribute__((visibility("default"))) const PRIOMethods* PR_GetDefaultIOMethods(void) | |||||
434 | { | |||||
435 | return &pl_methods; | |||||
436 | } /* PR_GetDefaultIOMethods */ | |||||
437 | ||||||
438 | PR_IMPLEMENT(PRFileDesc*)__attribute__((visibility("default"))) PRFileDesc* PR_CreateIOLayerStub( | |||||
439 | PRDescIdentity ident, const PRIOMethods *methods) | |||||
440 | { | |||||
441 | PRFileDesc *fd = NULL((void*)0); | |||||
442 | PR_ASSERT((PR_NSPR_IO_LAYER != ident) && (PR_TOP_IO_LAYER != ident))((((PRDescIdentity)0 != ident) && ((PRDescIdentity)-2 != ident))?((void)0):PR_Assert("(PR_NSPR_IO_LAYER != ident) && (PR_TOP_IO_LAYER != ident)" ,"/home/sylvestre/dev/mozilla/ff/firefox.hg/nsprpub/pr/src/io/prlayer.c" ,442)); | |||||
443 | if ((PR_NSPR_IO_LAYER(PRDescIdentity)0 == ident) || (PR_TOP_IO_LAYER(PRDescIdentity)-2 == ident)) | |||||
444 | PR_SetError(PR_INVALID_ARGUMENT_ERROR(-5987L), 0); | |||||
445 | else | |||||
446 | { | |||||
447 | fd = PR_NEWZAP(PRFileDesc)((PRFileDesc*)PR_Calloc(1, sizeof(PRFileDesc))); | |||||
448 | if (NULL((void*)0) == fd) | |||||
449 | PR_SetError(PR_OUT_OF_MEMORY_ERROR(-6000L), 0); | |||||
450 | else | |||||
451 | { | |||||
452 | fd->methods = methods; | |||||
453 | fd->dtor = pl_FDDestructor; | |||||
454 | fd->identity = ident; | |||||
455 | } | |||||
456 | } | |||||
457 | return fd; | |||||
458 | } /* PR_CreateIOLayerStub */ | |||||
459 | ||||||
460 | /* | |||||
461 | * PR_CreateIOLayer | |||||
462 | * Create a new style stack, where the stack top is a dummy header. | |||||
463 | * Unlike the old style stacks, the contents of the stack head | |||||
464 | * are not modified when a layer is pushed onto or popped from a new | |||||
465 | * style stack. | |||||
466 | */ | |||||
467 | ||||||
468 | PR_IMPLEMENT(PRFileDesc*)__attribute__((visibility("default"))) PRFileDesc* PR_CreateIOLayer(PRFileDesc *top) | |||||
469 | { | |||||
470 | PRFileDesc *fd = NULL((void*)0); | |||||
471 | ||||||
472 | fd = PR_NEWZAP(PRFileDesc)((PRFileDesc*)PR_Calloc(1, sizeof(PRFileDesc))); | |||||
473 | if (NULL((void*)0) == fd) | |||||
474 | PR_SetError(PR_OUT_OF_MEMORY_ERROR(-6000L), 0); | |||||
475 | else | |||||
476 | { | |||||
477 | fd->methods = &pl_methods; | |||||
478 | fd->dtor = pl_FDDestructor; | |||||
479 | fd->identity = PR_IO_LAYER_HEAD(PRDescIdentity)-3; | |||||
480 | fd->higher = NULL((void*)0); | |||||
481 | fd->lower = top; | |||||
482 | top->higher = fd; | |||||
483 | top->lower = NULL((void*)0); | |||||
484 | } | |||||
485 | return fd; | |||||
486 | } /* PR_CreateIOLayer */ | |||||
487 | ||||||
488 | /* | |||||
489 | * _PR_DestroyIOLayer | |||||
490 | * Delete the stack head of a new style stack. | |||||
491 | */ | |||||
492 | ||||||
493 | static PRStatus _PR_DestroyIOLayer(PRFileDesc *stack) | |||||
494 | { | |||||
495 | if (NULL((void*)0) == stack) | |||||
496 | return PR_FAILURE; | |||||
497 | else { | |||||
498 | PR_DELETE(stack){ PR_Free(stack); (stack) = ((void*)0); }; | |||||
499 | return PR_SUCCESS; | |||||
500 | } | |||||
501 | } /* _PR_DestroyIOLayer */ | |||||
502 | ||||||
503 | PR_IMPLEMENT(PRStatus)__attribute__((visibility("default"))) PRStatus PR_PushIOLayer( | |||||
504 | PRFileDesc *stack, PRDescIdentity id, PRFileDesc *fd) | |||||
505 | { | |||||
506 | PRFileDesc *insert = PR_GetIdentitiesLayer(stack, id); | |||||
507 | ||||||
508 | PR_ASSERT(fd != NULL)((fd != ((void*)0))?((void)0):PR_Assert("fd != NULL","/home/sylvestre/dev/mozilla/ff/firefox.hg/nsprpub/pr/src/io/prlayer.c" ,508)); | |||||
509 | PR_ASSERT(stack != NULL)((stack != ((void*)0))?((void)0):PR_Assert("stack != NULL","/home/sylvestre/dev/mozilla/ff/firefox.hg/nsprpub/pr/src/io/prlayer.c" ,509)); | |||||
510 | PR_ASSERT(insert != NULL)((insert != ((void*)0))?((void)0):PR_Assert("insert != NULL", "/home/sylvestre/dev/mozilla/ff/firefox.hg/nsprpub/pr/src/io/prlayer.c" ,510)); | |||||
511 | PR_ASSERT(PR_IO_LAYER_HEAD != id)(((PRDescIdentity)-3 != id)?((void)0):PR_Assert("PR_IO_LAYER_HEAD != id" ,"/home/sylvestre/dev/mozilla/ff/firefox.hg/nsprpub/pr/src/io/prlayer.c" ,511)); | |||||
512 | if ((NULL((void*)0) == stack) || (NULL((void*)0) == fd) || (NULL((void*)0) == insert)) | |||||
513 | { | |||||
514 | PR_SetError(PR_INVALID_ARGUMENT_ERROR(-5987L), 0); | |||||
515 | return PR_FAILURE; | |||||
516 | } | |||||
517 | ||||||
518 | if (stack == insert) | |||||
519 | { | |||||
520 | /* going on top of the stack */ | |||||
521 | /* old-style stack */ | |||||
522 | PRFileDesc copy = *stack; | |||||
523 | *stack = *fd; | |||||
524 | *fd = copy; | |||||
525 | fd->higher = stack; | |||||
526 | if (fd->lower) | |||||
527 | { | |||||
528 | PR_ASSERT(fd->lower->higher == stack)((fd->lower->higher == stack)?((void)0):PR_Assert("fd->lower->higher == stack" ,"/home/sylvestre/dev/mozilla/ff/firefox.hg/nsprpub/pr/src/io/prlayer.c" ,528)); | |||||
529 | fd->lower->higher = fd; | |||||
530 | } | |||||
531 | stack->lower = fd; | |||||
532 | stack->higher = NULL((void*)0); | |||||
533 | } else { | |||||
534 | /* | |||||
535 | * going somewhere in the middle of the stack for both old and new | |||||
536 | * style stacks, or going on top of stack for new style stack | |||||
537 | */ | |||||
538 | fd->lower = insert; | |||||
539 | fd->higher = insert->higher; | |||||
540 | ||||||
541 | insert->higher->lower = fd; | |||||
542 | insert->higher = fd; | |||||
543 | } | |||||
544 | ||||||
545 | return PR_SUCCESS; | |||||
546 | } | |||||
547 | ||||||
548 | PR_IMPLEMENT(PRFileDesc*)__attribute__((visibility("default"))) PRFileDesc* PR_PopIOLayer(PRFileDesc *stack, PRDescIdentity id) | |||||
549 | { | |||||
550 | PRFileDesc *extract = PR_GetIdentitiesLayer(stack, id); | |||||
551 | ||||||
552 | PR_ASSERT(0 != id)((0 != id)?((void)0):PR_Assert("0 != id","/home/sylvestre/dev/mozilla/ff/firefox.hg/nsprpub/pr/src/io/prlayer.c" ,552)); | |||||
553 | PR_ASSERT(NULL != stack)((((void*)0) != stack)?((void)0):PR_Assert("NULL != stack","/home/sylvestre/dev/mozilla/ff/firefox.hg/nsprpub/pr/src/io/prlayer.c" ,553)); | |||||
554 | PR_ASSERT(NULL != extract)((((void*)0) != extract)?((void)0):PR_Assert("NULL != extract" ,"/home/sylvestre/dev/mozilla/ff/firefox.hg/nsprpub/pr/src/io/prlayer.c" ,554)); | |||||
555 | if ((NULL((void*)0) == stack) || (0 == id) || (NULL((void*)0) == extract)) | |||||
556 | { | |||||
557 | PR_SetError(PR_INVALID_ARGUMENT_ERROR(-5987L), 0); | |||||
558 | return NULL((void*)0); | |||||
559 | } | |||||
560 | ||||||
561 | if (extract == stack) { | |||||
562 | /* popping top layer of the stack */ | |||||
563 | /* old style stack */ | |||||
564 | PRFileDesc copy = *stack; | |||||
565 | extract = stack->lower; | |||||
566 | *stack = *extract; | |||||
567 | *extract = copy; | |||||
568 | stack->higher = NULL((void*)0); | |||||
569 | if (stack->lower) { | |||||
570 | PR_ASSERT(stack->lower->higher == extract)((stack->lower->higher == extract)?((void)0):PR_Assert( "stack->lower->higher == extract","/home/sylvestre/dev/mozilla/ff/firefox.hg/nsprpub/pr/src/io/prlayer.c" ,570)); | |||||
571 | stack->lower->higher = stack; | |||||
572 | } | |||||
573 | } else if ((PR_IO_LAYER_HEAD(PRDescIdentity)-3 == stack->identity) && | |||||
574 | (extract == stack->lower) && (extract->lower == NULL((void*)0))) { | |||||
575 | /* | |||||
576 | * new style stack | |||||
577 | * popping the only layer in the stack; delete the stack too | |||||
578 | */ | |||||
579 | stack->lower = NULL((void*)0); | |||||
580 | _PR_DestroyIOLayer(stack); | |||||
581 | } else { | |||||
582 | /* for both kinds of stacks */ | |||||
583 | extract->lower->higher = extract->higher; | |||||
584 | extract->higher->lower = extract->lower; | |||||
585 | } | |||||
586 | extract->higher = extract->lower = NULL((void*)0); | |||||
587 | return extract; | |||||
588 | } /* PR_PopIOLayer */ | |||||
589 | ||||||
590 | #define ID_CACHE_INCREMENT16 16 | |||||
591 | typedef struct _PRIdentity_cache | |||||
592 | { | |||||
593 | PRLock *ml; | |||||
594 | char **name; | |||||
595 | PRIntn length; | |||||
596 | PRDescIdentity ident; | |||||
597 | } _PRIdentity_cache; | |||||
598 | ||||||
599 | static _PRIdentity_cache identity_cache; | |||||
600 | ||||||
601 | PR_IMPLEMENT(PRDescIdentity)__attribute__((visibility("default"))) PRDescIdentity PR_GetUniqueIdentity(const char *layer_name) | |||||
602 | { | |||||
603 | PRDescIdentity identity, length; | |||||
604 | char **names = NULL((void*)0), *name = NULL((void*)0), **old = NULL((void*)0); | |||||
605 | ||||||
606 | if (!_pr_initialized) _PR_ImplicitInitialization(); | |||||
607 | ||||||
608 | PR_ASSERT((PRDescIdentity)0x7fff > identity_cache.ident)(((PRDescIdentity)0x7fff > identity_cache.ident)?((void)0) :PR_Assert("(PRDescIdentity)0x7fff > identity_cache.ident" ,"/home/sylvestre/dev/mozilla/ff/firefox.hg/nsprpub/pr/src/io/prlayer.c" ,608)); | |||||
609 | ||||||
610 | if (NULL((void*)0) != layer_name) | |||||
611 | { | |||||
612 | name = (char*)PR_Malloc(strlen(layer_name) + 1); | |||||
613 | if (NULL((void*)0) == name) | |||||
614 | { | |||||
615 | PR_SetError(PR_OUT_OF_MEMORY_ERROR(-6000L), 0); | |||||
616 | return PR_INVALID_IO_LAYER(PRDescIdentity)-1; | |||||
617 | } | |||||
618 | strcpy(name, layer_name); | |||||
619 | } | |||||
620 | ||||||
621 | /* this initial code runs unsafe */ | |||||
622 | retry: | |||||
623 | PR_ASSERT(NULL == names)((((void*)0) == names)?((void)0):PR_Assert("NULL == names","/home/sylvestre/dev/mozilla/ff/firefox.hg/nsprpub/pr/src/io/prlayer.c" ,623)); | |||||
624 | /* | |||||
625 | * In the initial round, both identity_cache.ident and | |||||
626 | * identity_cache.length are 0, so (identity_cache.ident + 1) is greater | |||||
627 | * than length. In later rounds, identity_cache.ident is always less | |||||
628 | * than length, so (identity_cache.ident + 1) can be equal to but cannot | |||||
629 | * be greater than length. | |||||
630 | */ | |||||
631 | length = identity_cache.length; | |||||
632 | if ((identity_cache.ident + 1) >= length) | |||||
633 | { | |||||
634 | length += ID_CACHE_INCREMENT16; | |||||
635 | names = (char**)PR_CALLOC(length * sizeof(char*))(PR_Calloc(1, (length * sizeof(char*)))); | |||||
636 | if (NULL((void*)0) == names) | |||||
637 | { | |||||
638 | if (NULL((void*)0) != name) PR_DELETE(name){ PR_Free(name); (name) = ((void*)0); }; | |||||
639 | PR_SetError(PR_OUT_OF_MEMORY_ERROR(-6000L), 0); | |||||
640 | return PR_INVALID_IO_LAYER(PRDescIdentity)-1; | |||||
641 | } | |||||
642 | } | |||||
643 | ||||||
644 | /* now we get serious about thread safety */ | |||||
645 | PR_Lock(identity_cache.ml); | |||||
646 | PR_ASSERT(identity_cache.length == 0 ||((identity_cache.length == 0 || identity_cache.ident < identity_cache .length)?((void)0):PR_Assert("identity_cache.length == 0 || identity_cache.ident < identity_cache.length" ,"/home/sylvestre/dev/mozilla/ff/firefox.hg/nsprpub/pr/src/io/prlayer.c" ,647)) | |||||
647 | identity_cache.ident < identity_cache.length)((identity_cache.length == 0 || identity_cache.ident < identity_cache .length)?((void)0):PR_Assert("identity_cache.length == 0 || identity_cache.ident < identity_cache.length" ,"/home/sylvestre/dev/mozilla/ff/firefox.hg/nsprpub/pr/src/io/prlayer.c" ,647)); | |||||
648 | identity = identity_cache.ident + 1; | |||||
649 | if (identity >= identity_cache.length) /* there's no room */ | |||||
650 | { | |||||
651 | /* we have to do something - hopefully it's already done */ | |||||
652 | if ((NULL((void*)0) != names) && (identity < length)) | |||||
653 | { | |||||
654 | /* what we did is still okay */ | |||||
655 | memcpy( | |||||
656 | names, identity_cache.name, | |||||
657 | identity_cache.length * sizeof(char*)); | |||||
658 | old = identity_cache.name; | |||||
659 | identity_cache.name = names; | |||||
660 | identity_cache.length = length; | |||||
661 | names = NULL((void*)0); | |||||
662 | } | |||||
663 | else | |||||
664 | { | |||||
665 | PR_Unlock(identity_cache.ml); | |||||
666 | if (NULL((void*)0) != names) PR_DELETE(names){ PR_Free(names); (names) = ((void*)0); }; | |||||
667 | goto retry; | |||||
668 | } | |||||
669 | } | |||||
670 | if (NULL((void*)0) != name) /* there's a name to be stored */ | |||||
671 | { | |||||
672 | identity_cache.name[identity] = name; | |||||
673 | } | |||||
674 | identity_cache.ident = identity; | |||||
675 | PR_ASSERT(identity_cache.ident < identity_cache.length)((identity_cache.ident < identity_cache.length)?((void)0): PR_Assert("identity_cache.ident < identity_cache.length","/home/sylvestre/dev/mozilla/ff/firefox.hg/nsprpub/pr/src/io/prlayer.c" ,675)); | |||||
676 | PR_Unlock(identity_cache.ml); | |||||
677 | ||||||
678 | if (NULL((void*)0) != old) PR_DELETE(old){ PR_Free(old); (old) = ((void*)0); }; | |||||
679 | if (NULL((void*)0) != names) PR_DELETE(names){ PR_Free(names); (names) = ((void*)0); }; | |||||
680 | ||||||
681 | return identity; | |||||
682 | } /* PR_GetUniqueIdentity */ | |||||
683 | ||||||
684 | PR_IMPLEMENT(const char*)__attribute__((visibility("default"))) const char* PR_GetNameForIdentity(PRDescIdentity ident) | |||||
685 | { | |||||
686 | if (!_pr_initialized) _PR_ImplicitInitialization(); | |||||
687 | ||||||
688 | if (PR_TOP_IO_LAYER(PRDescIdentity)-2 == ident) return NULL((void*)0); | |||||
689 | ||||||
690 | PR_ASSERT(ident <= identity_cache.ident)((ident <= identity_cache.ident)?((void)0):PR_Assert("ident <= identity_cache.ident" ,"/home/sylvestre/dev/mozilla/ff/firefox.hg/nsprpub/pr/src/io/prlayer.c" ,690)); | |||||
691 | return (ident > identity_cache.ident) ? NULL((void*)0) : identity_cache.name[ident]; | |||||
692 | } /* PR_GetNameForIdentity */ | |||||
693 | ||||||
694 | PR_IMPLEMENT(PRDescIdentity)__attribute__((visibility("default"))) PRDescIdentity PR_GetLayersIdentity(PRFileDesc* fd) | |||||
695 | { | |||||
696 | PR_ASSERT(NULL != fd)((((void*)0) != fd)?((void)0):PR_Assert("NULL != fd","/home/sylvestre/dev/mozilla/ff/firefox.hg/nsprpub/pr/src/io/prlayer.c" ,696)); | |||||
697 | if (PR_IO_LAYER_HEAD(PRDescIdentity)-3 == fd->identity) { | |||||
698 | PR_ASSERT(NULL != fd->lower)((((void*)0) != fd->lower)?((void)0):PR_Assert("NULL != fd->lower" ,"/home/sylvestre/dev/mozilla/ff/firefox.hg/nsprpub/pr/src/io/prlayer.c" ,698)); | |||||
699 | return fd->lower->identity; | |||||
700 | } else | |||||
701 | return fd->identity; | |||||
702 | } /* PR_GetLayersIdentity */ | |||||
703 | ||||||
704 | PR_IMPLEMENT(PRFileDesc*)__attribute__((visibility("default"))) PRFileDesc* PR_GetIdentitiesLayer(PRFileDesc* fd, PRDescIdentity id) | |||||
705 | { | |||||
706 | PRFileDesc *layer = fd; | |||||
707 | ||||||
708 | if (PR_TOP_IO_LAYER(PRDescIdentity)-2 == id) { | |||||
709 | if (PR_IO_LAYER_HEAD(PRDescIdentity)-3 == fd->identity) | |||||
710 | return fd->lower; | |||||
711 | else | |||||
712 | return fd; | |||||
713 | } | |||||
714 | ||||||
715 | for (layer = fd; layer != NULL((void*)0); layer = layer->lower) | |||||
716 | { | |||||
717 | if (id == layer->identity) return layer; | |||||
718 | } | |||||
719 | for (layer = fd; layer != NULL((void*)0); layer = layer->higher) | |||||
720 | { | |||||
721 | if (id == layer->identity) return layer; | |||||
722 | } | |||||
723 | return NULL((void*)0); | |||||
724 | } /* PR_GetIdentitiesLayer */ | |||||
725 | ||||||
726 | void _PR_InitLayerCache(void) | |||||
727 | { | |||||
728 | memset(&identity_cache, 0, sizeof(identity_cache)); | |||||
729 | identity_cache.ml = PR_NewLock(); | |||||
730 | PR_ASSERT(NULL != identity_cache.ml)((((void*)0) != identity_cache.ml)?((void)0):PR_Assert("NULL != identity_cache.ml" ,"/home/sylvestre/dev/mozilla/ff/firefox.hg/nsprpub/pr/src/io/prlayer.c" ,730)); | |||||
731 | } /* _PR_InitLayerCache */ | |||||
732 | ||||||
733 | void _PR_CleanupLayerCache(void) | |||||
734 | { | |||||
735 | if (identity_cache.ml) | |||||
736 | { | |||||
737 | PR_DestroyLock(identity_cache.ml); | |||||
738 | identity_cache.ml = NULL((void*)0); | |||||
739 | } | |||||
740 | ||||||
741 | if (identity_cache.name) | |||||
742 | { | |||||
743 | PRDescIdentity ident; | |||||
744 | ||||||
745 | for (ident = 0; ident <= identity_cache.ident; ident++) | |||||
746 | PR_DELETE(identity_cache.name[ident]){ PR_Free(identity_cache.name[ident]); (identity_cache.name[ident ]) = ((void*)0); }; | |||||
747 | ||||||
748 | PR_DELETE(identity_cache.name){ PR_Free(identity_cache.name); (identity_cache.name) = ((void *)0); }; | |||||
749 | } | |||||
750 | } /* _PR_CleanupLayerCache */ | |||||
751 | ||||||
752 | /* prlayer.c */ |