· 8 years ago · Jun 14, 2018, 09:28 PM
1<?php
2$lang = 'en';
3$homedir = './';
4$editcols = 80;
5$editrows = 25;
6$htaccess = '.htaccess';
7$htpasswd = '.htpasswd';
8
9if (get_magic_quotes_gpc()) {
10 array_walk($_GET, 'strip');
11 array_walk($_POST, 'strip');
12 array_walk($_REQUEST, 'strip');
13}
14
15if (array_key_exists('image', $_GET)) {
16 header('Content-Type: image/gif');
17 die(getimage($_GET['image']));
18}
19
20if (!function_exists('lstat')) {
21 function lstat ($filename) {
22 return stat($filename);
23 }
24}
25
26$delim = DIRECTORY_SEPARATOR;
27
28if (function_exists('php_uname')) {
29 $win = (strtoupper(substr(PHP_OS, 0, 3)) === 'WIN') ? true : false;
30} else {
31 $win = ($delim == '\\') ? true : false;
32}
33
34if (!empty($_SERVER['PATH_TRANSLATED'])) {
35 $scriptdir = dirname($_SERVER['PATH_TRANSLATED']);
36} elseif (!empty($_SERVER['SCRIPT_FILENAME'])) {
37 $scriptdir = dirname($_SERVER['SCRIPT_FILENAME']);
38} elseif (function_exists('getcwd')) {
39 $scriptdir = getcwd();
40} else {
41 $scriptdir = '.';
42}
43
44$homedir = relative2absolute($homedir, $scriptdir);
45$dir = (array_key_exists('dir', $_REQUEST)) ? $_REQUEST['dir'] : $homedir;
46
47if (array_key_exists('olddir', $_POST) && !path_is_relative($_POST['olddir'])) {
48 $dir = relative2absolute($dir, $_POST['olddir']);
49}
50
51$directory = simplify_path(addslash($dir));
52$files = array();
53$action = '';
54
55if (!empty($_POST['submit_all'])) {
56 $action = $_POST['action_all'];
57 for ($i = 0; $i < $_POST['num']; $i++) {
58 if (array_key_exists("checked$i", $_POST) && $_POST["checked$i"] == 'true') {
59 $files[] = $_POST["file$i"];
60 }
61 }
62} elseif (!empty($_REQUEST['action'])) {
63 $action = $_REQUEST['action'];
64 $files[] = relative2absolute($_REQUEST['file'], $directory);
65} elseif (!empty($_POST['submit_upload']) && !empty($_FILES['upload']['name'])) {
66 $files[] = $_FILES['upload'];
67 $action = 'upload';
68} elseif (array_key_exists('num', $_POST)) {
69 for ($i = 0; $i < $_POST['num']; $i++) {
70 if (array_key_exists("submit$i", $_POST)) break;
71 }
72 if ($i < $_POST['num']) {
73 $action = $_POST["action$i"];
74 $files[] = $_POST["file$i"];
75 }
76}
77if (empty($action) && (!empty($_POST['submit_create']) || (array_key_exists('focus', $_POST) && $_POST['focus'] == 'create')) && !empty($_POST['create_name'])) {
78 $files[] = relative2absolute($_POST['create_name'], $directory);
79 switch ($_POST['create_type']) {
80 case 'directory':
81 $action = 'create_directory';
82 break;
83 case 'file':
84 $action = 'create_file';
85 }
86}
87if (sizeof($files) == 0) $action = ''; else $file = reset($files);
88
89if ($lang == 'auto') {
90 if (array_key_exists('HTTP_ACCEPT_LANGUAGE', $_SERVER) && strlen($_SERVER['HTTP_ACCEPT_LANGUAGE']) >= 2) {
91 $lang = substr($_SERVER['HTTP_ACCEPT_LANGUAGE'], 0, 2);
92 } else {
93 $lang = 'en';
94 }
95}
96
97$words = getwords($lang);
98
99if ($site_charset == 'auto') {
100 $site_charset = $word_charset;
101}
102
103$cols = ($win) ? 4 : 7;
104
105if (!isset($dirpermission)) {
106 $dirpermission = (function_exists('umask')) ? (0777 & ~umask()) : 0755;
107}
108if (!isset($filepermission)) {
109 $filepermission = (function_exists('umask')) ? (0666 & ~umask()) : 0644;
110}
111
112if (!empty($_SERVER['SCRIPT_NAME'])) {
113 $self = html(basename($_SERVER['SCRIPT_NAME']));
114} elseif (!empty($_SERVER['PHP_SELF'])) {
115 $self = html(basename($_SERVER['PHP_SELF']));
116} else {
117 $self = '';
118}
119
120if (!empty($_SERVER['SERVER_SOFTWARE'])) {
121 if (strtolower(substr($_SERVER['SERVER_SOFTWARE'], 0, 6)) == 'apache') {
122 $apache = true;
123 } else {
124 $apache = false;
125 }
126} else {
127 $apache = true;
128}
129
130switch ($action) {
131
132case 'view':
133
134 if (is_script($file)) {
135
136 /* highlight_file is a mess! */
137 ob_start();
138 highlight_file($file);
139 $src = ereg_replace('<font color="([^"]*)">', '<span style="color: \1">', ob_get_contents());
140 $src = str_replace(array('</font>', "\r", "\n"), array('</span>', '', ''), $src);
141 ob_end_clean();
142
143 html_header();
144 echo '<h2 style="text-align: left; margin-bottom: 0">' . html($file) . '</h2>
145
146<hr />
147
148<table>
149<tr>
150<td style="text-align: right; vertical-align: top; color: gray; padding-right: 3pt; border-right: 1px solid gray">
151<pre style="margin-top: 0"><code>';
152
153 for ($i = 1; $i <= sizeof(file($file)); $i++) echo "$i\n";
154
155 echo '</code></pre>
156</td>
157<td style="text-align: left; vertical-align: top; padding-left: 3pt">
158<pre style="margin-top: 0">' . $src . '</pre>
159</td>
160</tr>
161</table>
162
163';
164
165 html_footer();
166
167 } else {
168
169 header('Content-Type: ' . getmimetype($file));
170 header('Content-Disposition: filename=' . basename($file));
171
172 readfile($file);
173
174 }
175
176 break;
177
178case 'download':
179
180 header('Pragma: public');
181 header('Expires: 0');
182 header('Cache-Control: must-revalidate, post-check=0, pre-check=0');
183 header('Content-Type: ' . getmimetype($file));
184 header('Content-Disposition: attachment; filename=' . basename($file) . ';');
185 header('Content-Length: ' . filesize($file));
186
187 readfile($file);
188
189 break;
190
191case 'upload':
192
193 $dest = relative2absolute($file['name'], $directory);
194
195 if (@file_exists($dest)) {
196 listing_page(error('already_exists', $dest));
197 } elseif (@move_uploaded_file($file['tmp_name'], $dest)) {
198 @chmod($dest, $filepermission);
199 listing_page(notice('uploaded', $file['name']));
200 } else {
201 listing_page(error('not_uploaded', $file['name']));
202 }
203
204 break;
205
206case 'create_directory':
207
208 if (@file_exists($file)) {
209 listing_page(error('already_exists', $file));
210 } else {
211 $old = @umask(0777 & ~$dirpermission);
212 if (@mkdir($file, $dirpermission)) {
213 listing_page(notice('created', $file));
214 } else {
215 listing_page(error('not_created', $file));
216 }
217 @umask($old);
218 }
219
220 break;
221
222case 'create_file':
223
224 if (@file_exists($file)) {
225 listing_page(error('already_exists', $file));
226 } else {
227 $old = @umask(0777 & ~$filepermission);
228 if (@touch($file)) {
229 edit($file);
230 } else {
231 listing_page(error('not_created', $file));
232 }
233 @umask($old);
234 }
235
236 break;
237
238case 'execute':
239
240 chdir(dirname($file));
241
242 $output = array();
243 $retval = 0;
244 exec('echo "./' . basename($file) . '" | /bin/sh', $output, $retval);
245
246 $error = ($retval == 0) ? false : true;
247
248 if (sizeof($output) == 0) $output = array('<' . $words['no_output'] . '>');
249
250 if ($error) {
251 listing_page(error('not_executed', $file, implode("\n", $output)));
252 } else {
253 listing_page(notice('executed', $file, implode("\n", $output)));
254 }
255
256 break;
257
258case 'delete':
259
260 if (!empty($_POST['no'])) {
261 listing_page();
262 } elseif (!empty($_POST['yes'])) {
263
264 $failure = array();
265 $success = array();
266
267 foreach ($files as $file) {
268 if (del($file)) {
269 $success[] = $file;
270 } else {
271 $failure[] = $file;
272 }
273 }
274
275 $message = '';
276 if (sizeof($failure) > 0) {
277 $message = error('not_deleted', implode("\n", $failure));
278 }
279 if (sizeof($success) > 0) {
280 $message .= notice('deleted', implode("\n", $success));
281 }
282
283 listing_page($message);
284
285 } else {
286
287 html_header();
288
289 echo '<form action="' . $self . '" method="post">
290<table class="dialog">
291<tr>
292<td class="dialog">
293';
294
295 request_dump();
296
297 echo "\t<b>" . word('really_delete') . '</b>
298 <p>
299';
300
301 foreach ($files as $file) {
302 echo "\t" . html($file) . "<br />\n";
303 }
304
305 echo ' </p>
306 <hr />
307 <input type="submit" name="no" value="' . word('no') . '" id="red_button" />
308 <input type="submit" name="yes" value="' . word('yes') . '" id="green_button" style="margin-left: 50px" />
309</td>
310</tr>
311</table>
312</form>
313
314';
315
316 html_footer();
317
318 }
319
320 break;
321
322case 'rename':
323
324 if (!empty($_POST['destination'])) {
325
326 $dest = relative2absolute($_POST['destination'], $directory);
327
328 if (!@file_exists($dest) && @rename($file, $dest)) {
329 listing_page(notice('renamed', $file, $dest));
330 } else {
331 listing_page(error('not_renamed', $file, $dest));
332 }
333
334 } else {
335
336 $name = basename($file);
337
338 html_header();
339
340 echo '<form action="' . $self . '" method="post">
341
342<table class="dialog">
343<tr>
344<td class="dialog">
345 <input type="hidden" name="action" value="rename" />
346 <input type="hidden" name="file" value="' . html($file) . '" />
347 <input type="hidden" name="dir" value="' . html($directory) . '" />
348 <b>' . word('rename_file') . '</b>
349 <p>' . html($file) . '</p>
350 <b>' . substr($file, 0, strlen($file) - strlen($name)) . '</b>
351 <input type="text" name="destination" size="' . textfieldsize($name) . '" value="' . html($name) . '" />
352 <hr />
353 <input type="submit" value="' . word('rename') . '" />
354</td>
355</tr>
356</table>
357
358<p><a href="' . $self . '?dir=' . urlencode($directory) . '">[ ' . word('back') . ' ]</a></p>
359
360</form>
361
362';
363
364 html_footer();
365
366 }
367
368 break;
369
370case 'move':
371
372 if (!empty($_POST['destination'])) {
373
374 $dest = relative2absolute($_POST['destination'], $directory);
375
376 $failure = array();
377 $success = array();
378
379 foreach ($files as $file) {
380 $filename = substr($file, strlen($directory));
381 $d = $dest . $filename;
382 if (!@file_exists($d) && @rename($file, $d)) {
383 $success[] = $file;
384 } else {
385 $failure[] = $file;
386 }
387 }
388
389 $message = '';
390 if (sizeof($failure) > 0) {
391 $message = error('not_moved', implode("\n", $failure), $dest);
392 }
393 if (sizeof($success) > 0) {
394 $message .= notice('moved', implode("\n", $success), $dest);
395 }
396
397 listing_page($message);
398
399 } else {
400
401 html_header();
402
403 echo '<form action="' . $self . '" method="post">
404
405<table class="dialog">
406<tr>
407<td class="dialog">
408';
409
410 request_dump();
411
412 echo "\t<b>" . word('move_files') . '</b>
413 <p>
414';
415
416 foreach ($files as $file) {
417 echo "\t" . html($file) . "<br />\n";
418 }
419
420 echo ' </p>
421 <hr />
422 ' . word('destination') . ':
423 <input type="text" name="destination" size="' . textfieldsize($directory) . '" value="' . html($directory) . '" />
424 <input type="submit" value="' . word('move') . '" />
425</td>
426</tr>
427</table>
428
429<p><a href="' . $self . '?dir=' . urlencode($directory) . '">[ ' . word('back') . ' ]</a></p>
430
431</form>
432
433';
434
435 html_footer();
436
437 }
438
439 break;
440
441case 'copy':
442
443 if (!empty($_POST['destination'])) {
444
445 $dest = relative2absolute($_POST['destination'], $directory);
446
447 if (@is_dir($dest)) {
448
449 $failure = array();
450 $success = array();
451
452 foreach ($files as $file) {
453 $filename = substr($file, strlen($directory));
454 $d = addslash($dest) . $filename;
455 if (!@is_dir($file) && !@file_exists($d) && @copy($file, $d)) {
456 $success[] = $file;
457 } else {
458 $failure[] = $file;
459 }
460 }
461
462 $message = '';
463 if (sizeof($failure) > 0) {
464 $message = error('not_copied', implode("\n", $failure), $dest);
465 }
466 if (sizeof($success) > 0) {
467 $message .= notice('copied', implode("\n", $success), $dest);
468 }
469
470 listing_page($message);
471
472 } else {
473
474 if (!@file_exists($dest) && @copy($file, $dest)) {
475 listing_page(notice('copied', $file, $dest));
476 } else {
477 listing_page(error('not_copied', $file, $dest));
478 }
479
480 }
481
482 } else {
483
484 html_header();
485
486 echo '<form action="' . $self . '" method="post">
487
488<table class="dialog">
489<tr>
490<td class="dialog">
491';
492
493 request_dump();
494
495 echo "\n<b>" . word('copy_files') . '</b>
496 <p>
497';
498
499 foreach ($files as $file) {
500 echo "\t" . html($file) . "<br />\n";
501 }
502
503 echo ' </p>
504 <hr />
505 ' . word('destination') . ':
506 <input type="text" name="destination" size="' . textfieldsize($directory) . '" value="' . html($directory) . '" />
507 <input type="submit" value="' . word('copy') . '" />
508</td>
509</tr>
510</table>
511
512<p><a href="' . $self . '?dir=' . urlencode($directory) . '">[ ' . word('back') . ' ]</a></p>
513
514</form>
515
516';
517
518 html_footer();
519
520 }
521
522 break;
523
524case 'create_symlink':
525
526 if (!empty($_POST['destination'])) {
527
528 $dest = relative2absolute($_POST['destination'], $directory);
529
530 if (substr($dest, -1, 1) == $delim) $dest .= basename($file);
531
532 if (!empty($_POST['relative'])) $file = absolute2relative(addslash(dirname($dest)), $file);
533
534 if (!@file_exists($dest) && @symlink($file, $dest)) {
535 listing_page(notice('symlinked', $file, $dest));
536 } else {
537 listing_page(error('not_symlinked', $file, $dest));
538 }
539
540 } else {
541
542 html_header();
543
544 echo '<form action="' . $self . '" method="post">
545
546<table class="dialog" id="symlink">
547<tr>
548 <td style="vertical-align: top">' . word('destination') . ': </td>
549 <td>
550 <b>' . html($file) . '</b><br />
551 <input type="checkbox" name="relative" value="yes" id="checkbox_relative" checked="checked" style="margin-top: 1ex" />
552 <label for="checkbox_relative">' . word('relative') . '</label>
553 <input type="hidden" name="action" value="create_symlink" />
554 <input type="hidden" name="file" value="' . html($file) . '" />
555 <input type="hidden" name="dir" value="' . html($directory) . '" />
556 </td>
557</tr>
558<tr>
559 <td>' . word('symlink') . ': </td>
560 <td>
561 <input type="text" name="destination" size="' . textfieldsize($directory) . '" value="' . html($directory) . '" />
562 <input type="submit" value="' . word('create_symlink') . '" />
563 </td>
564</tr>
565</table>
566
567<p><a href="' . $self . '?dir=' . urlencode($directory) . '">[ ' . word('back') . ' ]</a></p>
568
569</form>
570
571';
572
573 html_footer();
574
575 }
576
577 break;
578
579case 'edit':
580
581 if (!empty($_POST['save'])) {
582
583 $content = str_replace("\r\n", "\n", $_POST['content']);
584
585 if (($f = @fopen($file, 'w')) && @fwrite($f, $content) !== false && @fclose($f)) {
586 listing_page(notice('saved', $file));
587 } else {
588 listing_page(error('not_saved', $file));
589 }
590
591 } else {
592
593 if (@is_readable($file) && @is_writable($file)) {
594 edit($file);
595 } else {
596 listing_page(error('not_edited', $file));
597 }
598
599 }
600
601 break;
602
603case 'permission':
604
605 if (!empty($_POST['set'])) {
606
607 $mode = 0;
608 if (!empty($_POST['ur'])) $mode |= 0400; if (!empty($_POST['uw'])) $mode |= 0200; if (!empty($_POST['ux'])) $mode |= 0100;
609 if (!empty($_POST['gr'])) $mode |= 0040; if (!empty($_POST['gw'])) $mode |= 0020; if (!empty($_POST['gx'])) $mode |= 0010;
610 if (!empty($_POST['or'])) $mode |= 0004; if (!empty($_POST['ow'])) $mode |= 0002; if (!empty($_POST['ox'])) $mode |= 0001;
611
612 if (@chmod($file, $mode)) {
613 listing_page(notice('permission_set', $file, decoct($mode)));
614 } else {
615 listing_page(error('permission_not_set', $file, decoct($mode)));
616 }
617
618 } else {
619
620 html_header();
621
622 $mode = fileperms($file);
623
624 echo '<form action="' . $self . '" method="post">
625
626<table class="dialog">
627<tr>
628<td class="dialog">
629
630 <p style="margin: 0">' . phrase('permission_for', $file) . '</p>
631
632 <hr />
633
634 <table id="permission">
635 <tr>
636 <td></td>
637 <td style="border-right: 1px solid black">' . word('owner') . '</td>
638 <td style="border-right: 1px solid black">' . word('group') . '</td>
639 <td>' . word('other') . '</td>
640 </tr>
641 <tr>
642 <td style="text-align: right">' . word('read') . ':</td>
643 <td><input type="checkbox" name="ur" value="1"'; if ($mode & 00400) echo ' checked="checked"'; echo ' /></td>
644 <td><input type="checkbox" name="gr" value="1"'; if ($mode & 00040) echo ' checked="checked"'; echo ' /></td>
645 <td><input type="checkbox" name="or" value="1"'; if ($mode & 00004) echo ' checked="checked"'; echo ' /></td>
646 </tr>
647 <tr>
648 <td style="text-align: right">' . word('write') . ':</td>
649 <td><input type="checkbox" name="uw" value="1"'; if ($mode & 00200) echo ' checked="checked"'; echo ' /></td>
650 <td><input type="checkbox" name="gw" value="1"'; if ($mode & 00020) echo ' checked="checked"'; echo ' /></td>
651 <td><input type="checkbox" name="ow" value="1"'; if ($mode & 00002) echo ' checked="checked"'; echo ' /></td>
652 </tr>
653 <tr>
654 <td style="text-align: right">' . word('execute') . ':</td>
655 <td><input type="checkbox" name="ux" value="1"'; if ($mode & 00100) echo ' checked="checked"'; echo ' /></td>
656 <td><input type="checkbox" name="gx" value="1"'; if ($mode & 00010) echo ' checked="checked"'; echo ' /></td>
657 <td><input type="checkbox" name="ox" value="1"'; if ($mode & 00001) echo ' checked="checked"'; echo ' /></td>
658 </tr>
659 </table>
660
661 <hr />
662
663 <input type="submit" name="set" value="' . word('set') . '" />
664
665 <input type="hidden" name="action" value="permission" />
666 <input type="hidden" name="file" value="' . html($file) . '" />
667 <input type="hidden" name="dir" value="' . html($directory) . '" />
668
669</td>
670</tr>
671</table>
672
673<p><a href="' . $self . '?dir=' . urlencode($directory) . '">[ ' . word('back') . ' ]</a></p>
674
675</form>
676
677';
678
679 html_footer();
680
681 }
682
683 break;
684
685default:
686
687 listing_page();
688
689}
690
691function getlist ($directory) {
692 global $delim, $win;
693
694 if ($d = @opendir($directory)) {
695
696 while (($filename = @readdir($d)) !== false) {
697
698 $path = $directory . $filename;
699
700 if ($stat = @lstat($path)) {
701
702 $file = array(
703 'filename' => $filename,
704 'path' => $path,
705 'is_file' => @is_file($path),
706 'is_dir' => @is_dir($path),
707 'is_link' => @is_link($path),
708 'is_readable' => @is_readable($path),
709 'is_writable' => @is_writable($path),
710 'size' => $stat['size'],
711 'permission' => $stat['mode'],
712 'owner' => $stat['uid'],
713 'group' => $stat['gid'],
714 'mtime' => @filemtime($path),
715 'atime' => @fileatime($path),
716 'ctime' => @filectime($path)
717 );
718
719 if ($file['is_dir']) {
720 $file['is_executable'] = @file_exists($path . $delim . '.');
721 } else {
722 if (!$win) {
723 $file['is_executable'] = @is_executable($path);
724 } else {
725 $file['is_executable'] = true;
726 }
727 }
728
729 if ($file['is_link']) $file['target'] = @readlink($path);
730
731 if (function_exists('posix_getpwuid')) $file['owner_name'] = @reset(posix_getpwuid($file['owner']));
732 if (function_exists('posix_getgrgid')) $file['group_name'] = @reset(posix_getgrgid($file['group']));
733
734 $files[] = $file;
735
736 }
737
738 }
739
740 return $files;
741
742 } else {
743 return false;
744 }
745
746}
747
748function sortlist ($list, $key, $reverse) {
749
750 $dirs = array();
751 $files = array();
752
753 for ($i = 0; $i < sizeof($list); $i++) {
754 if ($list[$i]['is_dir']) $dirs[] = $list[$i];
755 else $files[] = $list[$i];
756 }
757
758 quicksort($dirs, 0, sizeof($dirs) - 1, $key);
759 if ($reverse) $dirs = array_reverse($dirs);
760
761 quicksort($files, 0, sizeof($files) - 1, $key);
762 if ($reverse) $files = array_reverse($files);
763
764 return array_merge($dirs, $files);
765
766}
767
768function quicksort (&$array, $first, $last, $key) {
769
770 if ($first < $last) {
771
772 $cmp = $array[floor(($first + $last) / 2)][$key];
773
774 $l = $first;
775 $r = $last;
776
777 while ($l <= $r) {
778
779 while ($array[$l][$key] < $cmp) $l++;
780 while ($array[$r][$key] > $cmp) $r--;
781
782 if ($l <= $r) {
783
784 $tmp = $array[$l];
785 $array[$l] = $array[$r];
786 $array[$r] = $tmp;
787
788 $l++;
789 $r--;
790
791 }
792
793 }
794
795 quicksort($array, $first, $r, $key);
796 quicksort($array, $l, $last, $key);
797
798 }
799
800}
801
802function permission_octal2string ($mode) {
803
804 if (($mode & 0xC000) === 0xC000) {
805 $type = 's';
806 } elseif (($mode & 0xA000) === 0xA000) {
807 $type = 'l';
808 } elseif (($mode & 0x8000) === 0x8000) {
809 $type = '-';
810 } elseif (($mode & 0x6000) === 0x6000) {
811 $type = 'b';
812 } elseif (($mode & 0x4000) === 0x4000) {
813 $type = 'd';
814 } elseif (($mode & 0x2000) === 0x2000) {
815 $type = 'c';
816 } elseif (($mode & 0x1000) === 0x1000) {
817 $type = 'p';
818 } else {
819 $type = '?';
820 }
821
822 $owner = ($mode & 00400) ? 'r' : '-';
823 $owner .= ($mode & 00200) ? 'w' : '-';
824 if ($mode & 0x800) {
825 $owner .= ($mode & 00100) ? 's' : 'S';
826 } else {
827 $owner .= ($mode & 00100) ? 'x' : '-';
828 }
829
830 $group = ($mode & 00040) ? 'r' : '-';
831 $group .= ($mode & 00020) ? 'w' : '-';
832 if ($mode & 0x400) {
833 $group .= ($mode & 00010) ? 's' : 'S';
834 } else {
835 $group .= ($mode & 00010) ? 'x' : '-';
836 }
837
838 $other = ($mode & 00004) ? 'r' : '-';
839 $other .= ($mode & 00002) ? 'w' : '-';
840 if ($mode & 0x200) {
841 $other .= ($mode & 00001) ? 't' : 'T';
842 } else {
843 $other .= ($mode & 00001) ? 'x' : '-';
844 }
845
846 return $type . $owner . $group . $other;
847
848}
849
850function is_script ($filename) {
851 return ereg('\.php$|\.php3$|\.php4$|\.php5$', $filename);
852}
853
854function getmimetype ($filename) {
855 static $mimes = array(
856 '\.jpg$|\.jpeg$' => 'image/jpeg',
857 '\.gif$' => 'image/gif',
858 '\.png$' => 'image/png',
859 '\.html$|\.html$' => 'text/html',
860 '\.txt$|\.asc$' => 'text/plain',
861 '\.xml$|\.xsl$' => 'application/xml',
862 '\.pdf$' => 'application/pdf'
863 );
864
865 foreach ($mimes as $regex => $mime) {
866 if (eregi($regex, $filename)) return $mime;
867 }
868
869 // return 'application/octet-stream';
870 return 'text/plain';
871
872}
873
874function del ($file) {
875 global $delim;
876
877 if (!file_exists($file)) return false;
878
879 if (@is_dir($file) && !@is_link($file)) {
880
881 $success = false;
882
883 if (@rmdir($file)) {
884
885 $success = true;
886
887 } elseif ($dir = @opendir($file)) {
888
889 $success = true;
890
891 while (($f = readdir($dir)) !== false) {
892 if ($f != '.' && $f != '..' && !del($file . $delim . $f)) {
893 $success = false;
894 }
895 }
896 closedir($dir);
897
898 if ($success) $success = @rmdir($file);
899
900 }
901
902 return $success;
903
904 }
905
906 return @unlink($file);
907
908}
909
910function addslash ($directory) {
911 global $delim;
912
913 if (substr($directory, -1, 1) != $delim) {
914 return $directory . $delim;
915 } else {
916 return $directory;
917 }
918
919}
920
921function relative2absolute ($string, $directory) {
922
923 if (path_is_relative($string)) {
924 return simplify_path(addslash($directory) . $string);
925 } else {
926 return simplify_path($string);
927 }
928
929}
930
931function path_is_relative ($path) {
932 global $win;
933
934 if ($win) {
935 return (substr($path, 1, 1) != ':');
936 } else {
937 return (substr($path, 0, 1) != '/');
938 }
939
940}
941
942function absolute2relative ($directory, $target) {
943 global $delim;
944
945 $path = '';
946 while ($directory != $target) {
947 if ($directory == substr($target, 0, strlen($directory))) {
948 $path .= substr($target, strlen($directory));
949 break;
950 } else {
951 $path .= '..' . $delim;
952 $directory = substr($directory, 0, strrpos(substr($directory, 0, -1), $delim) + 1);
953 }
954 }
955 if ($path == '') $path = '.';
956
957 return $path;
958
959}
960
961function simplify_path ($path) {
962 global $delim;
963
964 if (@file_exists($path) && function_exists('realpath') && @realpath($path) != '') {
965 $path = realpath($path);
966 if (@is_dir($path)) {
967 return addslash($path);
968 } else {
969 return $path;
970 }
971 }
972
973 $pattern = $delim . '.' . $delim;
974
975 if (@is_dir($path)) {
976 $path = addslash($path);
977 }
978
979 while (strpos($path, $pattern) !== false) {
980 $path = str_replace($pattern, $delim, $path);
981 }
982
983 $e = addslashes($delim);
984 $regex = $e . '((\.[^\.' . $e . '][^' . $e . ']*)|(\.\.[^' . $e . ']+)|([^\.][^' . $e . ']*))' . $e . '\.\.' . $e;
985
986 while (ereg($regex, $path)) {
987 $path = ereg_replace($regex, $delim, $path);
988 }
989
990 return $path;
991
992}
993
994function human_filesize ($filesize) {
995
996 $suffices = 'kMGTPE';
997
998 $n = 0;
999 while ($filesize >= 1000) {
1000 $filesize /= 1024;
1001 $n++;
1002 }
1003
1004 $filesize = round($filesize, 3 - strpos($filesize, '.'));
1005
1006 if (strpos($filesize, '.') !== false) {
1007 while (in_array(substr($filesize, -1, 1), array('0', '.'))) {
1008 $filesize = substr($filesize, 0, strlen($filesize) - 1);
1009 }
1010 }
1011
1012 $suffix = (($n == 0) ? '' : substr($suffices, $n - 1, 1));
1013
1014 return $filesize . " {$suffix}B";
1015
1016}
1017
1018function strip (&$str) {
1019 $str = stripslashes($str);
1020}
1021
1022/* ------------------------------------------------------------------------- */
1023
1024function listing_page ($message = null) {
1025 global $self, $directory, $sort, $reverse;
1026
1027 html_header();
1028
1029 $list = getlist($directory);
1030
1031 if (array_key_exists('sort', $_GET)) $sort = $_GET['sort']; else $sort = 'filename';
1032 if (array_key_exists('reverse', $_GET) && $_GET['reverse'] == 'true') $reverse = true; else $reverse = false;
1033
1034 echo '<h1 style="margin-bottom: 0">webadmin.php</h1>
1035
1036<form enctype="multipart/form-data" action="' . $self . '" method="post">
1037
1038<table id="main">
1039';
1040
1041 directory_choice();
1042
1043 if (!empty($message)) {
1044 spacer();
1045 echo $message;
1046 }
1047
1048 if (@is_writable($directory)) {
1049 upload_box();
1050 create_box();
1051 } else {
1052 spacer();
1053 }
1054
1055 if ($list) {
1056 $list = sortlist($list, $sort, $reverse);
1057 listing($list);
1058 } else {
1059 echo error('not_readable', $directory);
1060 }
1061
1062 echo '</table>
1063
1064</form>
1065
1066';
1067
1068 html_footer();
1069
1070}
1071
1072function listing ($list) {
1073 global $directory, $homedir, $sort, $reverse, $win, $cols, $date_format, $self;
1074
1075 echo '<tr class="listing">
1076 <th style="text-align: center; vertical-align: middle"><img src="' . $self . '?image=smiley" alt="smiley" /></th>
1077';
1078
1079 column_title('filename', $sort, $reverse);
1080 column_title('size', $sort, $reverse);
1081
1082 if (!$win) {
1083 column_title('permission', $sort, $reverse);
1084 column_title('owner', $sort, $reverse);
1085 column_title('group', $sort, $reverse);
1086 }
1087
1088 echo ' <th class="functions">' . word('functions') . '</th>
1089</tr>
1090';
1091
1092 for ($i = 0; $i < sizeof($list); $i++) {
1093 $file = $list[$i];
1094
1095 $timestamps = 'mtime: ' . date($date_format, $file['mtime']) . ', ';
1096 $timestamps .= 'atime: ' . date($date_format, $file['atime']) . ', ';
1097 $timestamps .= 'ctime: ' . date($date_format, $file['ctime']);
1098
1099 echo '<tr class="listing">
1100 <td class="checkbox"><input type="checkbox" name="checked' . $i . '" value="true" onfocus="activate(\'other\')" /></td>
1101 <td class="filename" title="' . html($timestamps) . '">';
1102
1103 if ($file['is_link']) {
1104
1105 echo '<img src="' . $self . '?image=link" alt="link" /> ';
1106 echo html($file['filename']) . ' → ';
1107
1108 $real_file = relative2absolute($file['target'], $directory);
1109
1110 if (@is_readable($real_file)) {
1111 if (@is_dir($real_file)) {
1112 echo '[ <a href="' . $self . '?dir=' . urlencode($real_file) . '">' . html($file['target']) . '</a> ]';
1113 } else {
1114 echo '<a href="' . $self . '?action=view&file=' . urlencode($real_file) . '">' . html($file['target']) . '</a>';
1115 }
1116 } else {
1117 echo html($file['target']);
1118 }
1119
1120 } elseif ($file['is_dir']) {
1121
1122 echo '<img src="' . $self . '?image=folder" alt="folder" /> [ ';
1123 if ($win || $file['is_executable']) {
1124 echo '<a href="' . $self . '?dir=' . urlencode($file['path']) . '">' . html($file['filename']) . '</a>';
1125 } else {
1126 echo html($file['filename']);
1127 }
1128 echo ' ]';
1129
1130 } else {
1131
1132 if (substr($file['filename'], 0, 1) == '.') {
1133 echo '<img src="' . $self . '?image=hidden_file" alt="hidden file" /> ';
1134 } else {
1135 echo '<img src="' . $self . '?image=file" alt="file" /> ';
1136 }
1137
1138 if ($file['is_file'] && $file['is_readable']) {
1139 echo '<a href="' . $self . '?action=view&file=' . urlencode($file['path']) . '">' . html($file['filename']) . '</a>';
1140 } else {
1141 echo html($file['filename']);
1142 }
1143
1144 }
1145
1146 if ($file['size'] >= 1000) {
1147 $human = ' title="' . human_filesize($file['size']) . '"';
1148 } else {
1149 $human = '';
1150 }
1151
1152 echo "</td>\n";
1153
1154 echo "\t<td class=\"size\"$human>{$file['size']} B</td>\n";
1155
1156 if (!$win) {
1157
1158 echo "\t<td class=\"permission\" title=\"" . decoct($file['permission']) . '">';
1159
1160 $l = !$file['is_link'] && (!function_exists('posix_getuid') || $file['owner'] == posix_getuid());
1161 if ($l) echo '<a href="' . $self . '?action=permission&file=' . urlencode($file['path']) . '&dir=' . urlencode($directory) . '">';
1162 echo html(permission_octal2string($file['permission']));
1163 if ($l) echo '</a>';
1164
1165 echo "</td>\n";
1166
1167 if (array_key_exists('owner_name', $file)) {
1168 echo "\t<td class=\"owner\" title=\"uid: {$file['owner']}\">{$file['owner_name']}</td>\n";
1169 } else {
1170 echo "\t<td class=\"owner\">{$file['owner']}</td>\n";
1171 }
1172
1173 if (array_key_exists('group_name', $file)) {
1174 echo "\t<td class=\"group\" title=\"gid: {$file['group']}\">{$file['group_name']}</td>\n";
1175 } else {
1176 echo "\t<td class=\"group\">{$file['group']}</td>\n";
1177 }
1178
1179 }
1180
1181 echo ' <td class="functions">
1182 <input type="hidden" name="file' . $i . '" value="' . html($file['path']) . '" />
1183';
1184
1185 $actions = array();
1186 if (function_exists('symlink')) {
1187 $actions[] = 'create_symlink';
1188 }
1189 if (@is_writable(dirname($file['path']))) {
1190 $actions[] = 'delete';
1191 $actions[] = 'rename';
1192 $actions[] = 'move';
1193 }
1194 if ($file['is_file'] && $file['is_readable']) {
1195 $actions[] = 'copy';
1196 $actions[] = 'download';
1197 if ($file['is_writable']) $actions[] = 'edit';
1198 }
1199 if (!$win && function_exists('exec') && $file['is_file'] && $file['is_executable'] && file_exists('/bin/sh')) {
1200 $actions[] = 'execute';
1201 }
1202
1203 if (sizeof($actions) > 0) {
1204
1205 echo ' <select class="small" name="action' . $i . '" size="1">
1206 <option value="">' . str_repeat(' ', 30) . '</option>
1207';
1208
1209 foreach ($actions as $action) {
1210 echo "\t\t<option value=\"$action\">" . word($action) . "</option>\n";
1211 }
1212
1213 echo ' </select>
1214 <input class="small" type="submit" name="submit' . $i . '" value=" > " onfocus="activate(\'other\')" />
1215';
1216
1217 }
1218
1219 echo ' </td>
1220</tr>
1221';
1222
1223 }
1224
1225 echo '<tr class="listing_footer">
1226 <td style="text-align: right; vertical-align: top"><img src="' . $self . '?image=arrow" alt=">" /></td>
1227 <td colspan="' . ($cols - 1) . '">
1228 <input type="hidden" name="num" value="' . sizeof($list) . '" />
1229 <input type="hidden" name="focus" value="" />
1230 <input type="hidden" name="olddir" value="' . html($directory) . '" />
1231';
1232
1233 $actions = array();
1234 if (@is_writable(dirname($file['path']))) {
1235 $actions[] = 'delete';
1236 $actions[] = 'move';
1237 }
1238 $actions[] = 'copy';
1239 echo ' <select class="small" name="action_all" size="1">
1240 <option value="">' . str_repeat(' ', 30) . '</option>
1241';
1242
1243 foreach ($actions as $action) {
1244 echo "\t\t<option value=\"$action\">" . word($action) . "</option>\n";
1245 }
1246
1247 echo ' </select>
1248 <input class="small" type="submit" name="submit_all" value=" > " onfocus="activate(\'other\')" />
1249 </td>
1250</tr>
1251';
1252}
1253
1254function column_title ($column, $sort, $reverse) {
1255 global $self, $directory;
1256 $d = 'dir=' . urlencode($directory) . '&';
1257 $arr = '';
1258 if ($sort == $column) {
1259 if (!$reverse) {
1260 $r = '&reverse=true';
1261 $arr = ' ∧';
1262 } else {
1263 $arr = ' ∨';
1264 }
1265 } else {
1266 $r = '';
1267 }
1268 echo "\t<th class=\"$column\"><a href=\"$self?{$d}sort=$column$r\">" . word($column) . "</a>$arr</th>\n";
1269}
1270
1271function directory_choice () {
1272 global $directory, $homedir, $cols, $self;
1273 echo '<tr>
1274 <td colspan="' . $cols . '" id="directory">
1275 <a href="' . $self . '?dir=' . urlencode($homedir) . '">' . word('directory') . '</a>:
1276 <input type="text" name="dir" size="' . textfieldsize($directory) . '" value="' . html($directory) . '" onfocus="activate(\'directory\')" />
1277 <input type="submit" name="changedir" value="' . word('change') . '" onfocus="activate(\'directory\')" />
1278 </td>
1279</tr>
1280';
1281}
1282
1283function upload_box () {
1284 global $cols;
1285 echo '<tr>
1286 <td colspan="' . $cols . '" id="upload">
1287 ' . word('file') . ':
1288 <input type="file" name="upload" onfocus="activate(\'other\')" />
1289 <input type="submit" name="submit_upload" value="' . word('upload') . '" onfocus="activate(\'other\')" />
1290 </td>
1291</tr>
1292';
1293}
1294
1295function create_box () {
1296 global $cols;
1297 echo '<tr>
1298 <td colspan="' . $cols . '" id="create">
1299 <select name="create_type" size="1" onfocus="activate(\'create\')">
1300 <option value="file">' . word('file') . '</option>
1301 <option value="directory">' . word('directory') . '</option>
1302 </select>
1303 <input type="text" name="create_name" onfocus="activate(\'create\')" />
1304 <input type="submit" name="submit_create" value="' . word('create') . '" onfocus="activate(\'create\')" />
1305 </td>
1306</tr>
1307';
1308}
1309
1310function edit ($file) {
1311 global $self, $directory, $editcols, $editrows, $apache, $htpasswd, $htaccess;
1312 html_header();
1313 echo '<h2 style="margin-bottom: 3pt">' . html($file) . '</h2>
1314<form action="' . $self . '" method="post">
1315<table class="dialog">
1316<tr>
1317<td class="dialog">
1318 <textarea name="content" cols="' . $editcols . '" rows="' . $editrows . '" WRAP="off">';
1319
1320 if (array_key_exists('content', $_POST)) {
1321 echo $_POST['content'];
1322 } else {
1323 $f = fopen($file, 'r');
1324 while (!feof($f)) {
1325 echo html(fread($f, 8192));
1326 }
1327 fclose($f);
1328 }
1329
1330 if (!empty($_POST['user'])) {
1331 echo "\n" . $_POST['user'] . ':' . crypt($_POST['password']);
1332 }
1333 if (!empty($_POST['basic_auth'])) {
1334 if ($win) {
1335 $authfile = str_replace('\\', '/', $directory) . $htpasswd;
1336 } else {
1337 $authfile = $directory . $htpasswd;
1338 }
1339 echo "\nAuthType Basic\nAuthName "Restricted Directory"\n";
1340 echo 'AuthUserFile "' . html($authfile) . ""\n";
1341 echo 'Require valid-user';
1342 }
1343 echo '</textarea>
1344 <hr />
1345';
1346 if ($apache && basename($file) == $htpasswd) {
1347 echo '
1348 ' . word('user') . ': <input type="text" name="user" />
1349 ' . word('password') . ': <input type="password" name="password" />
1350 <input type="submit" value="' . word('add') . '" />
1351 <hr />
1352';
1353 }
1354 if ($apache && basename($file) == $htaccess) {
1355 echo '
1356 <input type="submit" name="basic_auth" value="' . word('add_basic_auth') . '" />
1357 <hr />
1358';
1359 }
1360 echo '
1361 <input type="hidden" name="action" value="edit" />
1362 <input type="hidden" name="file" value="' . html($file) . '" />
1363 <input type="hidden" name="dir" value="' . html($directory) . '" />
1364 <input type="reset" value="' . word('reset') . '" id="red_button" />
1365 <input type="submit" name="save" value="' . word('save') . '" id="green_button" style="margin-left: 50px" />
1366</td>
1367</tr>
1368</table>
1369<p><a href="' . $self . '?dir=' . urlencode($directory) . '">[ ' . word('back') . ' ]</a></p>
1370</form>
1371';
1372 html_footer();
1373}
1374
1375function spacer () {
1376 global $cols;
1377 echo '<tr>
1378 <td colspan="' . $cols . '" style="height: 1em"></td>
1379</tr>
1380';
1381}
1382
1383function textfieldsize ($content) {
1384 $size = strlen($content) + 5;
1385 if ($size < 30) $size = 30;
1386 return $size;
1387}
1388
1389function request_dump () {
1390 foreach ($_REQUEST as $key => $value) {
1391 echo "\t<input type=\"hidden\" name=\"" . html($key) . '" value="' . html($value) . "\" />\n";
1392 }
1393}
1394
1395function html ($string) {
1396 global $site_charset;
1397 return htmlentities($string, ENT_COMPAT, $site_charset);
1398}
1399
1400function word ($word) {
1401 global $words, $word_charset;
1402 return htmlentities($words[$word], ENT_COMPAT, $word_charset);
1403}
1404
1405function phrase ($phrase, $arguments) {
1406 global $words;
1407 static $search;
1408 if (!is_array($search)) for ($i = 1; $i <= 8; $i++) $search[] = "%$i";
1409 for ($i = 0; $i < sizeof($arguments); $i++) {
1410 $arguments[$i] = nl2br(html($arguments[$i]));
1411 }
1412 $replace = array('{' => '<pre>', '}' =>'</pre>', '[' => '<b>', ']' => '</b>');
1413 return str_replace($search, $arguments, str_replace(array_keys($replace), $replace, nl2br(html($words[$phrase]))));
1414}
1415
1416function getwords ($lang) {
1417 global $date_format, $word_charset;
1418 $word_charset = 'UTF-8';
1419 switch ($lang) {
1420 case 'en':
1421 default:
1422 $date_format = 'n/j/y H:i:s';
1423 return array(
1424'directory' => 'Directory',
1425'file' => 'File',
1426'filename' => 'Filename',
1427'size' => 'Size',
1428'permission' => 'Permission',
1429'owner' => 'Owner',
1430'group' => 'Group',
1431'other' => 'Others',
1432'functions' => 'Functions',
1433'read' => 'read',
1434'write' => 'write',
1435'execute' => 'execute',
1436'create_symlink' => 'create symlink',
1437'delete' => 'delete',
1438'rename' => 'rename',
1439'move' => 'move',
1440'copy' => 'copy',
1441'edit' => 'edit',
1442'download' => 'download',
1443'upload' => 'upload',
1444'create' => 'create',
1445'change' => 'change',
1446'save' => 'save',
1447'set' => 'set',
1448'reset' => 'reset',
1449'relative' => 'Relative path to target',
1450'yes' => 'Yes',
1451'no' => 'No',
1452'back' => 'back',
1453'destination' => 'Destination',
1454'symlink' => 'Symlink',
1455'no_output' => 'no output',
1456'user' => 'User',
1457'password' => 'Password',
1458'add' => 'add',
1459'add_basic_auth' => 'add basic-authentification',
1460'uploaded' => '"[%1]" has been uploaded.',
1461'not_uploaded' => '"[%1]" could not be uploaded.',
1462'already_exists' => '"[%1]" already exists.',
1463'created' => '"[%1]" has been created.',
1464'not_created' => '"[%1]" could not be created.',
1465'really_delete' => 'Delete these files?',
1466'deleted' => "These files have been deleted:\n[%1]",
1467'not_deleted' => "These files could not be deleted:\n[%1]",
1468'rename_file' => 'Rename file:',
1469'renamed' => '"[%1]" has been renamed to "[%2]".',
1470'not_renamed' => '"[%1] could not be renamed to "[%2]".',
1471'move_files' => 'Move these files:',
1472'moved' => "These files have been moved to \"[%2]\":\n[%1]",
1473'not_moved' => "These files could not be moved to \"[%2]\":\n[%1]",
1474'copy_files' => 'Copy these files:',
1475'copied' => "These files have been copied to \"[%2]\":\n[%1]",
1476'not_copied' => "These files could not be copied to \"[%2]\":\n[%1]",
1477'not_edited' => '"[%1]" can not be edited.',
1478'executed' => "\"[%1]\" has been executed successfully:\n{%2}",
1479'not_executed' => "\"[%1]\" could not be executed successfully:\n{%2}",
1480'saved' => '"[%1]" has been saved.',
1481'not_saved' => '"[%1]" could not be saved.',
1482'symlinked' => 'Symlink from "[%2]" to "[%1]" has been created.',
1483'not_symlinked' => 'Symlink from "[%2]" to "[%1]" could not be created.',
1484'permission_for' => 'Permission of "[%1]":',
1485'permission_set' => 'Permission of "[%1]" was set to [%2].',
1486'permission_not_set' => 'Permission of "[%1]" could not be set to [%2].',
1487'not_readable' => '"[%1]" can not be read.'
1488 );
1489 }
1490}
1491
1492function getimage ($image) {
1493 switch ($image) {
1494 case 'file':
1495 return base64_decode('R0lGODlhEQANAJEDAJmZmf///wAAAP///yH5BAHoAwMALAAAAAARAA0AAAItnIGJxg0B42rsiSvCA/REmXQWhmnih3LUSGaqg35vFbSXucbSabunjnMohq8CADsA');
1496 case 'folder':
1497 return base64_decode('R0lGODlhEQANAJEDAJmZmf///8zMzP///yH5BAHoAwMALAAAAAARAA0AAAIqnI+ZwKwbYgTPtIudlbwLOgCBQJYmCYrn+m3smY5vGc+0a7dhjh7ZbygAADsA');
1498 case 'hidden_file':
1499 return base64_decode('R0lGODlhEQANAJEDAMwAAP///5mZmf///yH5BAHoAwMALAAAAAARAA0AAAItnIGJxg0B42rsiSvCA/REmXQWhmnih3LUSGaqg35vFbSXucbSabunjnMohq8CADsA');
1500 case 'link':
1501 return base64_decode('R0lGODlhEQANAKIEAJmZmf///wAAAMwAAP///wAAAAAAAAAAACH5BAHoAwQALAAAAAARAA0AAAM5SArcrDCCQOuLcIotwgTYUllNOA0DxXkmhY4shM5zsMUKTY8gNgUvW6cnAaZgxMyIM2zBLCaHlJgAADsA');
1502 case 'smiley':
1503 return base64_decode('R0lGODlhEQANAJECAAAAAP//AP///wAAACH5BAHoAwIALAAAAAARAA0AAAIslI+pAu2wDAiz0jWD3hqmBzZf1VCleJQch0rkdnppB3dKZuIygrMRE/oJDwUAOwA=');
1504 case 'arrow':
1505 return base64_decode('R0lGODlhEQANAIABAAAAAP///yH5BAEKAAEALAAAAAARAA0AAAIdjA9wy6gNQ4pwUmav0yvn+hhJiI3mCJ6otrIkxxQAOw==');
1506 }
1507}
1508
1509function html_header () {
1510 global $site_charset;
1511
1512 echo <<<END
1513<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN"
1514 "http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd">
1515<html xmlns="http://www.w3.org/1999/xhtml">
1516<head>
1517
1518<meta http-equiv="Content-Type" content="text/html; charset=$site_charset" />
1519
1520<title>webadmin.php</title>
1521
1522<style type="text/css">
1523body { font: small sans-serif; text-align: center }
1524img { width: 17px; height: 13px }
1525a, a:visited { text-decoration: none; color: navy }
1526hr { border-style: none; height: 1px; background-color: silver; color: silver }
1527#main { margin-top: 6pt; margin-left: auto; margin-right: auto; border-spacing: 1px }
1528#main th { background: #eee; padding: 3pt 3pt 0pt 3pt }
1529.listing th, .listing td { padding: 1px 3pt 0 3pt }
1530.listing th { border: 1px solid silver }
1531.listing td { border: 1px solid #ddd; background: white }
1532.listing .checkbox { text-align: center }
1533.listing .filename { text-align: left }
1534.listing .size { text-align: right }
1535.listing th.permission { text-align: left }
1536.listing td.permission { font-family: monospace }
1537.listing .owner { text-align: left }
1538.listing .group { text-align: left }
1539.listing .functions { text-align: left }
1540.listing_footer td { background: #eee; border: 1px solid silver }
1541#directory, #upload, #create, .listing_footer td, #error td, #notice td { text-align: left; padding: 3pt }
1542#directory { background: #eee; border: 1px solid silver }
1543#upload { padding-top: 1em }
1544#create { padding-bottom: 1em }
1545.small, .small option { font-size: x-small }
1546textarea { border: none; background: white }
1547table.dialog { margin-left: auto; margin-right: auto }
1548td.dialog { background: #eee; padding: 1ex; border: 1px solid silver; text-align: center }
1549#permission { margin-left: auto; margin-right: auto }
1550#permission td { padding-left: 3pt; padding-right: 3pt; text-align: center }
1551td.permission_action { text-align: right }
1552#symlink { background: #eee; border: 1px solid silver }
1553#symlink td { text-align: left; padding: 3pt }
1554#red_button { width: 120px; color: #400 }
1555#green_button { width: 120px; color: #040 }
1556#error td { background: maroon; color: white; border: 1px solid silver }
1557#notice td { background: green; color: white; border: 1px solid silver }
1558#notice pre, #error pre { background: silver; color: black; padding: 1ex; margin-left: 1ex; margin-right: 1ex }
1559code { font-size: 12pt }
1560td { white-space: nowrap }
1561</style>
1562
1563<script type="text/javascript">
1564<!--
1565function activate (name) {
1566 if (document && document.forms[0] && document.forms[0].elements['focus']) {
1567 document.forms[0].elements['focus'].value = name;
1568 }
1569}
1570//-->
1571</script>
1572</head>
1573<body>
1574END;
1575}
1576
1577function html_footer () {
1578 echo <<<END
1579</body>
1580</html>
1581END;
1582
1583}
1584
1585function notice ($phrase) {
1586 global $cols;
1587 $args = func_get_args();
1588 array_shift($args);
1589 return '<tr id="notice">
1590 <td colspan="' . $cols . '">' . phrase($phrase, $args) . '</td>
1591</tr>
1592';
1593
1594}
1595
1596function error ($phrase) {
1597 global $cols;
1598 $args = func_get_args();
1599 array_shift($args);
1600 return '<tr id="error">
1601 <td colspan="' . $cols . '">' . phrase($phrase, $args) . '</td>
1602</tr>
1603';
1604
1605}
1606?>