A small performance patch for consideration:

Currently, mod_mime scans through the extensions in the
requested filename using ap_getword, which does a strdup
of each extension.

This patch replaces the ap_getword loop with an inline scan
that doesn't do apr_pstrdup.  Based on past function call profiles
that I've done, this change should eliminate 15-20% of the
ap_pstrdup calls in the httpd.  (I'll try to address the other
80-85% with some future patches; apr_pstrdup currently is one
of the top 10 consumers of usr-mode CPU time in the httpd,
so it's worthwhile to optimize it away where possible.)

Important note: on platforms with case-insensitive filenames,
the elimination of the strdup means that this patch will result
in the extensions in request_rec->filename being converted
to lowercase.  I assume that's not a problem, but if it is I
can add some code to do a strdup on (only) the affected platforms.

--Brian

Index: mod_mime.c
===================================================================
RCS file: /home/cvspublic/httpd-2.0/modules/http/mod_mime.c,v
retrieving revision 1.43
diff -r1.43 mod_mime.c
778c778,779
<     while ((ext = ap_getword(r->pool, &fn, '.')) && *ext) {
---
 >     ext = ap_strchr(fn, '.');
 >     while (ext) {
780a782,789
 >     char *nextdot;
 >
 >     ext++; /* skip the '.' */
 >     if (!*ext)
 >         break;
 >     nextdot = ap_strchr(ext, '.');
 >     if (nextdot)
 >         *nextdot = 0;
846a856,863
 >
 >     /* Restore the '.' that starts the next extension, if applicable */
 >     if (nextdot) {
 >         *nextdot = '.';
 >         ext = nextdot;
 >     }
 >     else
 >         break;




Index: mod_mime.c
===================================================================
RCS file: /home/cvspublic/httpd-2.0/modules/http/mod_mime.c,v
retrieving revision 1.43
diff -r1.43 mod_mime.c
778c778,779
<     while ((ext = ap_getword(r->pool, &fn, '.')) && *ext) {
---
>     ext = ap_strchr_c(fn, '.');
>     while (ext) {
780a782,789
>       char *nextdot;
> 
>       ext++; /* skip the '.' */
>       if (!*ext)
>           break;
>       nextdot = ap_strchr_c(ext, '.');
>       if (nextdot)
>           *nextdot = 0;
846a856,863
> 
>       /* Restore the '.' that starts the next extension, if applicable */
>       if (nextdot) {
>           *nextdot = '.';
>           ext = nextdot;
>       }
>       else
>           break;

Reply via email to