$version, 'key' => $key, 'file' => $file, 'archive' => $archive, 'zipfile' => $zipfile ); } function display_from_archive( $params, $content_map = array(), $override_extractor = null, $expires = null) { $params['template'] = dirname(__FILE__)."/template.php"; $params['title'] = NULL; $params['charset'] = NULL; $params['content'] = NULL; // Check file exists. if ($params['zipfile']) { $check_file = $params['archive']; if (!is_readable($check_file)) { file_not_found($params, 'Unable to find zipfile.'); return; } } else { $check_file = $params['file']; if (is_dir($check_file)) { if(substr($check_file, -1) != '/') { $redirect = resolve_url(basename($check_file).'/'); header("Location: $redirect", TRUE, 301); return; } $found_file = NULL; if (is_readable("$check_file/index.html")) $found_file = 'index.html'; else if (is_readable("$check_file/index.htm")) $found_file = 'index.htm'; if ($found_file) { $params['file'] = $check_file = $check_file.$found_file; $params['key'] = $params['key'].$found_file; } else { if (!http_headers('text/html', filemtime($check_file), $expires)) return; return display_dir($params, $check_file); } } else if (!is_readable($check_file)) { file_not_found($params, 'Unable to find file.'); return; } } // Choose filter to use $info_map = array_merge($content_map, array( array('@.*@','@[.](txt|py|rst|jam|v2|bat|sh|xml|toyxml)$@i','text','text/plain'), array('@.*@','@[.](qbk|quickbook)$@i','qbk','text/plain'), array('@.*@','@[.](c|h|cpp|hpp)$@i','cpp','text/plain'), array('@.*@','@[.]png$@i','raw','image/png'), array('@.*@','@[.]gif$@i','raw','image/gif'), array('@.*@','@[.](jpg|jpeg|jpe)$@i','raw','image/jpeg'), array('@.*@','@[.]css$@i','raw','text/css'), array('@.*@','@[.]js$@i','raw','application/x-javascript'), array('@.*@','@[.]pdf$@i','raw','application/pdf'), array('@.*@','@[.](html|htm)$@i','raw','text/html'), array('@.*@','@(/|^)(Jamroot|Jamfile|ChangeLog|configure)$@i','text','text/plain'), array('@.*@','@[.]dtd$@i','raw','application/xml-dtd'), )); $preprocess = null; $extractor = null; $type = null; foreach ($info_map as $i) { if (preg_match($i[1],$params['key'])) { $extractor = $i[2]; $type = $i[3]; $preprocess = isset($i[4]) ? $i[4] : NULL; break; } } if ($override_extractor) $extractor = $override_extractor; if (!$extractor) { file_not_found($params); return; } // Handle ETags and Last-Modified HTTP headers. // Output raw files. if($extractor == 'raw') { if (!http_headers($type, filemtime($check_file), $expires)) return; if($_SERVER['REQUEST_METHOD'] != 'HEAD') display_raw_file($params, $type); } else { if (!http_headers('text/html', filemtime($check_file), $expires)) return; // Read file from hard drive or zipfile // Note: this sets $params['content'] with either the content or an error // message: if(!extract_file($params, $params['content'])) { file_not_found($params, $params['content']); return; } // Check if the file contains a redirect. if($type == 'text/html') { if($redirect = detect_redirect($params['content'])) { header("Location: $redirect", TRUE, 301); if($_SERVER['REQUEST_METHOD'] != 'HEAD') echo $params['content']; return; } } // Finally process the file and display it. if($_SERVER['REQUEST_METHOD'] != 'HEAD') { if ($preprocess) { $params['content'] = call_user_func($preprocess, $params['content']); } echo_filtered($extractor, $params); } } } // HTTP header handling function http_headers($type, $last_modified, $expires = null) { header('Content-type: '.$type); switch($type) { case 'image/png': case 'image/gif': case 'image/jpeg': case 'text/css': case 'application/x-javascript': case 'application/pdf': case 'application/xml-dtd': header('Expires: '.date(DATE_RFC2822, strtotime("+1 year"))); header('Cache-Control: max-age=31556926'); // A year, give or take a day. break; default: if($expires) { header('Expires: '.date(DATE_RFC2822, strtotime($expires))); header('Cache-Control: max-age='.strtotime($expires, 0)); } break; } return conditional_get(max(strtotime(BOOST_DOCS_MODIFIED_DATE), $last_modified)); } function conditional_get($last_modified) { if(!$last_modified) return true; $last_modified_text = date(DATE_RFC2822, $last_modified); $etag = '"'.md5($last_modified).'"'; header("Last-Modified: $last_modified_text"); header("ETag: $etag"); $checked = false; if(isset($_SERVER['HTTP_IF_MODIFIED_SINCE'])) { $checked = true; $if_modified_since = strtotime(stripslashes($_SERVER['HTTP_IF_MODIFIED_SINCE'])); if(!$if_modified_since || $if_modified_since < $last_modified) return true; } if(isset($_SERVER['HTTP_IF_NONE_MATCH'])) { $checked = true; if(stripslashes($_SERVER['HTTP_IF_NONE_MATCH'] != $etag)) return true; } if(!$checked) return true; header($_SERVER["SERVER_PROTOCOL"].' 304 Not Modified'); return false; } // General purpose render callbacks. function boost_archive_render_callbacks($content, $params) { $version_title = str_replace('_', ' ', preg_replace('@(?<=\d)_(?=\d)@', '.', ucwords($params['version']))); $charset = $params['charset'] ? $params['charset'] : 'us-ascii'; $title = $params['title'] ? "$params[title] - $version_title" : 'Boost C++ Libraries'; $head = "\n"; if (!empty($params['noindex'])) $head .= "\n"; $head .= "