Skip to content

Commit b2b570b

Browse files
committed
Support sysconf(_SC_GETPW_R_SIZE_MAX) == -1
1 parent 3aefaaa commit b2b570b

File tree

3 files changed

+64
-19
lines changed

3 files changed

+64
-19
lines changed

ext/standard/filestat.c

Lines changed: 28 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -279,13 +279,24 @@ PHPAPI zend_result php_get_gid_by_name(const char *name, gid_t *gid)
279279
struct group *retgrptr;
280280
long grbuflen = sysconf(_SC_GETGR_R_SIZE_MAX);
281281
char *grbuf;
282+
int err;
282283

283284
if (grbuflen < 1) {
284-
return FAILURE;
285+
grbuflen = 1024;
285286
}
286-
287+
# if ZEND_DEBUG
288+
grbuflen = 1;
289+
# endif
287290
grbuf = emalloc(grbuflen);
288-
if (getgrnam_r(name, &gr, grbuf, grbuflen, &retgrptr) != 0 || retgrptr == NULL) {
291+
292+
try_again:
293+
err = getgrnam_r(name, &gr, grbuf, grbuflen, &retgrptr);
294+
if (err != 0 || retgrptr == NULL) {
295+
if (err == ERANGE) {
296+
grbuflen *= 2;
297+
grbuf = erealloc(grbuf, grbuflen);
298+
goto try_again;
299+
}
289300
efree(grbuf);
290301
return FAILURE;
291302
}
@@ -405,13 +416,24 @@ PHPAPI zend_result php_get_uid_by_name(const char *name, uid_t *uid)
405416
struct passwd *retpwptr = NULL;
406417
long pwbuflen = sysconf(_SC_GETPW_R_SIZE_MAX);
407418
char *pwbuf;
419+
int err;
408420

409421
if (pwbuflen < 1) {
410-
return FAILURE;
422+
pwbuflen = 1024;
411423
}
412-
424+
# if ZEND_DEBUG
425+
pwbuflen = 1;
426+
# endif
413427
pwbuf = emalloc(pwbuflen);
414-
if (getpwnam_r(name, &pw, pwbuf, pwbuflen, &retpwptr) != 0 || retpwptr == NULL) {
428+
429+
try_again:
430+
err = getpwnam_r(name, &pw, pwbuf, pwbuflen, &retpwptr);
431+
if (err != 0 || retpwptr == NULL) {
432+
if (err == EAGAIN) {
433+
pwbuflen *= 2;
434+
pwbuf = erealloc(pwbuf, pwbuflen);
435+
goto try_again;
436+
}
415437
efree(pwbuf);
416438
return FAILURE;
417439
}

main/fopen_wrappers.c

Lines changed: 22 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -374,26 +374,37 @@ PHPAPI int php_fopen_primary_script(zend_file_handle *file_handle)
374374

375375
if (s) { /* if there is no path name after the file, do not bother */
376376
char user[32]; /* to try open the directory */
377+
378+
length = s - (path_info + 2);
379+
if (length > sizeof(user) - 1) {
380+
length = sizeof(user) - 1;
381+
}
382+
memcpy(user, path_info + 2, length);
383+
user[length] = '\0';
384+
377385
struct passwd *pw;
378386
#if defined(ZTS) && defined(HAVE_GETPWNAM_R) && defined(_SC_GETPW_R_SIZE_MAX)
379387
struct passwd pwstruc;
380388
long pwbuflen = sysconf(_SC_GETPW_R_SIZE_MAX);
381389
char *pwbuf;
390+
int err;
382391

383392
if (pwbuflen < 1) {
384-
return FAILURE;
393+
pwbuflen = 1024;
385394
}
386-
395+
# if ZEND_DEBUG
396+
pwbuflen = 1;
397+
# endif
387398
pwbuf = emalloc(pwbuflen);
388-
#endif
389-
length = s - (path_info + 2);
390-
if (length > sizeof(user) - 1) {
391-
length = sizeof(user) - 1;
392-
}
393-
memcpy(user, path_info + 2, length);
394-
user[length] = '\0';
395-
#if defined(ZTS) && defined(HAVE_GETPWNAM_R) && defined(_SC_GETPW_R_SIZE_MAX)
396-
if (getpwnam_r(user, &pwstruc, pwbuf, pwbuflen, &pw)) {
399+
400+
try_again:
401+
err = getpwnam_r(user, &pwstruc, pwbuf, pwbuflen, &pw);
402+
if (err) {
403+
if (err == ERANGE) {
404+
pwbuflen *= 2;
405+
pwbuf = erealloc(pwbuf, pwbuflen);
406+
goto try_again;
407+
}
397408
efree(pwbuf);
398409
return FAILURE;
399410
}

main/main.c

Lines changed: 14 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1460,12 +1460,24 @@ PHPAPI char *php_get_current_user(void)
14601460
struct passwd *retpwptr = NULL;
14611461
int pwbuflen = sysconf(_SC_GETPW_R_SIZE_MAX);
14621462
char *pwbuf;
1463+
int err;
14631464

14641465
if (pwbuflen < 1) {
1465-
return "";
1466+
pwbuflen = 1024;
14661467
}
1468+
# if ZEND_DEBUG
1469+
pwbuflen = 1;
1470+
# endif
14671471
pwbuf = emalloc(pwbuflen);
1468-
if (getpwuid_r(pstat->st_uid, &_pw, pwbuf, pwbuflen, &retpwptr) != 0) {
1472+
1473+
try_again:
1474+
err = getpwuid_r(pstat->st_uid, &_pw, pwbuf, pwbuflen, &retpwptr);
1475+
if (err != 0) {
1476+
if (err == ERANGE) {
1477+
pwbuflen *= 2;
1478+
pwbuf = erealloc(pwbuf, pwbuflen);
1479+
goto try_again;
1480+
}
14691481
efree(pwbuf);
14701482
return "";
14711483
}

0 commit comments

Comments
 (0)