39 |
* *** BIG SURPRISE! It stays even after child exits! *** |
* *** BIG SURPRISE! It stays even after child exits! *** |
40 |
* |
* |
41 |
* This is a design bug in UNIX API. |
* This is a design bug in UNIX API. |
42 |
* fcntl(0, F_SETFL, fcntl(0, F_GETFL, 0) | O_NONBLOCK); |
* fcntl(0, F_SETFL, fcntl(0, F_GETFL) | O_NONBLOCK); |
43 |
* will set nonblocking mode not only on _your_ stdin, but |
* will set nonblocking mode not only on _your_ stdin, but |
44 |
* also on stdin of your parent, etc. |
* also on stdin of your parent, etc. |
45 |
* |
* |
46 |
* In general, |
* In general, |
47 |
* fd2 = dup(fd1); |
* fd2 = dup(fd1); |
48 |
* fcntl(fd2, F_SETFL, fcntl(fd2, F_GETFL, 0) | O_NONBLOCK); |
* fcntl(fd2, F_SETFL, fcntl(fd2, F_GETFL) | O_NONBLOCK); |
49 |
* sets both fd1 and fd2 to O_NONBLOCK. This includes cases |
* sets both fd1 and fd2 to O_NONBLOCK. This includes cases |
50 |
* where duping is done implicitly by fork() etc. |
* where duping is done implicitly by fork() etc. |
51 |
* |
* |
52 |
* We need |
* We need |
53 |
* fcntl(fd2, F_SETFD, fcntl(fd2, F_GETFD, 0) | O_NONBLOCK); |
* fcntl(fd2, F_SETFD, fcntl(fd2, F_GETFD) | O_NONBLOCK); |
54 |
* (note SETFD, not SETFL!) but such thing doesn't exist. |
* (note SETFD, not SETFL!) but such thing doesn't exist. |
55 |
* |
* |
56 |
* Alternatively, we need nonblocking_read(fd, ...) which doesn't |
* Alternatively, we need nonblocking_read(fd, ...) which doesn't |
141 |
{ |
{ |
142 |
char *p; |
char *p; |
143 |
size_t sz = buf ? strlen(buf) : 0; |
size_t sz = buf ? strlen(buf) : 0; |
144 |
size_t maxsz = maxsz_p ? *maxsz_p : MAXINT(size_t); |
size_t maxsz = maxsz_p ? *maxsz_p : (INT_MAX - 4095); |
145 |
|
|
146 |
goto jump_in; |
goto jump_in; |
147 |
while (sz < maxsz) { |
while (sz < maxsz) { |
198 |
size_t to_read; |
size_t to_read; |
199 |
struct stat st; |
struct stat st; |
200 |
|
|
201 |
to_read = maxsz_p ? *maxsz_p : MAXINT(ssize_t); /* max to read */ |
to_read = maxsz_p ? *maxsz_p : (INT_MAX - 4095); /* max to read */ |
202 |
|
|
203 |
/* Estimate file size */ |
/* Estimate file size */ |
204 |
st.st_size = 0; /* in case fstat fails, assume 0 */ |
st.st_size = 0; /* in case fstat fails, assume 0 */ |
229 |
if (size > 64*1024) |
if (size > 64*1024) |
230 |
size = 64*1024; |
size = 64*1024; |
231 |
} |
} |
232 |
xrealloc(buf, total + 1); |
buf = xrealloc(buf, total + 1); |
233 |
buf[total] = '\0'; |
buf[total] = '\0'; |
234 |
|
|
235 |
if (maxsz_p) |
if (maxsz_p) |
262 |
len = lseek(fd, 0, SEEK_END) | 0x3ff; /* + up to 1k */ |
len = lseek(fd, 0, SEEK_END) | 0x3ff; /* + up to 1k */ |
263 |
if (len != (off_t)-1) { |
if (len != (off_t)-1) { |
264 |
xlseek(fd, 0, SEEK_SET); |
xlseek(fd, 0, SEEK_SET); |
265 |
size = maxsz_p ? *maxsz_p : INT_MAX; |
size = maxsz_p ? *maxsz_p : (INT_MAX - 4095); |
266 |
if (len < size) |
if (len < size) |
267 |
size = len; |
size = len; |
268 |
} |
} |
273 |
free(buf); |
free(buf); |
274 |
return NULL; |
return NULL; |
275 |
} |
} |
276 |
xrealloc(buf, size + 1); |
buf = xrealloc(buf, size + 1); |
277 |
buf[size] = '\0'; |
buf[size] = '\0'; |
278 |
|
|
279 |
if (maxsz_p) |
if (maxsz_p) |
315 |
char *sfx; |
char *sfx; |
316 |
int fd; |
int fd; |
317 |
#if BB_MMU |
#if BB_MMU |
318 |
USE_DESKTOP(long long) int FAST_FUNC (*xformer)(int src_fd, int dst_fd); |
IF_DESKTOP(long long) int FAST_FUNC (*xformer)(int src_fd, int dst_fd); |
319 |
enum { xformer_prog = 0 }; |
enum { xformer_prog = 0 }; |
320 |
#else |
#else |
321 |
enum { xformer = 0 }; |
enum { xformer = 0 }; |
336 |
|| (ENABLE_FEATURE_SEAMLESS_BZ2 && strcmp(sfx, ".bz2") == 0) |
|| (ENABLE_FEATURE_SEAMLESS_BZ2 && strcmp(sfx, ".bz2") == 0) |
337 |
) { |
) { |
338 |
/* .gz and .bz2 both have 2-byte signature, and their |
/* .gz and .bz2 both have 2-byte signature, and their |
339 |
* unpack_XXX_stream want this header skipped. */ |
* unpack_XXX_stream wants this header skipped. */ |
340 |
xread(fd, &magic, 2); |
xread(fd, &magic, 2); |
341 |
#if ENABLE_FEATURE_SEAMLESS_GZ |
#if ENABLE_FEATURE_SEAMLESS_GZ |
342 |
#if BB_MMU |
#if BB_MMU |
352 |
|| magic[0] != 'B' || magic[1] != 'Z' |
|| magic[0] != 'B' || magic[1] != 'Z' |
353 |
) { |
) { |
354 |
bb_error_msg_and_die("no gzip" |
bb_error_msg_and_die("no gzip" |
355 |
USE_FEATURE_SEAMLESS_BZ2("/bzip2") |
IF_FEATURE_SEAMLESS_BZ2("/bzip2") |
356 |
" magic"); |
" magic"); |
357 |
} |
} |
358 |
#if BB_MMU |
#if BB_MMU |