221 int _rtl_read(); |
221 int _rtl_read(); |
222 int _rtl_write(); |
222 int _rtl_write(); |
223 |
223 |
224 # define READ(ret,f, cp, n, handleType) \ |
224 # define READ(ret,f, cp, n, handleType) \ |
225 { int __res;\ |
225 { int __res;\ |
226 HANDLE h; \ |
226 HANDLE h; \ |
227 h = _get_osfhandle(fileno(f)); \ |
227 h = _get_osfhandle(fileno(f)); \ |
228 if ((handleType == @symbol(socketFilePointer)) \ |
228 if ((handleType == @symbol(socketFilePointer)) \ |
229 || ((handleType == nil) && (ioctlsocket((SOCKET)h,FIONREAD,&__res)==0))) { \ |
229 || ((handleType == nil) && (ioctlsocket((SOCKET)h,FIONREAD,&__res)==0))) { \ |
230 (ret) = __STX_WSA_NOINT_CALL4("recv", recv, h, (cp), (n), 0);\ |
230 (ret) = __STX_WSA_NOINT_CALL4("recv", recv, h, (cp), (n), 0);\ |
231 } else { \ |
231 } else { \ |
232 (ret) = __STX_C_NOINT_CALL3("_rtl_read", _rtl_read, fileno(f), (cp), (n));\ |
232 (ret) = __STX_C_NOINT_CALL3("_rtl_read", _rtl_read, fileno(f), (cp), (n));\ |
233 } \ |
233 } \ |
234 } |
234 } |
235 |
235 |
236 # define WRITE(ret,f, cp, n, handleType) \ |
236 # define WRITE(ret,f, cp, n, handleType) \ |
237 { int __res;\ |
237 { int __res;\ |
238 HANDLE h; \ |
238 HANDLE h; \ |
239 h = _get_osfhandle(fileno(f)); \ |
239 h = _get_osfhandle(fileno(f)); \ |
240 if ((handleType == @symbol(socketFilePointer)) \ |
240 if ((handleType == @symbol(socketFilePointer)) \ |
241 || ((handleType == nil) && (ioctlsocket((SOCKET)h,FIONREAD,&__res)==0))) { \ |
241 || ((handleType == nil) && (ioctlsocket((SOCKET)h,FIONREAD,&__res)==0))) { \ |
242 (ret) = __STX_WSA_NOINT_CALL4("send", send, h, (cp), (n), 0);\ |
242 (ret) = __STX_WSA_NOINT_CALL4("send", send, h, (cp), (n), 0);\ |
243 } else { \ |
243 } else { \ |
244 (ret) = __STX_C_NOINT_CALL3("_rtl_write", _rtl_write, fileno(f), (cp), (n));\ |
244 (ret) = __STX_C_NOINT_CALL3("_rtl_write", _rtl_write, fileno(f), (cp), (n));\ |
245 } \ |
245 } \ |
246 } |
246 } |
247 |
247 |
248 # else /* MSC */ |
248 # else /* MSC */ |
249 |
249 |
250 # define READ(ret,f, cp, n, handleType) \ |
250 # define READ(ret,f, cp, n, handleType) \ |
251 { int __res;\ |
251 { int __res;\ |
252 int fd; \ |
252 int fd; \ |
253 HANDLE h; \ |
253 HANDLE h; \ |
254 fd = fileno(f); \ |
254 fd = fileno(f); \ |
255 if ((handleType == @symbol(socketFileDescriptor)) \ |
255 if ((handleType == @symbol(socketFileDescriptor)) \ |
256 || ((handleType == nil) && (ioctlsocket((SOCKET)fd,FIONREAD,&__res)==0))) { \ |
256 || ((handleType == nil) && (ioctlsocket((SOCKET)fd,FIONREAD,&__res)==0))) { \ |
257 (ret) = __STX_WSA_NOINT_CALL4("recv", recv, fd, (cp), (n), 0);\ |
257 (ret) = __STX_WSA_NOINT_CALL4("recv", recv, fd, (cp), (n), 0);\ |
258 } else { \ |
258 } else { \ |
259 h = _get_osfhandle(fd); \ |
259 h = _get_osfhandle(fd); \ |
260 if ((handleType == @symbol(socketFilePointer)) \ |
260 if ((handleType == @symbol(socketFilePointer)) \ |
261 || ((handleType == nil) && (ioctlsocket((SOCKET)h,FIONREAD,&__res)==0))) { \ |
261 || ((handleType == nil) && (ioctlsocket((SOCKET)h,FIONREAD,&__res)==0))) { \ |
262 (ret) = __STX_WSA_NOINT_CALL4("recv", recv, h, (cp), (n), 0);\ |
262 (ret) = __STX_WSA_NOINT_CALL4("recv", recv, h, (cp), (n), 0);\ |
263 } else { \ |
263 } else { \ |
264 (ret) = __STX_API_NOINT_CALL5("ReadFile", ReadFile, h, (cp), (n), &__res, 0);\ |
264 (ret) = __STX_API_NOINT_CALL5("ReadFile", ReadFile, h, (cp), (n), &__res, 0);\ |
265 if (ret) \ |
265 if (ret) \ |
266 ret = __res; \ |
266 ret = __res; \ |
267 } \ |
267 } \ |
268 } \ |
268 } \ |
269 } |
269 } |
270 # define WRITE(ret,f, cp, n, handleType) \ |
270 # define WRITE(ret,f, cp, n, handleType) \ |
271 { int __res;\ |
271 { int __res;\ |
272 int fd; \ |
272 int fd; \ |
273 HANDLE h; \ |
273 HANDLE h; \ |
274 fd = fileno(f); \ |
274 fd = fileno(f); \ |
275 if ((handleType == @symbol(socketFileDescriptor)) \ |
275 if ((handleType == @symbol(socketFileDescriptor)) \ |
276 || ((handleType == nil) && (ioctlsocket((SOCKET)fd,FIONREAD,&__res)==0))) { \ |
276 || ((handleType == nil) && (ioctlsocket((SOCKET)fd,FIONREAD,&__res)==0))) { \ |
277 (ret) = __STX_WSA_NOINT_CALL4("send", send, fd, (cp), (n), 0);\ |
277 (ret) = __STX_WSA_NOINT_CALL4("send", send, fd, (cp), (n), 0);\ |
278 } else {\ |
278 } else {\ |
279 h = _get_osfhandle(fd); \ |
279 h = _get_osfhandle(fd); \ |
280 if ((handleType == @symbol(socketFilePointer)) \ |
280 if ((handleType == @symbol(socketFilePointer)) \ |
281 || ((handleType == nil) && (ioctlsocket((SOCKET)h,FIONREAD,&__res)==0))) { \ |
281 || ((handleType == nil) && (ioctlsocket((SOCKET)h,FIONREAD,&__res)==0))) { \ |
282 (ret) = __STX_WSA_NOINT_CALL4("send", send, h, (cp), (n), 0);\ |
282 (ret) = __STX_WSA_NOINT_CALL4("send", send, h, (cp), (n), 0);\ |
283 } else {\ |
283 } else {\ |
284 (ret) = __STX_API_NOINT_CALL5("WriteFile", WriteFile, h, (cp), (n), &__res, 0);\ |
284 (ret) = __STX_API_NOINT_CALL5("WriteFile", WriteFile, h, (cp), (n), &__res, 0);\ |
285 if (ret) \ |
285 if (ret) \ |
286 ret = __res; \ |
286 ret = __res; \ |
287 } \ |
287 } \ |
288 } \ |
288 } \ |
289 } |
289 } |
290 # endif /* MSC */ |
290 # endif /* MSC */ |
291 |
291 |
292 # define FFLUSH(fp) fflush(fp) |
292 # define FFLUSH(fp) fflush(fp) |
293 # undef STDIO_NEEDS_FSEEK |
293 # undef STDIO_NEEDS_FSEEK |
295 # define FILENO(f) fileno(f) |
295 # define FILENO(f) fileno(f) |
296 |
296 |
297 # define __READING__(f) \ |
297 # define __READING__(f) \ |
298 if ((__INST(didWrite) != false) \ |
298 if ((__INST(didWrite) != false) \ |
299 && (__INST(mode) == @symbol(readwrite))) { \ |
299 && (__INST(mode) == @symbol(readwrite))) { \ |
300 __INST(didWrite) = false; \ |
300 __INST(didWrite) = false; \ |
301 OPT_FSEEK(f, 0L, SEEK_CUR); /* needed in stdio */ \ |
301 OPT_FSEEK(f, 0L, SEEK_CUR); /* needed in stdio */ \ |
302 } |
302 } |
303 |
303 |
304 # define __WRITING__(f) \ |
304 # define __WRITING__(f) \ |
305 if ((__INST(didWrite) != true) \ |
305 if ((__INST(didWrite) != true) \ |
306 && (__INST(mode) == @symbol(readwrite))) { \ |
306 && (__INST(mode) == @symbol(readwrite))) { \ |
307 __INST(didWrite) = true; \ |
307 __INST(didWrite) = true; \ |
308 OPT_FSEEK(f, 0L, SEEK_CUR); /* needed in stdio */ \ |
308 OPT_FSEEK(f, 0L, SEEK_CUR); /* needed in stdio */ \ |
309 } |
309 } |
310 |
310 |
311 # define __UNGETC__(c, f, isBuffered) \ |
311 # define __UNGETC__(c, f, isBuffered) \ |
312 if (isBuffered) { \ |
312 if (isBuffered) { \ |
313 ungetc((c), (f)); \ |
313 ungetc((c), (f)); \ |
314 } else { \ |
314 } else { \ |
315 __INST(readAhead) = __mkSmallInteger((c)); \ |
315 __INST(readAhead) = __mkSmallInteger((c)); \ |
316 } |
316 } |
317 |
317 |
318 # define __READBYTE__(ret, f, buf, isBuffered, handleType) \ |
318 # define __READBYTE__(ret, f, buf, isBuffered, handleType) \ |
319 if (isBuffered) { \ |
319 if (isBuffered) { \ |
320 for (;;) { \ |
320 for (;;) { \ |
321 CLEAR_ERRNO; \ |
321 CLEAR_ERRNO; \ |
322 (ret) = getc(f); \ |
322 (ret) = getc(f); \ |
323 if ((ret) >= 0) { \ |
323 if ((ret) >= 0) { \ |
324 *(buf) = (ret); \ |
324 *(buf) = (ret); \ |
325 (ret) = 1; \ |
325 (ret) = 1; \ |
326 } else if (ferror(f)) { \ |
326 } else if (ferror(f)) { \ |
327 if (__threadErrno == EINTR) { \ |
327 if (__threadErrno == EINTR) { \ |
328 clearerr(f); \ |
328 clearerr(f); \ |
329 continue; \ |
329 continue; \ |
330 } \ |
330 } \ |
331 } else { \ |
331 } else { \ |
332 (ret) = 0; \ |
332 (ret) = 0; \ |
333 } \ |
333 } \ |
334 break; \ |
334 break; \ |
335 } \ |
335 } \ |
336 } else { \ |
336 } else { \ |
337 OBJ rA = __INST(readAhead); \ |
337 OBJ rA = __INST(readAhead); \ |
338 if (rA != nil) { \ |
338 if (rA != nil) { \ |
339 *(buf) = (char)__intVal(rA); \ |
339 *(buf) = (char)__intVal(rA); \ |
340 __INST(readAhead) = nil; \ |
340 __INST(readAhead) = nil; \ |
341 (ret) = 1; \ |
341 (ret) = 1; \ |
342 } else { \ |
342 } else { \ |
343 for (;;) { \ |
343 for (;;) { \ |
344 CLEAR_ERRNO; \ |
344 CLEAR_ERRNO; \ |
345 READ(ret,f, buf, 1, handleType); \ |
345 READ(ret,f, buf, 1, handleType); \ |
346 if ((ret) >= 0 || __threadErrno != EINTR) \ |
346 if ((ret) >= 0 || __threadErrno != EINTR) \ |
347 break; \ |
347 break; \ |
348 } \ |
348 } \ |
349 } \ |
349 } \ |
350 } |
350 } |
351 |
351 |
352 /* |
352 /* |
353 * read_bytes into a c-buffer |
353 * read_bytes into a c-buffer |
354 * (which may NOT move) |
354 * (which may NOT move) |
355 */ |
355 */ |
356 # define __READBYTES__(ret, f, buf, cnt, isBuffered, handleType) \ |
356 # define __READBYTES__(ret, f, buf, cnt, isBuffered, handleType) \ |
357 (ret) = 0; \ |
357 (ret) = 0; \ |
358 if (isBuffered) { \ |
358 if (isBuffered) { \ |
359 int __offs = 0; \ |
359 int __offs = 0; \ |
360 while (__offs < (cnt)) { \ |
360 while (__offs < (cnt)) { \ |
361 CLEAR_ERRNO; \ |
361 CLEAR_ERRNO; \ |
362 (ret) = getc(f); \ |
362 (ret) = getc(f); \ |
363 if ((ret) < 0) { \ |
363 if ((ret) < 0) { \ |
364 if (ferror(f)) { \ |
364 if (ferror(f)) { \ |
365 if (__threadErrno == EINTR) { \ |
365 if (__threadErrno == EINTR) { \ |
366 clearerr(f); \ |
366 clearerr(f); \ |
367 continue; \ |
367 continue; \ |
368 } \ |
368 } \ |
369 } else { \ |
369 } else { \ |
370 (ret) = 0; \ |
370 (ret) = 0; \ |
371 } \ |
371 } \ |
372 break; \ |
372 break; \ |
373 } \ |
373 } \ |
374 (buf)[__offs++] = (ret); \ |
374 (buf)[__offs++] = (ret); \ |
375 } \ |
375 } \ |
376 if (__offs > 0) \ |
376 if (__offs > 0) \ |
377 (ret) = __offs; \ |
377 (ret) = __offs; \ |
378 } else { \ |
378 } else { \ |
379 int __offs = 0; \ |
379 int __offs = 0; \ |
380 \ |
380 \ |
381 while (__offs < (cnt)) { \ |
381 while (__offs < (cnt)) { \ |
382 OBJ rA = __INST(readAhead); \ |
382 OBJ rA = __INST(readAhead); \ |
383 if (rA != nil) { \ |
383 if (rA != nil) { \ |
384 (buf)[__offs] = __intVal(rA); \ |
384 (buf)[__offs] = __intVal(rA); \ |
385 __INST(readAhead) = nil; \ |
385 __INST(readAhead) = nil; \ |
386 (ret) = 1; \ |
386 (ret) = 1; \ |
387 } else { \ |
387 } else { \ |
388 CLEAR_ERRNO; \ |
388 CLEAR_ERRNO; \ |
389 READ(ret,f, (buf)+__offs, (cnt)-__offs, handleType); \ |
389 READ(ret,f, (buf)+__offs, (cnt)-__offs, handleType); \ |
390 if ((ret) <= 0) { \ |
390 if ((ret) <= 0) { \ |
391 if ((ret) < 0 && __threadErrno == EINTR) { \ |
391 if ((ret) < 0 && __threadErrno == EINTR) { \ |
392 continue; \ |
392 continue; \ |
393 } \ |
393 } \ |
394 break; \ |
394 break; \ |
395 } \ |
395 } \ |
396 } \ |
396 } \ |
397 __offs += (ret); \ |
397 __offs += (ret); \ |
398 } \ |
398 } \ |
399 if (__offs > 0) \ |
399 if (__offs > 0) \ |
400 (ret) = __offs; \ |
400 (ret) = __offs; \ |
401 } |
401 } |
402 |
402 |
403 # define __READAVAILBYTES__(ret, f, buf, cnt, isBuffered, handleType) \ |
403 # define __READAVAILBYTES__(ret, f, buf, cnt, isBuffered, handleType) \ |
404 { \ |
404 { \ |
405 int __offs = 0; \ |
405 int __offs = 0; \ |
406 int oldFlags; \ |
406 int oldFlags; \ |
407 \ |
407 \ |
408 (ret) = 0; \ |
408 (ret) = 0; \ |
409 if (isBuffered) { \ |
409 if (isBuffered) { \ |
410 while (__offs < (cnt)) { \ |
410 while (__offs < (cnt)) { \ |
411 CLEAR_ERRNO; \ |
411 CLEAR_ERRNO; \ |
412 (ret) = getc(f); \ |
412 (ret) = getc(f); \ |
413 if ((ret) < 0) { \ |
413 if ((ret) < 0) { \ |
414 if (ferror(f)) { \ |
414 if (ferror(f)) { \ |
415 if (__threadErrno == EINTR) { \ |
415 if (__threadErrno == EINTR) { \ |
416 clearerr(f); \ |
416 clearerr(f); \ |
417 continue; \ |
417 continue; \ |
418 } \ |
418 } \ |
419 } else { \ |
419 } else { \ |
420 (ret) = 0; \ |
420 (ret) = 0; \ |
421 } \ |
421 } \ |
422 break; \ |
422 break; \ |
423 } \ |
423 } \ |
424 (buf)[__offs++] = (ret); \ |
424 (buf)[__offs++] = (ret); \ |
425 } \ |
425 } \ |
426 if (__offs > 0) \ |
426 if (__offs > 0) \ |
427 (ret) = __offs; \ |
427 (ret) = __offs; \ |
428 } else { \ |
428 } else { \ |
429 while (__offs < (cnt)) { \ |
429 while (__offs < (cnt)) { \ |
430 OBJ rA = __INST(readAhead); \ |
430 OBJ rA = __INST(readAhead); \ |
431 if (rA != nil) { \ |
431 if (rA != nil) { \ |
432 (buf)[__offs] = __intVal(rA); \ |
432 (buf)[__offs] = __intVal(rA); \ |
433 __INST(readAhead) = nil; \ |
433 __INST(readAhead) = nil; \ |
434 (ret) = 1; \ |
434 (ret) = 1; \ |
435 __offs += (ret); \ |
435 __offs += (ret); \ |
436 continue; \ |
436 continue; \ |
437 } \ |
437 } \ |
438 CLEAR_ERRNO; \ |
438 CLEAR_ERRNO; \ |
439 { \ |
439 { \ |
440 int res; \ |
440 int res; \ |
441 if ((handleType == @symbol(socketFilePointer)) \ |
441 if ((handleType == @symbol(socketFilePointer)) \ |
442 || ((handleType == nil) && (ioctlsocket((SOCKET)_get_osfhandle(fileno(f)),FIONREAD,&res)==0))) { \ |
442 || ((handleType == nil) && (ioctlsocket((SOCKET)_get_osfhandle(fileno(f)),FIONREAD,&res)==0))) { \ |
443 if (res > 0) { \ |
443 if (res > 0) { \ |
444 if (res > ((cnt)-__offs)) \ |
444 if (res > ((cnt)-__offs)) \ |
445 res = (cnt)-__offs; \ |
445 res = (cnt)-__offs; \ |
446 READ(ret,f, (buf)+__offs, res, handleType); \ |
446 READ(ret,f, (buf)+__offs, res, handleType); \ |
447 } else { \ |
447 } else { \ |
448 (ret) = 0; \ |
448 (ret) = 0; \ |
449 } \ |
449 } \ |
450 } else if ((handleType == @symbol(pipeFilePointer)) \ |
450 } else if ((handleType == @symbol(pipeFilePointer)) \ |
451 || ((handleType == nil) && (PeekNamedPipe((HANDLE)_get_osfhandle(fileno(f)),0, 0,0,&res,0)))) { \ |
451 || ((handleType == nil) && (PeekNamedPipe((HANDLE)_get_osfhandle(fileno(f)),0, 0,0,&res,0)))) { \ |
452 if (res > 0) { \ |
452 if (res > 0) { \ |
453 if (res > ((cnt)-__offs)) \ |
453 if (res > ((cnt)-__offs)) \ |
454 res = (cnt)-__offs; \ |
454 res = (cnt)-__offs; \ |
455 READ(ret,f, (buf)+__offs, res, handleType); \ |
455 READ(ret,f, (buf)+__offs, res, handleType); \ |
456 } else \ |
456 } else \ |
457 ret = 0; \ |
457 ret = 0; \ |
458 } else { \ |
458 } else { \ |
459 READ(ret,f, (buf)+__offs, (cnt)-__offs, handleType); \ |
459 READ(ret,f, (buf)+__offs, (cnt)-__offs, handleType); \ |
460 } \ |
460 } \ |
461 } \ |
461 } \ |
462 if ((ret) < 0) { \ |
462 if ((ret) < 0) { \ |
463 if (__threadErrno == EINTR) { \ |
463 if (__threadErrno == EINTR) { \ |
464 continue; \ |
464 continue; \ |
465 } \ |
465 } \ |
466 break; \ |
466 break; \ |
467 } \ |
467 } \ |
468 __offs += (ret); \ |
468 __offs += (ret); \ |
469 break; \ |
469 break; \ |
470 } \ |
470 } \ |
471 if (__offs > 0) \ |
471 if (__offs > 0) \ |
472 (ret) = __offs; \ |
472 (ret) = __offs; \ |
473 } \ |
473 } \ |
474 } |
474 } |
475 |
475 |
476 # define IO_BUFFER_SIZE (8*1024) |
476 # define IO_BUFFER_SIZE (8*1024) |
477 |
477 |
478 # define __READBYTES_OBJ__(ret, f, obj, obj_offs, cnt, isBuffered, handleType) \ |
478 # define __READBYTES_OBJ__(ret, f, obj, obj_offs, cnt, isBuffered, handleType) \ |
479 { \ |
479 { \ |
480 int __ooffs = obj_offs; \ |
480 int __ooffs = obj_offs; \ |
481 int __offs = 0; \ |
481 int __offs = 0; \ |
482 char *buf = (char *)(obj); \ |
482 char *buf = (char *)(obj); \ |
483 \ |
483 \ |
484 (ret) = 0; \ |
484 (ret) = 0; \ |
485 if (isBuffered) { \ |
485 if (isBuffered) { \ |
486 while (__offs < (cnt)) { \ |
486 while (__offs < (cnt)) { \ |
487 CLEAR_ERRNO; \ |
487 CLEAR_ERRNO; \ |
488 (ret) = getc(f); \ |
488 (ret) = getc(f); \ |
489 if ((ret) < 0) { \ |
489 if ((ret) < 0) { \ |
490 if (ferror(f)) { \ |
490 if (ferror(f)) { \ |
491 if (__threadErrno == EINTR) { \ |
491 if (__threadErrno == EINTR) { \ |
492 clearerr(f); \ |
492 clearerr(f); \ |
493 /* refetch */ \ |
493 /* refetch */ \ |
494 buf = (char *)(obj); \ |
494 buf = (char *)(obj); \ |
495 continue; \ |
495 continue; \ |
496 } \ |
496 } \ |
497 } else { \ |
497 } else { \ |
498 (ret) = 0; \ |
498 (ret) = 0; \ |
499 } \ |
499 } \ |
500 break; \ |
500 break; \ |
501 } \ |
501 } \ |
502 (buf)[__ooffs+__offs] = (ret); \ |
502 (buf)[__ooffs+__offs] = (ret); \ |
503 __offs++; \ |
503 __offs++; \ |
504 } \ |
504 } \ |
505 if (__offs > 0) \ |
505 if (__offs > 0) \ |
506 (ret) = __offs; \ |
506 (ret) = __offs; \ |
507 } else { \ |
507 } else { \ |
508 while (__offs < (cnt)) { \ |
508 while (__offs < (cnt)) { \ |
509 char __buf[IO_BUFFER_SIZE]; \ |
509 char __buf[IO_BUFFER_SIZE]; \ |
510 OBJ rA = __INST(readAhead); \ |
510 OBJ rA = __INST(readAhead); \ |
511 if (rA != nil) { \ |
511 if (rA != nil) { \ |
512 (buf)[__ooffs+__offs] = __intVal(rA); \ |
512 (buf)[__ooffs+__offs] = __intVal(rA); \ |
513 __INST(readAhead) = nil; \ |
513 __INST(readAhead) = nil; \ |
514 (ret) = 1; \ |
514 (ret) = 1; \ |
515 } else { \ |
515 } else { \ |
516 int l; \ |
516 int l; \ |
517 CLEAR_ERRNO; \ |
517 CLEAR_ERRNO; \ |
518 l = (cnt)-__offs; \ |
518 l = (cnt)-__offs; \ |
519 if ( l > IO_BUFFER_SIZE) \ |
519 if ( l > IO_BUFFER_SIZE) \ |
520 l = IO_BUFFER_SIZE; \ |
520 l = IO_BUFFER_SIZE; \ |
521 READ(ret,f, __buf, l, handleType); \ |
521 READ(ret,f, __buf, l, handleType); \ |
522 if ((ret) <= 0) { \ |
522 if ((ret) <= 0) { \ |
523 if ((ret) < 0 && __threadErrno == EINTR) { \ |
523 if ((ret) < 0 && __threadErrno == EINTR) { \ |
524 continue; \ |
524 continue; \ |
525 } \ |
525 } \ |
526 break; \ |
526 break; \ |
527 } \ |
527 } \ |
528 } \ |
528 } \ |
529 if( (ret) > 0 ) { \ |
529 if( (ret) > 0 ) { \ |
530 /* refetch */ \ |
530 /* refetch */ \ |
531 buf = (char *)(obj); \ |
531 buf = (char *)(obj); \ |
532 memcpy((buf)+__ooffs+__offs,__buf,(ret)); \ |
532 memcpy((buf)+__ooffs+__offs,__buf,(ret)); \ |
533 __offs += (ret); \ |
533 __offs += (ret); \ |
534 } else { \ |
534 } else { \ |
535 (ret) = 0; \ |
535 (ret) = 0; \ |
536 } \ |
536 } \ |
537 } \ |
537 } \ |
538 if (__offs > 0) \ |
538 if (__offs > 0) \ |
539 (ret) = __offs; \ |
539 (ret) = __offs; \ |
540 } \ |
540 } \ |
541 } |
541 } |
542 |
542 |
543 # define __READAVAILBYTES_OBJ__(ret, f, obj, obj_offs, cnt, isBuffered, handleType)\ |
543 # define __READAVAILBYTES_OBJ__(ret, f, obj, obj_offs, cnt, isBuffered, handleType)\ |
544 { \ |
544 { \ |
545 int __ooffs = obj_offs; \ |
545 int __ooffs = obj_offs; \ |
546 int __offs = 0; \ |
546 int __offs = 0; \ |
547 char *buf = (char *)(obj); \ |
547 char *buf = (char *)(obj); \ |
548 \ |
548 \ |
549 (ret) = 0; \ |
549 (ret) = 0; \ |
550 if (isBuffered) { \ |
550 if (isBuffered) { \ |
551 while (__offs < (cnt)) { \ |
551 while (__offs < (cnt)) { \ |
552 CLEAR_ERRNO; \ |
552 CLEAR_ERRNO; \ |
553 (ret) = getc(f); \ |
553 (ret) = getc(f); \ |
554 if ((ret) < 0) { \ |
554 if ((ret) < 0) { \ |
555 if (ferror(f)) { \ |
555 if (ferror(f)) { \ |
556 if (__threadErrno == EINTR) { \ |
556 if (__threadErrno == EINTR) { \ |
557 clearerr(f); \ |
557 clearerr(f); \ |
558 /* refetch */ \ |
558 /* refetch */ \ |
559 buf = (char *)(obj);\ |
559 buf = (char *)(obj);\ |
560 continue; \ |
560 continue; \ |
561 } \ |
561 } \ |
562 } else { \ |
562 } else { \ |
563 (ret) = 0; \ |
563 (ret) = 0; \ |
564 } \ |
564 } \ |
565 break; \ |
565 break; \ |
566 } \ |
566 } \ |
567 (buf)[__ooffs+__offs] = (ret); \ |
567 (buf)[__ooffs+__offs] = (ret); \ |
568 __offs++; \ |
568 __offs++; \ |
569 } \ |
569 } \ |
570 if (__offs > 0) \ |
570 if (__offs > 0) \ |
571 (ret) = __offs; \ |
571 (ret) = __offs; \ |
572 } else { \ |
572 } else { \ |
573 while (__offs < (cnt)) { \ |
573 while (__offs < (cnt)) { \ |
574 char __buf[IO_BUFFER_SIZE]; \ |
574 char __buf[IO_BUFFER_SIZE]; \ |
575 OBJ rA = __INST(readAhead); \ |
575 OBJ rA = __INST(readAhead); \ |
576 if (rA != nil) { \ |
576 if (rA != nil) { \ |
577 (buf)[__ooffs+__offs] = __intVal(rA);\ |
577 (buf)[__ooffs+__offs] = __intVal(rA);\ |
578 __INST(readAhead) = nil; \ |
578 __INST(readAhead) = nil; \ |
579 (ret) = 1; \ |
579 (ret) = 1; \ |
580 __offs += (ret); \ |
580 __offs += (ret); \ |
581 continue; \ |
581 continue; \ |
582 } \ |
582 } \ |
583 { \ |
583 { \ |
584 int l; \ |
584 int l; \ |
585 int res; \ |
585 int res; \ |
586 CLEAR_ERRNO; \ |
586 CLEAR_ERRNO; \ |
587 l = (cnt)-__offs; \ |
587 l = (cnt)-__offs; \ |
588 if ( l > IO_BUFFER_SIZE) \ |
588 if ( l > IO_BUFFER_SIZE) \ |
589 l = IO_BUFFER_SIZE; \ |
589 l = IO_BUFFER_SIZE; \ |
590 if (ioctlsocket((SOCKET)_get_osfhandle(fileno(f)),FIONREAD,&res)==0) { \ |
590 if (ioctlsocket((SOCKET)_get_osfhandle(fileno(f)),FIONREAD,&res)==0) { \ |
591 if (res > 0) { \ |
591 if (res > 0) { \ |
592 if (res > l) \ |
592 if (res > l) \ |
593 res = l; \ |
593 res = l; \ |
594 READ(ret,f, __buf, res, handleType); \ |
594 READ(ret,f, __buf, res, handleType); \ |
595 } else { \ |
595 } else { \ |
596 (ret) = 0; \ |
596 (ret) = 0; \ |
597 } \ |
597 } \ |
598 } else if (PeekNamedPipe((HANDLE)_get_osfhandle(fileno(f)),0, 0,0,&res,0)) { \ |
598 } else if (PeekNamedPipe((HANDLE)_get_osfhandle(fileno(f)),0, 0,0,&res,0)) { \ |
599 if (res > 0) { \ |
599 if (res > 0) { \ |
600 if (res > l) \ |
600 if (res > l) \ |
601 res = l; \ |
601 res = l; \ |
602 READ(ret,f, __buf, res, handleType); \ |
602 READ(ret,f, __buf, res, handleType); \ |
603 } else \ |
603 } else \ |
604 (ret) = 0; \ |
604 (ret) = 0; \ |
605 } else { \ |
605 } else { \ |
606 READ(ret,f, __buf, l, handleType); \ |
606 READ(ret,f, __buf, l, handleType); \ |
607 } \ |
607 } \ |
608 if ((ret) < 0 && __threadErrno == EINTR) { \ |
608 if ((ret) < 0 && __threadErrno == EINTR) { \ |
609 continue; \ |
609 continue; \ |
610 } \ |
610 } \ |
611 } \ |
611 } \ |
612 if( (ret) > 0 ) { \ |
612 if( (ret) > 0 ) { \ |
613 /* refetch */ \ |
613 /* refetch */ \ |
614 buf = (char *)(obj); \ |
614 buf = (char *)(obj); \ |
615 memcpy((buf)+__ooffs+__offs,__buf,(ret)); \ |
615 memcpy((buf)+__ooffs+__offs,__buf,(ret)); \ |
616 __offs += (ret); \ |
616 __offs += (ret); \ |
617 } else { \ |
617 } else { \ |
618 (ret) = 0; \ |
618 (ret) = 0; \ |
619 } \ |
619 } \ |
620 break; \ |
620 break; \ |
621 } \ |
621 } \ |
622 if (__offs > 0) \ |
622 if (__offs > 0) \ |
623 (ret) = __offs; \ |
623 (ret) = __offs; \ |
624 } \ |
624 } \ |
625 } |
625 } |
626 |
626 |
627 # define __WRITEBYTE__(ret, f, buf, isBuffered, handleType) \ |
627 # define __WRITEBYTE__(ret, f, buf, isBuffered, handleType) \ |
628 if (isBuffered) { \ |
628 if (isBuffered) { \ |
629 for (;;) { \ |
629 for (;;) { \ |
630 CLEAR_ERRNO; \ |
630 CLEAR_ERRNO; \ |
631 ret = putc(*(buf), f); \ |
631 ret = putc(*(buf), f); \ |
632 if ((ret) >= 0) { \ |
632 if ((ret) >= 0) { \ |
633 (ret) = 1; \ |
633 (ret) = 1; \ |
634 } else if (ferror(f)) { \ |
634 } else if (ferror(f)) { \ |
635 if (__threadErrno == EINTR) { \ |
635 if (__threadErrno == EINTR) { \ |
636 clearerr(f); \ |
636 clearerr(f); \ |
637 continue; \ |
637 continue; \ |
638 } \ |
638 } \ |
639 } else \ |
639 } else \ |
640 (ret) = 0; \ |
640 (ret) = 0; \ |
641 break; \ |
641 break; \ |
642 } \ |
642 } \ |
643 } else { \ |
643 } else { \ |
644 for (;;) { \ |
644 for (;;) { \ |
645 CLEAR_ERRNO; \ |
645 CLEAR_ERRNO; \ |
646 WRITE(ret,f, buf, 1, handleType); \ |
646 WRITE(ret,f, buf, 1, handleType); \ |
647 if ((ret) >= 0 || __threadErrno != EINTR) \ |
647 if ((ret) >= 0 || __threadErrno != EINTR) \ |
648 break; \ |
648 break; \ |
649 } \ |
649 } \ |
650 } |
650 } |
651 |
651 |
652 # define __WRITEBYTES__(ret, f, buf, cnt, isBuffered, handleType) \ |
652 # define __WRITEBYTES__(ret, f, buf, cnt, isBuffered, handleType) \ |
653 (ret) = 0; \ |
653 (ret) = 0; \ |
654 if (isBuffered) { \ |
654 if (isBuffered) { \ |
655 int __offs = 0; \ |
655 int __offs = 0; \ |
656 while (__offs < (cnt)) { \ |
656 while (__offs < (cnt)) { \ |
657 CLEAR_ERRNO; \ |
657 CLEAR_ERRNO; \ |
658 (ret) = fwrite((buf)+__offs, 1, (cnt)-__offs, f);\ |
658 (ret) = fwrite((buf)+__offs, 1, (cnt)-__offs, f);\ |
659 if ((ret) <= 0) { \ |
659 if ((ret) <= 0) { \ |
660 if (ferror(f)) { \ |
660 if (ferror(f)) { \ |
661 if (__threadErrno == EINTR) { \ |
661 if (__threadErrno == EINTR) { \ |
662 clearerr(f); \ |
662 clearerr(f); \ |
663 continue; \ |
663 continue; \ |
664 } \ |
664 } \ |
665 break; \ |
665 break; \ |
666 } else { \ |
666 } else { \ |
667 (ret) = 0; \ |
667 (ret) = 0; \ |
668 } \ |
668 } \ |
669 } \ |
669 } \ |
670 __offs += (ret); \ |
670 __offs += (ret); \ |
671 } \ |
671 } \ |
672 if (__offs > 0) \ |
672 if (__offs > 0) \ |
673 (ret) = __offs; \ |
673 (ret) = __offs; \ |
674 } else { \ |
674 } else { \ |
675 int __offs = 0; \ |
675 int __offs = 0; \ |
676 while (__offs < (cnt)) { \ |
676 while (__offs < (cnt)) { \ |
677 CLEAR_ERRNO; \ |
677 CLEAR_ERRNO; \ |
678 WRITE(ret,f, (buf)+__offs, (cnt)-__offs, handleType); \ |
678 WRITE(ret,f, (buf)+__offs, (cnt)-__offs, handleType); \ |
679 if (ret <= 0) { \ |
679 if (ret <= 0) { \ |
680 if (ret < 0 && __threadErrno == EINTR) { \ |
680 if (ret < 0 && __threadErrno == EINTR) { \ |
681 continue; \ |
681 continue; \ |
682 } \ |
682 } \ |
683 break; \ |
683 break; \ |
684 } \ |
684 } \ |
685 __offs += (ret); \ |
685 __offs += (ret); \ |
686 } \ |
686 } \ |
687 if (__offs > 0) \ |
687 if (__offs > 0) \ |
688 (ret) = __offs; \ |
688 (ret) = __offs; \ |
689 } |
689 } |
690 |
690 |
691 # define __WRITEBYTES_OBJ__(ret, f, obj, obj_offs, cnt, isBuffered, handleType) \ |
691 # define __WRITEBYTES_OBJ__(ret, f, obj, obj_offs, cnt, isBuffered, handleType) \ |
692 { \ |
692 { \ |
693 int __ooffs = obj_offs; \ |
693 int __ooffs = obj_offs; \ |
694 int __offs = 0; \ |
694 int __offs = 0; \ |
695 char *buf = (char *)(obj); \ |
695 char *buf = (char *)(obj); \ |
696 \ |
696 \ |
697 (ret) = 0; \ |
697 (ret) = 0; \ |
698 if (isBuffered) { \ |
698 if (isBuffered) { \ |
699 while (__offs < (cnt)) { \ |
699 while (__offs < (cnt)) { \ |
700 CLEAR_ERRNO; \ |
700 CLEAR_ERRNO; \ |
701 ret = fwrite((buf)+__ooffs+__offs, 1, (cnt)-__offs, f); \ |
701 ret = fwrite((buf)+__ooffs+__offs, 1, (cnt)-__offs, f); \ |
702 if ((ret) <= 0) { \ |
702 if ((ret) <= 0) { \ |
703 if (ferror(f)) { \ |
703 if (ferror(f)) { \ |
704 if (__threadErrno == EINTR) { \ |
704 if (__threadErrno == EINTR) { \ |
705 /* refetch */ \ |
705 /* refetch */ \ |
706 buf = (char *)(obj); \ |
706 buf = (char *)(obj); \ |
707 clearerr(f); \ |
707 clearerr(f); \ |
708 continue; \ |
708 continue; \ |
709 } \ |
709 } \ |
710 break; \ |
710 break; \ |
711 } else { \ |
711 } else { \ |
712 (ret) = 0; \ |
712 (ret) = 0; \ |
713 } \ |
713 } \ |
714 } \ |
714 } \ |
715 __offs += (ret); \ |
715 __offs += (ret); \ |
716 } \ |
716 } \ |
717 if (__offs > 0) \ |
717 if (__offs > 0) \ |
718 (ret) = __offs; \ |
718 (ret) = __offs; \ |
719 } else { \ |
719 } else { \ |
720 while (__offs < (cnt)) { \ |
720 while (__offs < (cnt)) { \ |
721 char __buf[IO_BUFFER_SIZE]; \ |
721 char __buf[IO_BUFFER_SIZE]; \ |
722 int l; \ |
722 int l; \ |
723 CLEAR_ERRNO; \ |
723 CLEAR_ERRNO; \ |
724 l = (cnt)-__offs; \ |
724 l = (cnt)-__offs; \ |
725 if ( l > IO_BUFFER_SIZE) \ |
725 if ( l > IO_BUFFER_SIZE) \ |
726 l = IO_BUFFER_SIZE; \ |
726 l = IO_BUFFER_SIZE; \ |
727 /* refetch */ \ |
727 /* refetch */ \ |
728 buf = (char *)(obj); \ |
728 buf = (char *)(obj); \ |
729 memcpy(__buf,(buf)+__ooffs+__offs,l); \ |
729 memcpy(__buf,(buf)+__ooffs+__offs,l); \ |
730 WRITE(ret,f, __buf, l, handleType); \ |
730 WRITE(ret,f, __buf, l, handleType); \ |
731 if (ret <= 0) { \ |
731 if (ret <= 0) { \ |
732 if (ret < 0 && __threadErrno == EINTR) { \ |
732 if (ret < 0 && __threadErrno == EINTR) { \ |
733 continue; \ |
733 continue; \ |
734 } \ |
734 } \ |
735 break; \ |
735 break; \ |
736 } \ |
736 } \ |
737 __offs += (ret); \ |
737 __offs += (ret); \ |
738 } \ |
738 } \ |
739 if (__offs > 0) \ |
739 if (__offs > 0) \ |
740 (ret) = __offs; \ |
740 (ret) = __offs; \ |
741 } \ |
741 } \ |
742 } |
742 } |
743 |
743 |
744 #else /* ! WIN32 */ |
744 #else /* ! WIN32 */ |
745 /* ======================== UNIX / LINUX ====================================================== */ |
745 /* ======================== UNIX / LINUX ====================================================== */ |
746 # define __READING__(f) \ |
746 # define __READING__(f) \ |
747 if ((__INST(didWrite) != false) \ |
747 if ((__INST(didWrite) != false) \ |
748 && (__INST(mode) == @symbol(readwrite))) { \ |
748 && (__INST(mode) == @symbol(readwrite))) { \ |
749 __INST(didWrite) = false; \ |
749 __INST(didWrite) = false; \ |
750 OPT_FSEEK(f, 0L, SEEK_CUR); /* needed in stdio */ \ |
750 OPT_FSEEK(f, 0L, SEEK_CUR); /* needed in stdio */ \ |
751 } |
751 } |
752 |
752 |
753 # define __WRITING__(f) \ |
753 # define __WRITING__(f) \ |
754 if ((__INST(didWrite) != true) \ |
754 if ((__INST(didWrite) != true) \ |
755 && (__INST(mode) == @symbol(readwrite))) { \ |
755 && (__INST(mode) == @symbol(readwrite))) { \ |
756 __INST(didWrite) = true; \ |
756 __INST(didWrite) = true; \ |
757 OPT_FSEEK(f, 0L, SEEK_CUR); /* needed in stdio */ \ |
757 OPT_FSEEK(f, 0L, SEEK_CUR); /* needed in stdio */ \ |
758 } |
758 } |
759 |
759 |
760 |
760 |
761 # ifdef NO_STDIO |
761 # ifdef NO_STDIO |
762 # define __UNGETC__(c, f, isBuffered) \ |
762 # define __UNGETC__(c, f, isBuffered) \ |
763 __INST(readAhead) = __mkSmallInteger((c)); |
763 __INST(readAhead) = __mkSmallInteger((c)); |
764 # else /* use STDIO */ |
764 # else /* use STDIO */ |
765 # define __UNGETC__(c, f, isBuffered) \ |
765 # define __UNGETC__(c, f, isBuffered) \ |
766 if (isBuffered) { \ |
766 if (isBuffered) { \ |
767 ungetc((c), (f)); \ |
767 ungetc((c), (f)); \ |
768 } else { \ |
768 } else { \ |
769 __INST(readAhead) = __mkSmallInteger((c)); \ |
769 __INST(readAhead) = __mkSmallInteger((c)); \ |
770 } |
770 } |
771 # endif /* use STDIO */ |
771 # endif /* use STDIO */ |
772 |
772 |
773 # ifdef NO_STDIO |
773 # ifdef NO_STDIO |
774 # define __READBYTE__(ret, f, buf, isBuffered, handleType) \ |
774 # define __READBYTE__(ret, f, buf, isBuffered, handleType) \ |
775 { \ |
775 { \ |
776 OBJ rA = __INST(readAhead); \ |
776 OBJ rA = __INST(readAhead); \ |
777 if (rA != nil) { \ |
777 if (rA != nil) { \ |
778 *(buf) = __intVal(rA); \ |
778 *(buf) = __intVal(rA); \ |
779 DEBUGBUFFER(buf); \ |
779 DEBUGBUFFER(buf); \ |
780 __INST(readAhead) = nil; \ |
780 __INST(readAhead) = nil; \ |
781 (ret) = 1; \ |
781 (ret) = 1; \ |
782 } else { \ |
782 } else { \ |
783 for (;;) { \ |
783 for (;;) { \ |
784 CLEAR_ERRNO; \ |
784 CLEAR_ERRNO; \ |
785 (ret) = READ(f, buf, 1, handleType); \ |
785 (ret) = READ(f, buf, 1, handleType); \ |
786 DEBUGBUFFER(buf); \ |
786 DEBUGBUFFER(buf); \ |
787 if ((ret) >= 0) break; \ |
787 if ((ret) >= 0) break; \ |
788 if (errno != EINTR) { \ |
788 if (errno != EINTR) { \ |
789 break; \ |
789 break; \ |
790 } \ |
790 } \ |
791 __HANDLE_INTERRUPTS__; \ |
791 __HANDLE_INTERRUPTS__; \ |
792 } \ |
792 } \ |
793 } \ |
793 } \ |
794 } |
794 } |
795 # else /* use STDIO */ |
795 # else /* use STDIO */ |
796 # define __READBYTE__(ret, f, buf, isBuffered, handleType) \ |
796 # define __READBYTE__(ret, f, buf, isBuffered, handleType) \ |
797 if (isBuffered) { \ |
797 if (isBuffered) { \ |
798 for (;;) { \ |
798 for (;;) { \ |
799 CLEAR_ERRNO; \ |
799 CLEAR_ERRNO; \ |
800 (ret) = getc(f); \ |
800 (ret) = getc(f); \ |
801 if ((ret) >= 0) { \ |
801 if ((ret) >= 0) { \ |
802 DEBUGBUFFER(buf); \ |
802 DEBUGBUFFER(buf); \ |
803 *(buf) = (ret); \ |
803 *(buf) = (ret); \ |
804 (ret) = 1; \ |
804 (ret) = 1; \ |
805 } else if (ferror(f)) { \ |
805 } else if (ferror(f)) { \ |
806 if (errno == EINTR) { \ |
806 if (errno == EINTR) { \ |
807 __HANDLE_INTERRUPTS__; \ |
807 __HANDLE_INTERRUPTS__; \ |
808 clearerr(f); \ |
808 clearerr(f); \ |
809 continue; \ |
809 continue; \ |
810 } \ |
810 } \ |
811 } else \ |
811 } else \ |
812 (ret) = 0; \ |
812 (ret) = 0; \ |
813 break; \ |
813 break; \ |
814 } \ |
814 } \ |
815 } else { \ |
815 } else { \ |
816 OBJ rA = __INST(readAhead); \ |
816 OBJ rA = __INST(readAhead); \ |
817 if (rA != nil) { \ |
817 if (rA != nil) { \ |
818 *(buf) = __intVal(rA); \ |
818 *(buf) = __intVal(rA); \ |
819 DEBUGBUFFER(buf); \ |
819 DEBUGBUFFER(buf); \ |
820 __INST(readAhead) = nil; \ |
820 __INST(readAhead) = nil; \ |
821 (ret) = 1; \ |
821 (ret) = 1; \ |
822 } else { \ |
822 } else { \ |
823 for (;;) { \ |
823 for (;;) { \ |
824 CLEAR_ERRNO; \ |
824 CLEAR_ERRNO; \ |
825 (ret) = read(fileno(f), buf, 1); \ |
825 (ret) = read(fileno(f), buf, 1); \ |
826 DEBUGBUFFER(buf); \ |
826 DEBUGBUFFER(buf); \ |
827 if ((ret) >= 0) break; \ |
827 if ((ret) >= 0) break; \ |
828 if (errno != EINTR) { \ |
828 if (errno != EINTR) { \ |
829 break; \ |
829 break; \ |
830 } \ |
830 } \ |
831 __HANDLE_INTERRUPTS__; \ |
831 __HANDLE_INTERRUPTS__; \ |
832 } \ |
832 } \ |
833 } \ |
833 } \ |
834 } |
834 } |
835 # endif /* use STDIO */ |
835 # endif /* use STDIO */ |
836 |
836 |
837 /* |
837 /* |
838 * read_bytes into a c-buffer |
838 * read_bytes into a c-buffer |
839 * (which may NOT move) |
839 * (which may NOT move) |
840 */ |
840 */ |
841 # ifdef NO_STDIO |
841 # ifdef NO_STDIO |
842 # define __READBYTES__(ret, f, buf, cnt, isBuffered, handleType) \ |
842 # define __READBYTES__(ret, f, buf, cnt, isBuffered, handleType) \ |
843 { \ |
843 { \ |
844 int __offs = 0, __cnt; \ |
844 int __offs = 0, __cnt; \ |
845 \ |
845 \ |
846 while (__offs < (cnt)) { \ |
846 while (__offs < (cnt)) { \ |
847 OBJ rA = __INST(readAhead); \ |
847 OBJ rA = __INST(readAhead); \ |
848 if (rA != nil) { \ |
848 if (rA != nil) { \ |
849 (buf)[__offs] = __intVal(rA); \ |
849 (buf)[__offs] = __intVal(rA); \ |
850 DEBUGBUFFER(buf); \ |
850 DEBUGBUFFER(buf); \ |
851 __INST(readAhead) = nil; \ |
851 __INST(readAhead) = nil; \ |
852 __offs++; \ |
852 __offs++; \ |
853 } else { \ |
853 } else { \ |
854 CLEAR_ERRNO; \ |
854 CLEAR_ERRNO; \ |
855 __cnt = READ(f, (buf)+__offs, (cnt)-__offs, handleType); \ |
855 __cnt = READ(f, (buf)+__offs, (cnt)-__offs, handleType); \ |
856 DEBUGBUFFER(buf); \ |
856 DEBUGBUFFER(buf); \ |
857 if (__cnt <= 0) { \ |
857 if (__cnt <= 0) { \ |
858 if (__cnt < 0 && errno == EINTR) { \ |
858 if (__cnt < 0 && errno == EINTR) { \ |
859 __HANDLE_INTERRUPTS__; \ |
859 __HANDLE_INTERRUPTS__; \ |
860 continue; \ |
860 continue; \ |
861 } \ |
861 } \ |
862 break; \ |
862 break; \ |
863 } \ |
863 } \ |
864 __offs += __cnt; \ |
864 __offs += __cnt; \ |
865 } \ |
865 } \ |
866 } \ |
866 } \ |
867 if (__offs > 0) \ |
867 if (__offs > 0) \ |
868 (ret) = __offs; \ |
868 (ret) = __offs; \ |
869 } |
869 } |
870 # else /* use STDIO */ |
870 # else /* use STDIO */ |
871 # define __READBYTES__(ret, f, buf, cnt, isBuffered, handleType) \ |
871 # define __READBYTES__(ret, f, buf, cnt, isBuffered, handleType) \ |
872 (ret) = 0; \ |
872 (ret) = 0; \ |
873 if (isBuffered) { \ |
873 if (isBuffered) { \ |
874 int __offs = 0; \ |
874 int __offs = 0; \ |
875 while (__offs < (cnt)) { \ |
875 while (__offs < (cnt)) { \ |
876 CLEAR_ERRNO; \ |
876 CLEAR_ERRNO; \ |
877 (ret) = getc(f); \ |
877 (ret) = getc(f); \ |
878 if ((ret) < 0) { \ |
878 if ((ret) < 0) { \ |
879 if (ferror(f)) { \ |
879 if (ferror(f)) { \ |
880 if (errno == EINTR) { \ |
880 if (errno == EINTR) { \ |
881 __HANDLE_INTERRUPTS__; \ |
881 __HANDLE_INTERRUPTS__; \ |
882 clearerr(f); \ |
882 clearerr(f); \ |
883 continue; \ |
883 continue; \ |
884 } \ |
884 } \ |
885 } else { \ |
885 } else { \ |
886 (ret) = 0; \ |
886 (ret) = 0; \ |
887 } \ |
887 } \ |
888 break; \ |
888 break; \ |
889 } \ |
889 } \ |
890 DEBUGBUFFER(buf); \ |
890 DEBUGBUFFER(buf); \ |
891 (buf)[__offs++] = (ret); \ |
891 (buf)[__offs++] = (ret); \ |
892 } \ |
892 } \ |
893 if (__offs > 0) \ |
893 if (__offs > 0) \ |
894 (ret) = __offs; \ |
894 (ret) = __offs; \ |
895 } else { \ |
895 } else { \ |
896 int __offs = 0, __cnt; \ |
896 int __offs = 0, __cnt; \ |
897 int fd = fileno(f); \ |
897 int fd = fileno(f); \ |
898 \ |
898 \ |
899 while (__offs < (cnt)) { \ |
899 while (__offs < (cnt)) { \ |
900 OBJ rA = __INST(readAhead); \ |
900 OBJ rA = __INST(readAhead); \ |
901 if (rA != nil) { \ |
901 if (rA != nil) { \ |
902 DEBUGBUFFER(buf); \ |
902 DEBUGBUFFER(buf); \ |
903 (buf)[__offs] = __intVal(rA); \ |
903 (buf)[__offs] = __intVal(rA); \ |
904 __INST(readAhead) = nil; \ |
904 __INST(readAhead) = nil; \ |
905 __offs++; \ |
905 __offs++; \ |
906 } else { \ |
906 } else { \ |
907 CLEAR_ERRNO; \ |
907 CLEAR_ERRNO; \ |
908 __cnt = read(fd, (buf)+__offs, (cnt)-__offs); \ |
908 __cnt = read(fd, (buf)+__offs, (cnt)-__offs); \ |
909 DEBUGBUFFER(buf); \ |
909 DEBUGBUFFER(buf); \ |
910 if (__cnt <= 0) { \ |
910 if (__cnt <= 0) { \ |
911 if (__cnt < 0 && errno == EINTR) { \ |
911 if (__cnt < 0 && errno == EINTR) { \ |
912 __HANDLE_INTERRUPTS__; \ |
912 __HANDLE_INTERRUPTS__; \ |
913 continue; \ |
913 continue; \ |
914 } \ |
914 } \ |
915 break; \ |
915 break; \ |
916 } \ |
916 } \ |
917 __offs += __cnt; \ |
917 __offs += __cnt; \ |
918 } \ |
918 } \ |
919 } \ |
919 } \ |
920 if (__offs > 0) \ |
920 if (__offs > 0) \ |
921 (ret) = __offs; \ |
921 (ret) = __offs; \ |
922 } |
922 } |
923 |
923 |
924 |
924 |
925 /* |
925 /* |
926 * FNDELAY and O_NDELAY is deprecated, O_NONBLOCK is used in POSIX, XPG, etc... |
926 * FNDELAY and O_NDELAY is deprecated, O_NONBLOCK is used in POSIX, XPG, etc... |
927 */ |
927 */ |
928 |
928 |
929 # if defined(F_GETFL) && defined(F_SETFL) && (defined(O_NONBLOCK) || defined(O_NDELAY) || defined(FNDELAY)) |
929 # if defined(F_GETFL) && defined(F_SETFL) && (defined(O_NONBLOCK) || defined(O_NDELAY) || defined(FNDELAY)) |
930 # define SETFLAGS(fd, flags) \ |
930 # define SETFLAGS(fd, flags) \ |
931 fcntl(fd, F_SETFL, flags) |
931 fcntl(fd, F_SETFL, flags) |
932 |
932 |
933 # if defined(O_NONBLOCK) |
933 # if defined(O_NONBLOCK) |
934 # define __STX_NONBLOCK_FLAG O_NONBLOCK |
934 # define __STX_NONBLOCK_FLAG O_NONBLOCK |
935 # else |
935 # else |
936 # if defined(O_NDELAY) |
936 # if defined(O_NDELAY) |
1057 { \ |
1057 { \ |
1058 int __ooffs = obj_offs; \ |
1058 int __ooffs = obj_offs; \ |
1059 int __offs = 0; \ |
1059 int __offs = 0; \ |
1060 int __cnt; \ |
1060 int __cnt; \ |
1061 char *buf = (char *)(obj); \ |
1061 char *buf = (char *)(obj); \ |
1062 \ |
1062 \ |
1063 (ret) = 0; \ |
1063 (ret) = 0; \ |
1064 if (isBuffered) { \ |
1064 if (isBuffered) { \ |
1065 while (__offs < (cnt)) { \ |
1065 while (__offs < (cnt)) { \ |
1066 CLEAR_ERRNO; \ |
1066 CLEAR_ERRNO; \ |
1067 (ret) = getc(f); \ |
1067 (ret) = getc(f); \ |
1068 if ((ret) < 0) { \ |
1068 if ((ret) < 0) { \ |
1069 if (ferror(f)) { \ |
1069 if (ferror(f)) { \ |
1070 if (errno == EINTR) { \ |
1070 if (errno == EINTR) { \ |
1071 __HANDLE_INTERRUPTS__; \ |
1071 __HANDLE_INTERRUPTS__; \ |
1072 clearerr(f); \ |
1072 clearerr(f); \ |
1073 /* refetch */ \ |
1073 /* refetch */ \ |
1074 buf = (char *)(obj); \ |
1074 buf = (char *)(obj); \ |
1075 DEBUGBUFFER(buf); \ |
1075 DEBUGBUFFER(buf); \ |
1076 continue; \ |
1076 continue; \ |
1077 } \ |
1077 } \ |
1078 } else { \ |
1078 } else { \ |
1079 (ret) = 0; \ |
1079 (ret) = 0; \ |
1080 } \ |
1080 } \ |
1081 break; \ |
1081 break; \ |
1082 } \ |
1082 } \ |
1083 (buf)[__ooffs+__offs] = (ret); \ |
1083 (buf)[__ooffs+__offs] = (ret); \ |
1084 DEBUGBUFFER(buf); \ |
1084 DEBUGBUFFER(buf); \ |
1085 __offs++; \ |
1085 __offs++; \ |
1086 } \ |
1086 } \ |
1087 if (__offs > 0) \ |
1087 if (__offs > 0) \ |
1088 (ret) = __offs; \ |
1088 (ret) = __offs; \ |
1089 } else { \ |
1089 } else { \ |
1090 int fd = fileno(f); \ |
1090 int fd = fileno(f); \ |
1091 \ |
1091 \ |
1092 while (__offs < (cnt)) { \ |
1092 while (__offs < (cnt)) { \ |
1093 OBJ rA = __INST(readAhead); \ |
1093 OBJ rA = __INST(readAhead); \ |
1094 if (rA != nil) { \ |
1094 if (rA != nil) { \ |
1095 (buf)[__ooffs+__offs] = __intVal(rA); \ |
1095 (buf)[__ooffs+__offs] = __intVal(rA); \ |
1096 DEBUGBUFFER(buf); \ |
1096 DEBUGBUFFER(buf); \ |
1097 __INST(readAhead) = nil; \ |
1097 __INST(readAhead) = nil; \ |
1098 __offs++; \ |
1098 __offs++; \ |
1099 } else { \ |
1099 } else { \ |
1100 CLEAR_ERRNO; \ |
1100 CLEAR_ERRNO; \ |
1101 __cnt = read(fd, (buf)+__ooffs+__offs, (cnt)-__offs); \ |
1101 __cnt = read(fd, (buf)+__ooffs+__offs, (cnt)-__offs); \ |
1102 DEBUGBUFFER(buf); \ |
1102 DEBUGBUFFER(buf); \ |
1103 if (__cnt <= 0) { \ |
1103 if (__cnt <= 0) { \ |
1104 if (__cnt < 0 && errno == EINTR) { \ |
1104 if (__cnt < 0 && errno == EINTR) { \ |
1105 __HANDLE_INTERRUPTS__; \ |
1105 __HANDLE_INTERRUPTS__; \ |
1106 /* refetch */ \ |
1106 /* refetch */ \ |
1107 buf = (char *)(obj); \ |
1107 buf = (char *)(obj); \ |
1108 continue; \ |
1108 continue; \ |
1109 } \ |
1109 } \ |
1110 break; \ |
1110 break; \ |
1111 } \ |
1111 } \ |
1112 __offs += __cnt; \ |
1112 __offs += __cnt; \ |
1113 } \ |
1113 } \ |
1114 } \ |
1114 } \ |
1115 if (__offs > 0) \ |
1115 if (__offs > 0) \ |
1116 (ret) = __offs; \ |
1116 (ret) = __offs; \ |
1117 } \ |
1117 } \ |
1118 } |
1118 } |
1119 |
1119 |
1120 # define __READAVAILBYTES_OBJ__(ret, f, obj, obj_offs, cnt, isBuffered, handleType) \ |
1120 # define __READAVAILBYTES_OBJ__(ret, f, obj, obj_offs, cnt, isBuffered, handleType) \ |
1121 { \ |
1121 { \ |
1122 int __ooffs = obj_offs; \ |
1122 int __ooffs = obj_offs; \ |
1123 int __offs = 0; \ |
1123 int __offs = 0; \ |
1124 int __cnt; \ |
1124 int __cnt; \ |
1125 char *buf = (char *)(obj); \ |
1125 char *buf = (char *)(obj); \ |
1126 int oldFlags; \ |
1126 int oldFlags; \ |
1127 \ |
1127 \ |
1128 (ret) = 0; \ |
1128 (ret) = 0; \ |
1129 SETNONBLOCKING(fileno(f), oldFlags); \ |
1129 SETNONBLOCKING(fileno(f), oldFlags); \ |
1130 \ |
1130 \ |
1131 if (isBuffered) { \ |
1131 if (isBuffered) { \ |
1132 while (__offs < (cnt)) { \ |
1132 while (__offs < (cnt)) { \ |
1133 CLEAR_ERRNO; \ |
1133 CLEAR_ERRNO; \ |
1134 (ret) = getc(f); \ |
1134 (ret) = getc(f); \ |
1135 if ((ret) < 0) { \ |
1135 if ((ret) < 0) { \ |
1136 if (ferror(f)) { \ |
1136 if (ferror(f)) { \ |
1137 if (errno == EINTR) { \ |
1137 if (errno == EINTR) { \ |
1138 clearerr(f); \ |
1138 clearerr(f); \ |
1139 /* refetch */ \ |
1139 /* refetch */ \ |
1140 buf = (char *)(obj); \ |
1140 buf = (char *)(obj); \ |
1141 (ret) = 0; \ |
1141 (ret) = 0; \ |
1142 break; \ |
1142 break; \ |
1143 } \ |
1143 } \ |
1144 } else { \ |
1144 } else { \ |
1145 (ret) = 0; \ |
1145 (ret) = 0; \ |
1146 } \ |
1146 } \ |
1147 break; \ |
1147 break; \ |
1148 } \ |
1148 } \ |
1149 (buf)[__ooffs+__offs] = (ret); \ |
1149 (buf)[__ooffs+__offs] = (ret); \ |
1150 DEBUGBUFFER(buf); \ |
1150 DEBUGBUFFER(buf); \ |
1151 __offs++; \ |
1151 __offs++; \ |
1152 } \ |
1152 } \ |
1153 if (__offs > 0) \ |
1153 if (__offs > 0) \ |
1154 (ret) = __offs; \ |
1154 (ret) = __offs; \ |
1155 } else { \ |
1155 } else { \ |
1156 int fd = fileno(f); \ |
1156 int fd = fileno(f); \ |
1157 \ |
1157 \ |
1158 while (__offs < (cnt)) { \ |
1158 while (__offs < (cnt)) { \ |
1159 OBJ rA = __INST(readAhead); \ |
1159 OBJ rA = __INST(readAhead); \ |
1160 if (rA != nil) { \ |
1160 if (rA != nil) { \ |
1161 (buf)[__ooffs+__offs] = __intVal(rA); \ |
1161 (buf)[__ooffs+__offs] = __intVal(rA); \ |
1162 DEBUGBUFFER(buf); \ |
1162 DEBUGBUFFER(buf); \ |
1163 __INST(readAhead) = nil; \ |
1163 __INST(readAhead) = nil; \ |
1164 __offs++; \ |
1164 __offs++; \ |
1165 continue; \ |
1165 continue; \ |
1166 } \ |
1166 } \ |
1167 CLEAR_ERRNO; \ |
1167 CLEAR_ERRNO; \ |
1168 __cnt = read(fd, (buf)+__ooffs+__offs, (cnt)-__offs); \ |
1168 __cnt = read(fd, (buf)+__ooffs+__offs, (cnt)-__offs); \ |
1169 DEBUGBUFFER(buf); \ |
1169 DEBUGBUFFER(buf); \ |
1170 if (__cnt > 0) { \ |
1170 if (__cnt > 0) { \ |
1171 __offs += __cnt; \ |
1171 __offs += __cnt; \ |
1172 } \ |
1172 } \ |
1173 break; \ |
1173 break; \ |
1174 } \ |
1174 } \ |
1175 if (__offs > 0) \ |
1175 if (__offs > 0) \ |
1176 (ret) = __offs; \ |
1176 (ret) = __offs; \ |
1177 } \ |
1177 } \ |
1178 SETFLAGS(fileno(f), oldFlags); \ |
1178 SETFLAGS(fileno(f), oldFlags); \ |
1179 } |
1179 } |
1180 |
1180 |
1181 |
1181 |
1182 # endif /* use STDIO */ |
1182 # endif /* use STDIO */ |
1183 |
1183 |
1184 # ifdef NO_STDIO |
1184 # ifdef NO_STDIO |
1185 # define __WRITEBYTE__(ret, f, buf, isBuffered, handleType) \ |
1185 # define __WRITEBYTE__(ret, f, buf, isBuffered, handleType) \ |
1186 for (;;) { \ |
1186 for (;;) { \ |
1187 CLEAR_ERRNO; \ |
1187 CLEAR_ERRNO; \ |
1188 (ret) = WRITE(f, buf, 1, handleType); \ |
1188 (ret) = WRITE(f, buf, 1, handleType); \ |
1189 if ((ret) >= 0) break; \ |
1189 if ((ret) >= 0) break; \ |
1190 if (errno != EINTR) { \ |
1190 if (errno != EINTR) { \ |
1191 break; \ |
1191 break; \ |
1192 } \ |
1192 } \ |
1193 __HANDLE_INTERRUPTS__; \ |
1193 __HANDLE_INTERRUPTS__; \ |
1194 } |
1194 } |
1195 # else /* use STDIO */ |
1195 # else /* use STDIO */ |
1196 # define __WRITEBYTE__(ret, f, buf, isBuffered, handleType) \ |
1196 # define __WRITEBYTE__(ret, f, buf, isBuffered, handleType) \ |
1197 if (isBuffered) { \ |
1197 if (isBuffered) { \ |
1198 for (;;) { \ |
1198 for (;;) { \ |
1199 CLEAR_ERRNO; \ |
1199 CLEAR_ERRNO; \ |
1200 ret = putc(*(buf), f); \ |
1200 ret = putc(*(buf), f); \ |
1201 if ((ret) >= 0) { \ |
1201 if ((ret) >= 0) { \ |
1202 (ret) = 1; \ |
1202 (ret) = 1; \ |
1203 } else if (ferror(f)) { \ |
1203 } else if (ferror(f)) { \ |
1204 /* SOLARIS/SPARC (2.6) generates spurious errors with errno = 0 */ \ |
1204 /* SOLARIS/SPARC (2.6) generates spurious errors with errno = 0 */ \ |
1205 if (errno == EINTR || errno == 0) { \ |
1205 if (errno == EINTR || errno == 0) { \ |
1206 __HANDLE_INTERRUPTS__; \ |
1206 __HANDLE_INTERRUPTS__; \ |
1207 clearerr(f); \ |
1207 clearerr(f); \ |
1208 continue; \ |
1208 continue; \ |
1209 } \ |
1209 } \ |
1210 } else \ |
1210 } else \ |
1211 (ret) = 0; \ |
1211 (ret) = 0; \ |
1212 break; \ |
1212 break; \ |
1213 } \ |
1213 } \ |
1214 } else { \ |
1214 } else { \ |
1215 for (;;) { \ |
1215 for (;;) { \ |
1216 CLEAR_ERRNO; \ |
1216 CLEAR_ERRNO; \ |
1217 (ret) = write(fileno(f), buf, 1); \ |
1217 (ret) = write(fileno(f), buf, 1); \ |
1218 if ((ret) >= 0) break; \ |
1218 if ((ret) >= 0) break; \ |
1219 if (errno != EINTR) { \ |
1219 if (errno != EINTR) { \ |
1220 break; \ |
1220 break; \ |
1221 } \ |
1221 } \ |
1222 __HANDLE_INTERRUPTS__; \ |
1222 __HANDLE_INTERRUPTS__; \ |
1223 } \ |
1223 } \ |
1224 } |
1224 } |
1225 # endif /* use STDIO */ |
1225 # endif /* use STDIO */ |
1226 |
1226 |
1227 /* |
1227 /* |
1228 * write_bytes from a c-buffer |
1228 * write_bytes from a c-buffer |