\n" . $extra_message; die(); }; $work_dir = dirname(dirname(__FILE__)) . '/work/'; if (isset($_GET['r'])) { if (base64_decode($_GET['r'],true)===false) throw_http_error(400, 'Invalid base64'); if (!isset($_GET['t'])) throw_http_error(400, 'Repository type not given'); if (($_GET['t']!='git') && ($_GET['t']!='hg')) throw_http_error(501, 'Repository type not implemented'); if (!is_dir($work_dir . 'repositories/' . $_GET['t'] . '/' . $_GET['r'])) { $wish_list = fopen($work_dir . 'wish-list','a'); if ($wish_list === false) throw_http_error(500, 'Internal Server Error' , 'Cannot open wish-list'); fwrite($wish_list, $_GET['t'] . " " . $_GET['r'] . "\n"); fclose($wish_list); throw_http_error(503, 'Service Unavailable', 'I put repository onto wish-list'); } if (isset($_GET['tag'])) { if (base64_decode($_GET['tag'],true)===false) $_GET['tag'] = base64_encode($_GET['tag']); $commit_identifier = '$(' . 'echo "' . $_GET['tag'] . '" | ' . 'base64 -d' . ')'; } elseif (($_GET['t']=='git') && isset($_GET['commit'])) { if (!preg_match('/^[A-Fa-f0-9]{40}$/', $_GET['commit'])) throw_http_error(400, 'The given commit does not have exactly 40 hex digits'); $commit_identifier = $_GET['commit']; } function expand_key($key) { if (preg_match('/^[A-Fa-f0-9]{16}$/', $key)) return '.\{24\}' . $key; elseif (preg_match('/^[A-Fa-f0-9]{40}$/', $key)) return $key; else throw_http_error(400, 'The given key does not have exactly 16 or 40 hex digits'); } if (isset($commit_identifier)) { if (isset($_GET['valid_keys'])) { $key_regex = '\(' . implode( '\|', array_map( 'expand_key', explode( ',', $_GET['valid_keys'] ) ) ) . '\)'; /* shell_exec( 'GNUPGHOME="' . $work_dir . 'gnupg" gpg ' . '--keyserver=hkp://keys.gnupg.net ' . '--recv-keys ' . implode(' ',explode(',',$_GET['valid_keys'])) ); */ if ($_GET['t']=='git') { if (trim(shell_exec( 'GNUPGHOME="' . $work_dir . 'gnupg" git -C "' . $work_dir . 'repositories/' . $_GET['t'] . '/' . $_GET['r'] . '" verify-tag --raw "' . $commit_identifier . '" 2>&1 | ' . 'grep -c "\[GNUPG:\] VALIDSIG ' . $key_regex . ' "' )) == '0') throw_http_error(409, 'Commit ' . $commit_identifier . ' is not signed by ' . $_GET['valid_keys']); } else throw_http_error(400, 'Checking signatures is not implemented for ' . $_GET['t'] . ' repositories'); } if (isset($_GET['p'])) { if (base64_decode($_GET['p'],true)===false) throw_http_error(400, 'Invalid base64'); $prefix = ' --prefix="$(' . 'echo "' . $_GET['p'] . '" | ' . 'base64 -d' . ')"'; } else { $prefix = ''; } if ($_GET['t']=='git') $handle = popen( 'git -C "' . $work_dir . 'repositories/' . $_GET['t'] . '/' . $_GET['r'] . '"' . ' archive' . $prefix . ' "' . $commit_identifier . '" | ' . 'gzip -nc', 'r' ); elseif ($_GET['t']=='hg') $handle = popen( 'hg archive' . ' -t tgz' . $prefix . ' -R "' . $work_dir . 'repositories/' . $_GET['t'] . '/' . $_GET['r'] . '"' . ' -r "' . $commit_identifier . '"' . ' /dev/stdout', 'r' ); else $handle = false; if ($handle === false) throw_http_error(500, 'Unable to create archive'); header('Content-type: application/x-gzip'); header('Content-Disposition: attachment; filename="archive.tar.gz"'); fpassthru($handle); pclose($handle); die(); } throw_http_error(501, 'Not implemented'); } print 'Hi, this is an archive server!
' . "\n"; print 'I provide archives of these upstreams:
' . "\n"; print implode( "
\n", array_map( "base64_decode", explode( "\n", shell_exec( 'find "' . $work_dir . 'repositories" -mindepth 2 -maxdepth 2 -printf "%f\n" | sort' ) ) ) ); die();