Skip to content
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
7 changes: 6 additions & 1 deletion sapi/fpm/fpm/fpm_unix.c
Original file line number Diff line number Diff line change
Expand Up @@ -269,6 +269,11 @@ static int fpm_unix_conf_wp(struct fpm_worker_pool_s *wp) /* {{{ */
if (wp->config->user && *wp->config->user) {
if (strlen(wp->config->user) == strspn(wp->config->user, "0123456789")) {
wp->set_uid = strtoul(wp->config->user, 0, 10);
pwd = getpwuid(wp->set_uid);
if (pwd) {
wp->set_gid = pwd->pw_gid;
wp->set_user = strdup(pwd->pw_name);
}
} else {
struct passwd *pwd;

Expand Down Expand Up @@ -392,7 +397,7 @@ int fpm_unix_init_child(struct fpm_worker_pool_s *wp) /* {{{ */
}
}
if (wp->set_uid) {
if (0 > initgroups(wp->config->user, wp->set_gid)) {
if (0 > initgroups(wp->set_user ? wp->set_user : wp->config->user, wp->set_gid)) {
zlog(ZLOG_SYSERROR, "[pool %s] failed to initgroups(%s, %d)", wp->config->name, wp->config->user, wp->set_gid);
return -1;
}
Expand Down
3 changes: 3 additions & 0 deletions sapi/fpm/fpm/fpm_worker_pool.c
Original file line number Diff line number Diff line change
Expand Up @@ -34,6 +34,9 @@ void fpm_worker_pool_free(struct fpm_worker_pool_s *wp) /* {{{ */
if (wp->user) {
free(wp->user);
}
if (wp->set_user) {
free(wp->set_user);
}
if (wp->home) {
free(wp->home);
}
Expand Down
1 change: 1 addition & 0 deletions sapi/fpm/fpm/fpm_worker_pool.h
Original file line number Diff line number Diff line change
Expand Up @@ -24,6 +24,7 @@ struct fpm_worker_pool_s {
enum fpm_address_domain listen_address_domain;
int listening_socket;
int set_uid, set_gid; /* config uid and gid */
char *set_user; /* config user name */
int socket_uid, socket_gid, socket_mode;

/* runtime */
Expand Down
52 changes: 52 additions & 0 deletions sapi/fpm/tests/bug80669-uid-user-groups.phpt
Original file line number Diff line number Diff line change
@@ -0,0 +1,52 @@
--TEST--
FPM: Process user setting ignored when FPM is not running as root
--SKIPIF--
<?php
include "skipif.inc";
FPM\Tester::skipIfNotRoot();
FPM\Tester::skipIfUserDoesNotExist('www-data');
?>
--FILE--
<?php

require_once "tester.inc";

$pw = posix_getpwnam('www-data');
$uid = $pw['uid'];
$gid = $pw['gid'];

$cfg = <<<EOT
[global]
error_log = {{FILE:LOG}}
[unconfined]
listen = {{ADDR}}
user = $uid
pm = dynamic
pm.max_children = 5
pm.start_servers = 1
pm.min_spare_servers = 1
pm.max_spare_servers = 3
EOT;

$code = <<<EOT
<?php
echo posix_getgid();
EOT;

$tester = new FPM\Tester($cfg, $code);
$tester->start();
$tester->expectLogStartNotices();
$tester->request()->expectBody((string) $gid);
$tester->terminate();
$tester->expectLogTerminatingNotices();
$tester->close();

?>
Done
--EXPECT--
Done
--CLEAN--
<?php
require_once "tester.inc";
FPM\Tester::clean();
?>
10 changes: 5 additions & 5 deletions sapi/fpm/tests/response.inc
Original file line number Diff line number Diff line change
Expand Up @@ -71,11 +71,11 @@ class Response
$body = implode("\n", $body);
}

if (
$this->checkIfValid() &&
$this->checkDefaultHeaders($contentType) &&
$body !== $this->rawBody
) {
if (!$this->checkIfValid()) {
$this->error('Response is invalid');
} elseif (!$this->checkDefaultHeaders($contentType)) {
$this->error('Response default headers not found');
} elseif ($body !== $this->rawBody) {
if ($multiLine) {
$this->error(
"==> The expected body:\n$body\n" .
Expand Down
15 changes: 13 additions & 2 deletions sapi/fpm/tests/tester.inc
Original file line number Diff line number Diff line change
Expand Up @@ -294,7 +294,7 @@ class Tester
*/
static public function skipIfNotRoot()
{
if (getmyuid() != 0) {
if (exec('whoami') !== 'root') {
die('skip not running as root');
}
}
Expand All @@ -304,7 +304,7 @@ class Tester
*/
static public function skipIfRoot()
{
if (getmyuid() == 0) {
if (exec('whoami') === 'root') {
die('skip running as root');
}
}
Expand All @@ -319,6 +319,17 @@ class Tester
}
}

/**
* Skip if posix extension not loaded.
*/
static public function skipIfUserDoesNotExist($userName)
{
self::skipIfPosixNotLoaded();
if (posix_getpwnam($userName) === false) {
die("skip user $userName does not exist");
}
}

/**
* Tester constructor.
*
Expand Down