31static void destroy_phar_data(
zval *
zv);
39static int phar_set_writeable_bit(
zval *
zv,
void *argument)
41 bool keep = *(
bool *)argument;
57 if (
ZSTR_LEN(entry->name) ==
sizeof(
"phar.readonly")-1) {
67 if (
ZSTR_LEN(entry->name) ==
sizeof(
"phar.readonly")-1) {
72 }
else if (old && !
ini) {
76 if (
ZSTR_LEN(entry->name) ==
sizeof(
"phar.readonly")-1) {
93static void phar_split_cache_list(
void)
112 EG(regular_list).nNextFreeElement=1;
178 phar_split_cache_list();
197 if (phar->alias && phar->alias != phar->fname) {
198 pefree(phar->alias, phar->is_persistent);
203 pefree(phar->fname, phar->is_persistent);
207 if (phar->signature) {
208 pefree(phar->signature, phar->is_persistent);
209 phar->signature = NULL;
213 zend_hash_destroy(&phar->manifest);
214 HT_INVALIDATE(&phar->manifest);
218 zend_hash_destroy(&phar->mounted_dirs);
219 HT_INVALIDATE(&phar->mounted_dirs);
223 zend_hash_destroy(&phar->virtual_dirs);
224 HT_INVALIDATE(&phar->virtual_dirs);
230 php_stream_close(phar->fp);
235 php_stream_close(phar->ufp);
239 pefree(phar, phar->is_persistent);
274 if (!zend_hash_num_elements(&phar->
manifest)) {
290static void destroy_phar_data_only(
zval *
zv)
303static int phar_unalias_apply(
zval *
zv,
void *argument)
312static int phar_tmpclose_apply(
zval *
zv)
332static void destroy_phar_data(
zval *
zv)
340 destroy_phar_data_only(
zv);
441#define MAPPHAR_ALLOC_FAIL(msg) \
443 php_stream_close(fp);\
446 spprintf(error, 0, msg, fname);\
450#define MAPPHAR_FAIL(msg) \
453 phar_destroy_phar_data(mydata);\
456 pefree(signature, PHAR_G(persist));\
458 MAPPHAR_ALLOC_FAIL(msg)
460#ifdef WORDS_BIGENDIAN
461# define PHAR_GET_32(buffer, var) \
462 var = ((uint32_t)(((unsigned char*)(buffer))[3]) << 24) \
463 | ((uint32_t)(((unsigned char*)(buffer))[2]) << 16) \
464 | ((uint32_t)(((unsigned char*)(buffer))[1]) << 8) \
465 | ((uint32_t)((unsigned char*)(buffer))[0]); \
467# define PHAR_GET_16(buffer, var) \
468 var = ((uint16_t)(((unsigned char*)(buffer))[1]) << 8) \
469 | ((uint16_t)((unsigned char*)(buffer))[0]); \
472# define PHAR_GET_32(buffer, var) \
473 memcpy(&var, buffer, sizeof(var)); \
475# define PHAR_GET_16(buffer, var) \
476 var = *(uint16_t*)(buffer); \
479#define PHAR_ZIP_16(var) ((uint16_t)((((uint16_t)var[0]) & 0xff) | \
480 (((uint16_t)var[1]) & 0xff) << 8))
481#define PHAR_ZIP_32(var) ((uint32_t)((((uint32_t)var[0]) & 0xff) | \
482 (((uint32_t)var[1]) & 0xff) << 8 | \
483 (((uint32_t)var[2]) & 0xff) << 16 | \
484 (((uint32_t)var[3]) & 0xff) << 24))
502 if (memchr(fname,
'\\', fname_len)) {
503 fname =
do_alloca(fname_len + 1, fname_use_heap);
504 memcpy(fname, save_fname, fname_len);
505 fname[fname_len] =
'\0';
506 phar_unixify_path_separators(fname, fname_len);
510 && ((alias && fname_len == phar->
fname_len
515 if (fname != save_fname) {
529 if (
PHAR_G(
readonly) &&
NULL == (stub = zend_hash_str_find_ptr(&(phar->
manifest),
".phar/stub.php",
sizeof(
".phar/stub.php")-1))) {
531 spprintf(
error, 0,
"'%s' is not a phar archive. Use PharData::__construct() for a standard zip or tar archive", fname);
545 if (fname != save_fname) {
581 if (!metadata_str.
s) {
584 tracker->
str = metadata_str.
s;
595 const bool has_unserialize_options = unserialize_options !=
NULL && zend_hash_num_elements(unserialize_options) > 0;
599 if (
Z_ISUNDEF(tracker->
val) || has_unserialize_options) {
648 zend_string_release(tracker->
str);
676 dest->
str = zend_string_copy(source->
str);
689 tracker->
str = zend_string_dup(tracker->
str,
false);
705 if (zip_metadata_len) {
716#define MANIFEST_FIXED_LEN 18
718#define SAFE_PHAR_GET_32(buffer, endbuffer, var) \
719 if (UNEXPECTED(buffer + 4 > endbuffer)) { \
720 MAPPHAR_FAIL("internal corruption of phar \"%s\" (truncated manifest header)"); \
722 PHAR_GET_32(buffer, var);
735 char b32[4], *
buffer, *endbuffer, *savebuf;
738 uint32_t manifest_len, manifest_count, manifest_flags, manifest_index, tmp_len, sig_flags;
739 uint16_t manifest_ver;
743 int register_alias = 0, temp_alias = 0;
744 char *signature =
NULL;
763 MAPPHAR_ALLOC_FAIL(
"internal corruption of phar \"%s\" (truncated manifest at stub end)")
770 MAPPHAR_ALLOC_FAIL(
"internal corruption of phar \"%s\" (truncated manifest at stub end)")
773 if ((
char) nextchar ==
'\r') {
775 if (EOF == (nextchar =
php_stream_getc(fp)) || (
char)nextchar !=
'\n') {
776 MAPPHAR_ALLOC_FAIL(
"internal corruption of phar \"%s\" (truncated manifest at stub end)")
781 if ((
char) nextchar ==
'\n') {
795 MAPPHAR_ALLOC_FAIL(
"internal corruption of phar \"%s\" (truncated manifest at manifest length)")
800 if (manifest_len > 1048576 * 100) {
807 endbuffer =
buffer + manifest_len;
810 MAPPHAR_FAIL(
"internal corruption of phar \"%s\" (truncated manifest header)")
816 if (manifest_count == 0) {
817 MAPPHAR_FAIL(
"in phar \"%s\", manifest claims to have zero entries. Phars must have at least 1 entry");
821 manifest_ver = (((
unsigned char)
buffer[0]) << 8)
822 + ((
unsigned char)
buffer[1]);
829 spprintf(
error, 0,
"phar \"%s\" is API version %1.u.%1.u.%1.u, and cannot be processed", fname, manifest_ver >> 12, (manifest_ver >> 8) & 0xF, (manifest_ver >> 4) & 0x0F);
839 manifest_flags |= compression;
844 char sig_buf[8], *sig_ptr = sig_buf;
851 || memcmp(sig_buf+4,
"GBMB", 4)) {
855 spprintf(
error, 0,
"phar \"%s\" has a broken signature", fname);
866 uint32_t signature_len;
876 spprintf(
error, 0,
"phar \"%s\" openssl signature length could not be read", fname);
883 sig = (
char *)
emalloc(signature_len);
884 whence = signature_len + 4;
894 spprintf(
error, 0,
"phar \"%s\" openssl signature could not be read", fname);
905 spprintf(
error, 0,
"phar \"%s\" openssl signature could not be verified: %s", fname, *
error);
914 unsigned char digest[64];
919 if (
php_stream_read(fp, (
char*)digest,
sizeof(digest)) !=
sizeof(digest)) {
923 spprintf(
error, 0,
"phar \"%s\" has a broken signature", fname);
933 spprintf(
error, 0,
"phar \"%s\" SHA512 signature could not be verified: %s", fname, *
error);
941 unsigned char digest[32];
946 if (
php_stream_read(fp, (
char*)digest,
sizeof(digest)) !=
sizeof(digest)) {
950 spprintf(
error, 0,
"phar \"%s\" has a broken signature", fname);
960 spprintf(
error, 0,
"phar \"%s\" SHA256 signature could not be verified: %s", fname, *
error);
968 unsigned char digest[20];
973 if (
php_stream_read(fp, (
char*)digest,
sizeof(digest)) !=
sizeof(digest)) {
977 spprintf(
error, 0,
"phar \"%s\" has a broken signature", fname);
987 spprintf(
error, 0,
"phar \"%s\" SHA1 signature could not be verified: %s", fname, *
error);
995 unsigned char digest[16];
1000 if (
php_stream_read(fp, (
char*)digest,
sizeof(digest)) !=
sizeof(digest)) {
1004 spprintf(
error, 0,
"phar \"%s\" has a broken signature", fname);
1013 char *save = *
error;
1014 spprintf(
error, 0,
"phar \"%s\" MD5 signature could not be verified: %s", fname, *
error);
1026 spprintf(
error, 0,
"phar \"%s\" has a broken or unsupported signature", fname);
1035 spprintf(
error, 0,
"phar \"%s\" does not have a signature", fname);
1046 if (
buffer + tmp_len > endbuffer) {
1047 MAPPHAR_FAIL(
"internal corruption of phar \"%s\" (buffer overrun)");
1051 MAPPHAR_FAIL(
"internal corruption of phar \"%s\" (truncated manifest header)")
1057 if (alias && alias_len && (alias_len != tmp_len ||
strncmp(alias,
buffer, tmp_len)))
1066 spprintf(
error, 0,
"cannot load phar \"%s\" with implicit alias \"%.*s\" under different alias \"%s\"", fname, tmp_len,
buffer, alias);
1073 alias_len = tmp_len;
1077 }
else if (!alias_len || !alias) {
1082 }
else if (alias_len) {
1088 if (manifest_count > ((manifest_len -
MANIFEST_FIXED_LEN - tmp_len) / (5 * 4 + 1))) {
1090 MAPPHAR_FAIL(
"internal corruption of phar \"%s\" (too many manifest entries for size of manifest)")
1107 if(
len > (
size_t)(endbuffer -
buffer)) {
1108 MAPPHAR_FAIL(
"internal corruption of phar \"%s\" (trying to read past buffer end)");
1123 phar_unixify_path_separators(mydata->
fname, fname_len);
1126 offset = halt_offset + manifest_len + 4;
1128 entry.
phar = mydata;
1132 for (manifest_index = 0; manifest_index < manifest_count; ++manifest_index) {
1133 if (
buffer + 28 > endbuffer) {
1134 MAPPHAR_FAIL(
"internal corruption of phar \"%s\" (truncated manifest entry)")
1140 MAPPHAR_FAIL(
"zero-length filename encountered in phar \"%s\"");
1148 MAPPHAR_FAIL(
"internal corruption of phar \"%s\" (truncated manifest entry)");
1163 if (
offset == halt_offset + manifest_len + 4) {
1184 if (
len > (
size_t)(endbuffer -
buffer)) {
1186 MAPPHAR_FAIL(
"internal corruption of phar \"%s\" (truncated manifest entry)");
1203 MAPPHAR_FAIL(
"zlib extension is required for gz compressed .phar file \"%s\"");
1210 MAPPHAR_FAIL(
"bz2 extension is required for bzip2 compressed .phar file \"%s\"");
1217 MAPPHAR_FAIL(
"internal corruption of phar \"%s\" (compressed and uncompressed size does not match for uncompressed entry)");
1225 phar_set_inode(&entry);
1232 zend_string_release(str);
1235 snprintf(mydata->
version,
sizeof(mydata->
version),
"%u.%u.%u", manifest_ver >> 12, (manifest_ver >> 8) & 0xF, (manifest_ver >> 4) & 0xF);
1237 mydata->
flags = manifest_flags;
1241 mydata->
ext = memchr(endbuffer,
'.', (mydata->
fname + fname_len) - endbuffer);
1242 if (mydata->
ext == endbuffer) {
1243 mydata->
ext = memchr(endbuffer + 1,
'.', (mydata->
fname + fname_len) - endbuffer - 1);
1250 mydata->
alias = alias ?
1253 mydata->
alias_len = alias ? alias_len : fname_len;
1260 if (register_alias) {
1268 MAPPHAR_FAIL(
"Cannot open archive \"%s\", invalid alias");
1275 MAPPHAR_FAIL(
"Cannot open archive \"%s\", alias is already in use by existing archive");
1282 str = zend_string_init(alias, alias_len, 0);
1285 zend_string_release(str);
1293 str = zend_string_init(mydata->
fname, fname_len, 0);
1296 zend_string_release(str);
1312 const char *ext_str, *z;
1331 if (ext_len == -2) {
1332 spprintf(
error, 0,
"Cannot create a phar archive from a URL like \"%s\". Phar objects can only be created from local files", fname);
1334 spprintf(
error, 0,
"Cannot create phar '%s', file extension (or combination) not recognised or the directory does not exist", fname);
1340 if (phar_open_parsed_phar(fname, fname_len, alias, alias_len, is_data,
options,
test, &my_error) ==
SUCCESS) {
1345 if ((*test)->is_data && !(*test)->is_tar && !(*test)->is_zip) {
1347 spprintf(
error, 0,
"Cannot open '%s' as a PharData object. Use Phar::__construct() for executable archives", fname);
1352 if (
PHAR_G(
readonly) && !(*test)->is_data && ((*test)->is_tar || (*test)->is_zip)) {
1354 if (
NULL == (stub = zend_hash_str_find_ptr(&((*test)->manifest),
".phar/stub.php",
sizeof(
".phar/stub.php")-1))) {
1355 spprintf(
error, 0,
"'%s' is not a phar archive. Use PharData::__construct() for a standard zip or tar archive", fname);
1361 (*test)->is_writeable = 1;
1364 }
else if (my_error) {
1373 if (ext_len > 3 && (z = memchr(ext_str,
'z', ext_len)) && ((ext_str + ext_len) - z >= 2) && !memcmp(z + 1,
"ip", 2)) {
1378 if (ext_len > 3 && (z = memchr(ext_str,
't', ext_len)) && ((ext_str + ext_len) - z >= 2) && !memcmp(z + 1,
"ar", 2)) {
1412 if (phar_open_from_fp(fp, fname, fname_len, alias, alias_len,
options, pphar,
error) ==
SUCCESS) {
1414 (*pphar)->is_writeable = 1;
1436 spprintf(
error, 0,
"creating archive \"%s\" disabled by the php.ini setting phar.readonly", fname);
1451 phar_unixify_path_separators(mydata->
fname, fname_len);
1456 mydata->
ext = memchr(
p,
'.', (mydata->
fname + fname_len) -
p);
1457 if (mydata->
ext ==
p) {
1458 mydata->
ext = memchr(
p + 1,
'.', (mydata->
fname + fname_len) -
p - 1);
1472 zend_get_hash_value,
NULL, 0);
1496 spprintf(
error, 4096,
"phar error: phar \"%s\" cannot set alias \"%s\", already in use by another phar archive", mydata->
fname, alias);
1511 mydata->
alias_len = alias ? alias_len : fname_len;
1514 if (alias_len && alias) {
1518 spprintf(
error, 0,
"archive \"%s\" cannot be associated with alias \"%s\", already in use", fname, alias);
1547 bool is_data =
false;
1553 if (!
strstr(fname,
".phar")) {
1557 if (phar_open_parsed_phar(fname, fname_len, alias, alias_len, is_data,
options, pphar,
error) ==
SUCCESS) {
1571 spprintf(
error, 0,
"unable to open phar for reading \"%s\"", fname);
1595static inline char *phar_strnstr(
const char *
buf,
int buf_len,
const char *search,
int search_len)
1600 if (buf_len < search_len) {
1607 if (!(c = memchr(c + 1, search[0], buf_len - search_len - so_far))) {
1608 return (
char *)
NULL;
1613 if (so_far >= (buf_len - search_len)) {
1614 return (
char *)
NULL;
1617 if (!memcmp(c, search, search_len)) {
1631 static const char token[] =
"__HALT_COMPILER();";
1632 static const char zip_magic[] =
"PK\x03\x04";
1633 static const char gz_magic[] =
"\x1f\x8b\x08";
1634 static const char bz_magic[] =
"BZh";
1636 int recursion_count = 3;
1637 const int window_size = 1024;
1638 char buffer[1024 +
sizeof(token)];
1640 const zend_long tokenlen =
sizeof(token) - 1;
1664 if (!
test && recursion_count) {
1667 if (!memcmp(
pos, gz_magic, 3)) {
1675 MAPPHAR_ALLOC_FAIL(
"unable to decompress gzipped phar archive \"%s\" to temporary file, enable zlib extension in php.ini")
1686 MAPPHAR_ALLOC_FAIL(
"unable to create temporary file for decompression of gzipped phar archive \"%s\"")
1700 MAPPHAR_ALLOC_FAIL(
"unable to decompress gzipped phar archive \"%s\", ext/zlib is buggy in PHP versions older than 5.2.6")
1711 MAPPHAR_ALLOC_FAIL(
"unable to decompress gzipped phar archive \"%s\", ext/zlib is buggy in PHP versions older than 5.2.6")
1714 MAPPHAR_ALLOC_FAIL(
"unable to decompress gzipped phar archive \"%s\" to temporary file")
1726 if (!--recursion_count) {
1731 }
else if (!memcmp(
pos, bz_magic, 3)) {
1736 MAPPHAR_ALLOC_FAIL(
"unable to decompress bzipped phar archive \"%s\" to temporary file, enable bz2 extension in php.ini")
1741 MAPPHAR_ALLOC_FAIL(
"unable to create temporary file for decompression of bzipped phar archive \"%s\"")
1749 MAPPHAR_ALLOC_FAIL(
"unable to decompress bzipped phar archive \"%s\", filter creation failed")
1756 MAPPHAR_ALLOC_FAIL(
"unable to decompress bzipped phar archive \"%s\" to temporary file")
1768 if (!--recursion_count) {
1775 if (!memcmp(
pos, zip_magic, 4)) {
1788 if (got > 0 && (
pos = phar_strnstr(
buffer, got +
sizeof(token), token,
sizeof(token)-1)) !=
NULL) {
1790 return phar_parse_pharfile(fp, fname, fname_len, alias, alias_len, halt_offset, pphar, compression,
error);
1797 MAPPHAR_ALLOC_FAIL(
"internal corruption of phar \"%s\" (__HALT_COMPILER(); not found)")
1810static zend_result phar_analyze_path(
const char *fname,
const char *
ext,
size_t ext_len,
int for_create)
1814 char *filename =
estrndup(fname, (
ext - fname) + ext_len);
1838 if (ssb.
sb.st_mode & S_IFDIR) {
1842 if (for_create == 1) {
1855 slash = (
char *)
strrchr(filename,
'/');
1872 slash += ((
ext - fname) + ext_len);
1893 if (ssb.
sb.st_mode & S_IFDIR) {
1905 if (ssb.
sb.st_mode & S_IFDIR) {
1915static zend_result phar_check_str(
const char *fname,
const char *ext_str,
size_t ext_len,
int executable,
int for_create)
1919 if (ext_len >= 50) {
1922 if (executable == 1) {
1928 || (
pos != ext_str && (*(
pos - 1) ==
'/'))
1929 || (ext_len - (
pos - ext_str)) < 5
1931 || !(*
pos ==
'\0' || *
pos ==
'/' || *
pos ==
'.')) {
1934 return phar_analyze_path(fname, ext_str, ext_len, for_create);
1940 if (!(
pos && (*(
pos - 1) !=
'/')
1941 && (
pos += 5) && (*
pos ==
'\0' || *
pos ==
'/' || *
pos ==
'.')) && *(ext_str + 1) !=
'.' && *(ext_str + 1) !=
'/' && *(ext_str + 1) !=
'\0') {
1942 return phar_analyze_path(fname, ext_str, ext_len, for_create);
1945 if (*(ext_str + 1) !=
'.' && *(ext_str + 1) !=
'/' && *(ext_str + 1) !=
'\0') {
1946 return phar_analyze_path(fname, ext_str, ext_len, for_create);
1969 const char *
pos, *slash;
1982 if (
pos &&
pos != filename) {
2011 if (executable == 2) {
2015 if (executable == 1 && !pphar->
is_data) {
2019 if (!executable && pphar->
is_data) {
2039 || filename[
ZSTR_LEN(str_key)] ==
'/' || filename[
ZSTR_LEN(str_key)] ==
'\0')) {
2052 || filename[
ZSTR_LEN(str_key)] ==
'/' || filename[
ZSTR_LEN(str_key)] ==
'\0')) {
2068 while (
pos != filename && (*(
pos - 1) ==
'/' || *(
pos - 1) ==
'\0')) {
2083 return phar_check_str(filename, *ext_str, *ext_len, executable, for_create);
2088 *ext_len = slash -
pos;
2090 if (phar_check_str(filename, *ext_str, *ext_len, executable, for_create) ==
SUCCESS) {
2099 goto next_extension;
2106static bool php_check_dots(
const char *element,
size_t n)
2109 if (element[
n] !=
'.') {
2117#define IS_DIRECTORY_UP(element, len) \
2118 (len >= 2 && !php_check_dots(element, len))
2120#define IS_DIRECTORY_CURRENT(element, len) \
2121 (len == 1 && element[0] == '.')
2123#define IS_BACKSLASH(c) ((c) == '/')
2134 size_t ptr_length, path_length = *new_len;
2136 if (
PHAR_G(
cwd_len) && use_cwd && path_length > 2 && path[0] ==
'.' && path[1] ==
'/') {
2155 ptr = memchr(
ptr,
'/', path_length - (
ptr - path));
2156 }
while (
ptr &&
ptr - tok == 0 && *
ptr ==
'/' && ++
ptr && ++tok);
2158 if (!
ptr && (path_length - (tok - path))) {
2159 switch (path_length - (tok - path)) {
2169 if (tok[0] ==
'.' && tok[1] ==
'.') {
2181 ptr_length =
ptr - tok;
2184 while (newpath_len > 1 && !
IS_BACKSLASH(newpath[newpath_len - 1])) {
2188 if (newpath[0] !=
'/') {
2189 newpath[newpath_len] =
'\0';
2190 }
else if (newpath_len > 1) {
2194 if (newpath_len > 1) {
2195 newpath[newpath_len++] =
'/';
2196 memcpy(newpath + newpath_len, tok, ptr_length+1);
2198 memcpy(newpath + newpath_len, tok, ptr_length+1);
2201 newpath_len += ptr_length;
2204 if (
ptr == path + path_length) {
2211 ptr = memchr(
ptr,
'/', path_length - (
ptr - path));
2212 }
while (
ptr &&
ptr - tok == 0 && *
ptr ==
'/' && ++
ptr && ++tok);
2214 if (!
ptr && (path_length - (tok - path))) {
2215 ptr_length = path_length - (tok - path);
2216 ptr = path + path_length;
2222 *new_len = newpath_len;
2223 newpath[newpath_len] =
'\0';
2224 return erealloc(newpath, newpath_len + 1);
2242 const char *ext_str;
2259 save = (
char *)filename;
2262 phar_unixify_path_separators((
char *)filename,
filename_len);
2266 if (ext_len != -1) {
2272 *arch = (
char*)filename;
2277 if (filename != save) {
2278 efree((
char *)filename);
2288 *arch_len = ext_str - filename + ext_len;
2289 *arch =
estrndup(filename, *arch_len);
2291 if (ext_str[ext_len]) {
2293 *entry =
estrndup(ext_str+ext_len, *entry_len);
2295 phar_unixify_path_separators(*entry, *entry_len);
2304 if (filename != save) {
2305 efree((
char *)filename);
2327 spprintf(
error, 0,
"cannot initialize a phar outside of PHP execution");
2338 spprintf(
error, 0,
"__HALT_COMPILER(); must be declared in a phar");
2387 if (entry->
is_zip && process_zip > 0) {
2393 spprintf(
error, 0,
"phar error: unable to open zip-based phar archive \"%s\" to verify local file header for file \"%s\"", idata->
phar->
fname, entry->
filename);
2400 spprintf(
error, 0,
"phar error: internal corruption of zip-based phar \"%s\" (cannot read local file header for file \"%s\")", idata->
phar->
fname, entry->
filename);
2412 (
char *) &desc,
sizeof(desc))) {
2413 spprintf(
error, 0,
"phar error: internal corruption of zip-based phar \"%s\" (cannot read local data descriptor for file \"%s\")", idata->
phar->
fname, entry->
filename);
2416 if (desc.signature[0] ==
'P' && desc.signature[1] ==
'K') {
2425 spprintf(
error, 0,
"phar error: internal corruption of zip-based phar \"%s\" (local header of file \"%s\" does not match central directory)", idata->
phar->
fname, entry->
filename);
2438 if (process_zip == 1) {
2459static inline void phar_set_32(
char *
buffer, uint32_t var)
2461#ifdef WORDS_BIGENDIAN
2462 *((
buffer) + 3) = (
unsigned char) (((var) >> 24) & 0xFF);
2463 *((
buffer) + 2) = (
unsigned char) (((var) >> 16) & 0xFF);
2464 *((
buffer) + 1) = (
unsigned char) (((var) >> 8) & 0xFF);
2465 *((
buffer) + 0) = (
unsigned char) ((var) & 0xFF);
2471static int phar_flush_clean_deleted_apply(
zval *
zv)
2487 size_t index_len, web_len;
2494 index_php =
"index.php";
2498 web_index =
"index.php";
2501 index_len =
strlen(index_php);
2502 web_len =
strlen(web_index);
2504 if (index_len > 400) {
2507 spprintf(
error, 0,
"Illegal filename passed in for stub creation, was %zd characters long, and only 400 or less is allowed", index_len);
2512 if (web_len > 400) {
2515 spprintf(
error, 0,
"Illegal web filename passed in for stub creation, was %zd characters long, and only 400 or less is allowed", web_len);
2520 return phar_get_stub(index_php, web_index, index_len+1, web_len+1);
2535 static const char halt_stub[] =
"__HALT_COMPILER();";
2539 int restore_alias_len, global_flags = 0;
2540 bool must_close_old_file =
false;
2541 bool has_dirs =
false;
2542 char manifest[18], entry_buffer[24];
2546 uint32_t manifest_len, mytime, new_manifest_count;
2552 bool free_fp =
true;
2553 bool free_ufp =
true;
2554 bool manifest_hack =
false;
2559 spprintf(
error, 0,
"internal error: attempt to flush cached zip-based phar \"%s\"", phar->
fname);
2568 if (!zend_hash_num_elements(&phar->
manifest) && !user_stub) {
2590 must_close_old_file =
false;
2594 must_close_old_file = oldfile !=
NULL;
2601 if (must_close_old_file) {
2611 if (must_close_old_file) {
2616 spprintf(
error, 0,
"illegal stub for phar \"%s\" (__HALT_COMPILER(); is missing)", phar->
fname);
2622 const char end_sequence[] =
" ?>\r\n";
2623 size_t end_sequence_len =
strlen(end_sequence);
2627 || end_sequence_len !=
php_stream_write(newfile, end_sequence, end_sequence_len)
2629 if (must_close_old_file) {
2634 spprintf(
error, 0,
"unable to create stub from string in new phar \"%s\"", phar->
fname);
2652 if (must_close_old_file) {
2660 spprintf(
error, 0,
"unable to copy stub of old phar to new phar \"%s\"", phar->
fname);
2664 zend_string_free(new_stub);
2669 zend_string_free(new_stub);
2673 halt_offset = manifest_ftell;
2681 main_metadata_str.
s =
NULL;
2689 new_manifest_count = 0;
2714 ++new_manifest_count;
2755 if (must_close_old_file) {
2775 if (must_close_old_file) {
2794 if (shared_cfp ==
NULL) {
2797 entry->
cfp = shared_cfp;
2802 if (must_close_old_file) {
2813 if (must_close_old_file) {
2824 if (must_close_old_file) {
2829 spprintf(
error, 0,
"unable to copy compressed file contents of file \"%s\" while creating new phar \"%s\"", entry->
filename, phar->
fname);
2861 phar_set_32(manifest, manifest_len);
2863 if(manifest[0] ==
'\r' || manifest[0] ==
'\n') {
2865 phar_set_32(manifest, manifest_len);
2866 manifest_hack =
true;
2868 phar_set_32(manifest+4, new_manifest_count);
2876 phar_set_32(manifest+10, global_flags);
2877 phar_set_32(manifest+14, phar->
alias_len);
2880 if (
sizeof(manifest) !=
php_stream_write(newfile, manifest,
sizeof(manifest))
2883 if (must_close_old_file) {
2891 spprintf(
error, 0,
"unable to write manifest header of new phar \"%s\"", phar->
fname);
2899 phar_set_32(manifest, main_metadata_str.
s ?
ZSTR_LEN(main_metadata_str.
s) : 0);
2902 smart_str_free(&main_metadata_str);
2904 if (must_close_old_file) {
2912 spprintf(
error, 0,
"unable to write manifest meta-data of new phar \"%s\"", phar->
fname);
2917 smart_str_free(&main_metadata_str);
2940 if (must_close_old_file) {
2946 spprintf(
error, 0,
"unable to write filename of directory \"%s\" to manifest of new phar \"%s\"", entry->
filename, phar->
fname);
2965 phar_set_32(entry_buffer+4, mytime);
2967 phar_set_32(entry_buffer+12, entry->
crc32);
2968 phar_set_32(entry_buffer+16, entry->
flags);
2970 phar_set_32(entry_buffer+20, metadata_str ?
ZSTR_LEN(metadata_str) : 0);
2972 if (
sizeof(entry_buffer) !=
php_stream_write(newfile, entry_buffer,
sizeof(entry_buffer))
2975 if (must_close_old_file) {
2982 spprintf(
error, 0,
"unable to write temporary manifest of file \"%s\" to manifest of new phar \"%s\"", entry->
filename, phar->
fname);
2989 if (manifest_hack) {
2991 if (must_close_old_file) {
2998 spprintf(
error, 0,
"unable to write manifest padding byte");
3018 if (must_close_old_file) {
3030 if (must_close_old_file) {
3044 if (must_close_old_file) {
3077 if (shared_cfp !=
NULL) {
3095 char *digest =
NULL;
3100 char *save = *
error;
3101 spprintf(
error, 0,
"phar error: unable to write signature: %s", save);
3107 if (must_close_old_file) {
3119 phar_set_32(sig_buf, digest_len);
3133 if (phar->
fp && free_fp) {
3144 if (must_close_old_file) {
3171 add_assoc_long(&filterparams,
"window",
MAX_WBITS+16);
3177 spprintf(
error, 4096,
"unable to compress all contents of phar \"%s\" using zlib, PHP versions older than 5.2.6 have a buggy zlib", phar->
fname);
3207 spprintf(
error, 0,
"unable to seek to __HALT_COMPILER(); in new phar \"%s\"", phar->
fname);
3214 if (shared_cfp !=
NULL) {
3226#ifdef COMPILE_DL_PHAR
3233static ssize_t phar_zend_stream_reader(
void *
handle,
char *
buf,
size_t len)
3239static size_t phar_zend_stream_fsizer(
void *
handle)
3250 ret = phar_save_resolve_path(filename);
3262 if (!file_handle || !file_handle->
filename) {
3281 switch (file_handle->
type) {
3311 CG(zend_lineno) = 0;
3319 zend_string_release(
name);
3330static void mime_type_dtor(
zval *
zv)
3337#if defined(COMPILE_DL_PHAR) && defined(ZTS)
3350#define PHAR_SET_MIME(mimetype, ret, fileext) \
3351 mime.mime = mimetype; \
3352 mime.len = sizeof((mimetype))+1; \
3354 zend_hash_str_add_mem(&phar_globals->mime_types, fileext, sizeof(fileext)-1, (void *)&mime, sizeof(phar_mime_type)); \
3496 for (uint32_t i = 0; i < zend_hash_num_elements(&
cached_phars); ++i) {
3546#ifdef PHAR_HAVE_OPENSSL
3558 PUTS(
"Phar based on pear/PHP_Archive, original concept by Davey Shafik.");
3560 PUTS(
"Phar fully realized by Gregory Beaver and Marcus Boerger.");
3562 PUTS(
"Portions of tar implementation Copyright (c) 2003-2009 Tim Kientzle.");
SAPI_API sapi_module_struct sapi_module
file_private const char ext[]
file(string $filename, int $flags=0, $context=null)
strrchr(string $haystack, string $needle, bool $before_needle=false)
strstr(string $haystack, string $needle, bool $before_needle=false)
strchr(string $haystack, string $needle, bool $before_needle=false)
PHPAPI zend_result php_crc32_stream_bulk_update(uint32_t *crc, php_stream *fp, size_t nr)
#define php_crc32_bulk_init()
#define php_crc32_bulk_end(c)
zend_ffi_ctype_name_buf buf
PHPAPI int php_check_open_basedir(const char *path)
PHPAPI char * expand_filepath(const char *filepath, char *real_path)
void phar_restore_orig_functions(void)
void phar_release_functions(void)
foreach($dp as $el) foreach( $dp as $el) if( $pass2< 2) echo ""
PHPAPI php_stream_filter * php_stream_filter_create(const char *filtername, zval *filterparams, uint8_t persistent)
PHPAPI php_stream_filter * php_stream_filter_remove(php_stream_filter *filter, int call_dtor)
void phar_flush_ex(phar_archive_data *phar, zend_string *user_stub, bool is_default_stub, char **error)
zend_result phar_detect_phar_fname_ext(const char *filename, size_t filename_len, const char **ext_str, size_t *ext_len, int executable, int for_create, int is_complete)
php_info_print_table_start()
#define SAFE_PHAR_GET_32(buffer, endbuffer, var)
zend_module_entry phar_module_entry
#define PHAR_SET_MIME(mimetype, ret, fileext)
bool phar_metadata_tracker_has_data(const phar_metadata_tracker *tracker, bool persistent)
void phar_metadata_tracker_free(phar_metadata_tracker *tracker, bool persistent)
void phar_entry_remove(phar_entry_data *idata, char **error)
memset(phar_globals, 0, sizeof(zend_phar_globals))
char * phar_fix_filepath(char *path, size_t *new_len, int use_cwd)
zend_result phar_postprocess_file(phar_entry_data *idata, uint32_t crc32, char **error, int process_zip)
void phar_metadata_tracker_clone(phar_metadata_tracker *tracker)
bool phar_archive_delref(phar_archive_data *phar)
#define MANIFEST_FIXED_LEN
phar_intercept_functions_shutdown()
zend_result phar_metadata_tracker_unserialize_or_copy(phar_metadata_tracker *tracker, zval *metadata, bool persistent, HashTable *unserialize_options, const char *method_name)
void phar_destroy_phar_data(phar_archive_data *phar)
void phar_flush(phar_archive_data *phar, char **error)
#define MAPPHAR_ALLOC_FAIL(msg)
zend_result phar_split_fname(const char *filename, size_t filename_len, char **arch, size_t *arch_len, char **entry, size_t *entry_len, int executable, int for_create)
zend_result phar_create_or_parse_filename(char *fname, size_t fname_len, char *alias, size_t alias_len, bool is_data, uint32_t options, phar_archive_data **pphar, char **error)
void phar_metadata_tracker_copy(phar_metadata_tracker *dest, const phar_metadata_tracker *source, bool persistent)
phar_intercept_functions_init()
zend_result phar_open_or_create_filename(char *fname, size_t fname_len, char *alias, size_t alias_len, bool is_data, uint32_t options, phar_archive_data **pphar, char **error)
void phar_request_initialize(void)
void phar_metadata_tracker_try_ensure_has_serialized_data(phar_metadata_tracker *tracker, bool persistent)
#define PHAR_GET_32(buffer, var)
#define IS_DIRECTORY_CURRENT(element, len)
zend_result phar_open_executed_filename(char *alias, size_t alias_len, char **error)
void destroy_phar_manifest_entry_int(phar_entry_info *entry)
void destroy_phar_manifest_entry(zval *zv)
php_info_print_box_start(0)
#define IS_DIRECTORY_UP(element, len)
phar_save_orig_functions()
#define MAPPHAR_FAIL(msg)
zend_string * phar_create_default_stub(const char *index_php, const char *web_index, char **error)
php_info_print_table_end()
zend_op_array *(* phar_orig_compile_file)(zend_file_handle *file_handle, int type)
return php_register_url_stream_wrapper("phar", &php_stream_phar_wrapper)
void phar_parse_metadata_lazy(const char *buffer, phar_metadata_tracker *tracker, uint32_t zip_metadata_len, bool persistent)
php_info_print_table_row(2, "Phar: PHP Archive support", "enabled")
void phar_entry_delref(phar_entry_data *idata)
zend_result phar_open_from_filename(char *fname, size_t fname_len, char *alias, size_t alias_len, uint32_t options, phar_archive_data **pphar, char **error)
HT_INVALIDATE & phar_globals
#define PHAR_FILE_COMPRESSED_NONE
#define PHAR_API_MIN_READ
void phar_add_virtual_dirs(phar_archive_data *phar, char *filename, size_t filename_len)
int phar_parse_zipfile(php_stream *fp, char *fname, size_t fname_len, char *alias, size_t alias_len, phar_archive_data **pphar, char **error)
#define PHAR_SIG_OPENSSL_SHA512
char * phar_compress_filter(phar_entry_info *entry, int return_unknown)
#define PHAR_FILE_COMPRESSED_BZ2
struct _phar_metadata_tracker phar_metadata_tracker
#define PHAR_ENT_COMPRESSED_GZ
struct _phar_entry_fp phar_entry_fp
int phar_seek_efp(phar_entry_info *entry, zend_off_t offset, int whence, zend_off_t position, int follow_links)
#define PHAR_SIG_OPENSSL_SHA256
#define PHAR_FILE_COMPRESSED_GZ
#define PHP_PHAR_API_VERSION
#define PHAR_API_VERSION_NODIR
phar_archive_data * last_phar
struct _phar_entry_fp_info phar_entry_fp_info
zend_result phar_parse_tarfile(php_stream *fp, char *fname, size_t fname_len, char *alias, size_t alias_len, phar_archive_data **pphar, uint32_t compression, char **error)
#define PHAR_ENT_PERM_DEF_DIR
int phar_SERVER_mung_list
#define PHAR_HDR_SIGNATURE
#define PHAR_HDR_COMPRESSION_MASK
php_stream * phar_get_efp(phar_entry_info *entry, int follow_links)
HashTable phar_persist_map
struct _phar_archive_data phar_archive_data
#define PHAR_ENT_COMPRESSION_MASK
zend_result phar_create_signature(phar_archive_data *phar, php_stream *fp, char **signature, size_t *signature_length, char **error)
zend_result phar_open_archive_fp(phar_archive_data *phar)
void phar_tar_flush(phar_archive_data *phar, zend_string *user_stub, bool is_default_stub, char **error)
#define PHAR_ENT_COMPRESSED_BZ2
zend_result phar_free_alias(phar_archive_data *phar, char *alias, size_t alias_len)
zend_result phar_verify_signature(php_stream *fp, size_t end_of_phar, uint32_t sig_type, char *sig, size_t sig_len, char *fname, char **signature, size_t *signature_len, char **error)
void phar_zip_flush(phar_archive_data *archive, zend_string *user_stub, bool is_default_stub, char **error)
struct _phar_entry_info phar_entry_info
zend_string * phar_find_in_include_path(zend_string *file, phar_archive_data **pphar)
struct _phar_entry_data phar_entry_data
phar_entry_fp * cached_fp
struct _phar_mime_type phar_mime_type
#define PHAR_FILE_COMPRESSION_MASK
zend_result phar_get_archive(phar_archive_data **archive, char *fname, size_t fname_len, char *alias, size_t alias_len, char **error)
zend_result phar_open_or_create_tar(char *fname, size_t fname_len, char *alias, size_t alias_len, int is_data, uint32_t options, phar_archive_data **pphar, char **error)
int phar_open_or_create_zip(char *fname, size_t fname_len, char *alias, size_t alias_len, int is_data, uint32_t options, phar_archive_data **pphar, char **error)
phar_entry_info * phar_open_jit(phar_archive_data *phar, phar_entry_info *entry, char **error)
bool phar_is_tar(char *buf, char *fname)
#define PHAR_API_VER_MASK
struct _phar_zip_file_header phar_zip_file_header
struct _phar_zip_file_datadesc phar_zip_data_desc
#define PHP_MSHUTDOWN_FUNCTION
#define PHP_MINIT_FUNCTION
#define PHP_MINFO_FUNCTION
#define PHP_GINIT_FUNCTION
#define PHP_RSHUTDOWN_FUNCTION
#define PHP_GSHUTDOWN_FUNCTION
#define PHP_MODULE_GLOBALS
unsigned const char * end
unsigned const char * pos
#define STD_PHP_INI_ENTRY
#define STD_PHP_INI_BOOLEAN
PHP_JSON_API size_t int options
PHPAPI char * php_strtok_r(char *s, const char *delim, char **last)
unsigned char key[REFLECTION_KEY_LEN]
#define php_stream_filter_append(chain, filter)
#define php_stream_filter_flush(filter, finish)
#define php_stream_fopen_tmpfile()
#define php_stream_stat_path(path, ssb)
struct _php_stream php_stream
#define php_stream_read(stream, buf, count)
struct _php_stream_filter php_stream_filter
#define php_stream_rewind(stream)
#define PHP_STREAM_COPY_ALL
#define php_stream_getc(stream)
#define php_stream_seek(stream, offset, whence)
#define php_stream_flush(stream)
#define php_stream_eof(stream)
#define php_stream_close(stream)
#define php_stream_tell(stream)
#define php_stream_is_persistent(stream)
#define php_stream_open_wrapper(path, mode, options, opened)
PHPAPI zend_result php_unregister_url_stream_wrapper(const char *protocol)
#define php_stream_copy_to_stream_ex(src, dest, maxlen, len)
struct _php_stream_statbuf php_stream_statbuf
#define php_stream_write(stream, buf, count)
PHPAPI char * php_stristr(const char *s, const char *t, size_t s_len, size_t t_len)
struct php_serialize_data * php_serialize_data_t
PHPAPI void php_unserialize_with_options(zval *return_value, const char *buf, const size_t buf_len, HashTable *options, const char *function_name)
#define PHP_VAR_SERIALIZE_INIT(d)
PHPAPI void php_var_serialize(smart_str *buf, zval *struc, php_serialize_data_t *data)
#define PHP_VAR_SERIALIZE_DESTROY(d)
const php_stream_wrapper php_stream_phar_wrapper
phar_metadata_tracker metadata_tracker
uint32_t is_temporary_alias
phar_entry_info * internal_file
phar_entry_fp_info * manifest
uint32_t compressed_filesize
phar_metadata_tracker metadata_tracker
enum phar_fp_type fp_type
uint32_t uncompressed_filesize
php_stream_filter_chain writefilters
zend_string * opened_path
union _zend_file_handle::@045057025306333206016200356074063117305134322373 handle
zend_stream_closer_t closer
zend_stream_fsizer_t fsizer
zend_stream_reader_t reader
ZEND_API zend_string * zend_strpprintf(size_t max_len, const char *format,...)
ZEND_API zend_result(* zend_stream_open_function)(zend_file_handle *handle)
ZEND_API zend_string *(* zend_resolve_path)(zend_string *filename)
#define ZEND_TSRMLS_CACHE_UPDATE()
#define ZEND_TSRMLS_CACHE_DEFINE()
ZEND_API HashTable module_registry
ZEND_API void add_assoc_long_ex(zval *arg, const char *key, size_t key_len, zend_long n)
#define CHECK_NULL_PATH(p, l)
#define ZEND_DECLARE_MODULE_GLOBALS(module_name)
#define ZEND_GET_MODULE(name)
#define estrndup(s, length)
#define ecalloc(nmemb, size)
#define pestrndup(s, length, persistent)
#define pefree(ptr, persistent)
#define erealloc(ptr, size)
#define pecalloc(nmemb, size, persistent)
strncmp(string $string1, string $string2, int $length)
zend_string_release_ex(func->internal_function.function_name, 0)
ZEND_API zend_op_array *(* zend_compile_file)(zend_file_handle *file_handle, int type)
struct _zend_op_array zend_op_array
#define strncasecmp(s1, s2, n)
ZEND_API zval * zend_get_constant_str(const char *name, size_t name_len)
ZEND_API zend_string * zend_get_executed_filename_ex(void)
ZEND_API void ZEND_FASTCALL zend_hash_destroy(HashTable *ht)
ZEND_API void ZEND_FASTCALL zend_hash_apply(HashTable *ht, apply_func_t apply_func)
ZEND_API void ZEND_FASTCALL zend_hash_apply_with_argument(HashTable *ht, apply_func_arg_t apply_func, void *argument)
ZEND_API void ZEND_FASTCALL zend_hash_clean(HashTable *ht)
ZEND_API void ZEND_FASTCALL zend_hash_graceful_reverse_destroy(HashTable *ht)
ZEND_API void ZEND_FASTCALL zend_array_destroy(HashTable *ht)
ZEND_API zend_result ZEND_FASTCALL zend_hash_str_del(HashTable *ht, const char *str, size_t len)
#define zend_hash_init(ht, nSize, pHashFunction, pDestructor, persistent)
#define ZEND_HASH_MAP_FOREACH_PTR(ht, _ptr)
#define HT_IS_INITIALIZED(ht)
#define ZEND_HASH_APPLY_REMOVE
#define HT_INVALIDATE(ht)
#define ZEND_HASH_APPLY_KEEP
#define ZEND_HASH_MAP_FOREACH_STR_KEY_PTR(ht, _key, _ptr)
#define ZEND_HASH_FOREACH_END()
ZEND_API bool zend_ini_parse_bool(zend_string *str)
#define ZEND_INI_STAGE_STARTUP
#define REGISTER_INI_ENTRIES()
#define ZEND_INI_MH(name)
struct _zend_file_handle zend_file_handle
ZEND_API void zend_init_rsrc_list(void)
struct _zend_string zend_string
#define ZEND_MOD_OPTIONAL(name)
struct _zend_module_dep zend_module_dep
struct _zend_module_entry zend_module_entry
#define ZEND_MOD_REQUIRED(name)
#define STANDARD_MODULE_PROPERTIES_EX
#define STANDARD_MODULE_HEADER_EX
#define ALLOCA_FLAG(name)
#define do_alloca(p, use_heap)
#define free_alloca(p, use_heap)
ZEND_API void zend_stream_init_filename_ex(zend_file_handle *handle, zend_string *filename)
ZEND_API zend_string_init_interned_func_t zend_string_init_interned
#define Z_TRY_ADDREF_P(pz)
struct _zend_array HashTable
ZEND_RESULT_CODE zend_result
#define ZVAL_COPY_VALUE(z, v)
ZEND_API void zval_ptr_dtor(zval *zval_ptr)
#define DEFAULT_DIR_SEPARATOR