<name>Mutex</name>
<description>Configures mutex mechanism and lock file directory for all
or specified mutexes</description>
-<syntax>Mutex <var>default|mutex-name</var> <var>mechanism</var></syntax>
-<default>Mutex default default</default>
+<syntax>Mutex <var>mechanism</var> [default|<var>mutex-name</var>] ... [OmitPID]</syntax>
+<default>Mutex default</default>
<contextlist><context>server config</context></contextlist>
<compatibility>Available in Apache 2.3.4 and later</compatibility>
can be configured if this directive is supported.</p>
</note>
- <p>The following table documents the names of mutexes used by httpd
- and bundled modules.</p>
-
- <table border="1" style="zebra">
- <tr>
- <th>Mutex name</th>
- <th>Module(s)</th>
- <th>Protected resource</th>
- </tr>
- <tr>
- <td><code>mpm-accept</code></td>
- <td><module>prefork</module> and <module>worker</module> MPMs</td>
- <td>incoming connections, to avoid the thundering herd problem;
- for more information, refer to the
- <a href="../misc/perf-tuning.html">performance tuning</a>
- documentation</td>
- </tr>
- <tr>
- <td><code>authdigest-client</code></td>
- <td><module>mod_auth_digest</module></td>
- <td>client list in shared memory</td>
- </tr>
- <tr>
- <td><code>authdigest-opaque</code></td>
- <td><module>mod_auth_digest</module></td>
- <td>counter in shared memory</td>
- </tr>
- <tr>
- <td><code>ldap-cache</code></td>
- <td><module>mod_ldap</module></td>
- <td>LDAP result cache</td>
- </tr>
- <tr>
- <td><code>rewrite-map</code></td>
- <td><module>mod_rewrite</module></td>
- <td>communication with external mapping programs, to avoid
- intermixed I/O from multiple requests</td>
- </tr>
- <tr>
- <td><code>ssl-cache</code></td>
- <td><module>mod_ssl</module></td>
- <td>SSL session cache</td>
- </tr>
- <tr>
- <td><code>ssl-stapling</code></td>
- <td><module>mod_ssl</module></td>
- <td>OCSP stapling response cache</td>
- </tr>
- <tr>
- <td><code>watchdog-callback</code></td>
- <td><module>mod_watchdog</module></td>
- <td>callback function of a particular client module</td>
- </tr>
- </table>
-
<p>The following mutex <em>mechanisms</em> are available:</p>
<ul>
<li><code>default | yes</code>
<directive module="core">ServerRoot</directive>. Always use a local disk
filesystem for <code>/path/to/mutex</code> and never a directory residing
on a NFS- or AFS-filesystem. The basename of the file will be the mutex
- type, an optional instance string provided by the module, with the process
- id of the httpd parent process appended to to make it unique, avoiding
+ type, an optional instance string provided by the module, and unless the
+ <code>OmitPID</code> keyword is specified, the process id of the httpd
+ parent process will be appended to to make the file name unique, avoiding
conflicts when multiple httpd instances share a lock file directory. For
example, if the mutex name is <code>mpm-accept</code> and the lock file
directory is <code>/var/httpd/locks</code>, the lock file name for the
to create.</p>
</note>
+ <p>The following table documents the names of mutexes used by httpd
+ and bundled modules.</p>
+
+ <table border="1" style="zebra">
+ <tr>
+ <th>Mutex name</th>
+ <th>Module(s)</th>
+ <th>Protected resource</th>
+ </tr>
+ <tr>
+ <td><code>mpm-accept</code></td>
+ <td><module>prefork</module> and <module>worker</module> MPMs</td>
+ <td>incoming connections, to avoid the thundering herd problem;
+ for more information, refer to the
+ <a href="../misc/perf-tuning.html">performance tuning</a>
+ documentation</td>
+ </tr>
+ <tr>
+ <td><code>authdigest-client</code></td>
+ <td><module>mod_auth_digest</module></td>
+ <td>client list in shared memory</td>
+ </tr>
+ <tr>
+ <td><code>authdigest-opaque</code></td>
+ <td><module>mod_auth_digest</module></td>
+ <td>counter in shared memory</td>
+ </tr>
+ <tr>
+ <td><code>ldap-cache</code></td>
+ <td><module>mod_ldap</module></td>
+ <td>LDAP result cache</td>
+ </tr>
+ <tr>
+ <td><code>rewrite-map</code></td>
+ <td><module>mod_rewrite</module></td>
+ <td>communication with external mapping programs, to avoid
+ intermixed I/O from multiple requests</td>
+ </tr>
+ <tr>
+ <td><code>ssl-cache</code></td>
+ <td><module>mod_ssl</module></td>
+ <td>SSL session cache</td>
+ </tr>
+ <tr>
+ <td><code>ssl-stapling</code></td>
+ <td><module>mod_ssl</module></td>
+ <td>OCSP stapling response cache</td>
+ </tr>
+ <tr>
+ <td><code>watchdog-callback</code></td>
+ <td><module>mod_watchdog</module></td>
+ <td>callback function of a particular client module</td>
+ </tr>
+ </table>
+
+ <p>The <code>OmitPID</code> keyword suppresses the addition of the httpd
+ parent process id from the lock file name.</p>
+
<p>In the following example, the mutex mechanism for the MPM accept
mutex will be changed from the compiled-in default to <code>fcntl</code>,
with the associated lock file created in directory
apr_int32_t options;
int set;
int none;
+ int omit_pid;
apr_lockmech_e mech;
const char *dir;
} mutex_cfg_t;
}
AP_DECLARE_NONSTD(const char *)ap_set_mutex(cmd_parms *cmd, void *dummy,
- const char *type,
- const char *mechdir)
+ const char *arg)
{
apr_pool_t *p = cmd->pool;
+ const char **elt;
+ const char *mechdir;
+ const char *type;
+ int no_mutex = 0, omit_pid = 0;
+ apr_array_header_t *type_list;
apr_lockmech_e mech;
apr_status_t rv;
const char *mutexdir;
- mutex_cfg_t *mxcfg = apr_hash_get(mxcfg_by_type, type,
- APR_HASH_KEY_STRING);
+ mutex_cfg_t *mxcfg;
const char *err = ap_check_cmd_context(cmd, GLOBAL_ONLY);
if (err != NULL) {
return err;
}
- if (!mxcfg) {
- return apr_psprintf(p, "Mutex type %s is not valid", type);
+ mechdir = ap_getword_conf(cmd->pool, &arg);
+ if (*mechdir == NULL) {
+ return "Mutex requires at least a mechanism argument ("
+ AP_ALL_AVAILABLE_MUTEXES_STRING ")";
}
- mxcfg->none = 0; /* in case that was the default */
-
rv = ap_parse_mutex(mechdir, p, &mech, &mutexdir);
if (rv == APR_ENOTIMPL) {
return apr_pstrcat(p, "Invalid Mutex argument ", mechdir,
return apr_pstrcat(p, "Invalid Mutex directory in argument ",
mechdir, NULL);
}
+ else if (rv == APR_ENOLOCK) { /* "none" */
+ no_mutex = 1;
+ }
+
+ /* "OmitPID" can appear at the end of the list, so build a list of
+ * mutex type names while looking for "OmitPID" (anywhere) or the end
+ */
+ type_list = apr_array_make(cmd->pool, 4, sizeof(char *));
+ while (*arg) {
+ char *s = ap_getword_conf(cmd->pool, &arg);
- mxcfg->set = 1;
- if (rv == APR_ENOLOCK) { /* "none" */
- if (!(mxcfg->options & AP_MUTEX_ALLOW_NONE)) {
- return apr_psprintf(p,
- "None is not allowed for mutex type %s",
- type);
+ if (!strcasecmp(s, "omitpid")) {
+ omit_pid = 1;
+ }
+ else {
+ char **new_type = (char **)apr_array_push(type_list);
+ *new_type = s;
}
- mxcfg->none = 1;
}
- else {
- mxcfg->mech = mech;
- if (mutexdir) { /* retain mutex default if not configured */
- mxcfg->dir = mutexdir;
+
+ if (apr_is_empty_array(type_list)) { /* no mutex type? assume "default" */
+ char **new_type = (char **)apr_array_push(type_list);
+ *new_type = "default";
+ }
+
+ while ((elt = (const char **)apr_array_pop(type_list)) != NULL) {
+ const char *type = *elt;
+ mxcfg = apr_hash_get(mxcfg_by_type, type, APR_HASH_KEY_STRING);
+ if (!mxcfg) {
+ return apr_psprintf(p, "Mutex type %s is not valid", type);
+ }
+
+ mxcfg->none = 0; /* in case that was the default */
+ mxcfg->omit_pid = omit_pid;
+
+ mxcfg->set = 1;
+ if (no_mutex) {
+ if (!(mxcfg->options & AP_MUTEX_ALLOW_NONE)) {
+ return apr_psprintf(p,
+ "None is not allowed for mutex type %s",
+ type);
+ }
+ mxcfg->none = 1;
+ }
+ else {
+ mxcfg->mech = mech;
+ if (mutexdir) { /* retain mutex default if not configured */
+ mxcfg->dir = mutexdir;
+ }
}
}
}
#if HAVE_UNISTD_H
- pid_suffix = apr_psprintf(p, ".%" APR_PID_T_FMT, getpid());
+ if (!mxcfg->omit_pid) {
+ pid_suffix = apr_psprintf(p, ".%" APR_PID_T_FMT, getpid());
+ }
#endif
return ap_server_root_relative(p,