php - What encoding does xsendfile expect? -
it seems googling xsendfile issues produces number of hits contradictory/outdated.
in involvement of total disclosure, i'm taking xsendfile 1.0 beta, documented @ https://tn123.org/mod_xsendfile/beta/ (this site doesn't show in search results, 1 without /beta does). i'm using apache 2.4 , php 5.4.34 on both linux , windows. besides beingness latest version, need utilize beta version because beta site has windows binaries built vc9 apache 2.4.
i made error of reading documentation, description of file name value in header says:
the value (file name) given header assmumed url-encoded, i.e. unescaping/url-decoding performed. see xsendfileunescape. if happen store files using url-encoded file names, must "double" encode names... %20 -> %2520
and description of xsendfileunescape says:
setting xsendfileunescape off restore pre-1.0 behavior of using raw header value, instead of trying unescape/url-decode first.
the documentation relative paths makes pretty clear file name on x-sendfile
header should total pathname. ran pathnames through php's urlencode
function.
the end result me invariably server internal error (500 status code) on both linux , windows. when had xsendfilepath directive in server config
context, documentation says allowed, got nil more specific in error log. when (eventually) moved directive directory
context, graduated getting in error log:
(404)unknown error: [client 127.0.0.1:20742] xsendfile: bad file name encoding
eventually, out of desperation, said "screw documentation", , removed urlencode
on pathname. , started working (both windows , linux)!!!
i don't have pathnames non-ascii characters in them, i'm set. wonder sort of encoding supposed applied allow non-ascii characters work. if google xsendfile: bad file name encoding
, you'll find next source code @ https://github.com/nmaier/mod_xsendfile/blob/master/mod_xsendfile.c message string produced taking true branch of:
rv = ap_unescape_url(file); if (rv != ok) {
but can't find description or source code ap_unescape_url()
. unless source on github outdated, function objects simple %-encoding php's urlencode()
function performs. wild guess tried calling ap_escape_url()
, it's not defined in php. leaves question of encoding supposed applied pathname parameter in x-sendfile
header??
one more observation/question description of xsendfile
using "apache internals" send file might create think build content-type
header filename extension using mod_mime
. in fact doesn't, , examples show explicit header()
phone call content-type
. follow-on "right" way build header pathname beingness passed x-sendfile
, such guaranteed match mod_mime
if weren't using x-sendfile
? best come next code using php's fileinfo
extension - far know there's no particular reason expect match apache when given url filename.
$finfo = new finfo(fileinfo_mime); $mime_info = $finfo->file($pathname); if (! strlen($mime_info)) { $mime_info = 'application/octet-stream; charset=binary'; } $basename = basename($pathname); $encoded = "$pathname"; header("content-type: $mime_info"); header("content-disposition: attachment; filename=\"$basename\""); header("x-sendfile: $encoded");
i'm not going take reply question, because still haven't found "the" encoding function expected used. did find ancient apache api documentation: http://pedrowa.weba.sk/docs/apidoc/apidoc_ap_unescape_url.html. documents retuen value of ap_unescape_url() as:
returns 0 on success, bad_request if bad escape sequence found, or not_found if %2f (/) found.
but of course of study in php, both urlencode() , rawurlencode() encode '/' %2f.
so clearly, total pathname used in xsendfile header must not urlencoded using either of these functions!!
my guess "best" solution me use:
$encoded = str_replace('%2f', '/', rawurlencode($pathname));
i must admit i'm amazed xsendfile documentation not mention this. , i'm more amazed question has not gotten answers here. should have posted in different stack exchange site?
php apache encoding x-sendfile
No comments:
Post a Comment