… | |
… | |
142 | errno = req->errorno; |
142 | errno = req->errorno; |
143 | |
143 | |
144 | if (req->type == REQ_READ) |
144 | if (req->type == REQ_READ) |
145 | SvCUR_set (req->data, req->dataoffset + (req->result > 0 ? req->result : 0)); |
145 | SvCUR_set (req->data, req->dataoffset + (req->result > 0 ? req->result : 0)); |
146 | |
146 | |
|
|
147 | if (req->data2ptr && (req->type == REQ_READ || req->type == REQ_WRITE)) |
|
|
148 | SvREADONLY_off (req->data); |
|
|
149 | |
147 | if (req->statdata) |
150 | if (req->statdata) |
148 | { |
151 | { |
149 | PL_laststype = req->type == REQ_LSTAT ? OP_LSTAT : OP_STAT; |
152 | PL_laststype = req->type == REQ_LSTAT ? OP_LSTAT : OP_STAT; |
150 | PL_laststatval = req->result; |
153 | PL_laststatval = req->result; |
151 | PL_statcache = *(req->statdata); |
154 | PL_statcache = *(req->statdata); |
… | |
… | |
294 | croak ("cannot set result pipe to nonblocking mode"); |
297 | croak ("cannot set result pipe to nonblocking mode"); |
295 | } |
298 | } |
296 | |
299 | |
297 | static void atfork_prepare (void) |
300 | static void atfork_prepare (void) |
298 | { |
301 | { |
299 | for (;;) { |
|
|
300 | |
|
|
301 | for (;;) |
|
|
302 | { |
|
|
303 | poll_cb (); |
|
|
304 | |
|
|
305 | if (!nreqs) |
|
|
306 | break; |
|
|
307 | |
|
|
308 | poll_wait (); |
|
|
309 | } |
|
|
310 | |
|
|
311 | pthread_mutex_lock (&reqlock); |
302 | pthread_mutex_lock (&reqlock); |
312 | |
|
|
313 | if (!nreqs) |
|
|
314 | break; |
|
|
315 | |
|
|
316 | pthread_mutex_unlock (&reqlock); |
|
|
317 | } |
|
|
318 | |
|
|
319 | pthread_mutex_lock (&reslock); |
303 | pthread_mutex_lock (&reslock); |
320 | |
|
|
321 | assert (!nreqs && !reqs && !ress); |
|
|
322 | } |
304 | } |
323 | |
305 | |
324 | static void atfork_parent (void) |
306 | static void atfork_parent (void) |
325 | { |
307 | { |
326 | pthread_mutex_unlock (&reslock); |
308 | pthread_mutex_unlock (&reslock); |
327 | pthread_mutex_unlock (&reqlock); |
309 | pthread_mutex_unlock (&reqlock); |
328 | } |
310 | } |
329 | |
311 | |
330 | static void atfork_child (void) |
312 | static void atfork_child (void) |
331 | { |
313 | { |
|
|
314 | aio_req prv; |
|
|
315 | |
332 | int restart = started; |
316 | int restart = started; |
333 | started = 0; |
317 | started = 0; |
|
|
318 | |
|
|
319 | while (reqs) |
|
|
320 | { |
|
|
321 | prv = reqs; |
|
|
322 | reqs = prv->next; |
|
|
323 | free_req (prv); |
|
|
324 | } |
|
|
325 | |
|
|
326 | reqs = reqe = 0; |
|
|
327 | |
|
|
328 | while (ress) |
|
|
329 | { |
|
|
330 | prv = ress; |
|
|
331 | ress = prv->next; |
|
|
332 | free_req (prv); |
|
|
333 | } |
|
|
334 | |
|
|
335 | ress = rese = 0; |
|
|
336 | |
|
|
337 | close (respipe [0]); |
|
|
338 | close (respipe [1]); |
|
|
339 | create_pipe (); |
334 | |
340 | |
335 | atfork_parent (); |
341 | atfork_parent (); |
336 | |
342 | |
337 | min_parallel (restart); |
343 | min_parallel (restart); |
338 | } |
344 | } |
… | |
… | |
629 | req->offset = offset; |
635 | req->offset = offset; |
630 | req->length = length; |
636 | req->length = length; |
631 | req->data = SvREFCNT_inc (data); |
637 | req->data = SvREFCNT_inc (data); |
632 | req->dataptr = (char *)svptr + dataoffset; |
638 | req->dataptr = (char *)svptr + dataoffset; |
633 | |
639 | |
|
|
640 | if (!SvREADONLY (data)) |
|
|
641 | { |
|
|
642 | SvREADONLY_on (data); |
|
|
643 | req->data2ptr = (void *)data; |
|
|
644 | } |
|
|
645 | |
634 | send_req (req); |
646 | send_req (req); |
635 | } |
647 | } |
636 | } |
648 | } |
637 | |
649 | |
638 | void |
650 | void |