home *** CD-ROM | disk | FTP | other *** search
/ H4CK3R 16 / hacker16 / 16_HACKER16.ISO / linux / tpm-security-server-1.2.1.iso / archive / etc / autopsy / base / autopsyfunc.pm.base < prev   
Encoding:
Text File  |  2004-01-29  |  266.3 KB  |  10,314 lines

  1. #
  2. # autopsyfunc.pm
  3. # Autopsy Forensic Browser
  4. #
  5. # This file requires The Sleuth Kit
  6. #    www.sleuthkit.org
  7. #
  8. # version 1.71+
  9. # Brian Carrier [carrier@sleuthkit.org]
  10. # Copyright (c) 2003 by Brian Carrier.  All rights reserved
  11. #
  12. # version 1.5, 1.6, 1.7
  13. # Copyright (c) 2001-2003 by Brian Carrier, @stake Inc.  All rights reserved
  14. #
  15. # version 1.0
  16. # Brian Carrier [carrier@cerias.purdue.edu]
  17. # Copyright (c) 2001 by Brian Carrier.  All rights reserved
  18. #
  19. #
  20. # This file is part of the Autopsy Forensic Browser (Autopsy)
  21. #
  22. # Autopsy is free software; you can redistribute it and/or modify
  23. # it under the terms of the GNU General Public License as published by
  24. # the Free Software Foundation; either version 2 of the License, or
  25. # (at your option) any later version.
  26. #
  27. # Autopsy is distributed in the hope that it will be useful,
  28. # but WITHOUT ANY WARRANTY; without even the implied warranty of
  29. # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  30. # GNU General Public License for more details.
  31. #
  32. # You should have received a copy of the GNU General Public License
  33. # along with Autopsy; if not, write to the Free Software
  34. # Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
  35. #
  36. #
  37. # THIS SOFTWARE IS NOT AFFILIATED WITH PURDUE UNIVERSITY OR THE CENTER FOR
  38. # EDUCATION IN INFORMATION ASSURANCE AND SECURITY (CERIAS) AND THEY BEAR
  39. # NO RESPONSIBILITY FOR ITS USE OR MISUSE.
  40. #
  41. #
  42. # THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR IMPLIED
  43. # WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
  44. # MERCHANTABILITY AND FITNESS FOR ANY PARTICULAR PURPOSE.
  45. # IN NO EVENT SHALL THE AUTHORS OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT,
  46. # INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
  47. # (INCLUDING, BUT NOT LIMITED TO, LOSS OF USE, DATA, OR PROFITS OR
  48. # BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
  49. # WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
  50. # OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
  51. # ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
  52. #
  53.  
  54.  
  55. #
  56. # This file has become a huge mess!  The history behind this is that it
  57. # was originally designed as a single CGI script.  The basic flow is that
  58. # every HTML page or frameset has a different 'func' value in the URL.      
  59. # There is an array of functions and the 'func' value is the index into
  60. # that array.  Every request is first sent to 'autopsy_main' where basic
  61. # arguments are checked and then the specific function is called.  It
  62. # checks the specific arguments (using the check_*() functions) and the
  63. # proper data is displayed to STDOUT, which is the socket.
  64. #
  65.  
  66. use lib './';
  67. use strict;
  68. use POSIX;        # needed for tzset
  69. require 'conf.pl';
  70. require 'fs.pl';
  71. require 'define.pl';
  72. require 'search.pl';
  73.  
  74. # Get rid of insecure settings
  75. $ENV{PATH} = "";
  76. delete @ENV{'IFS', 'CDPATH', 'ENV', 'BASH_ENV'};
  77.  
  78. # import variables from conf.pl
  79. use vars '$PROGNAME', '$TASKDIR', '$LOCKDIR';
  80. use vars '$VER', '$GREP_EXE', '$STRINGS_EXE';
  81. use vars '$SANITIZE_TAG';
  82. use vars '$AUT_HOME_PAGE', '$MD5_FILE';
  83. use vars '$USE_NOTES', '$USE_LOG';
  84. use vars '$IMGDIR', '$DATADIR', '$LOGDIR', '$REPDIR';
  85. use vars '$NSRLDB', '$HTTP_NL';
  86. use vars '%first_inode', '%root_inode', '%addr_unit', '%first_addr';
  87. use vars '%ctime_str', '%mtime_str', '%auto_srch', '%auto_srch_reg';
  88. use vars '%auto_srch_csense', '%meta_str';
  89.  
  90.  
  91. # Formats for regular expressions
  92. # Year.Mon.Day Hr:Min:Sec (TZ)
  93. my $REG_DAY = '\d\d\d\d.\d\d.\d\d';
  94. my $REG_TIME = '\d\d:\d\d:\d\d';
  95. my $REG_ZONE1 = '[\w\+\-]+';
  96. my $REG_ZONE2 = '\([\w\+\-]+\)';
  97. my $REG_DATE = "$REG_DAY".'\s+'."$REG_TIME".'\s+'."$REG_ZONE2";
  98. my $REG_FTYPE = '[\w\-]+';
  99. my $REG_SKEW = '[\+\-]?\d+';
  100.  
  101.  
  102. my $REG_FILE = '[\w\-\_\.]+';
  103. my $REG_IMG = "$REG_FILE".'/'."$REG_FILE";
  104. my $REG_IMG_PATH = '/[\w\-\_\.\/]+';
  105. my $REG_CASE = $REG_FILE;
  106. my $REG_HOST = $REG_FILE;
  107. my $REG_FNAME = $REG_FILE;
  108. my $REG_MNT = '[\w\-\_\.\/\:\\\\]+';
  109. my $REG_SEQ_FILE = '[\w\s\-\_\.\/\:\\\\]+';
  110. my $REG_HASHDB = '[\w\-\_\.\,\/]+';
  111. my $REG_BODY = $REG_FILE;
  112. my $REG_TL = $REG_FILE;
  113.  
  114. my $REG_INODE = '[\d-]+';
  115. my $REG_MD5 = '[0-9a-fA-F]{32,32}';
  116.  
  117. my $REG_INVESTIG = '[\w]+';
  118.  
  119. my $HELP_URL = "help/index.html";
  120.  
  121. # Give new directories user and group write permissions
  122. my $MKDIR_MASK = 0775;
  123.  
  124. # constants for different functions (the func argument)
  125. my $WELCOME = 0x00;
  126. my $BLANK = 0x01;
  127.  
  128. my $MAIN_FR = 0x02;      
  129. my $MAIN_LO = $MAIN_FR;
  130. my $MAIN_TABS = 0x03;
  131. my $MAIN_MSG = 0x04;
  132. my $MAIN_HI = $MAIN_MSG;       
  133.  
  134.  
  135. my $SORTER_MAIN = 0x06;
  136. my $SORTER_LO = $SORTER_MAIN;
  137. my $SORTER_LIST = 0x07;
  138. my $SORTER_ENT = 0x08;
  139. my $SORTER_DOIT = 0x09;       
  140. my $SORTER_HI = $SORTER_DOIT;      
  141.  
  142.  
  143. my $NOTES_READ = 0x0A;
  144. my $NOTES_LO = $NOTES_READ;
  145. my $NOTES_MAIN = $NOTES_READ;
  146. my $NOTES_WRITE = 0x0B;
  147. my $NOTES_ENT = 0x0C;
  148. my $NOTES_SEQ_READ = 0x0D;
  149. my $NOTES_SEQ_WRITE = 0x0E;
  150. my $NOTES_HI = $NOTES_SEQ_WRITE;
  151.  
  152. #################################################
  153. # File Mode
  154. my $FIL_LO = 0x10;       
  155. my $FIL_MAIN = $FIL_LO + 0;
  156. my $FIL_DIR = $FIL_LO + 1;
  157. my $FIL_LIST = $FIL_LO + 2;
  158. my $FIL_CONT = $FIL_LO + 3;
  159. my $FIL_REP = $FIL_LO + 4;
  160. my $FIL_CMENU_FR = $FIL_LO + 5;
  161. my $FIL_CMENU = $FIL_LO + 6;
  162. my $FIL_DEL = $FIL_LO + 7;
  163. my $FIL_SAVE = $FIL_LO + 8;
  164. my $FIL_MD5 = $FIL_LO + 9;
  165. my $FIL_NAME = $FIL_LO + 10;
  166. my $FIL_HI = $FIL_LO + 10;
  167.  
  168. # Sorting and display types
  169. my $FIL_SORT_ASC=0;
  170. my $FIL_SORT_STR=1;
  171.  
  172. # Methods of sorting the file listings
  173. my $SORT_DTYPE=0;    # type according to dentry
  174. my $SORT_ITYPE=1;    # type according to inode
  175. my $SORT_NAME=2;
  176. my $SORT_MOD=3;
  177. my $SORT_ACC=4;
  178. my $SORT_CHG=5;
  179. my $SORT_SIZE=6;
  180. my $SORT_GID=7;
  181. my $SORT_UID=8;
  182. my $SORT_INODE=9;
  183. my $SORT_DEL=10;
  184.  
  185. my $DMODE_SHOW = 1;
  186. my $DMODE_NOSHOW = 2;
  187.  
  188. #################################################
  189. # Data Mode
  190. my $BLK_MAIN = 0x20;
  191. my $BLK_LO=$BLK_MAIN;
  192. my $BLK_ENT = 0x21;
  193. my $BLK_CONT = 0x22;
  194. my $BLK_REP = 0x23;
  195. my $BLK_CMENU_FR = 0x24;
  196. my $BLK_CMENU = 0x25;
  197. my $BLK_DLS = 0x26;
  198. my $BLK_SAVE = 0x27;
  199. my $BLK_HI=$BLK_SAVE;
  200.  
  201.  
  202. # Display types that use the sort variable 
  203. my $BLK_SORT_ASC=0;
  204. my $BLK_SORT_HEX=1;
  205. my $BLK_SORT_STR=2;
  206.  
  207. # Types of block numbers 
  208. my $BTYPE_DD=0;
  209. my $BTYPE_DLS=1;
  210.  
  211.  
  212. #################################################
  213. # Hash Database 
  214. my $HASH_LO = 0x2A;
  215. my $HASH_LOOKUP = $HASH_LO + 0;
  216. my $HASH_INDEX = $HASH_LO + 1;
  217. my $HASH_MAIN = $HASH_LO + 2;
  218. my $HASH_HI = $HASH_LO + 2;
  219.  
  220.  
  221.  
  222.  
  223. #################################################
  224. # Search Mode
  225. my $SRCH_ENT = 0x30;
  226. my $SRCH_MAIN = $SRCH_ENT;
  227. my $SRCH_LO = $SRCH_ENT;
  228. my $SRCH_RMAIN = 0x31;
  229. my $SRCH_DOSRCH = 0x32;
  230. my $SRCH_READSRCH = 0x33;
  231. my $SRCH_HI = $SRCH_READSRCH;
  232.  
  233. # Types of modes for fname (i.e. can we overwrite it if it exists)
  234. my $FNAME_MODE_INIT=0;
  235. my $FNAME_MODE_OVER=1;
  236.  
  237.  
  238.  
  239. #################################################
  240. # Sanitized Environment for picts and HTML
  241. my $CELL_LO = 0x38;
  242. my $CELL_MAIN = $CELL_LO + 0;
  243. my $CELL_MENU = $CELL_LO + 1;
  244. my $CELL_CONT = $CELL_LO + 2;
  245. my $CELL_HI = $CELL_LO + 2;
  246.  
  247.  
  248. #################################################
  249. # Inode / Meta Mode
  250. my $INO_MAIN = 0x40;
  251. my $INO_LO = $INO_MAIN;
  252. my $INO_ENT = 0x41;
  253. my $INO_CONT = 0x42;
  254. my $INO_SAVE = 0x43;
  255. my $INO_REP = 0x44;
  256. my $INO_ILS = 0x45;
  257. my $INO_FFIND = 0x46;
  258. my $INO_HI = $INO_FFIND;
  259.  
  260.  
  261. ################################################
  262. # File System
  263. my $FS_STAT = 0x50;
  264. my $FS_LO = $FS_STAT;
  265. my $FS_MAIN = $FS_STAT;
  266. my $FS_HI = $FS_STAT;
  267.  
  268. ################################################
  269. # Integrity
  270. my $INT_CHECK = 0x56;
  271. my $INT_MAIN = $INT_CHECK;
  272. my $INT_LO = $INT_CHECK;
  273. my $INT_CREATE = 0x57;
  274. my $INT_LIST_FR = 0x58;
  275. my $INT_LIST = 0x59;
  276. my $INT_HI = $INT_LIST;
  277.  
  278. ################################################
  279. # Timeline
  280. my $TL_LO = 0x60;
  281. my $TL_MAIN = $TL_LO + 0;
  282. my $TL_BODY_ENT = $TL_LO + 1;
  283. my $TL_BODY_DOIT = $TL_LO + 2;
  284. my $TL_TL_ENT = $TL_LO + 3;
  285. my $TL_TL_DOIT = $TL_LO + 4;
  286. my $TL_VIEW_MENU = $TL_LO + 5;
  287. my $TL_VIEW_FR = $TL_LO + 6;
  288. my $TL_VIEW_IDX = $TL_LO + 7;
  289. my $TL_VIEW_SUM = $TL_LO + 8;
  290. my $TL_VIEW = $TL_LO + 9;
  291. my $TL_TABS = $TL_LO + 10;
  292. my $TL_HI = $TL_LO + 10;
  293.  
  294.  
  295. ################################################
  296. # Setup / Menu values
  297. my $CASE_OPEN = 0x70;
  298. my $CASE_LO = $CASE_OPEN;
  299. my $CASE_OPEN_LOG = 0x71;
  300. my $CASE_NEW = 0x72;
  301. my $CASE_NEW_DOIT = 0x73;
  302. my $CASE_DETAILS = 0x74;
  303. my $CASE_DEL = 0x75;
  304. my $CASE_HI = $CASE_DEL;
  305.  
  306. my $HOST_OPEN = 0x76;
  307. my $HOST_LO = $HOST_OPEN;
  308. my $HOST_OPEN_LOG = 0x77;
  309. my $HOST_ADD = 0x78;
  310. my $HOST_ADD_DOIT = 0x79;
  311. my $HOST_DETAILS = 0x7A;
  312. my $HOST_DEL = 0x7B;
  313. my $HOST_HI = $HOST_DEL;
  314.  
  315. my $IMG_OPEN = 0x7C;
  316. my $IMG_LO = $IMG_OPEN;
  317. my $IMG_OPEN_LOG = 0x7D;
  318. my $IMG_ADD = 0x7E;
  319. my $IMG_ADD_DOIT = 0x7F;
  320. my $IMG_DETAILS = 0x80;
  321. my $IMG_DEL = 0x81;
  322. my $IMG_MAKESTR = 0x82;
  323. my $IMG_MAKEDLS = 0x83;
  324. my $IMG_HI = $IMG_MAKEDLS;
  325.  
  326. my $IMG_ADD_SYM = 0x1;
  327. my $IMG_ADD_COPY = 0x2;
  328. my $IMG_ADD_MOVE = 0x3;
  329.  
  330.  
  331. my $BACK_COLOR="#CCCC99";
  332. my $BACK_COLOR_TABLE="#CCCCCC";
  333. my @DEL_COLOR;
  334. $DEL_COLOR[0] = "red";
  335. $DEL_COLOR[1] = "#800000";     # used when inode has been reallocated 
  336. my $NORM_COLOR = "";
  337. my $LINK_COLOR = "blue";
  338.  
  339. my $YEL_PIX = "pict/back_pix.jpg";
  340.  
  341. my @funcs;        # Array for function references
  342. my %args;        # Arguments that are decoded
  343. my %enc_args;    # Arguments that are encoded
  344. my $baseargs;    # Arguments that never change such as case,host,mnt and img
  345. my $baseargs_noimg;    # baseargs w/out img info
  346.  
  347.  
  348. my %img2mnt;    # Mapping for mount point, given the image name
  349. my %img2ftype;    # Mapping for file system type, given the image name
  350. my %mod2img;    # Mapping for image, given the strings or dls 
  351. my %img2str;    # Mapping for strings file, given  the image name
  352. my %img2dls;    # Mapping for dls file, given  the image name
  353.  
  354. # hash databases 
  355. # NSRL is global
  356. my $exclude_db = "";
  357. my $alert_db = "";
  358.  
  359. my $tz = "";
  360. my $ts = 0;    # time skew (in seconds)
  361. my $host_desc = "";
  362. my $host_dir = "";
  363. my $case_dir = "";
  364.  
  365. my $is_html = 0;
  366. my $is_body = 0;
  367.  
  368.  
  369. # Main Menu
  370. #
  371. # Display the title page 
  372. $funcs[$WELCOME] = sub {
  373.     print_javascript_header("Autopsy Forensic Browser");
  374.  
  375.  
  376.     print "<CENTER>\n";
  377.     if ($] >= 5.008) {
  378.         print "<P><FONT COLOR=\"red\">Warning: You are using Perl v5.8.</FONT><BR>\n".
  379.           "  Some buffer problems have been reported with Autopsy and Perl 5.8 ".
  380.           "where output is not shown.<BR>\n".
  381.           "Perl 5.6 should be used if available.\n".
  382.           "If data is missing, reload the page<BR><HR>\n";
  383.     }
  384.  
  385. print <<EOF;
  386. <TABLE CELLSPACING=0 CELLPADDING=2 WIDTH=600 HEIGHT=350 BORDER=0>
  387.  
  388. <TR>
  389.   <TD COLSPAN=\"3\" ALIGN=\"CENTER\" VALIGN=\"MIDDLE\">
  390.     <A HREF=\"./about\">
  391.       <IMG SRC=\"pict/logo.jpg\" BORDER=0>
  392.     </A>
  393.   </TD>
  394. </TR>
  395. <TR>
  396.   <TD COLSPAN=\"3\" ALIGN=\"CENTER\" VALIGN=\"MIDDLE\">
  397.     <A HREF=$AUT_HOME_PAGE>
  398.       <TT>$AUT_HOME_PAGE</TT>
  399.     </A>
  400.   </TD>
  401. </TR>
  402. <TR><TD COLSPAN=3> </TD></TR>
  403. <TR>
  404.   <TD ALIGN=CENTER WIDTH=200 VALIGN=\"MIDDLE\">
  405.     <A HREF=\"$PROGNAME?func=$CASE_OPEN\">
  406.       <IMG SRC=\"pict/menu_b_copen.jpg\" ALT=\"Open Case\" WIDTH=176 HEIGHT=20 BORDER=0>
  407.     </A>
  408.   </TD>
  409.   <TD ALIGN=CENTER WIDTH=200 VALIGN=\"MIDDLE\">
  410.     <A HREF=\"$PROGNAME?func=$CASE_NEW\">
  411.       <IMG SRC=\"pict/menu_b_cnew.jpg\" ALT=\"New Case\" WIDTH=176 HEIGHT=20 BORDER=0>
  412.     </A>
  413.   </TD>
  414.   <TD ALIGN=CENTER WIDTH=200 VALIGN=\"MIDDLE\">
  415.     <A HREF=\"$HELP_URL\" TARGET=\"_blank\">
  416.       <IMG SRC=\"pict/menu_b_help.jpg\" ALT=\"Help\" WIDTH=167 HEIGHT=20 BORDER=0>
  417.     </A>
  418.   </TD>
  419. </TR>
  420. </TABLE>
  421.  
  422. EOF
  423.  
  424.     return;
  425. };
  426.  
  427.  
  428. # create the frame for the tabs on top and the generic message on the bottom
  429. $funcs[$MAIN_FR] = sub {
  430.     print_html_header_frameset("$args{'case'}:$args{'host'}:$args{'img'}");
  431.  
  432.     my $mode = $MAIN_FR;
  433.     $mode = get_mode() if (exists $args{'mode'});
  434.  
  435.     # Print the rest of the frames
  436.     my $str = "";
  437.     if ($mode == $MAIN_FR) {
  438.         $mode = $MAIN_MSG;
  439.     } 
  440.     elsif ($mode == $FIL_MAIN) {
  441.         $str .= "&inode=$args{'inode'}" if (exists $args{'inode'});
  442.         $str .= "&dir=$args{'dir'}" if (exists $args{'dir'});
  443.         $str .= "&sort=$args{'sort'}" if (exists $args{'sort'});
  444.         $str .= "&dmode=$args{'dmode'}" if (exists $args{'dmode'});
  445.     } 
  446.     elsif ($mode == $BLK_MAIN) {
  447.         $str .= "&block=$args{'block'}" if (exists $args{'block'});
  448.         $str .= "&len=$args{'len'}" if (exists $args{'len'});
  449.     } 
  450.     elsif ($mode == $INO_MAIN) {
  451.         $str .= "&inode=$args{'inode'}" if (exists $args{'inode'});
  452.     } 
  453.     # elsif ($mode == $FS_MAIN) 
  454.     # elsif ($mode == $SRCH_MAIN) 
  455.     # elsif ($mode == $INT_MAIN) 
  456.     # elsif ($mode == $NOTES_MAIN) 
  457.  
  458.  
  459. print <<EOF;
  460.  
  461. <FRAMESET ROWS=\"40,*\">
  462.   <FRAME SRC=\"$PROGNAME?func=$MAIN_TABS&$baseargs&mode=$mode\">
  463.  
  464.   <FRAME SRC=\"$PROGNAME?func=$mode&$baseargs$str\">
  465. </FRAMESET>
  466.  
  467. <NOFRAMES>
  468.   <CENTER>
  469.     Autopsy requires a browser that supports frames.
  470.   </CENTER>
  471. </NOFRAMES>
  472.  
  473. EOF
  474.     return;
  475. };
  476.  
  477.  
  478. # Display a message when the image is opened (below the tabs)
  479. $funcs[$MAIN_MSG] = sub {
  480.     print_html_header("Main Message");
  481.  
  482. print <<EOF;
  483.  
  484. <CENTER>
  485.   <BR><BR><BR><BR><BR><BR><BR>
  486.   (select an analysis type)
  487. </CENTER>
  488.  
  489. EOF
  490.     return;
  491. };
  492.  
  493.  
  494. $funcs[$MAIN_TABS] = sub {
  495.     check_mode();
  496.     print_html_header_tabs("Mode Tabs");
  497.  
  498.     my $mode = get_mode();
  499.  
  500.     my $special = 0;
  501.     $special = 1 if (($img2ftype{$args{'img'}} eq "strings") || 
  502.       ($img2ftype{$args{'img'}} eq "dls") ||
  503.       ($img2ftype{$args{'img'}} eq "swap") ||
  504.       ($img2ftype{$args{'img'}} eq "raw")) ;
  505.  
  506.     print "<CENTER><TABLE WIDTH=\"800\" BORDER=\"0\" CELLSPACING=\"0\" ".
  507.       "CELLPADDING=\"0\"><TR>\n";
  508.  
  509.     # Files
  510.     print "<TD ALIGN=\"CENTER\" WIDTH=116>";
  511.     if ($special == 0) {
  512.  
  513.         print "<A HREF=\"$PROGNAME?func=$MAIN_FR&mode=$FIL_MAIN&$baseargs\"".
  514.           "TARGET=\"_top\">";
  515.  
  516.         # Current 
  517.         if ($mode == $FIL_MAIN) {
  518.             print "<IMG BORDER=0 ".
  519.               "SRC=\"pict/main_t_fil_cur.jpg\" ".
  520.               "WIDTH=116 HEIGHT=38 ".
  521.               "ALT=\"File Analysis (Current Mode)\"></A>";
  522.         }
  523.         # Link
  524.         else {
  525.             print "<IMG BORDER=0 ".
  526.               "SRC=\"pict/main_t_fil_link.jpg\" ".
  527.               "WIDTH=116 HEIGHT=38 ".
  528.               "ALT=\"File Analysis\"></A>";
  529.         }
  530.     # non-link
  531.     } else {
  532.         print "<IMG BORDER=0 ".
  533.           "SRC=\"pict/main_t_fil_org.jpg\" ".
  534.           "WIDTH=116 HEIGHT=38 ".
  535.           "ALT=\"File Analysis (not available)\">";
  536.     }
  537.  
  538.     # Search
  539.     print "</TD>\n".
  540.       "<TD ALIGN=\"CENTER\" WIDTH=116>";
  541.  
  542.     print "<A HREF=\"$PROGNAME?func=$MAIN_FR&mode=$SRCH_MAIN&$baseargs\"".
  543.       " TARGET=\"_top\">";
  544.  
  545.     if ($mode == $SRCH_MAIN) {
  546.         print "<IMG BORDER=0 ".
  547.           "SRC=\"pict/main_t_srch_cur.jpg\" ".
  548.           "WIDTH=116 HEIGHT=38 ".
  549.           "ALT=\"Keyword Search Mode (Current Mode)\"></A>";
  550.     }
  551.     else {
  552.           print "<IMG BORDER=0 ".
  553.           "SRC=\"pict/main_t_srch_link.jpg\" ".
  554.           "WIDTH=116 HEIGHT=38 ".
  555.           "ALT=\"Keyword Search Mode\"></A>";
  556.     }
  557.  
  558.     # File Type
  559.     print "</TD>\n".
  560.       "<TD ALIGN=\"CENTER\" WIDTH=116>";
  561.  
  562.     if ($special == 0) {
  563.  
  564.         print "<A HREF=\"$PROGNAME?func=$MAIN_FR&mode=$SORTER_MAIN&$baseargs\"".
  565.           " TARGET=\"_top\">";
  566.  
  567.         # Current
  568.         if ($mode == $SORTER_MAIN) {
  569.             print "<IMG BORDER=0 ".
  570.               "SRC=\"pict/main_t_ftype_cur.jpg\" ".
  571.               "WIDTH=116 HEIGHT=38 ".
  572.               "ALT=\"File Type (Current Mode)\"></A>";
  573.         }
  574.         else {
  575.             print "<IMG BORDER=0 ".
  576.               "SRC=\"pict/main_t_ftype_link.jpg\" ".
  577.               "WIDTH=116 HEIGHT=38 ".
  578.               "ALT=\"File Type\"></A>";
  579.         }
  580.     } else {
  581.         print "<IMG BORDER=0 ".
  582.           "SRC=\"pict/main_t_ftype_org.jpg\" ".
  583.           "WIDTH=116 HEIGHT=38 ".
  584.           "ALT=\"File Type (not available)\">";
  585.     }
  586.  
  587.     # File System
  588.     print "</TD>\n".
  589.       "<TD ALIGN=\"CENTER\" WIDTH=116>";
  590.  
  591.     if ($special == 0) {
  592.  
  593.         print "<A HREF=\"$PROGNAME?func=$MAIN_FR&mode=$FS_MAIN&$baseargs\"".
  594.           " TARGET=\"_top\">";
  595.  
  596.         if ($mode == $FS_MAIN) {
  597.             print "<IMG BORDER=0 ".
  598.               "SRC=\"pict/main_t_img_cur.jpg\" ".
  599.               "WIDTH=116 HEIGHT=38 ".
  600.               "ALT=\"Image Details Mode (Current Mode)\"></A>";
  601.         } else {
  602.             print "<IMG BORDER=0 ".
  603.               "SRC=\"pict/main_t_img_link.jpg\" ".
  604.               "WIDTH=116 HEIGHT=38 ".
  605.               "ALT=\"Image Details Mode\"></A>";
  606.         }
  607.     } else {
  608.         print "<IMG BORDER=0 ".
  609.           "SRC=\"pict/main_t_img_org.jpg\" ".
  610.           "WIDTH=116 HEIGHT=38 ".
  611.           "ALT=\"Image Details Mode (not available)\">";
  612.     }
  613.  
  614.     # Meta Data
  615.     print "</TD>\n".
  616.       "<TD ALIGN=\"CENTER\" WIDTH=116>";
  617.  
  618.     if ($special == 0) {
  619.         print "<A HREF=\"$PROGNAME?func=$MAIN_FR&mode=$INO_MAIN&$baseargs\"".
  620.           " TARGET=\"_top\">";
  621.  
  622.         if ($mode == $INO_MAIN) {
  623.             print "<IMG BORDER=0 ".
  624.               "SRC=\"pict/main_t_met_cur.jpg\" ".
  625.               "WIDTH=116 HEIGHT=38 ".
  626.               "ALT=\"Meta Data Mode (Current Mode)\"></A>";
  627.         } else {
  628.             print "<IMG BORDER=0 ".
  629.               "SRC=\"pict/main_t_met_link.jpg\" ".
  630.               "WIDTH=116 HEIGHT=38 ".
  631.               "ALT=\"Meta Data Mode\"></A>";
  632.         }
  633.     } else {
  634.         print "<IMG BORDER=0 ".
  635.           "SRC=\"pict/main_t_met_org.jpg\" ".
  636.           "WIDTH=116 HEIGHT=38 ".
  637.           "ALT=\"Meta Data Mode (not available)\">";
  638.     }
  639.  
  640.     # Data Units
  641.     print "</TD>\n".
  642.       "<TD ALIGN=\"CENTER\" WIDTH=116>";
  643.  
  644.     print "<A HREF=\"$PROGNAME?func=$MAIN_FR&mode=$BLK_MAIN&$baseargs\"".
  645.       " TARGET=\"_top\">";
  646.     # Current
  647.     if ($mode == $BLK_MAIN) {
  648.         print "<IMG BORDER=0 ".
  649.           "SRC=\"pict/main_t_dat_cur.jpg\" ".
  650.           "WIDTH=116 HEIGHT=38 ".
  651.           "ALT=\"Data Units Mode (Current Mode)\"></A>";
  652.     }
  653.     # Link
  654.     else {
  655.         print "<IMG BORDER=0 ".
  656.           "SRC=\"pict/main_t_dat_link.jpg\" ".
  657.           "WIDTH=116 HEIGHT=38 ".
  658.           "ALT=\"Data Units Mode\"></A>";
  659.     }
  660.  
  661.  
  662.  
  663.     # Help - set to current mode
  664.     print "</TD>\n".
  665.       "<TD ALIGN=\"CENTER\" WIDTH=52>".
  666.       "<A HREF=\"$HELP_URL\"".
  667.       " TARGET=\"_blank\">".
  668.       "<IMG BORDER=0 ".
  669.       "SRC=\"pict/tab_help.jpg\" ".
  670.       "WIDTH=52 ".
  671.       "ALT=\"Help\">".
  672.       "</A></TD>\n";
  673.  
  674.     # Close
  675.     print "<TD ALIGN=\"CENTER\" WIDTH=52>".
  676.       "<A HREF=\"$PROGNAME?func=$IMG_OPEN&$baseargs_noimg\"".
  677.       " TARGET=\"_top\">".
  678.       "<IMG BORDER=0 ".
  679.       "SRC=\"pict/tab_close.jpg\" ".
  680.       "WIDTH=52 ".
  681.       "ALT=\"Close Image\">".
  682.       "</A></TD>\n";
  683.  
  684.     print "</TR></TABLE>\n";
  685.  
  686.     return;
  687. };
  688.  
  689.  
  690.  
  691. # The tabs / button images in timeline view
  692. $funcs[$TL_TABS] = sub {
  693.     check_mode();
  694.     print_html_header_tabs("Timeline Mode Tabs");
  695.  
  696.     my $mode = get_mode();
  697.  
  698.     print "<CENTER><TABLE WIDTH=\"800\" BORDER=\"0\" ".
  699.       "CELLSPACING=\"0\" CELLPADDING=\"0\"><TR>\n";
  700.  
  701.     # Create Datafile
  702.     print "<TD ALIGN=\"CENTER\" WIDTH=174>".
  703.       "<A HREF=\"$PROGNAME?func=$TL_MAIN&mode=$TL_BODY_ENT&$baseargs\" ".
  704.       "TARGET=\"_top\">";
  705.  
  706.     if ($mode == $TL_BODY_ENT) {
  707.         print "<IMG BORDER=0 ".
  708.           "SRC=\"pict/tl_t_data_cur.jpg\" ".
  709.           "WIDTH=174 HEIGHT=38 ".
  710.           "ALT=\"Create Data File (Current Mode)\"></A>\n";
  711.     } else {
  712.         print "<IMG BORDER=0 ".
  713.           "SRC=\"pict/tl_t_data_link.jpg\" ".
  714.           "WIDTH=174 HEIGHT=38 ".
  715.           "ALT=\"Create Data File\"></A>\n";
  716.     }
  717.  
  718.     print "</TD>\n".
  719.       "<TD ALIGN=\"CENTER\" WIDTH=174>".
  720.  
  721.       "<A HREF=\"$PROGNAME?func=$TL_MAIN&mode=$TL_TL_ENT&$baseargs\" ".
  722.       "TARGET=\"_top\">";
  723.  
  724.     # Create Timeline
  725.     if ($mode == $TL_TL_ENT) {
  726.         print "<IMG BORDER=0 ".
  727.           "SRC=\"pict/tl_t_tl_cur.jpg\" ".
  728.           "WIDTH=174 HEIGHT=38 ".
  729.           "ALT=\"Create Timeline (Current Mode)\"></A>\n";
  730.     } else {
  731.         print "<IMG BORDER=0 ".
  732.           "SRC=\"pict/tl_t_tl_link.jpg\" ".
  733.           "WIDTH=174 HEIGHT=38 ".
  734.           "ALT=\"Create Timeline\"></A>\n";
  735.     }
  736.     print "</TD>\n".
  737.       "<TD ALIGN=\"CENTER\" WIDTH=174>".
  738.       "<A HREF=\"$PROGNAME?func=$TL_MAIN&mode=$TL_VIEW_MENU&$baseargs\" ".
  739.       "TARGET=\"_top\">";
  740.  
  741.     # View Timeline
  742.     if (($mode == $TL_VIEW_FR) || ($mode == $TL_VIEW_MENU)) {
  743.         print "<IMG BORDER=0 ".
  744.           "SRC=\"pict/tl_t_view_cur.jpg\" ".
  745.           "WIDTH=174 HEIGHT=38 ".
  746.           "ALT=\"View Timeline (Current Mode)\"></A>\n";
  747.     } else {
  748.         print "<IMG BORDER=0 ".
  749.           "SRC=\"pict/tl_t_view_link.jpg\" ".
  750.           "WIDTH=174 HEIGHT=38 ".
  751.           "ALT=\"View Timeline\"></A>\n";
  752.     }
  753.  
  754.     # Notes
  755.     print "</TD>\n".
  756.       "<TD ALIGN=\"CENTER\" WIDTH=174>";
  757.     if ($USE_NOTES == 1) {
  758.         print "<A HREF=\"$PROGNAME?func=$NOTES_MAIN&${baseargs_noimg}\" ".
  759.           "TARGET=\"_blank\">".
  760.           "<IMG BORDER=0 ".
  761.           "SRC=\"pict/tl_t_notes_link.jpg\" ".
  762.           "WIDTH=174 HEIGHT=38 ".
  763.           "ALT=\"View Notes\"></A></TD>\n";
  764.     } else {
  765.         print "<IMG BORDER=0 ".
  766.           "SRC=\"pict/tl_t_notes_org.jpg\" ".
  767.           "WIDTH=174 HEIGHT=38 ".
  768.           "ALT=\"View Notes\"></A></TD>\n";
  769.     }
  770.  
  771.     # Help - set to current mode
  772.     print "<TD ALIGN=\"CENTER\" WIDTH=52>".
  773.       "<A HREF=\"$HELP_URL\" ".
  774.       "TARGET=\"_blank\">".
  775.       "<IMG BORDER=0 ".
  776.       "SRC=\"pict/tab_help.jpg\" ".
  777.       "WIDTH=52 ".
  778.       "ALT=\"Help\"></A></TD>\n";
  779.  
  780.     # Close
  781.     print "<TD ALIGN=\"CENTER\" WIDTH=52>".
  782.       "<A HREF=\"$PROGNAME?func=$IMG_OPEN&$baseargs\" ".
  783.       "TARGET=\"_top\">".
  784.       "<IMG BORDER=0 ".
  785.       "SRC=\"pict/tab_close.jpg\" ".
  786.       "WIDTH=52 ".
  787.       "ALT=\"Exit to Host Manager\"></A></TD>\n".
  788.       "</TR></TABLE>\n";
  789.  
  790.     return;
  791. };
  792.  
  793.  
  794.  
  795. ####################################################################
  796. # General menu Functions
  797.  
  798. sub print_menu_tabs {
  799.  
  800.     print "<B>Case:</B> $args{'case'}" if (exists $args{'case'});
  801.     print "<BR>\n";
  802.     print "<B>Host:</B> $args{'host'}" if (exists $args{'host'});
  803.     print "<BR>\n";
  804.  
  805.     print "<CENTER>\n";
  806.  
  807.     print "<TABLE WIDTH=\"600\" HEIGHT=\"60\" BACKGROUND=\"$YEL_PIX\" ".
  808.       "BORDER=\"0\" CELLSPACING=\"0\" CELLPADDING=\"0\">\n<TR>\n".
  809.       "<TD ALIGN=\"CENTER\" WIDTH=\"200\">";
  810.  
  811.     # Case Gallery
  812.     if ($args{'func'} == $CASE_OPEN) {
  813.         print "<IMG BORDER=0 ".
  814.           "SRC=\"pict/menu_t_cg_cur.jpg\" ".
  815.           "WIDTH=200 HEIGHT=65 ".
  816.           "ALT=\"Case Gallery (Current Mode)\">\n";
  817.     }
  818.     else {
  819.         print "<A HREF=\"$PROGNAME?func=$CASE_OPEN\">".
  820.           "<IMG BORDER=0 ".
  821.           "SRC=\"pict/menu_t_cg_link.jpg\" ".
  822.           "WIDTH=200 HEIGHT=65 ".
  823.           "ALT=\"Case Gallery\"></A>\n";
  824.     }
  825.     print "</TD>\n".
  826.       "<TD ALIGN=\"CENTER\" WIDTH=\"200\">";
  827.  
  828.     # Host Gallery
  829.     # Current
  830.     if ($args{'func'} == $HOST_OPEN) {
  831.         print "<IMG BORDER=0 ".
  832.           "SRC=\"pict/menu_t_hg_cur.jpg\" ".
  833.           "WIDTH=200 HEIGHT=65 ".
  834.           "ALT=\"Host Gallery (Current Mode)\">\n";
  835.     }
  836.     # Link
  837.     elsif ($args{'func'} == $IMG_OPEN) {
  838.         print "<A HREF=\"$PROGNAME?func=$HOST_OPEN&case=$args{'case'}\">".
  839.           "<IMG BORDER=0 ".
  840.           "SRC=\"pict/menu_t_hg_link.jpg\" ".
  841.           "WIDTH=200 HEIGHT=65 ".
  842.           "ALT=\"Host Gallery\"></A>\n";
  843.     }
  844.     # non-link
  845.     else {
  846.         print "<IMG BORDER=0 ".
  847.           "SRC=\"pict/menu_t_hg_org.jpg\" ".
  848.           "WIDTH=200 HEIGHT=65 ".
  849.           "ALT=\"Host Gallery (Not Available)\">\n";
  850.     }
  851.  
  852.     print "</TD>\n".
  853.       "<TD ALIGN=\"CENTER\" WIDTH=\"200\">";
  854.  
  855.     # Host Manager
  856.     # Current
  857.     if ($args{'func'} == $IMG_OPEN) {
  858.         print "<IMG BORDER=0 ".
  859.           "SRC=\"pict/menu_t_hm_cur.jpg\" ".
  860.           "WIDTH=200 HEIGHT=65 ".
  861.           "ALT=\"Host Manager (Current Mode)\">\n";
  862.     }
  863.     # non-link
  864.     else {
  865.         print "<IMG BORDER=0 ".
  866.           "SRC=\"pict/menu_t_hm_org.jpg\" ".
  867.           "WIDTH=200 HEIGHT=65 ".
  868.           "ALT=\"Host Manager (Not Available)\">\n";
  869.     }
  870.  
  871.     print "</TD>\n".
  872.       "</TABLE>\n";
  873. };
  874.  
  875. ####################################################################
  876. # Case Functions
  877.  
  878. $funcs[$CASE_NEW] = sub {
  879.     print_html_header("Create A New Case");
  880.  
  881. print <<EOF;
  882. <BR>
  883. <BR>
  884. <CENTER>
  885. <IMG SRC=\"pict/menu_h_cnew.jpg\" ALT=\"New Case\">
  886. <BR><BR><BR>
  887.  
  888. <TABLE WIDTH=\"600\" BACKGROUND=\"$YEL_PIX\" CELLSPACING=\"0\"
  889.   CELLPADDING=\"2\" BORDER=0>
  890. <FORM ACTION=\"$PROGNAME\" METHOD=\"GET\">
  891. <INPUT TYPE=\"hidden\" NAME=\"func\" VALUE=\"$CASE_NEW_DOIT\">
  892. <TR>
  893.   <TD COLSPAN=2 ALIGN=center>
  894.     1.  Enter Case Name (directory name): 
  895.     <INPUT TYPE=\"text\" NAME=\"case\">
  896.   </TD>
  897. </TR>
  898. <TR><TD COLSPAN=2> </TD></TR>
  899. <TR>
  900.   <TD COLSPAN=2 ALIGN=center>
  901.     2.  Enter Description (one line, optional): 
  902.     <INPUT TYPE=\"text\" NAME=\"desc\">
  903.   </TD>
  904. </TR>
  905. <TR><TD COLSPAN=2> </TD></TR>
  906. <TR>
  907.   <TD COLSPAN=2 ALIGN=center>
  908.     3.  Enter Investigator Logins (no spaces):
  909.   </TD>
  910. </TR>
  911. <TR>
  912.   <TD ALIGN=CENTER>a. <INPUT TYPE=\"text\" NAME=\"inv1\"></TD>
  913.   <TD ALIGN=CENTER>b. <INPUT TYPE=\"text\" NAME=\"inv2\"></TD>
  914. </TR>
  915. <TR>
  916.   <TD ALIGN=CENTER>c. <INPUT TYPE=\"text\" NAME=\"inv3\"></TD>
  917.   <TD ALIGN=CENTER>d. <INPUT TYPE=\"text\" NAME=\"inv4\"></TD>
  918. </TR>
  919. <TR>
  920.   <TD ALIGN=CENTER>e. <INPUT TYPE=\"text\" NAME=\"inv5\"></TD>
  921.   <TD ALIGN=CENTER>f. <INPUT TYPE=\"text\" NAME=\"inv6\"></TD>
  922. </TR>
  923. <TR>
  924.   <TD ALIGN=CENTER>g. <INPUT TYPE=\"text\" NAME=\"inv7\"></TD>
  925.   <TD ALIGN=CENTER>h. <INPUT TYPE=\"text\" NAME=\"inv8\"></TD>
  926. </TR>
  927. <TR>
  928.   <TD ALIGN=CENTER>i. <INPUT TYPE=\"text\" NAME=\"inv9\"></TD>
  929.   <TD ALIGN=CENTER>j. <INPUT TYPE=\"text\" NAME=\"inv10\"></TD>
  930. </TR>
  931. </TABLE>
  932.  
  933. <BR><BR>
  934. <TABLE WIDTH=\"600\" CELLSPACING=\"0\" CELLPADDING=\"2\">
  935. <TR>
  936.   <TD ALIGN=CENTER>
  937.     <INPUT TYPE=\"image\" SRC=\"pict/menu_b_cnew.jpg\" 
  938.       ALT=\"Create Case\" WIDTH=\"176\" HEIGHT=20 BORDER=0>
  939.   </TD>
  940. </FORM>
  941.   <TD ALIGN=CENTER>
  942.     <FORM ACTION=\"$PROGNAME\" METHOD=\"GET\">
  943.     <INPUT TYPE=\"hidden\" NAME=\"func\" VALUE=\"$CASE_OPEN\">
  944.     <INPUT TYPE=\"image\" SRC=\"pict/menu_b_cancel.jpg\" 
  945.     ALT=\"Cancel\" WIDTH=\"167\" HEIGHT=20 BORDER=0>
  946.     </FORM>
  947.   </TD>
  948.   <TD ALIGN=CENTER><A HREF=\"$HELP_URL\" 
  949.     TARGET=\"_blank\">
  950.     <IMG SRC=\"pict/menu_b_help.jpg\" ALT=\"Help\" 
  951.     WIDTH=\"167\" HEIGHT=20 BORDER=0></A>
  952.   </TD>
  953. </TR>
  954. </TABLE>
  955. EOF
  956.  
  957.     return;
  958. };
  959.  
  960.  
  961. # Create the directory and case configuration file
  962. # Gets the input from CASE_NEW
  963. $funcs[$CASE_NEW_DOIT] = sub {
  964.     check_case();
  965.     print_html_header("Creating Case: $args{'case'}");
  966.  
  967.     print "<H3>Creating Case: <TT>$args{'case'}</TT></H3>\n";
  968.     # Make the directory
  969.     if (-d "$case_dir") {
  970.         print_err ("Error: $case_dir already exists<BR>Please remove the directory and its contents and try again");
  971.     }
  972.  
  973.     unless (mkdir $case_dir, $MKDIR_MASK) {
  974.       print_err ("Error making directory $case_dir: $!");
  975.     }
  976.  
  977.     print "Case directory (<TT>$case_dir</TT>) created<BR>\n";
  978.     log_case_info ("Case $args{'case'} created");
  979.  
  980.  
  981.     my $fname = case_config_fname();
  982.  
  983.     open CASE_CONFIG, ">$fname" or die "Can't open case config: $fname";
  984.  
  985.     print CASE_CONFIG "# Autopsy case config file\n".
  986.       "# Case: $args{'case'}\n\n".
  987.       "created ".localtime()."\n";
  988.  
  989.     if ((exists $args{'desc'}) && ($args{'desc'} ne "")){
  990.         print_err ("Invalid Description") if ($args{'desc'} =~ /\n/);
  991.  
  992.         print CASE_CONFIG "desc $args{'desc'}\n";
  993.     }
  994.     print CASE_CONFIG "images    $IMGDIR\n";
  995.     print CASE_CONFIG "data        $DATADIR\n";
  996.     print CASE_CONFIG "log        $LOGDIR\n";
  997.     print CASE_CONFIG "reports    $REPDIR\n";
  998.  
  999.     close CASE_CONFIG;
  1000.     print "Configuration file (<TT>$fname</TT>) created<BR>\n";
  1001.  
  1002.     write_invest ($args{'inv1'}) 
  1003.       if ((exists $args{'inv1'}) && ($args{'inv1'} ne ""));
  1004.     write_invest ($args{'inv2'}) 
  1005.       if ((exists $args{'inv2'}) && ($args{'inv2'} ne ""));
  1006.     write_invest ($args{'inv3'}) 
  1007.       if ((exists $args{'inv3'}) && ($args{'inv3'} ne ""));
  1008.     write_invest ($args{'inv4'}) 
  1009.       if ((exists $args{'inv4'}) && ($args{'inv4'} ne ""));
  1010.     write_invest ($args{'inv5'}) 
  1011.       if ((exists $args{'inv5'}) && ($args{'inv5'} ne ""));
  1012.     write_invest ($args{'inv6'}) 
  1013.       if ((exists $args{'inv6'}) && ($args{'inv6'} ne ""));
  1014.     write_invest ($args{'inv7'}) 
  1015.       if ((exists $args{'inv7'}) && ($args{'inv7'} ne ""));
  1016.     write_invest ($args{'inv8'}) 
  1017.       if ((exists $args{'inv8'}) && ($args{'inv8'} ne ""));
  1018.     write_invest ($args{'inv9'}) 
  1019.       if ((exists $args{'inv9'}) && ($args{'inv9'} ne ""));
  1020.     write_invest ($args{'inv10'}) 
  1021.       if ((exists $args{'inv10'}) && ($args{'inv10'} ne ""));
  1022.  
  1023.     print "Investigators added<BR>\n";
  1024.  
  1025.     log_session_info ("Case $args{'case'} created");
  1026.  
  1027.     print "<BR><BR><A HREF=\"$PROGNAME?func=$CASE_OPEN\">".
  1028.       "<IMG SRC=\"pict/but_ok.jpg\" ALT=\"Ok\" ".
  1029.       "WIDTH=\"43\" HEIGHT=20 BORDER=\"0\"></A>\n";
  1030.  
  1031.     return;
  1032. };
  1033.  
  1034.  
  1035. # Open a Case
  1036. # This provides a form with a list of options
  1037. $funcs[$CASE_OPEN] = sub {
  1038.     print_html_header("Open A Case");
  1039.  
  1040.     print_menu_tabs();
  1041.  
  1042.     print "<TABLE WIDTH=\"600\" BACKGROUND=\"$YEL_PIX\" ".
  1043.       " CELLSPACING=\"0\" CELLPADDING=\"2\" BORDER=0>\n";
  1044.  
  1045.  
  1046.     # Read the directories of the Evidence Locker into an array
  1047.     # Verify that there is a config file in the directory
  1048.     my @cases;
  1049.     opendir CASES, $LOCKDIR or die "Can't open $LOCKDIR directory: $!";
  1050.     foreach my $c (readdir CASES) {
  1051.         next if (($c eq '.') || ($c eq '..'));
  1052.         my $cfile = case_config_fname($c);
  1053.  
  1054.         push @cases, $c 
  1055.           if ((-d "${LOCKDIR}$c") && (-e "$cfile"));
  1056.     }
  1057.  
  1058.     closedir CASES;
  1059.  
  1060.     # Were there any cases?  
  1061.     if (scalar @cases == 0) {
  1062.         print "<TR><TD ALIGN=\"CENTER\">".
  1063.           "No cases exist in <TT>$LOCKDIR</TT>".
  1064.           "</TD></TR>\n";
  1065.     }
  1066.  
  1067.     else {
  1068.         print "<FORM ACTION=\"$PROGNAME\" METHOD=\"GET\">\n".
  1069.           "<INPUT TYPE=\"hidden\" NAME=\"func\" VALUE=\"$CASE_OPEN_LOG\">\n".
  1070.           make_hidden().
  1071.           "<TR><TH>Name</TH>".
  1072.           "<TH>Description</TH>".
  1073.           "<TD> </TD></TR>\n";
  1074.  
  1075.         my $first = 0;
  1076.         foreach my $c (@cases) {
  1077.  
  1078.             print "<TR><TD ALIGN=\"left\">".
  1079.               "<INPUT TYPE=\"radio\" NAME=\"case\" VALUE=$c";
  1080.             if ($first == 0) {
  1081.                 print " CHECKED";
  1082.                 $first = 1;
  1083.             }
  1084.             print ">$c</TD>";
  1085.  
  1086.             my %cvals = read_case_config($c);
  1087.  
  1088.             print "<TD>$cvals{'desc'}</TD>".
  1089.               "<TD ALIGN=center>".
  1090.               "<A HREF=\"$PROGNAME?func=$CASE_DETAILS&case=$c\">".
  1091.               "details</A></TD>".
  1092.               "</TR>\n";
  1093.         }
  1094.     }
  1095.     print "</TABLE>\n";
  1096.  
  1097.     print "<BR><BR>".
  1098.       "<TABLE WIDTH=\"600\" CELLSPACING=\"0\" CELLPADDING=\"2\">\n".
  1099.       "<TR>\n";
  1100.  
  1101.     # Print the OK button if there were cases
  1102.     if (scalar @cases != 0) {
  1103.           print "<TD ALIGN=CENTER>".
  1104.             "<INPUT TYPE=\"image\" SRC=\"pict/menu_b_ok.jpg\" ".
  1105.             "WIDTH=167 HEIGHT=20 ALT=\"Ok\" BORDER=0>".
  1106.             "</FORM></TD>\n\n";
  1107.     }
  1108.  
  1109.     # Print a 'New Case' Button
  1110.     print "<TD ALIGN=CENTER>".
  1111.       "<FORM ACTION=\"$PROGNAME\" METHOD=\"GET\">\n". 
  1112.       "<INPUT TYPE=\"hidden\" NAME=\"func\" VALUE=\"$CASE_NEW\">\n".
  1113.       "<INPUT TYPE=\"image\" SRC=\"pict/menu_b_cnew.jpg\" ".
  1114.       "WIDTH=167 HEIGHT=20 ALT=\"New Case\" BORDER=0>\n".
  1115.       "</FORM></TD>".
  1116.  
  1117.     # Print a Menu Button
  1118.       "<TD ALIGN=CENTER>".
  1119.       "<FORM ACTION=\"$PROGNAME\" METHOD=\"GET\">\n". 
  1120.       "<INPUT TYPE=\"image\" SRC=\"pict/menu_b_menu.jpg\" ".
  1121.       "WIDTH=167 HEIGHT=20 ALT=\"Main Menu\" BORDER=0>\n".
  1122.       "</FORM></TD></TR></TABLE>\n";
  1123.  
  1124.     print 
  1125.       "<TABLE WIDTH=600 CELLSPACING=\"0\" CELLPADDING=\"2\">\n<TR>".
  1126.       "<TD> </TD>\n".
  1127.       "<TD ALIGN=CENTER WIDTH=200><A HREF=\"$HELP_URL\" ".
  1128.       " TARGET=\"_blank\">".
  1129.       "<IMG SRC=\"pict/menu_b_help.jpg\" ALT=\"Help\" ".
  1130.       "WIDTH=\"167\" HEIGHT=20 BORDER=0>".
  1131.       "</A></TD>".
  1132.       "<TD> </TD>\n".
  1133.       "</TR>\n".
  1134.       "</TABLE>";
  1135.  
  1136.     return;
  1137. };
  1138.  
  1139. # Log that a given case was opened and then proceed to open a host
  1140. $funcs[$CASE_OPEN_LOG] = sub {
  1141.     log_session_info ("Case $args{'case'} opened");
  1142.     log_case_info ("Case $args{'case'} opened");
  1143.     $args{'func'} = $enc_args{'func'} = $HOST_OPEN;
  1144.     & {$funcs[$HOST_OPEN]};
  1145. };
  1146.  
  1147. # Display Case Details
  1148. $funcs[$CASE_DETAILS] = sub {
  1149.     check_case();
  1150.  
  1151.     print_html_header("Details of $args{'case'}");
  1152.  
  1153.     my %cvals = read_case_config();
  1154.  
  1155.     $cvals{'desc'} = " " unless (exists $cvals{'desc'});
  1156.     $cvals{'created'} = " " unless (exists $cvals{'created'});
  1157.  
  1158.     print "<BR><BR>".
  1159.       "<CENTER>".
  1160.       "<IMG SRC=\"pict/menu_h_cdet.jpg\" ALT=\"Case Details\">".
  1161.       "<BR><BR><BR>\n".
  1162.       "<TABLE WIDTH=\"600\" CELLSPACING=\"0\" BACKGROUND=\"$YEL_PIX\" ".
  1163.       "CELLPADDING=\"2\" BORDER=0>\n".
  1164.       "  <TR><TD ALIGN=\"RIGHT\" WIDTH=300><B>Name:</B></TD>".
  1165.       "<TD ALIGN=\"LEFT\" WIDTH=300><TT>$args{'case'}</TT></TD></TR>\n".
  1166.  
  1167.       # Description
  1168.       "  <TR><TD ALIGN=\"RIGHT\"><B>Description:</B></TD>".
  1169.       "<TD ALIGN=\"LEFT\"><TT>$cvals{'desc'}</TT></TD></TR>\n".
  1170.       "  <TR><TD ALIGN=\"RIGHT\"><B>Created:</B></TD>".
  1171.       "<TD ALIGN=\"LEFT\"><TT>$cvals{'created'}</TT></TD></TR>\n".
  1172.  
  1173.       # Directories
  1174.       "  <TR><TD ALIGN=\"RIGHT\"><B>Directory:</B></TD>".
  1175.       "<TD ALIGN=\"LEFT\"><TT>$case_dir</TT></TD></TR>\n".
  1176.       "  <TR><TD COLSPAN=\"2\"> </TD></TR>\n".
  1177.       "  <TR><TD ALIGN=\"RIGHT\"><B>Images Dir:</B></TD>".
  1178.       "<TD ALIGN=\"LEFT\"><TT>$cvals{'images'}</TT></TD></TR>\n".
  1179.       "  <TR><TD ALIGN=\"RIGHT\"><B>Output Dir:</B></TD>".
  1180.       "<TD ALIGN=\"LEFT\"><TT>$cvals{'data'}</TT></TD></TR>\n".
  1181.       "  <TR><TD ALIGN=\"RIGHT\"><B>Report Dir:</B></TD>".
  1182.       "<TD ALIGN=\"LEFT\"><TT>$cvals{'reports'}</TT></TD></TR>\n".
  1183.       "  <TR><TD ALIGN=\"RIGHT\"><B>Log Dir:</B></TD>".
  1184.       "<TD ALIGN=\"LEFT\"><TT>$cvals{'log'}</TT></TD></TR>\n";
  1185.  
  1186.     # Display the valid investigators
  1187.     my @invs = read_invest();
  1188.     my $cnt = 0;
  1189.     print "  <TR><TD COLSPAN=\"2\"> </TD></TR>\n"
  1190.       if (scalar @invs > 0);
  1191.  
  1192.     foreach my $i (@invs) {
  1193.         if ($cnt == 0) {
  1194.             print "  <TR><TD ALIGN=\"RIGHT\"><B>Investigators:</B></TD>";
  1195.             $cnt++;
  1196.         } else {
  1197.             print "  <TR><TD> </TD>";
  1198.         }
  1199.         print "<TD ALIGN=\"LEFT\"><TT>$i</TT></TD></TR>\n";
  1200.     }
  1201.  
  1202.     print "</TABLE>\n".
  1203.       "<P><A HREF=\"$PROGNAME?func=$CASE_OPEN\">".
  1204.       "<IMG SRC=\"pict/menu_b_ok.jpg\" ALT=\"Ok\" ".
  1205.       "WIDTH=\"167\" HEIGHT=20 BORDER=\"0\"></A>";
  1206.  
  1207.     return;
  1208.  
  1209. };
  1210.  
  1211. ####################################################################
  1212. # Host Functions
  1213.  
  1214. $funcs[$HOST_ADD] = sub {
  1215.     print_html_header("Add A New Host To $args{'case'}");
  1216.  
  1217.     print "<B>Case: </B> $args{'case'}<BR><BR>\n";
  1218.  
  1219.     print "<CENTER>".
  1220.       "<IMG SRC=\"pict/menu_h_hnew.jpg\" ALT=\"Add Host\">".
  1221.       "<BR><BR><BR>\n";
  1222.  
  1223.     print "<TABLE WIDTH=\"600\" CELLSPACING=\"0\" BACKGROUND=\"$YEL_PIX\" ".
  1224.       "CELLPADDING=\"2\" BORDER=0>\n".
  1225.       "<FORM ACTION=\"$PROGNAME\" METHOD=\"GET\">\n".
  1226.       "<INPUT TYPE=\"hidden\" NAME=\"func\" VALUE=\"$HOST_ADD_DOIT\">\n".
  1227.       make_hidden().
  1228.       "<TR><TD COLSPAN=\"2\"> </TD></TR>".
  1229.       "<TR><TD ALIGN=\"right\">1.  Host Name (directory name):</TD>".
  1230.       "<TD ALIGN=\"left\"><INPUT TYPE=\"text\" NAME=\"host\"></TD></TR>\n".
  1231.       "<TR><TD ALIGN=\"right\">2.  Description (one line, optional):</TD>".
  1232.       "<TD ALIGN=\"left\">".
  1233.       "<INPUT TYPE=\"text\" NAME=\"desc\" SIZE=32 MAXLENGTH=32></TD></TR>\n".
  1234.       "<TR><TD COLSPAN=\"2\"> </TD></TR>".
  1235.       "<TR><TD ALIGN=\"right\">3.  Timezone:</TD>".
  1236.       "<TD ALIGN=\"left\">".
  1237.       "<INPUT TYPE=\"text\" NAME=\"tz\" SIZE=10 MAXLENGTH=16></TD></TR>\n".
  1238.       "<TR><TD ALIGN=\"right\">4.  Timeskew (in +/- seconds):</TD>".
  1239.       "<TD ALIGN=\"left\">".
  1240.       "<INPUT TYPE=\"text\" NAME=\"ts\" SIZE=8 MAXLENGTH=16 VALUE=\"0\">".
  1241.       "</TD></TR>\n".
  1242.       "<TR><TD COLSPAN=\"2\"> </TD></TR>".
  1243.       "<TR><TD ALIGN=\"right\">5.  Path of Alert Hash Database (optional)<BR>i.e. known bad files:</TD>".
  1244.       "<TD ALIGN=\"left\">".
  1245.       "<INPUT TYPE=\"text\" NAME=\"alert_db\" SIZE=32 MAXLENGTH=512>".
  1246.       "</TD></TR>\n".
  1247.       "<TR><TD ALIGN=\"right\">6.  Path of Ignore Hash Database (optional)<BR>i.e. known good files:</TD>".
  1248.       "<TD ALIGN=\"left\">".
  1249.       "<INPUT TYPE=\"text\" NAME=\"exclude_db\" SIZE=32 MAXLENGTH=512>".
  1250.       "</TD></TR>\n".
  1251.       "<TR><TD COLSPAN=\"2\"> </TD></TR>".
  1252.       "</TABLE>\n";
  1253.  
  1254.     # Ok Button
  1255.     print "<BR><BR><TABLE WIDTH=\"600\" CELLSPACING=\"8\" CELLPADDING=\"2\">\n".
  1256.       "<TR><TD ALIGN=CENTER>".
  1257.       "<INPUT TYPE=\"image\" SRC=\"pict/menu_b_hnew.jpg\" ".
  1258.       "WIDTH=167 HEIGHT=20 ALT=\"Add Host\" BORDER=0>\n".
  1259.       "</FORM></TD>\n".
  1260.  
  1261.     # Cancel Button
  1262.       "<TD ALIGN=CENTER>".
  1263.       "<FORM ACTION=\"$PROGNAME\" METHOD=\"GET\">\n". 
  1264.       "<INPUT TYPE=\"hidden\" NAME=\"func\" VALUE=\"$HOST_OPEN\">\n".
  1265.       "<INPUT TYPE=\"hidden\" NAME=\"case\" VALUE=\"$args{'case'}\">\n".
  1266.       "<INPUT TYPE=\"image\" SRC=\"pict/menu_b_cancel.jpg\" ".
  1267.       "ALT=\"Cancel\" WIDTH=\"167\" HEIGHT=20 BORDER=0>\n".
  1268.       "</FORM></TD>\n".
  1269.     # Help Button
  1270.       "<TD ALIGN=CENTER><A HREF=\"$HELP_URL\" ".
  1271.       "TARGET=\"_blank\">".
  1272.       "<IMG SRC=\"pict/menu_b_help.jpg\" ALT=\"Help\" ".
  1273.       "WIDTH=\"167\" HEIGHT=20 BORDER=0></A>".
  1274.       "</TD></TR>\n".
  1275.       "</TABLE>";
  1276.  
  1277.     return;
  1278.  
  1279. };
  1280.  
  1281.  
  1282. # Make the directories and config files for a host
  1283. $funcs[$HOST_ADD_DOIT] = sub {
  1284.     check_host(); check_tz(); check_ts();
  1285.     print_html_header("Adding Host $args{'host'} to $args{'case'}");
  1286.  
  1287.     print "<H3>Adding host: <TT>$args{'host'}</TT> to ".
  1288.       "case <TT>$args{'case'}</TT></H3>\n";
  1289.  
  1290.     # Do some sanity checks before we start making the directories and such
  1291.     if ((exists $args{'alert_db'}) && ($args{'alert_db'} ne "")) {
  1292.  
  1293.         unless ($args{'alert_db'} =~ /^$REG_HASHDB$/o) {
  1294.             print "Invalid Alert Database path\n". 
  1295.               "<P><A HREF=\"$PROGNAME?func=$HOST_ADD&case=$args{'case'}\">".
  1296.               "<IMG SRC=\"pict/but_ok.jpg\" ALT=\"Ok\" ".
  1297.               "WIDTH=\"43\" HEIGHT=20 BORDER=\"0\"></A>\n";
  1298.             return 1;
  1299.         }
  1300.  
  1301.         unless (-e "$args{'alert_db'}") {
  1302.             print "Alert Database Not Found: $args{'alert_db'}".
  1303.               "<P><A HREF=\"$PROGNAME?func=$HOST_ADD&case=$args{'case'}\">".
  1304.               "<IMG SRC=\"pict/but_ok.jpg\" ALT=\"Ok\" ".
  1305.               "WIDTH=\"43\" HEIGHT=20 BORDER=\"0\"></A>\n";
  1306.             return 1;
  1307.         }
  1308.     }
  1309.  
  1310.     if ((exists $args{'exclude_db'}) && ($args{'exclude_db'} ne "")) {
  1311.         unless ($args{'exclude_db'} =~ /^$REG_HASHDB$/o) {
  1312.             print "Invalid Exclude Database path\n". 
  1313.               "<P><A HREF=\"$PROGNAME?func=$HOST_ADD&case=$args{'case'}\">".
  1314.               "<IMG SRC=\"pict/but_ok.jpg\" ALT=\"Ok\" ".
  1315.               "WIDTH=\"43\" HEIGHT=20 BORDER=\"0\"></A>\n";
  1316.             return 1;
  1317.         }
  1318.  
  1319.         unless (-e "$args{'exclude_db'}") {
  1320.             print "Exclude Database Not Found: $args{'exclude_db'}".
  1321.               "<P><A HREF=\"$PROGNAME?func=$HOST_ADD&case=$args{'case'}\">".
  1322.               "<IMG SRC=\"pict/but_ok.jpg\" ALT=\"Ok\" ".
  1323.               "WIDTH=\"43\" HEIGHT=20 BORDER=\"0\"></A>\n";
  1324.             return 1;
  1325.         }
  1326.     }
  1327.  
  1328.     # Make the directory
  1329.     if (-d "$host_dir") {
  1330.         print_err ("Error: $host_dir already exists<BR>Please remove the ".
  1331.           "directory and its contents and try again");
  1332.     }
  1333.     unless (mkdir $host_dir, $MKDIR_MASK) {
  1334.         print_err ("Error making directory $host_dir: $!");
  1335.     }
  1336.  
  1337.     print "Host Directory (<TT>$host_dir</TT>) created<P>\n";
  1338.     log_case_info ("Host $args{'host'} added to case");
  1339.  
  1340.     # @@@ READ CASE CONFIG FOR DIR NAMES
  1341.     # Images directory
  1342.     unless (mkdir "${host_dir}$IMGDIR", $MKDIR_MASK) {
  1343.         rmdir "${host_dir}";
  1344.         print_err ("Error making ${host_dir}$IMGDIR");
  1345.     }
  1346.     # Output Directory
  1347.     unless (mkdir "${host_dir}$DATADIR", $MKDIR_MASK) {
  1348.         rmdir "${host_dir}$IMGDIR";
  1349.         rmdir "${host_dir}";
  1350.         print_err ("Error making ${host_dir}$DATADIR");
  1351.     }
  1352.     # Log Directory
  1353.     unless (mkdir "${host_dir}$LOGDIR", $MKDIR_MASK) {
  1354.         rmdir "${host_dir}$DATADIR";
  1355.         rmdir "${host_dir}$IMGDIR";
  1356.         rmdir "${host_dir}";
  1357.         print_err ("Error making ${host_dir}$LOGDIR");
  1358.     }
  1359.     # Reports directory
  1360.     unless (mkdir "${host_dir}$REPDIR", $MKDIR_MASK) {
  1361.         rmdir "${host_dir}$LOGDIR";
  1362.         rmdir "${host_dir}$DATADIR";
  1363.         rmdir "${host_dir}$IMGDIR";
  1364.         rmdir "${host_dir}";
  1365.         print_err ("Error making ${host_dir}$REPDIR");
  1366.     }
  1367.     # Make a directory for mounting the image in loopback
  1368.     unless (mkdir "${host_dir}mnt", $MKDIR_MASK) {
  1369.         rmdir "${host_dir}$REPDIR";
  1370.         rmdir "${host_dir}$LOGDIR";
  1371.         rmdir "${host_dir}$DATADIR";
  1372.         rmdir "${host_dir}$IMGDIR";
  1373.         rmdir "${host_dir}";
  1374.         print_err ("Error making ${host_dir}mnt");
  1375.     }
  1376.  
  1377.     log_host_info ("Host $args{'host'} added to case $args{'case'}");
  1378.  
  1379.     # Create config file
  1380.     my $fname = host_config_fname();
  1381.     open HOST_CONFIG, ">$fname" or die "Can't open host config: $fname";
  1382.  
  1383.     print HOST_CONFIG "# Autopsy host config file\n".
  1384.       "# Case: $args{'case'}        Host: $args{'host'}\n".
  1385.       "# Created: ".localtime()."\n\n";
  1386.  
  1387.     if ((exists $args{'desc'}) && ($args{'desc'} ne "")) {
  1388.         print_err ("Invalid Description") if ($args{'desc'} =~ /\n/);
  1389.  
  1390.         print HOST_CONFIG "desc $args{'desc'}\n";
  1391.     }
  1392.  
  1393.     print HOST_CONFIG "timezone  ".get_tz()."\n";
  1394.     print HOST_CONFIG "timeskew  ".get_ts()."\n";
  1395.  
  1396.  
  1397.     if ((exists $args{'alert_db'}) && ($args{'alert_db'} ne "")) {
  1398.  
  1399.         # Index it if it is not
  1400.         unless (-e "$args{'alert_db'}-md5.idx") {
  1401.             print "Alert Database has not been indexed - it will be as an md5sum file<BR>\n";
  1402.  
  1403.             print "<HR>\n";
  1404.             hash_index_md5sum ($args{'alert_db'});
  1405.             print "<HR>\n";
  1406.         }
  1407.  
  1408.         # only print it if it was successful
  1409.         print HOST_CONFIG "alert_db \'$args{'alert_db'}\'\n"
  1410.           if (-e "$args{'alert_db'}-md5.idx");
  1411.     } 
  1412.  
  1413.     if ((exists $args{'exclude_db'}) && ($args{'exclude_db'} ne "")) {
  1414.         # Index it if it is not
  1415.         unless (-e "$args{'exclude_db'}-md5.idx") {
  1416.             print "Exclude Database has not been indexed - it will be as an md5sum file<BR>\n";
  1417.  
  1418.             print "<HR>\n";
  1419.             local *OUT;
  1420.             exec_pipe(*OUT, "'${TASKDIR}hfind' -i md5sum '$args{'exclude_db'}'");
  1421.             print "$_<BR>" while (<OUT>); 
  1422.             close (OUT);
  1423.             print "<HR>\n";
  1424.         }
  1425.  
  1426.         # only print it if it was successful
  1427.         print HOST_CONFIG "exclude_db \'$args{'exclude_db'}\'\n"
  1428.           if (-e "$args{'exclude_db'}-md5.idx");
  1429.     }
  1430.  
  1431.     close HOST_CONFIG;
  1432.  
  1433.     print "Configuration file (<TT>$fname</TT>) created<BR><BR>\n";
  1434.  
  1435.     print "<A HREF=\"$PROGNAME?func=$HOST_OPEN&case=$args{'case'}\">".
  1436.       "<IMG SRC=\"pict/but_ok.jpg\" ALT=\"Ok\" ".
  1437.       "WIDTH=\"43\" HEIGHT=20 BORDER=\"0\"></A>\n";
  1438.  
  1439.     return;
  1440. };
  1441.  
  1442. # Open a host in the given case
  1443. $funcs[$HOST_OPEN] = sub {
  1444.     print_html_header("Open Host In $args{'case'}");
  1445.  
  1446.     print_menu_tabs();
  1447.  
  1448.     print "<TABLE WIDTH=\"600\" CELLSPACING=\"0\" CELLPADDING=\"2\" ".
  1449.       "BACKGROUND=\"$YEL_PIX\" BORDER=0>\n";
  1450.  
  1451.     # Create an array of directories in the case, verifying that there is
  1452.     # a config file
  1453.     my @hosts;
  1454.     opendir HOSTS, $case_dir or die "Can't open $case_dir directory: $!";
  1455.     foreach my $h (readdir HOSTS) {
  1456.         next if (($h eq '.') || ($h eq '..'));
  1457.  
  1458.         my $hfile = host_config_fname($h);
  1459.         push @hosts, $h
  1460.             if ((-d "${case_dir}$h") && (-e "$hfile"));
  1461.     }
  1462.     closedir HOSTS;
  1463.  
  1464.     if (scalar @hosts == 0) {
  1465.         print "<TR><TD COLSPAN=\"4\" ALIGN=CENTER>".
  1466.           "No hosts have been added to case yet".
  1467.           "</TD></TR></TABLE>\n";
  1468.     }
  1469.     else {
  1470.         print "<FORM ACTION=\"$PROGNAME\" METHOD=\"GET\">\n".
  1471.           "<INPUT TYPE=\"hidden\" NAME=\"func\" VALUE=\"$HOST_OPEN_LOG\">\n".
  1472.           make_hidden().
  1473.           "<TR><TH>Name</TH>".
  1474.           "<TH>Description</TH><TH> </TH></TR>\n";
  1475.  
  1476.  
  1477.         my $first = 0;
  1478.         foreach my $h (@hosts) {
  1479.  
  1480.             print "<TR><TD ALIGN=\"left\">".
  1481.               "<INPUT TYPE=\"radio\" NAME=\"host\" VALUE=$h";
  1482.             if ($first == 0) {
  1483.                 print " CHECKED";
  1484.                 $first = 1;
  1485.             }
  1486.             print "> $h </TD>";
  1487.  
  1488.             my $fname = host_config_fname($h);
  1489.             open CONFIG, "<$fname" or die "Can't open host config file ($fname)";
  1490.  
  1491.             my $desc = "None Provided";
  1492.             while (<CONFIG>) {
  1493.                 s/^\s+//;
  1494.                 s/\s+$//;
  1495.  
  1496.                 if (/^desc\s+(.*)$/) {
  1497.                     $desc = $1; 
  1498.                     last;
  1499.                 }
  1500.             }
  1501.             close CONFIG;
  1502.  
  1503.             print "<TD ALIGN=left>$desc</TD>".
  1504.               "<TD ALIGN=center>".
  1505.               "<A HREF=\"$PROGNAME?func=$HOST_DETAILS&$baseargs&".
  1506.               "host=$h\">details</A></TD></TR>\n";
  1507.         }
  1508.         print "</TABLE>\n";
  1509.  
  1510.  
  1511.         # Display pulldown of investigators
  1512.         print "<BR>Investigator (for reports only): ";
  1513.         my @invs = read_invest();
  1514.         if (scalar @invs == 0) {
  1515.               print "None Provided<BR>\n".
  1516.               "<INPUT TYPE=\"hidden\" NAME=\"inv\" VALUE=\"unknown\">\n";
  1517.         }
  1518.         else {
  1519.             my $cur_inv = "";
  1520.             $cur_inv = $args{'inv'} if (exists $args{'inv'});
  1521.  
  1522.               print "<SELECT NAME=\"inv\" SIZE=\"1\">\n";
  1523.  
  1524.             if (($cur_inv eq "") && (scalar @invs != 1)) {
  1525.                 print "<OPTION VALUE=\"\" SELECTED>Select One".
  1526.                   "</OPTION>\n";
  1527.             }
  1528.             foreach my $i (@invs) {
  1529.                 print "<OPTION VALUE=\"$i\"";
  1530.                 print " SELECTED" if ($cur_inv eq $i);
  1531.                 print ">$i</OPTION>\n";
  1532.             }
  1533.             print "</SELECT>\n";
  1534.         }
  1535.  
  1536.     }
  1537.     print "<BR><BR><TABLE WIDTH=\"600\" CELLSPACING=\"0\" CELLPADDING=\"2\">\n".
  1538.       "<TR>\n";
  1539.  
  1540.     # Make a table for the buttons.  The table will either be 3 or 2 
  1541.     # entries wide, depending on if there is an 'Ok' button or not
  1542.  
  1543.     unless (scalar @hosts == 0) {
  1544.         print "<TD ALIGN=CENTER>".
  1545.             "<INPUT TYPE=\"image\" SRC=\"pict/menu_b_ok.jpg\" ".
  1546.             "ALT=\"Ok\" WIDTH=\"167\" HEIGHT=20 BORDER=0>\n".
  1547.           "</FORM>\n</TD>\n";
  1548.     }
  1549.  
  1550.     # Add Host
  1551.     print "<TD ALIGN=CENTER>".
  1552.       "<FORM ACTION=\"$PROGNAME\" METHOD=\"GET\">\n". 
  1553.       "<INPUT TYPE=\"hidden\" NAME=\"func\" VALUE=\"$HOST_ADD\">\n".
  1554.       "<INPUT TYPE=\"hidden\" NAME=\"case\" VALUE=\"$args{'case'}\">\n".
  1555.       "<INPUT TYPE=\"image\" SRC=\"pict/menu_b_hnew.jpg\" ".
  1556.         "ALT=\"Add Host\" WIDTH=\"176\" HEIGHT=20 BORDER=0>\n".
  1557.       "</FORM></TD>".
  1558.  
  1559.     # Close Button
  1560.       "<TD ALIGN=CENTER>".
  1561.       "<FORM ACTION=\"$PROGNAME\" METHOD=\"GET\">\n". 
  1562.       "<INPUT TYPE=\"hidden\" NAME=\"func\" VALUE=\"$CASE_OPEN\">\n".
  1563.       "<INPUT TYPE=\"image\" SRC=\"pict/menu_b_ccls.jpg\" ".
  1564.         "ALT=\"Close Case\" WIDTH=\"176\" HEIGHT=20 BORDER=0>\n".
  1565.       "</FORM></TD></TR></TABLE>\n";
  1566.  
  1567.     print 
  1568.       "<TABLE WIDTH=\"600\"  CELLSPACING=\"0\" CELLPADDING=\"2\">\n".
  1569.       "<TR><TD> </TD>".
  1570.       "<TD ALIGN=CENTER><A HREF=\"$HELP_URL\" ".
  1571.       " TARGET=\"_blank\">".
  1572.       "<IMG SRC=\"pict/menu_b_help.jpg\" ALT=\"Help\" ".
  1573.       "WIDTH=\"167\" HEIGHT=20 BORDER=0>".
  1574.       "</A></TD><TD> </TD></TR>\n".
  1575.       "</TABLE>\n";
  1576.  
  1577.     return;
  1578. };
  1579.  
  1580. # Log that a given host was opened and then proceed to open an image
  1581. $funcs[$HOST_OPEN_LOG] = sub {
  1582.     unless ((exists $args{'inv'}) && ($args{'inv'} ne "")) {
  1583.         print_html_header("Missing Investigator");
  1584.         print "<BR>An investigator must be selected<P>\n".
  1585.           "<FORM ACTION=\"$PROGNAME\" METHOD=\"GET\">\n".
  1586.           "<INPUT TYPE=\"hidden\" NAME=\"func\" VALUE=\"$HOST_OPEN_LOG\">\n".
  1587.           make_hidden();
  1588.  
  1589.         print "Select one of the following:";       
  1590.         my @invs = read_invest();
  1591.         print "<SELECT NAME=\"inv\" SIZE=\"1\">\n";
  1592.  
  1593.         print "<OPTION VALUE=\"\" SELECTED>Select One".
  1594.           "</OPTION>\n";
  1595.  
  1596.         foreach my $i (@invs) {
  1597.             print "<OPTION VALUE=\"$i\">$i</OPTION>\n";
  1598.         }
  1599.         print "</SELECT><P>\n".
  1600.           "<INPUT TYPE=\"IMAGE\" SRC=\"pict/but_ok.jpg\" ALT=\"Ok\" ".
  1601.           "WIDTH=43 HEIGHT=20 BORDER=\"0\">\n".
  1602.           "</FORM>\n";
  1603.  
  1604.         return;
  1605.     }
  1606.  
  1607.     check_inv();
  1608.     log_case_info ("Host $args{'host'} opened by $args{'inv'}");
  1609.     log_host_info ("Host $args{'host'} opened by $args{'inv'}");
  1610.     log_host_inv  ("Host $args{'host'} opened");
  1611.     $args{'func'} = $enc_args{'func'} = $IMG_OPEN;
  1612.     & {$funcs[$IMG_OPEN]};
  1613. };
  1614.  
  1615. # Provide details about the configuration of a host.  This window is
  1616. # a link from the HOST_OPEN window
  1617. $funcs[$HOST_DETAILS] = sub {
  1618.     print_html_header("Details of $args{'case'}:$args{'host'}");
  1619.  
  1620.     print "<B>Case: </B>$args{'case'}<BR><BR>".
  1621.       "<CENTER>".
  1622.       "<IMG SRC=\"pict/menu_h_hdet.jpg\" ALT=\"Host Details\">".
  1623.       "<BR><BR><BR>\n".
  1624.       "<TABLE WIDTH=\"600\" CELLSPACING=\"0\" CELLPADDING=\"2\" ".
  1625.       "BACKGROUND=\"$YEL_PIX\" BORDER=0>\n".
  1626.       # Name
  1627.       "<TR><TD ALIGN=\"RIGHT\" WIDTH=300><B>Name:</B></TD>".
  1628.       "<TD ALIGN=\"LEFT\" WIDTH=300><TT>$args{'host'}</TT></TD></TR>\n".
  1629.       # Description
  1630.       "<TR><TD ALIGN=\"RIGHT\"><B>Description:</B></TD>".
  1631.       "<TD ALIGN=\"LEFT\"><TT>".
  1632.       (($host_desc ne "") ? $host_desc : " ").
  1633.       "</TT></TD></TR>\n".
  1634.       # Timezone
  1635.       "<TR><TD ALIGN=\"RIGHT\"><B>Timezone: </B></TD>".
  1636.       "<TD ALIGN=\"LEFT\"><TT>$tz</TT></TD></TR>\n".
  1637.       # Timeskew
  1638.       "<TR><TD ALIGN=\"RIGHT\"><B>Timeskew:</B></TD>".
  1639.       "<TD ALIGN=\"LEFT\"><TT>$ts</TT></TD></TR>\n".
  1640.       "<TR><TD COLSPAN=2> </TD></TR>\n".
  1641.       # Actual Directory
  1642.       "<TR><TD ALIGN=\"RIGHT\"><B>Directory:</B></TD>".
  1643.       "<TD ALIGN=\"LEFT\"><TT>$host_dir</TT></TD></TR>\n".
  1644.       "<TR><TD COLSPAN=2> </TD></TR>\n".
  1645.       # Alert Database
  1646.       "<TR><TD ALIGN=\"RIGHT\"><B>Alert Hash Database:</B></TD>".
  1647.       "<TD ALIGN=\"LEFT\"><TT>".
  1648.       (($alert_db ne "") ? $alert_db : " ").
  1649.       "</TT></TD></TR>\n".
  1650.       # Exclude Database
  1651.       "<TR><TD ALIGN=\"RIGHT\"><B>Exclude Hash Database:</B></TD>".
  1652.       "<TD ALIGN=\"LEFT\"><TT>".
  1653.       (($exclude_db ne "") ? $exclude_db : " ").
  1654.       "</TT></TD></TR>\n".
  1655.       "</TABLE>\n";
  1656.  
  1657.     # Final Button
  1658.     print "<BR><BR><FORM ACTION=\"$PROGNAME\" METHOD=\"GET\">\n". 
  1659.       "<INPUT TYPE=\"hidden\" NAME=\"func\" VALUE=\"$HOST_OPEN\">\n".
  1660.       make_hidden().
  1661.       "<INPUT TYPE=\"IMAGE\" SRC=\"pict/menu_b_ok.jpg\" ".
  1662.       "ALT=\"Ok\" WIDTH=\"167\" HEIGHT=20 BORDER=\"0\">\n</FORM>";
  1663.  
  1664.  
  1665.     return;
  1666. };
  1667.  
  1668.  
  1669. ####################################################################
  1670. # Image Functions
  1671.  
  1672. # Open an image that has been configured
  1673. $funcs[$IMG_OPEN] = sub {
  1674.     print_html_header("Open Image In $args{'case'}:$args{'host'}");
  1675.  
  1676.     print_menu_tabs();
  1677.  
  1678.     print "<TABLE WIDTH=\"600\" CELLSPACING=\"0\" CELLPADDING=\"2\" ".
  1679.       "BACKGROUND=\"$YEL_PIX\" BORDER=0>\n";
  1680.  
  1681.     # the images have been loaded from reading the host config file in
  1682.     # autopsy_main
  1683.     if (scalar (keys %img2ftype) == 0) {
  1684.         print "</TABLE>No images have been added to this host yet<BR>\n";
  1685.         goto EGRESS;
  1686.     }
  1687.  
  1688.     # We want to sort by mounting point, so rearrange the hash
  1689.     my %mnt2img;
  1690.  
  1691.     # Cycle through each image we read from the host config
  1692.     foreach my $i (keys %img2ftype) {
  1693.         next if (($img2ftype{$i} eq "dls") || ($img2ftype{$i} eq "strings") ||
  1694.           ($img2ftype{$i} eq "body") || ($img2ftype{$i} eq "timeline") );
  1695.  
  1696.  
  1697.         if (($img2ftype{$i} eq "raw") || ($img2ftype{$i} eq "swap")) {
  1698.             $mnt2img{"$img2ftype{$i}--AUTOPSY--$i"} = $i;
  1699.         }
  1700.         else {
  1701.             $mnt2img{"$img2mnt{$i}--AUTOPSY--$i"} = $i;
  1702.         }
  1703.     }
  1704.  
  1705.     # sort via mount point (which includes the name)
  1706.     my @mnt = sort {
  1707.         lc($a) cmp lc($b)
  1708.     } keys %mnt2img;
  1709.  
  1710.  
  1711.     # It is possible to have only the dls image and not the original
  1712.     # We need to search for those now because they will not be in the
  1713.     # list that we just made (which are arranged via mount point)
  1714.     my @orphan_dls;
  1715.  
  1716.     # cycle through each image and check its type and original
  1717.     foreach my $k (keys %img2ftype) {
  1718.         if (($img2ftype{$k} eq "dls") && (!defined $mod2img{$k})) {
  1719.             push @orphan_dls, $k;
  1720.         } 
  1721.     }
  1722.  
  1723.  
  1724.     print "<FORM ACTION=\"$PROGNAME\" METHOD=\"GET\" TARGET=\"_top\">\n".
  1725.       "<INPUT TYPE=\"hidden\" NAME=\"func\" VALUE=\"$IMG_OPEN_LOG\">\n".
  1726.       make_hidden().
  1727.       "<TR><TH ALIGN=LEFT>mount</TH>".                    # mnt
  1728.       "<TH> </TH>".    # img button and unalloc
  1729.       "<TH ALIGN=LEFT>name</TH><TH> </TH></TR>\n";        # img name
  1730.  
  1731.     for (my $i = 0; $i <= $#mnt; $i++) {
  1732.         print "<TR>";
  1733.  
  1734.         my $img = $mnt2img{$mnt[$i]};
  1735.  
  1736.         # Mount Point
  1737.         # If we have the dummy string at the end of the duplicate
  1738.         # entry, then take it off and print the original
  1739.         $mnt[$i] = $1 if ($mnt[$i] =~ /^(.*?)--AUTOPSY--$REG_IMG$/o);
  1740.         print "<TD><TT>$mnt[$i]</TT></TD>";
  1741.  
  1742.         # Image button
  1743.         print "<TD><INPUT TYPE=\"radio\" ".
  1744.           "NAME=\"img\" VALUE=$img";
  1745.         print " CHECKED" if ($i == 0);    
  1746.         print ">";
  1747.  
  1748.         # if there is a corresponding dls entry, make an unalloc button
  1749.         if (defined $img2dls{$img}) {
  1750.             print " (<INPUT TYPE=\"radio\" NAME=\"img\" ".
  1751.               "VALUE=$img2dls{$img}> unalloc)</TD>";
  1752.         } else {
  1753.             print "</TD>";
  1754.         }
  1755.  
  1756.  
  1757.         # image name and ftype
  1758.         print "<TD><TT>$img</TT></TD>".
  1759.           "<TD ALIGN=center><A HREF=\"$PROGNAME?func=$IMG_DETAILS&$baseargs&".
  1760.           "img=$img&mnt=$mnt[$i]\">details</A></TD>".
  1761.           "</TR>\n";
  1762.     }
  1763.         
  1764.     # If we are done with the regular images and have some orphan
  1765.     # dls images, print them
  1766.     my @sort  = sort @orphan_dls;
  1767.     for (my $i = 0; $i <= $#sort; $i++) {
  1768.         print "<TR><TD> </TD><TD> </TD><TD>(<INPUT TYPE=\"radio\" NAME=\"img\" ".
  1769.               "VALUE=$sort[$i]";
  1770.         print " CHECKED" if ($#mnt == 0);    
  1771.         print "> unalloc)</TD><TD><TT>$sort[$i]</TT></TD></TR>\n";
  1772.     }
  1773.  
  1774.     # Begin Button
  1775.     print "</TABLE>\n";
  1776.  
  1777. EGRESS:
  1778.  
  1779.     print "<BR><BR>".
  1780.       "<TABLE WIDTH=\"600\" CELLSPACING=\"0\" CELLPADDING=\"2\"><TR>\n";
  1781.  
  1782.     my $width = 300;
  1783.     unless (scalar (keys %img2ftype) == 0) {
  1784.         $width = 200;
  1785.         print "<TD ALIGN=CENTER WIDTH=$width>".
  1786.           "<INPUT TYPE=\"image\" SRC=\"pict/menu_b_ok.jpg\" ".
  1787.           "ALT=\"Ok\" WIDTH=\"167\" HEIGHT=20 BORDER=0>\n".
  1788.           "</FORM></TD>\n";
  1789.     }
  1790.  
  1791.     print "<TD ALIGN=CENTER WIDTH=$width>".
  1792.       "<FORM ACTION=\"$PROGNAME\" METHOD=\"GET\">\n". 
  1793.       "<INPUT TYPE=\"hidden\" NAME=\"func\" VALUE=\"$IMG_ADD\">\n".
  1794.       make_hidden().
  1795.       "<INPUT TYPE=\"image\" SRC=\"pict/menu_b_inew.jpg\" ".
  1796.         "ALT=\"Add Image\" WIDTH=167 HEIGHT=20 BORDER=0></FORM></TD>\n".
  1797.       "<TD ALIGN=CENTER WIDTH=$width>".
  1798.       "<FORM ACTION=\"$PROGNAME\" METHOD=\"GET\">\n". 
  1799.       "<INPUT TYPE=\"hidden\" NAME=\"func\" VALUE=\"$HOST_OPEN\">\n".
  1800.       "<INPUT TYPE=\"hidden\" NAME=\"case\" VALUE=\"$args{'case'}\">\n".
  1801.       "<INPUT TYPE=\"image\" SRC=\"pict/menu_b_hcls.jpg\" ".
  1802.         "WIDTH=167 HEIGHT=20 ALT=\"Close Host\" BORDER=0>\n".
  1803.       "</FORM></TD></TR>\n</TABLE>\n";
  1804.  
  1805.     print 
  1806.       "<TABLE WIDTH=\"600\" CELLSPACING=\"0\" CELLPADDING=\"2\">\n".
  1807.       "<TR><TD> </TD>\n".
  1808.       "<TD ALIGN=CENTER WIDTH=200><A HREF=\"$HELP_URL\" ".
  1809.       " TARGET=\"_blank\">".
  1810.       "<IMG SRC=\"pict/menu_b_help.jpg\" ALT=\"Help\" ".
  1811.       "WIDTH=\"167\" HEIGHT=20 BORDER=0>".
  1812.       "</A></TD><TD> </TD></TR>\n".
  1813.       "</TABLE>\n";
  1814.  
  1815.     # Other features that can be done on a host
  1816.  
  1817.     print "<HR><P>".
  1818.       "<TABLE WIDTH=\"600\" CELLSPACING=\"0\" CELLPADDING=\"2\">\n".
  1819.       "<TR>\n";
  1820.  
  1821.  
  1822.     # Timeline of file activity
  1823.     print "<TD ALIGN=\"CENTER\" WIDTH=200>".
  1824.       "<A HREF=\"$PROGNAME?${baseargs_noimg}&func=$TL_MAIN\">".
  1825.       "<IMG BORDER=0 ".
  1826.       "SRC=\"pict/menu_b_tl.jpg\" ".
  1827.       "WIDTH=\"167\" HEIGHT=20 ".
  1828.       "ALT=\"File Activity Timelines\"></A></TD>\n";
  1829.  
  1830.     # verify the integrity of the images
  1831.     print "<TD ALIGN=\"CENTER\" WIDTH=200>".
  1832.       "<A HREF=\"$PROGNAME?${baseargs_noimg}&func=$INT_LIST_FR\">".
  1833.       "<IMG BORDER=0 ".
  1834.       "SRC=\"pict/menu_b_int.jpg\" ".
  1835.       "WIDTH=\"167\" HEIGHT=20 ".
  1836.       "ALT=\"Image Integrity\"></A></TD>\n".
  1837.  
  1838.       "<TD ALIGN=\"CENTER\" WIDTH=200>".
  1839.       "<A HREF=\"$PROGNAME?${baseargs_noimg}&func=$HASH_MAIN\">".
  1840.       "<IMG BORDER=0 ".
  1841.       "SRC=\"pict/menu_b_hashdb.jpg\" ".
  1842.       "WIDTH=\"167\" HEIGHT=20 ".
  1843.       "ALT=\"Hash Databases\"></A></TD>\n".
  1844.       "</TR></TABLE>\n";
  1845.  
  1846.     # Notes 
  1847.     if ($USE_NOTES == 1) {
  1848.         print 
  1849.           "<TABLE WIDTH=\"600\" CELLSPACING=\"0\" CELLPADDING=\"2\">\n".
  1850.           "<TR>\n".
  1851.           "<TD ALIGN=\"CENTER\" WIDTH=300>".
  1852.           "<A HREF=\"$PROGNAME?${baseargs_noimg}&func=$NOTES_READ\">".
  1853.           "<IMG BORDER=0 ".
  1854.           "SRC=\"pict/menu_b_note.jpg\" ".
  1855.           "WIDTH=\"167\" HEIGHT=20 ".
  1856.           "ALT=\"View Notes\"></A></TD>\n".
  1857.  
  1858.           "<TD WIDTH=300 ALIGN=\"CENTER\">".
  1859.           "<A HREF=\"$PROGNAME?${baseargs_noimg}&func=$NOTES_SEQ_READ\">".
  1860.           "<IMG BORDER=0 ".
  1861.           "SRC=\"pict/menu_b_seq.jpg\" ".
  1862.           "WIDTH=\"167\" HEIGHT=20 ".
  1863.           "ALT=\"Event Sequencer\"></A></TD>\n".
  1864.  
  1865.           "</TR>\n".
  1866.           "</TABLE>\n";
  1867.     }
  1868.  
  1869.  
  1870.     # check if the permissions are ok
  1871.     # if (((stat("$host_dir/$IMGDIR"))[2]) & 0000222) {
  1872.     #    print "<BR><BR><BR>".
  1873.     #      "<FONT COLOR=\"$DEL_COLOR[0]\">".
  1874.     #      "NOTE: The images directory allows for writes.<BR> It is ".
  1875.     #      "recommended that these permissions be turned off</FONT><BR>\n"; 
  1876.     #}
  1877.  
  1878.  
  1879.     return;
  1880. };
  1881.  
  1882. # Log in the host log that a given image was opened by what user
  1883. # then open the main window
  1884. $funcs[$IMG_OPEN_LOG] = sub {
  1885.     log_host_info ("Image $args{'img'} opened by $args{'inv'}");
  1886.     log_host_inv ("$args{'img'}: Image opened");
  1887.     $args{'func'} = $enc_args{'func'} = $MAIN_FR;
  1888.     & {$funcs[$MAIN_FR]};
  1889. };
  1890.  
  1891.  
  1892. my $MD5_NOTHING = 1;
  1893. my $MD5_CALC = 2;
  1894. my $MD5_ADD = 3;
  1895.  
  1896. # Menu to add a new image to the host
  1897. #
  1898. # The list of new images is determined by looking in the images directory
  1899. # and seeing which is not yet configured
  1900. #
  1901. $funcs[$IMG_ADD] = sub {
  1902.     print_html_header("Add Image To $args{'case'}:$args{'host'}");
  1903.  
  1904.     print "<B>Case:</B> $args{'case'}<BR>\n".
  1905.       "<B>Host:</B> $args{'host'}<BR>\n";
  1906.  
  1907.     print "<FORM ACTION=\"$PROGNAME\" METHOD=\"GET\" TARGET=\"_top\">\n".
  1908.       "<INPUT TYPE=\"hidden\" NAME=\"func\" VALUE=\"$IMG_ADD_DOIT\">\n".
  1909.       make_hidden();
  1910.  
  1911. print <<EOF1;
  1912. <CENTER>
  1913. <IMG SRC=\"pict/menu_h_inew.jpg\" ALT=\"Add Image\">
  1914. <BR><BR><BR>
  1915.  
  1916. <TABLE WIDTH=\"600\" CELLPADDING=\"2\" CELLSPACING=\"0\" BACKGROUND=\"$YEL_PIX\" BORDER=0>
  1917. <TR>
  1918.   <TD COLSPAN=2> </TD>
  1919. </TR>
  1920. <TR>
  1921.   <TD ALIGN=CENTER COLSPAN=2>
  1922.     <B>Image Details</B>
  1923.   </TD>
  1924. </TR>
  1925. <TR>
  1926.   <TD WIDTH=300 ALIGN=RIGHT>Location (starting with /): </TD>
  1927.   <TD WIDTH=300 ALIGN=LEFT>
  1928.     <INPUT TYPE=\"text\" NAME=\"img_path\" SIZE=36 MAXLENGTH=256>
  1929.   </TD>
  1930. </TR>
  1931. <TR>
  1932.   <TD WIDTH=300 ALIGN=RIGHT>Import Method:</TD>
  1933.   <TD WIDTH=300 ALIGN=LEFT>
  1934.     <INPUT TYPE=\"radio\" NAME=\"sort\" VALUE=$IMG_ADD_SYM CHECKED>
  1935.       Symlink to Evidence Locker
  1936.   </TD>
  1937. </TR>
  1938. <TR>
  1939.   <TD WIDTH=300 ALIGN=RIGHT> </TD>
  1940.   <TD WIDTH=300 ALIGN=LEFT>
  1941.     <INPUT TYPE=\"radio\" NAME=\"sort\" VALUE=$IMG_ADD_COPY>
  1942.       Copy to Evidence Locker
  1943.   </TD>
  1944. </TR>
  1945. <TR>
  1946.   <TD WIDTH=300 ALIGN=RIGHT> </TD>
  1947.   <TD WIDTH=300 ALIGN=LEFT>
  1948.     <INPUT TYPE=\"radio\" NAME=\"sort\" VALUE=$IMG_ADD_MOVE>
  1949.       Move to Evidence Locker (<FONT COLOR="red">Warning</FONT>: image loss could occur during a system failure)
  1950.   </TD>
  1951. </TR>
  1952.  
  1953. EOF1
  1954.  
  1955.     # Show the file system types that we know of
  1956.     print "<TR><TD ALIGN=RIGHT>File System Type: </TD>".
  1957.       "<TD ALIGN=LEFT><SELECT NAME=\"ftype\">\n";
  1958.     foreach my $fs (sort keys %root_inode) {
  1959.         print "<OPTION VALUE=\"$fs\">$fs</OPTION>\n";
  1960.     }
  1961.     
  1962.     # The following do not have 'inodes' but should be in the list
  1963.     print "<OPTION VALUE=\"\">======</OPTION>\n";
  1964.     print "<OPTION VALUE=\"raw\">raw</OPTION>\n";
  1965.     print "<OPTION VALUE=\"swap\">swap</OPTION>\n";
  1966.  
  1967.     print "</SELECT></TD></TR>\n";
  1968.  
  1969.  
  1970.     # Enter the mounting point and MD5
  1971.  
  1972. print <<EOF2;
  1973.  
  1974. <TR>
  1975.   <TD ALIGN=RIGHT>Original Mount Point (i.e. <TT>C:\\</TT>): </TD>
  1976.   <TD ALIGN=LEFT><INPUT TYPE=\"text\" NAME=\"mnt\"></TD>
  1977. </TR>
  1978. <TR>
  1979.   <TD ALIGN=RIGHT> </TD>
  1980.   <TD ALIGN=LEFT>Note: Mounting point not required for swap or raw types</TD>
  1981. </TR>
  1982.  
  1983. <TR>
  1984.   <TD COLSPAN=2> </TD>
  1985. </TR>
  1986.  
  1987. <TR>
  1988.   <TD ALIGN=CENTER COLSPAN=2>
  1989.     <B>Image Integrity Check Options (i.e. MD5)</B>
  1990.   </TD>
  1991. </TR>
  1992.  
  1993. <TR>
  1994.   <TD ALIGN=RIGHT>Calculate Now:</TD>
  1995.   <TD ALIGN=LEFT>
  1996.     <INPUT TYPE=\"radio\" NAME=\"do_md5\" VALUE=\"$MD5_CALC\" CHECKED>
  1997.   </TD>
  1998. </TR>
  1999.  
  2000. <TR>
  2001.   <TD ALIGN=RIGHT>Ignore:</TD>
  2002.   <TD ALIGN=LEFT>
  2003.     <INPUT TYPE=\"radio\" NAME=\"do_md5\" VALUE=\"$MD5_NOTHING\">
  2004.   </TD>
  2005. </TR>
  2006.  
  2007.  
  2008. <TR>
  2009.   <TD ALIGN=RIGHT>Add:</TD>
  2010.   <TD ALIGN=LEFT>
  2011.     <INPUT TYPE=\"radio\" NAME=\"do_md5\" VALUE=\"$MD5_ADD\">
  2012.   </TD>
  2013. </TR>
  2014.  
  2015. <TR>
  2016.   <TD ALIGN=RIGHT>MD5: </TD>
  2017.   <TD ALIGN=LEFT>
  2018.     <INPUT TYPE=\"text\" NAME=\"md5\" SIZE=36 MAXLENGTH=32>
  2019.   </TD>
  2020. </TR>
  2021.  
  2022. <TR>
  2023.   <TD ALIGN=RIGHT> </TD>
  2024.   <TD ALIGN=LEFT>
  2025.     <INPUT TYPE=\"checkbox\" NAME=\"ver_md5\" VALUE=\"1\">
  2026.      Verify MD5 After Importing?
  2027.   </TD>
  2028. </TR>
  2029.  
  2030. <TR>
  2031.   <TD COLSPAN=2> </TD>
  2032. </TR>
  2033.  
  2034. </TABLE>
  2035.  
  2036. <BR><BR>
  2037. <TABLE WIDTH=\"600\" CELLSPACING=\"0\" CELLPADDING=\"2\">
  2038. <TR>
  2039.   <TD ALIGN=CENTER>
  2040.     <INPUT TYPE=\"image\" SRC=\"pict/menu_b_inew.jpg\" ALT=\"Add Image\" WIDTH=\"167\" HEIGHT=20 BORDER=0>
  2041.   </TD>
  2042.  
  2043. </FORM>
  2044.  
  2045. EOF2
  2046.  
  2047.     print 
  2048.       "  <TD ALIGN=CENTER>\n".
  2049.       "    <FORM ACTION=\"$PROGNAME\" METHOD=\"GET\">\n".
  2050.       "    <INPUT TYPE=\"hidden\" NAME=\"func\" VALUE=\"$IMG_OPEN\">\n".
  2051.       make_hidden().
  2052.       "    <INPUT TYPE=\"image\" SRC=\"pict/menu_b_cancel.jpg\" ".
  2053.       "ALT=\"Cancel\" WIDTH=\"167\" HEIGHT=20 BORDER=0></FORM>\n".
  2054.       "  </TD>\n".
  2055.  
  2056.     # HELP
  2057.       "  <TD ALIGN=CENTER>\n".
  2058.       "    <A HREF=\"$HELP_URL\" TARGET=\"_blank\">\n".
  2059.       "    <IMG SRC=\"pict/menu_b_help.jpg\" ALT=\"Help\" ".
  2060.       "WIDTH=\"167\" HEIGHT=20 BORDER=0></A>\n".
  2061.       "  </TD>\n".
  2062.       "</TR>\n".
  2063.       "</TABLE>\n";
  2064.  
  2065.     return;
  2066. };
  2067.  
  2068.  
  2069. # Add the image to the configuration by adding it to the host config file
  2070. # and the md5.txt file if that data was provided
  2071. $funcs[$IMG_ADD_DOIT] = sub {
  2072.     check_img_path(); check_ftype(); 
  2073.     check_sort();
  2074.     check_do_md5();
  2075.  
  2076.     check_mnt()
  2077.       if (($args{'ftype'} ne 'raw') && ($args{'ftype'} ne 'swap')); 
  2078.  
  2079.     print_html_header("Add a new image to an Autopsy Case");
  2080.  
  2081.     my $mnt = get_mnt();
  2082.     my $fstype = get_ftype();
  2083.     my $img_path = get_img_path();
  2084.     my $import_type = get_sort();
  2085.  
  2086.     # Test the File System
  2087.     if (($fstype ne 'swap') && ($fstype ne 'raw')) {
  2088.         local *OUT;
  2089.         my $out;
  2090.         # Run 'fsstat' and see if there is any output - else there was
  2091.         # an error and the data went to STDERR
  2092.         exec_pipe(*OUT, "'${TASKDIR}fsstat' -f $fstype '$img_path'");
  2093.         unless (read (OUT, $out, 1)) {
  2094.             print "<P>The image is not a <TT>$fstype</TT> file system<BR>\n".
  2095.               "<P><A HREF=\"$PROGNAME?func=$IMG_ADD&$baseargs\">".
  2096.               "<IMG SRC=\"pict/but_ok.jpg\" BORDER=\"0\" ".
  2097.               "WIDTH=\"43\" HEIGHT=20 ALT=\"Ok\">".
  2098.               "</A>\n";
  2099.             return;
  2100.         }
  2101.         close (OUT);
  2102.     }
  2103.  
  2104.     # The get the images directory and file name
  2105.     my $img = "";
  2106.     if ($img_path =~ /\/($REG_FILE)$/) {
  2107.         $img = "$IMGDIR/$1";
  2108.     }
  2109.     else {
  2110.         print_err ("Error Parsing Image Path ($img_path)");
  2111.     }
  2112.  
  2113.     # Get the full path of the destination
  2114.     my $img_dst = "$host_dir/$img";
  2115.     if ((-e "$img_dst") || (-l "$img_dst")) {
  2116.         print_err ("Image by the same name already exists in the Host directory ($img)");
  2117.     }
  2118.  
  2119.     my $orig_size = (stat("$img_path"))[7];
  2120.  
  2121.     # Copy, Move, or link it
  2122.     if ($import_type == $IMG_ADD_SYM) {
  2123.  
  2124.         log_host_info 
  2125.           ("Sym Linking image $img_path into $args{'case'}:$args{'host'}");
  2126.  
  2127.         print_err ("ERROR: /bin/ln missing")
  2128.           unless (-x '/bin/ln');
  2129.  
  2130.         print "Linking <TT>$img_path</TT> to <TT>$img_dst</TT><BR>\n";
  2131.  
  2132.         exec_sys ("/bin/ln -s '$img_path' '$img_dst'");
  2133.         
  2134.     } elsif ($import_type == $IMG_ADD_COPY) {
  2135.         log_host_info 
  2136.           ("Copying image $img_path into $args{'case'}:$args{'host'}");
  2137.  
  2138.         print_err ("ERROR: /bin/cp missing")
  2139.           unless (-x '/bin/cp');
  2140.  
  2141.         print "Copying <TT>$img_path</TT> to <TT>$img_dst</TT><BR>\n";
  2142.         exec_sys ("/bin/cp '$img_path' '$img_dst'");
  2143.  
  2144.     } elsif ($import_type == $IMG_ADD_MOVE) {
  2145.         log_host_info 
  2146.           ("Moving image $img_path into $args{'case'}:$args{'host'}");
  2147.  
  2148.         print_err ("ERROR: /bin/mv missing")
  2149.           unless (-x '/bin/mv');
  2150.  
  2151.         print "Moving <TT>$img_path</TT> to <TT>$img_dst</TT><BR>\n";
  2152.  
  2153.         exec_sys ("/bin/mv '$img_path' '$img_dst'");
  2154.  
  2155.     } else {
  2156.         print_err ("Invalid Import Type: $import_type");
  2157.     }
  2158.  
  2159.     my $new_size = (stat("$img_dst"))[7];
  2160.  
  2161.     if ($new_size != $orig_size) {
  2162.         print_err ("Original image size ($orig_size) is not the same as the destination size ($new_size)");
  2163.     }
  2164.  
  2165.     my $do_md5 = get_do_md5();
  2166.  
  2167.     unless ($do_md5 == $MD5_NOTHING) {
  2168.  
  2169.         my $act_md5 = "";
  2170.  
  2171.         # Do we need to calculate an MD5?
  2172.         if (($do_md5 == $MD5_CALC) || (($do_md5 == $MD5_ADD) && 
  2173.           (exists $args{'ver_md5'}) && ($args{'ver_md5'} == 1) ) ) {
  2174.  
  2175.             print "<P>Calculating MD5 of <TT>$img</TT> ".
  2176.               "(this could take a while)<BR>\n";
  2177.             $act_md5 = calc_md5($img_dst);
  2178.             unless ($act_md5 =~ /^$REG_MD5$/o) {
  2179.                 print "Error calculating MD5<BR>\n";
  2180.                 return 1;
  2181.             }
  2182.             print "Current MD5: <TT>$act_md5</TT><BR>\n"; 
  2183.         }
  2184.  
  2185.         # And md5 value was given so we can add it to the md5.txt file
  2186.         if (($do_md5 == $MD5_ADD) && (exists $args{'md5'})) {
  2187.  
  2188.             my $md5 = $args{'md5'};
  2189.             unless ($md5 =~ /^$REG_MD5$/o) {
  2190.                 if ($md5 eq "") {
  2191.                     print "MD5 value missing<BR>\n";
  2192.                 }
  2193.                 else {
  2194.                     print "Invalid MD5 value (32 numbers or letters a-f)<BR>\n";
  2195.                 }
  2196.                 print "<P><A HREF=\"$PROGNAME?func=$IMG_ADD&$baseargs\">".
  2197.                   "<IMG SRC=\"pict/but_ok.jpg\" BORDER=\"0\" ".
  2198.                   "WIDTH=\"43\" HEIGHT=20 ALT=\"Ok\">".
  2199.                   "</A>\n";
  2200.                 return 1;
  2201.             }
  2202.             $md5 =~ tr/[a-f]/[A-F]/;
  2203.  
  2204.             # They also want us to validate the MD5
  2205.               if ((exists $args{'ver_md5'}) && ($args{'ver_md5'} == 1) ) {
  2206.  
  2207.                 if ($act_md5 eq $md5) {
  2208.                     print "Integrity Check Passed<BR>\n";
  2209.                     log_host_info ("Integrity check passed on new image ($img)");
  2210.                 } else { 
  2211.                     print "<FONT COLOR=\"$DEL_COLOR[0]\">".
  2212.                       "Integrity Check Failed<BR></FONT><BR>\n".
  2213.                       "Provided: <TT>$md5</TT><BR>\n";
  2214.  
  2215.                     log_host_info ("Integrity check failed on new image ($img)");
  2216.                     return 1;
  2217.                 }
  2218.             } 
  2219.             # set the act_md5 value to what was given and verified
  2220.             $act_md5 = $md5;
  2221.         }
  2222.         update_md5 ("$img", "$act_md5");
  2223.     }
  2224.  
  2225.     if ($fstype eq 'swap') {
  2226.         update_host_config ("swap", "$img");
  2227.     } elsif ($fstype eq 'raw') {
  2228.         update_host_config ("raw", "$img");
  2229.     } else {
  2230.         update_host_config ("image", "$img", "$fstype    $mnt");
  2231.     }
  2232.     print "<P>Image: <TT>$img_path</TT> added to config file as <TT>$img</TT>\n";
  2233.  
  2234. print <<EOF;
  2235. <P>
  2236. <CENTER>
  2237. <TABLE WIDTH=600>
  2238. <TR>
  2239.   <TD WIDTH=300 ALIGN=CENTER>
  2240.     <A HREF=\"$PROGNAME?func=$IMG_OPEN&${baseargs_noimg}\">
  2241.     <IMG SRC=\"pict/menu_b_ok.jpg\" ALT=\"Ok\" WIDTH=\"167\" HEIGHT=20 BORDER=\"0\">
  2242.     </A>
  2243.   </TD>
  2244.   <TD WIDTH=300 ALIGN=CENTER>
  2245.     <A HREF=\"$PROGNAME?func=$IMG_ADD&${baseargs_noimg}\">
  2246.     <IMG SRC=\"pict/menu_b_inew.jpg\" ALT=\"Ok\" WIDTH=\"167\" HEIGHT=20 BORDER=\"0\">
  2247.     </A>
  2248.   </TD>
  2249. </TR>
  2250. </TABLE>
  2251. </CENTER>
  2252.  
  2253. EOF
  2254.     return;
  2255. };
  2256.  
  2257. # Display details of image based on config values
  2258. # provides links to remove the config of the image and to get the file
  2259. # system details
  2260. $funcs[$IMG_DETAILS] = sub {
  2261.     check_img('img'); check_ftype(); check_mnt();
  2262.     print_html_header("Details of $args{'img'}");
  2263.  
  2264.     my $mnt = get_mnt();
  2265.     my $ftype = get_ftype();
  2266.  
  2267.     print "<CENTER>".
  2268.       "<IMG SRC=\"pict/menu_h_idet.jpg\" ALT=\"Image Details\">".
  2269.       "<BR><BR><BR>\n".
  2270.       "<TABLE WIDTH=\"600\" CELLSPACING=\"0\" CELLPADDING=\"2\" ".
  2271.       "BACKGROUND=\"$YEL_PIX\" BORDER=0>\n".
  2272.       "  <TR><TD COLSPAN=\"2\"> </TD></TR>\n".
  2273.       # Name
  2274.       "  <TR><TD ALIGN=\"RIGHT\" WIDTH=\"300\"><B>Name:</B></TD>".
  2275.       "<TD ALIGN=\"LEFT\"><TT>$args{'img'}</TT></TD></TR>\n".
  2276.       # Mount
  2277.       "  <TR><TD ALIGN=\"RIGHT\"><B>Mounting Point:</B></TD>".
  2278.       "<TD ALIGN=\"LEFT\"><TT>$mnt</TT></TD></TR>\n".
  2279.       # Type
  2280.       "  <TR><TD ALIGN=\"RIGHT\"><B>File System Type:</B></TD>".
  2281.       "<TD ALIGN=\"LEFT\"><TT>$ftype</TT></TD></TR>\n";
  2282.  
  2283.     my $md5 = lookup_md5($args{'img'}); 
  2284.     print "  <TR><TD ALIGN=\"RIGHT\"><B>MD5:</B></TD><TD><TT>".
  2285.       (($md5 =~ /^$REG_MD5$/o)? $md5 : " ").
  2286.       "</TT></TD></TR>\n".
  2287.  
  2288.       # Host Directory
  2289.       "  <TR><TD ALIGN=\"RIGHT\"><B>Host Directory:</B></TD>".
  2290.       "<TD ALIGN=\"LEFT\"><TT>$host_dir</TT></TD></TR>\n".
  2291.       "  <TR><TD COLSPAN=\"2\"> </TD></TR>\n".
  2292.  
  2293.       # Strings File
  2294.       "  <TR><TD ALIGN=\"RIGHT\"><B>Strings File:</B></TD>".
  2295.       "<TD ALIGN=\"LEFT\"><TT>".
  2296.       ((exists $img2str{$args{'img'}}) ? $img2str{$args{'img'}} : " ").
  2297.       "</TT></TD></TR>\n";
  2298.  
  2299.  
  2300.     if (($ftype ne "raw") && ($ftype ne "swap")) {
  2301.         # dls file
  2302.         print 
  2303.           "  <TR><TD ALIGN=\"RIGHT\"><B>Unallocated $addr_unit{$ftype}s (dls) File:</B></TD>".
  2304.           "<TD ALIGN=\"LEFT\"><TT>".
  2305.           ((exists $img2dls{$args{'img'}}) ? $img2dls{$args{'img'}} : " ").
  2306.           "</TT></TD></TR>\n";
  2307.  
  2308.         # Strings of dls
  2309.         print 
  2310.           "  <TR><TD ALIGN=\"RIGHT\"><B>Strings of Unallocated $addr_unit{$ftype}s File:</B></TD>".
  2311.           "<TD ALIGN=\"LEFT\"><TT>".
  2312.           ( ( (exists $img2dls{$args{'img'}}) &&
  2313.           (exists $img2str{$img2dls{$args{'img'}}})) ? 
  2314.             $img2str{$img2dls{$args{'img'}}} : " ").
  2315.           "</TT></TD></TR>\n";
  2316.     }
  2317.  
  2318.     print "  <TR><TD COLSPAN=\"2\"> </TD></TR>\n".
  2319.       "</TABLE>\n";
  2320.  
  2321.     # Section for Strings file and 'dls' file
  2322.  
  2323.     if ( (!(defined $img2str{$args{'img'}})) || 
  2324.       (!(defined $img2dls{$args{'img'}})) || 
  2325.       ((defined $img2dls{$args{'img'}}) && (!(defined $img2str{$img2dls{$args{'img'}}})))) { 
  2326.         print "<HR><TABLE WIDTH=600>\n<TR>";
  2327.     }
  2328.  
  2329.     # Strings File
  2330.     if (!(defined $img2str{$args{'img'}})) {
  2331.  
  2332.         (my $img_dir, my $str_img) = split (/\//,$args{'img'});
  2333.  
  2334.         print "<TD ALIGN=\"CENTER\" WIDTH=300><H3>Generate Strings File</H3>".
  2335.           "<FORM ACTION=\"$PROGNAME\" METHOD=\"GET\">\n".
  2336.           "File Name: <INPUT TYPE=\"text\" NAME=\"fname\" ".
  2337.           "VALUE=\"$str_img.str\"><BR><BR>\n".
  2338.           "Generate MD5? ".                      
  2339.           "<INPUT TYPE=\"checkbox\" NAME=\"md5\" VALUE=\"1\" CHECKED><BR><BR>".
  2340.           "<INPUT TYPE=\"hidden\" NAME=\"func\" VALUE=\"$IMG_MAKESTR\">\n".
  2341.           "<INPUT TYPE=\"hidden\" NAME=\"img\" VALUE=\"$args{'img'}\">\n".
  2342.           "<INPUT TYPE=\"hidden\" NAME=\"fname_mode\" VALUE=\"$FNAME_MODE_INIT\">\n".
  2343.           make_hidden().
  2344.           "<INPUT TYPE=\"IMAGE\" SRC=\"pict/srch_b_str.jpg\" ". 
  2345.           "ALT=\"Extract Strings\" BORDER=\"0\">\n</FORM></TD>\n";
  2346.     }
  2347.  
  2348.     if (($ftype eq 'dls') || ($ftype eq 'swap') || ($ftype eq 'raw')) {
  2349.         # Place holder for types that have no notion of unallocated
  2350.     }
  2351.     # Unallocated Space File
  2352.     elsif (!(defined $img2dls{$args{'img'}})) { 
  2353.  
  2354.         print "<TD ALIGN=\"CENTER\" WIDTH=300><H3>Create File of Unallocated $addr_unit{$ftype}s</H3>".
  2355.           "(Note: This Does Not Include Slack Space)<BR>\n".
  2356.           "<FORM ACTION=\"$PROGNAME\" METHOD=\"GET\">\n".
  2357.           "File Name: <INPUT TYPE=\"text\" NAME=\"fname\" ";
  2358.         
  2359.         (my $img_dir, my $dls_img) = split (/\//,$args{'img'});
  2360.         if ($dls_img =~ /^(.*?)\.dd$/) {
  2361.             print "VALUE=\"$1.dls\"><BR><BR>\n";
  2362.         } else {
  2363.             print "VALUE=\"${dls_img}.dls\"><BR><BR>\n";
  2364.         }
  2365.  
  2366.         print "Generate MD5? ".                      
  2367.           "<INPUT TYPE=\"checkbox\" NAME=\"md5\" VALUE=\"1\" CHECKED><BR><BR>".
  2368.           "<INPUT TYPE=\"hidden\" NAME=\"func\" VALUE=\"$IMG_MAKEDLS\">\n".
  2369.           "<INPUT TYPE=\"hidden\" NAME=\"img\" VALUE=\"$args{'img'}\">\n".
  2370.           "<INPUT TYPE=\"hidden\" NAME=\"fname_mode\" VALUE=\"$FNAME_MODE_INIT\">\n".
  2371.           make_hidden().
  2372.           "<INPUT TYPE=\"IMAGE\" SRC=\"pict/srch_b_un.jpg\" ". 
  2373.           "ALT=\"Extract Unallocated Data\" BORDER=\"0\">\n<BR></FORM>\n";
  2374.     }
  2375.  
  2376.     # strings of 'dls'
  2377.     elsif (!(defined $img2str{$img2dls{$args{'img'}}})) { 
  2378.         (my $img_dir, my $str_img) = split (/\//,$img2dls{$args{'img'}});
  2379.  
  2380.         print "<TD ALIGN=\"CENTER\" WIDTH=300><H3>Generate Strings File of Unallocated $addr_unit{$ftype}s</H3>".
  2381.           "<FORM ACTION=\"$PROGNAME\" METHOD=\"GET\">\n".
  2382.           "File Name: <INPUT TYPE=\"text\" NAME=\"fname\" ".
  2383.           "VALUE=\"$str_img.str\"><BR><BR>\n".
  2384.           "Generate MD5? ".                      
  2385.           "<INPUT TYPE=\"checkbox\" NAME=\"md5\" VALUE=\"1\" CHECKED><BR><BR>".
  2386.           "<INPUT TYPE=\"hidden\" NAME=\"func\" VALUE=\"$IMG_MAKESTR\">\n".
  2387.           "<INPUT TYPE=\"hidden\" NAME=\"img\" VALUE=\"$img2dls{$args{'img'}}\">\n".
  2388.           "<INPUT TYPE=\"hidden\" NAME=\"fname_mode\" VALUE=\"$FNAME_MODE_INIT\">\n".
  2389.           make_hidden().
  2390.           "<INPUT TYPE=\"IMAGE\" SRC=\"pict/srch_b_str.jpg\" ". 
  2391.           "ALT=\"Extract Strings\" BORDER=\"0\">\n</FORM></TD>\n";
  2392.     }
  2393.  
  2394.     if ( (!(defined $img2str{$args{'img'}})) || 
  2395.       (!(defined $img2dls{$args{'img'}})) || 
  2396.       ((defined $img2dls{$args{'img'}}) && (!(defined $img2str{$img2dls{$args{'img'}}})))) { 
  2397.         print "</TR></TABLE><HR>\n";
  2398.     }
  2399.  
  2400.     print "<P>".
  2401.       "<TABLE WIDTH=\"600\" CELLSPACING=\"0\" CELLPADDING=\"2\">\n".
  2402.     
  2403.     # Ok
  2404.       "<TR><TD ALIGN=CENTER WIDTH=200>".
  2405.       "<FORM ACTION=\"$PROGNAME\" METHOD=\"GET\">\n". 
  2406.       "<INPUT TYPE=\"hidden\" NAME=\"func\" VALUE=\"$IMG_OPEN\">\n".
  2407.       make_hidden().
  2408.       "<INPUT TYPE=\"image\" SRC=\"pict/menu_b_ok.jpg\" ".
  2409.       "ALT=\"Ok\" WIDTH=\"167\" HEIGHT=20 BORDER=0></FORM></TD>\n";
  2410.  
  2411.  
  2412.     print "<TD ALIGN=CENTER WIDTH=200>";
  2413.     if (($ftype ne "raw") && ($ftype ne "swap")) {
  2414.         # File System Details
  2415.         print 
  2416.           "<FORM ACTION=\"$PROGNAME\" METHOD=\"GET\" TARGET=\"_blank\">\n". 
  2417.           make_hidden().
  2418.              "<INPUT TYPE=\"hidden\" NAME=\"func\" VALUE=\"$MAIN_FR\">\n".
  2419.              "<INPUT TYPE=\"hidden\" NAME=\"mode\" VALUE=\"$FS_MAIN\">\n".
  2420.              "<INPUT TYPE=\"hidden\" NAME=\"img\" VALUE=\"$args{'img'}\">\n".
  2421.           "<INPUT TYPE=\"hidden\" NAME=\"mnt\" VALUE=\"$args{'mnt'}\">\n".
  2422.           "<INPUT TYPE=\"image\" SRC=\"pict/menu_b_fs.jpg\" ".
  2423.           "WIDTH=167 HEIGHT=20 ".
  2424.           "ALT=\"File System\" BORDER=0></FORM></TD>\n";
  2425.     } else {
  2426.         print " </TD>\n";
  2427.     }
  2428.  
  2429.     # Remove Image
  2430.     print 
  2431.       "<TD ALIGN=CENTER WIDTH=200>".
  2432.       "<FORM ACTION=\"$PROGNAME\" METHOD=\"GET\">\n". 
  2433.       "<INPUT TYPE=\"hidden\" NAME=\"func\" VALUE=\"$IMG_DEL\">\n".
  2434.       make_hidden().
  2435.       "<INPUT TYPE=\"hidden\" NAME=\"img\" VALUE=\"$args{'img'}\">\n".
  2436.       "<INPUT TYPE=\"hidden\" NAME=\"mnt\" VALUE=\"$args{'mnt'}\">\n".
  2437.       "<INPUT TYPE=\"image\" SRC=\"pict/menu_b_rem.jpg\" ".
  2438.       "WIDTH=167 HEIGHT=20 ".
  2439.       "ALT=\"Remove\" BORDER=0></FORM></TD>\n".
  2440.       "</TR></TABLE>\n";
  2441.  
  2442.     return;
  2443. };
  2444.  
  2445.  
  2446.  
  2447. # remove the config files
  2448. $funcs[$IMG_DEL] = sub {
  2449.     check_img('img'); check_ftype(); 
  2450.     print_html_header("Removing Configuration Settings for $args{'img'}");
  2451.  
  2452.     update_host_config("", $args{'img'}, "");
  2453.     update_md5($args{'img'}, "");
  2454.  
  2455.     print "Settings for <TT>$args{'img'}</TT> removed from ".
  2456.       "<TT>$args{'case'}:$args{'host'}</TT>.\n".
  2457.       "<P>NOTE: The actual file still exists in the host directory.\n";
  2458.  
  2459.  
  2460.     print "<P><A HREF=\"$PROGNAME?func=$IMG_OPEN&${baseargs_noimg}\">".
  2461.       "<IMG SRC=\"pict/but_ok.jpg\" ALT=\"Ok\" ".
  2462.       "WIDTH=\"43\" HEIGHT=20 BORDER=\"0\"></A>\n";
  2463.  
  2464.     return();
  2465. };
  2466.  
  2467. ###################################################################
  2468.  
  2469.  
  2470.  
  2471.  
  2472.  
  2473. # Blank Page
  2474. $funcs[$BLANK] = sub { 
  2475.     print_html_header("");
  2476.     print "<!-- This Page Intentionally Left Blank -->\n";
  2477.     return 0;
  2478. };
  2479.  
  2480.  
  2481. #
  2482. ###################### FILE MODE ###################
  2483. #
  2484.  
  2485. #
  2486. # Make the three frames and fill them in
  2487. #
  2488. $funcs[$FIL_MAIN] = sub {
  2489.  
  2490.     # If we were not given the inode, then look up the root
  2491.     unless (exists $args{'inode'}) {
  2492.         my $ftype = get_ftype();
  2493.         $args{'inode'} = $enc_args{'inode'} = $root_inode{$ftype};
  2494.     }
  2495.  
  2496.     unless (exists $args{'dir'}) {
  2497.         $args{'dir'} = "/";
  2498.     }
  2499.  
  2500.     check_inode('inode'); check_dir();
  2501.  
  2502.     print_html_header_frameset("$args{'mnt'}$args{'dir'} on $args{'img'}");
  2503.  
  2504.     my $sort = $SORT_NAME;
  2505.     $sort = $args{'sort'} if (exists $args{'sort'});
  2506.  
  2507.     my $dmode = $DMODE_NOSHOW;
  2508.     $dmode = $args{'dmode'} if (exists $args{'dmode'});
  2509.  
  2510.     print "<FRAMESET COLS=\"175,*\">\n";
  2511.  
  2512.     # Directory Listing on Left
  2513.     my $url = "$PROGNAME?$baseargs&dir=$enc_args{'dir'}&".
  2514.       "sort=$sort&dmode=$dmode&inode=$enc_args{'inode'}";
  2515.  
  2516.     print "<FRAME SRC=\"$url&func=$FIL_DIR\">\n";
  2517.  
  2518.     # File frameset on right
  2519.     print "<FRAMESET ROWS=\"50%,50%\">\n";
  2520.  
  2521.     # File Listings on top
  2522.     print "<FRAME SRC=\"$url&func=$FIL_LIST\" ".
  2523.       "NAME=\"list\">\n";
  2524.  
  2525.     # File Contents
  2526.     print "<FRAME SRC=\"$PROGNAME?func=$BLANK&$baseargs\" ".
  2527.       "NAME=\"content\">\n".
  2528.       "</FRAMESET>\n".
  2529.       "</FRAMESET>\n";
  2530.  
  2531.     return 0;
  2532. };
  2533.  
  2534. #
  2535. # Print the directory names for the lhs frame
  2536. # THIS NEEDS TO IMPROVE TO BECOME MORE USABLE
  2537. #
  2538.  
  2539. $funcs[$FIL_DIR] = sub {
  2540.     check_dir(); check_sort(); check_dmode();
  2541.  
  2542.     print_html_header("");
  2543.  
  2544.     my $ftype = get_ftype();
  2545.     my $sort = get_sort();
  2546.     my $dmode = get_dmode();
  2547.  
  2548.     my $lcldir = "";
  2549.     my $prev_plus = "";             # previous number of '+' directory spacers
  2550.     my $prev_fname = "";
  2551.     my $prev_meta = "";
  2552.     my $img = get_img('img');
  2553.  
  2554.  
  2555.     # Field to enter a directory into:
  2556.     print "<P><FORM ACTION=\"$PROGNAME\" METHOD=\"GET\" TARGET=\"list\">\n".
  2557.       "<B>View Directory:</B><BR><TT>$args{'mnt'}</TT>".
  2558.       "<INPUT TYPE=\"text\" NAME=\"dir\" SIZE=24 MAXLENGTH=100>\n".
  2559.       "<INPUT TYPE=\"hidden\" NAME=\"func\" VALUE=\"$FIL_NAME\">\n".
  2560.       "<INPUT TYPE=\"hidden\" NAME=\"img\" VALUE=\"$args{'img'}\">\n".
  2561.       "<INPUT TYPE=\"hidden\" NAME=\"mnt\" VALUE=\"$args{'mnt'}\">\n".
  2562.       "<INPUT TYPE=\"hidden\" NAME=\"sort\" VALUE=\"$args{'sort'}\">\n".
  2563.       "<INPUT TYPE=\"hidden\" NAME=\"dmode\" VALUE=\"$args{'dmode'}\">\n".
  2564.       "<INPUT TYPE=\"hidden\" NAME=\"inode\" VALUE=\"0\">\n".
  2565.       make_hidden().
  2566.  
  2567.     # Ok Button
  2568.       "<P><INPUT TYPE=\"IMAGE\" SRC=\"pict/but_ok.jpg\" ".
  2569.       "WIDTH=43 HEIGHT=20 ALT=\"Ok\" BORDER=\"0\"></FORM>\n";
  2570.  
  2571.     print "<P><HR><P>\n";
  2572.  
  2573.     my $base_url = "$PROGNAME?$baseargs&sort=$sort";
  2574.  
  2575.     # All deleted files button
  2576.     print "<A HREF=\"$base_url&func=$FIL_DEL&inode=$root_inode{$ftype}&dir=\" ".
  2577.       "TARGET=\"list\">".
  2578.       "<IMG BORDER=\"0\" ".
  2579.       "SRC=\"pict/file_b_alldel.jpg\" ".
  2580.       "WIDTH=\"127\" ".
  2581.       "ALT=\"Show All Deleted Files\">".
  2582.       "</A><P>\n";
  2583.  
  2584.     # The dmode arg shows if we should expand the whole directory listing
  2585.     # or not 
  2586.     if ($dmode == $DMODE_NOSHOW) {
  2587.         print "<A HREF=\"$base_url&func=$FIL_MAIN&dmode=$DMODE_SHOW\" ".
  2588.           "TARGET=\"_parent\">".
  2589.             "<IMG SRC=\"pict/file_b_expand.jpg\" ALT=\"Expand All Directories\" ".
  2590.             "BORDER=\"0\"></A><P><HR>\n";
  2591.  
  2592.         return;
  2593.     }
  2594.     else {
  2595.         print "<A HREF=\"$base_url&func=$FIL_MAIN&dmode=$DMODE_NOSHOW\" ".
  2596.           "TARGET=\"_parent\">".
  2597.           "<IMG SRC=\"pict/file_b_hide.jpg\" ALT=\"Hide All Directories\" ".
  2598.           "BORDER=\"0\"></A><P><HR>\n";
  2599.     }
  2600.  
  2601.  
  2602.     $base_url .= "&dmode=$dmode";
  2603.  
  2604.     log_host_inv ("$args{'img'}: List of all directories");
  2605.     
  2606.     # We need to maintain state to create dir and this is done by
  2607.     # counting the + marks.
  2608.     local *OUT;
  2609.     exec_pipe(*OUT, "'${TASKDIR}fls' -f $ftype -ruD '$img'");
  2610.  
  2611.  
  2612.     # Print root 
  2613.     my $url = "$base_url&func=$FIL_LIST&inode=$root_inode{$ftype}&dir=";
  2614.     print "<P><A HREF=\"$url\" TARGET=\"list\">$args{'mnt'}</A><BR>\n";
  2615.  
  2616.  
  2617.     while (<OUT>) {
  2618.         if (/^(\*)?(\+*)\s*[\-d]\/[\-d]\s*(\d+)\-?\d*\-?\d*\s*(\(realloc\))?:\t(.+)$/) {
  2619.  
  2620.             my $del = $1;
  2621.             my $plus = $2;
  2622.             my $meta = $3;
  2623.             my $re = $4;
  2624.             my $fname = $5;
  2625.     
  2626.             # Adjust the dir value using the '++' values to determine
  2627.             # how "deep" we are
  2628.             unless ($prev_plus eq $plus) {
  2629.                 # are we in 1 more
  2630.                 if ($plus eq $prev_plus.'+') {
  2631.                     $lcldir .= ($prev_fname."/");
  2632.                 }
  2633.                 # we are back (at least one)
  2634.                 elsif (defined $plus) {
  2635.                     my @dirs = split ('/', $lcldir); 
  2636.                     my $idx = -1;
  2637.                     $lcldir = "";
  2638.  
  2639.                     while (($idx = index ($plus, '+', $idx+1)) != -1) {
  2640.                         $lcldir .= ($dirs[$idx]."/");
  2641.                     }
  2642.                 }
  2643.             }
  2644.  
  2645.             $prev_plus = $plus;
  2646.             $prev_fname = $fname;
  2647.             $prev_meta = $meta;
  2648.  
  2649.             $url = "$base_url&func=$FIL_LIST&inode=$meta".
  2650.               "&dir=".url_encode($lcldir.$fname."/");
  2651.  
  2652.             print "<FONT COLOR=\"$DEL_COLOR[0]\">" if defined $del;
  2653.             print "+$plus<A HREF=\"$url\" TARGET=\"list\"><TT>/$fname</TT></A><BR>\n";
  2654.             print "</FONT>" if defined $del;
  2655.         }
  2656.     }
  2657.     close (OUT);
  2658.     return 0;
  2659.  
  2660. };    # end of FIL_DIR
  2661.  
  2662.  
  2663. # Print the files and directories for the upper rhs frame
  2664. # These can be sorted in any format
  2665. #
  2666. # We need to find a way to cache this data
  2667. #
  2668. $funcs[$FIL_LIST] = sub {
  2669.     check_inode('inode'); check_dir(); check_sort(); check_dmode();
  2670.  
  2671.     my $fname = "$args{'mnt'}$args{'dir'}";
  2672.  
  2673.     my $sp = "  ";
  2674.  
  2675.     print_html_header("Entries in $fname");
  2676.  
  2677.     my (@itype, @dtype, @name, @mod, @acc, @chg, @size, @gid, @uid, @inode);
  2678.     my (@dir, @entry, @del, @realloc, @inode_int);
  2679.  
  2680.     my $sort = get_sort();
  2681.     my $ftype = get_ftype();
  2682.     my $inode = get_inode('inode');
  2683.     my $img = get_img('img');
  2684.  
  2685.  
  2686.     log_host_inv ("$args{'img'}: Directory listing of $fname ($inode)");
  2687.  
  2688.     # execute command
  2689.     local *OUT;
  2690.     exec_pipe(*OUT, "'${TASKDIR}fls' -f $ftype -la -z '$tz' -s $ts '$img' $inode");
  2691.  
  2692.     # Make the big table, small table, and start the current directory
  2693.  
  2694.     my $iurl = 
  2695.       "$PROGNAME?$baseargs&dmode=$enc_args{'dmode'}&sort=$sort";
  2696.  
  2697. print <<EOF1;
  2698. <!-- Big Table -->
  2699. <TABLE CELLSPACING=\"0\" CELLPADDING=\"2\" BORDER=0>
  2700.  
  2701. <!-- Small Table -->
  2702. <TR>
  2703.   <TD COLSPAN=19>
  2704.     <TABLE BORDER=0 ALIGN=\"left\" CELLSPACING=\"0\" CELLPADDING=\"2\" WIDTH=500>
  2705.     <TR>
  2706.       <TD COLSPAN=2><B>Current Directory:</B> <TT>
  2707.  
  2708.         <A HREF=\"${iurl}&func=$FIL_LIST&inode=$root_inode{$ftype}&dir=\">$args{'mnt'}</A> 
  2709.  
  2710. EOF1
  2711.  
  2712.     # Each file in the path will get its own link
  2713.     $iurl .= "&func=$FIL_NAME&inode=0";
  2714.     my $path = "";
  2715.     my @dir_split = split ('/', $args{'dir'});
  2716.     while (scalar @dir_split > 1) {
  2717.         my $d = shift @dir_split;
  2718.  
  2719.         next if ($d eq '');
  2720.  
  2721.         $path .= "$d/";
  2722.         print 
  2723.           "        <A HREF=\"${iurl}&dir=$path\">/${d}/</A> \n";
  2724.     }
  2725.     print "        /$dir_split[0]/ \n"
  2726.       if (scalar @dir_split == 1);
  2727.  
  2728.     print "      </TT></TD>\n".
  2729.       "    </TR>\n";
  2730.  
  2731.  
  2732.     # Add Note Button
  2733.     $iurl = "&$baseargs&dir=$enc_args{'dir'}&inode=$enc_args{'inode'}";
  2734.     if ($USE_NOTES == 1) {
  2735.  
  2736. print <<EOF2;
  2737.     <TR>
  2738.       <TD WIDTH=\"100\" ALIGN=LEFT>
  2739.         <A HREF=\"$PROGNAME?func=$NOTES_ENT$iurl\" TARGET=\"_blank\">
  2740.           <IMG BORDER=\"0\" SRC=\"pict/but_addnote.jpg\" WIDTH=\"89\" HEIGHT=20 ALT=\"Add Note About Directory\">
  2741.          </A>
  2742.       </TD>
  2743. EOF2
  2744.  
  2745.     }
  2746.  
  2747.     # Generate MD5 List Button
  2748. print <<EOF3;
  2749.  
  2750.       <TD WIDTH=\"206\" ALIGN=LEFT>
  2751.         <A HREF=\"$PROGNAME?func=$FIL_MD5$iurl\" TARGET=\"_blank\">
  2752.           <IMG BORDER=\"0\" SRC=\"pict/file_b_md5list.jpg\" WIDTH=\"206\" ALT=\"Generate list of MD5 values\">
  2753.         </A>
  2754.       </TD>
  2755.     </TR>
  2756.   <!-- END of Little Table -->
  2757.   </TABLE>
  2758.   </TD>
  2759. </TR>
  2760. <TR>
  2761.   <TD COLSPAN=19><HR></TD>
  2762. </TR>
  2763.  
  2764. EOF3
  2765.  
  2766.     # Make the Table and Headers
  2767.     my $url="$PROGNAME?func=$FIL_MAIN&$baseargs&inode=$enc_args{'inode'}".
  2768.       "&dir=$enc_args{'dir'}&dmode=$enc_args{'dmode'}";
  2769.  
  2770.     print "<TR VALIGN=\"MIDDLE\" ".
  2771.       "BACKGROUND=\"$YEL_PIX\">\n";
  2772.  
  2773.  
  2774.     # Print the Headers - If the sorting mode is set to it, then don't
  2775.     # make it a link and print a different button
  2776.     if ($sort == $SORT_DEL) {
  2777.         print "  <TD ALIGN=\"LEFT\" BACKGROUND=\"$YEL_PIX\">".
  2778.           "<IMG BORDER=\"0\" ".
  2779.           "SRC=\"pict/file_h_del_cur.jpg\" ".
  2780.           "WIDTH=\"49\" HEIGHT=20 ".
  2781.           "ALT=\"Deleted Files\">".
  2782.           "</TD>\n";
  2783.     } else {
  2784.         $iurl = $url."&sort=$SORT_DEL";
  2785.         print "  <TD ALIGN=\"LEFT\" BACKGROUND=\"$YEL_PIX\">".
  2786.           "<A HREF=\"$iurl\" TARGET=\"_parent\">".
  2787.           "<IMG BORDER=\"0\" ".
  2788.           "SRC=\"pict/file_h_del_link.jpg\" ".
  2789.           "WIDTH=\"28\" HEIGHT=20 ".
  2790.           "ALT=\"Deleted Files\">".
  2791.           "</A></TD>\n";
  2792.     }
  2793.  
  2794.     # type only gets one column for two 'types'
  2795.     print "  <TD BACKGROUND=\"$YEL_PIX\">$sp</TD>\n".
  2796.       "  <TH ALIGN=\"CENTER\" BACKGROUND=\"$YEL_PIX\">".
  2797.       "  Type  <BR>";
  2798.  
  2799.     if ($sort == $SORT_DTYPE) {
  2800.         print "dir";
  2801.     } else {
  2802.         $iurl = $url."&sort=$SORT_DTYPE";
  2803.         print "<A HREF=\"$iurl\" TARGET=\"_parent\">dir</A>";
  2804.     }
  2805.  
  2806.     print " / ";
  2807.  
  2808.     if ($sort == $SORT_ITYPE) {
  2809.         print "in</TH>\n";
  2810.     } else {
  2811.         $iurl = $url."&sort=$SORT_ITYPE";
  2812.         print "<A HREF=\"$iurl\" TARGET=\"_parent\">in</A></TH>\n";
  2813.     }
  2814.  
  2815.     print "  <TD BACKGROUND=\"$YEL_PIX\">$sp</TD>\n";
  2816.  
  2817.     if ($sort == $SORT_NAME) {
  2818.         print "  <TD ALIGN=\"LEFT\" BACKGROUND=\"$YEL_PIX\">".
  2819.           "<IMG BORDER=\"0\" ".
  2820.           "SRC=\"pict/file_h_nam_cur.jpg\" ".
  2821.           "WIDTH=\"76\" HEIGHT=20 ".
  2822.           "ALT=\"File Name\">".
  2823.           "</TD>\n";
  2824.     } else {
  2825.         $iurl = $url."&sort=$SORT_NAME";
  2826.         print "  <TD ALIGN=\"LEFT\" BACKGROUND=\"$YEL_PIX\">".
  2827.           "<A HREF=\"$iurl\" TARGET=\"_parent\">".
  2828.           "<IMG BORDER=\"0\" ".
  2829.           "SRC=\"pict/file_h_nam_link.jpg\" ".
  2830.           "WIDTH=\"50\" HEIGHT=20 ".
  2831.           "ALT=\"File Name\">".
  2832.           "</A></TD>\n";
  2833.     }
  2834.  
  2835.     print "  <TD BACKGROUND=\"$YEL_PIX\">$sp</TD>\n";
  2836.  
  2837.     # Modified / Written
  2838.     if ($sort == $SORT_MOD) {
  2839.         print "  <TD ALIGN=\"LEFT\" BACKGROUND=\"$YEL_PIX\">";
  2840.         if ($mtime_str{$ftype} eq 'Modified') {    
  2841.             print "<IMG BORDER=\"0\" ".
  2842.               "SRC=\"pict/file_h_mod_cur.jpg\" ".
  2843.               "WIDTH=\"84\" HEIGHT=20 ".
  2844.               "ALT=\"Modified Time\">";
  2845.         } else {
  2846.             print "<IMG BORDER=\"0\" ".
  2847.               "SRC=\"pict/file_h_wr_cur.jpg\" ".
  2848.               "WIDTH=\"89\" HEIGHT=20 ".
  2849.               "ALT=\"Written Time\">";
  2850.         }
  2851.         print "</TD>\n";
  2852.     } else {
  2853.         $iurl = $url."&sort=$SORT_MOD";
  2854.         print "  <TD ALIGN=\"LEFT\" BACKGROUND=\"$YEL_PIX\">".
  2855.           "<A HREF=\"$iurl\" TARGET=\"_parent\">";
  2856.         if ($mtime_str{$ftype} eq 'Modified') {    
  2857.             print "<IMG BORDER=\"0\" ".
  2858.               "SRC=\"pict/file_h_mod_link.jpg\" ".
  2859.               "WIDTH=\"62\" HEIGHT=20 ".
  2860.               "ALT=\"Modified Time\">";
  2861.         } else {
  2862.             print "<IMG BORDER=\"0\" ".
  2863.               "SRC=\"pict/file_h_wr_link.jpg\" ".
  2864.               "WIDTH=\"60\" HEIGHT=20 ".
  2865.               "ALT=\"Written Time\">";
  2866.         }
  2867.         print "</A></TD>\n";
  2868.     }
  2869.  
  2870.     print "  <TD BACKGROUND=\"$YEL_PIX\">$sp</TD>\n";
  2871.  
  2872.     # Accessed
  2873.     if ($sort == $SORT_ACC) {
  2874.         print "  <TD ALIGN=\"LEFT\" BACKGROUND=\"$YEL_PIX\">".
  2875.           "<IMG BORDER=\"0\" ".
  2876.           "SRC=\"pict/file_h_acc_cur.jpg\" ".
  2877.           "WIDTH=\"90\" HEIGHT=20 ".
  2878.           "ALT=\"Access Time\">".
  2879.           "</TD>\n";
  2880.     } else {
  2881.         $iurl = $url."&sort=$SORT_ACC";
  2882.         print "  <TD ALIGN=\"LEFT\" BACKGROUND=\"$YEL_PIX\">".
  2883.           "<A HREF=\"$iurl\" TARGET=\"_parent\">".
  2884.           "<IMG BORDER=\"0\" ".
  2885.           "SRC=\"pict/file_h_acc_link.jpg\" ".
  2886.           "WIDTH=\"66\" HEIGHT=20 ".
  2887.           "ALT=\"Access Time\">".
  2888.           "</A></TD>\n";
  2889.     }
  2890.  
  2891.     print "  <TD BACKGROUND=\"$YEL_PIX\">$sp</TD>\n";
  2892.  
  2893.     # Change / Create
  2894.     if ($sort == $SORT_CHG) {
  2895.         print "  <TD ALIGN=\"LEFT\" BACKGROUND=\"$YEL_PIX\">";
  2896.         if ($ctime_str{$ftype} eq 'Changed') {    
  2897.             print "<IMG BORDER=\"0\" ".
  2898.               "SRC=\"pict/file_h_chg_cur.jpg\" ".
  2899.               "WIDTH=\"90\" HEIGHT=20 ".
  2900.               "ALT=\"Change Time\">";
  2901.         } else {
  2902.             print "<IMG BORDER=\"0\" ".
  2903.               "SRC=\"pict/file_h_cre_cur.jpg\" ".
  2904.               "WIDTH=\"84\" HEIGHT=20 ".
  2905.               "ALT=\"Create Time\">";
  2906.         }
  2907.         print "</TD>\n";
  2908.     } else {
  2909.         $iurl = $url."&sort=$SORT_CHG";
  2910.         print "  <TD ALIGN=\"LEFT\" BACKGROUND=\"$YEL_PIX\">".
  2911.           "<A HREF=\"$iurl\" TARGET=\"_parent\">";
  2912.         if ($ctime_str{$ftype} eq 'Changed') {    
  2913.             print "<IMG BORDER=\"0\" ".
  2914.               "SRC=\"pict/file_h_chg_link.jpg\" ".
  2915.               "WIDTH=\"62\" HEIGHT=20 ".
  2916.               "ALT=\"Change Time\">";
  2917.         } else {
  2918.             print "<IMG BORDER=\"0\" ".
  2919.               "SRC=\"pict/file_h_cre_link.jpg\" ".
  2920.               "WIDTH=\"59\" HEIGHT=20 ".
  2921.               "ALT=\"Create Time\">";
  2922.         }
  2923.         print "</A></TD>\n";
  2924.     }
  2925.  
  2926.     print "  <TD BACKGROUND=\"$YEL_PIX\">$sp</TD>\n";
  2927.  
  2928.     # Size
  2929.     if ($sort == $SORT_SIZE) {
  2930.         print "  <TD ALIGN=\"LEFT\" BACKGROUND=\"$YEL_PIX\">".
  2931.           "<IMG BORDER=\"0\" ".
  2932.           "SRC=\"pict/file_h_siz_cur.jpg\" ".
  2933.           "WIDTH=\"53\" HEIGHT=20 ".
  2934.           "ALT=\"Size\">".
  2935.           "</TD>\n";
  2936.     } else {
  2937.         $iurl = $url."&sort=$SORT_SIZE";
  2938.         print "  <TD ALIGN=\"LEFT\" BACKGROUND=\"$YEL_PIX\">".
  2939.           "<A HREF=\"$iurl\" TARGET=\"_parent\">".
  2940.           "<IMG BORDER=\"0\" ".
  2941.           "SRC=\"pict/file_h_siz_link.jpg\" ".
  2942.           "WIDTH=\"31\" HEIGHT=20 ".
  2943.           "ALT=\"Size\">".
  2944.           "</A></TD>\n";
  2945.     }
  2946.  
  2947.     print "  <TD BACKGROUND=\"$YEL_PIX\">$sp</TD>\n";
  2948.  
  2949.     # UID
  2950.     if ($sort == $SORT_UID) {
  2951.         print "  <TD ALIGN=\"LEFT\" BACKGROUND=\"$YEL_PIX\">".
  2952.           "<IMG BORDER=\"0\" ".
  2953.           "SRC=\"pict/file_h_uid_cur.jpg\" ".
  2954.           "WIDTH=\"49\" HEIGHT=20 ".
  2955.           "ALT=\"UID\">".
  2956.           "</TD>\n";
  2957.     } else {
  2958.         $iurl = $url."&sort=$SORT_UID";
  2959.         print "  <TD ALIGN=\"LEFT\" BACKGROUND=\"$YEL_PIX\">".
  2960.           "<A HREF=\"$iurl\" TARGET=\"_parent\">".
  2961.           "<IMG BORDER=\"0\" ".
  2962.           "SRC=\"pict/file_h_uid_link.jpg\" ".
  2963.           "WIDTH=\"27\" HEIGHT=20 ".
  2964.           "ALT=\"UID\">".
  2965.           "</A></TD>\n";
  2966.     }
  2967.  
  2968.     print "  <TD BACKGROUND=\"$YEL_PIX\">$sp</TD>\n";
  2969.  
  2970.     # GID
  2971.     if ($sort == $SORT_GID) {
  2972.         print "  <TD ALIGN=\"LEFT\" BACKGROUND=\"$YEL_PIX\">".
  2973.           "<IMG BORDER=\"0\" ".
  2974.           "SRC=\"pict/file_h_gid_cur.jpg\" ".
  2975.           "WIDTH=\"49\" HEIGHT=20 ".
  2976.           "ALT=\"GID\">".
  2977.           "</TD>\n";
  2978.     } else {
  2979.         $iurl = $url."&sort=$SORT_GID";
  2980.         print "  <TD ALIGN=\"LEFT\" BACKGROUND=\"$YEL_PIX\">".
  2981.           "<A HREF=\"$iurl\" TARGET=\"_parent\">".
  2982.           "<IMG BORDER=\"0\" ".
  2983.           "SRC=\"pict/file_h_gid_link.jpg\" ".
  2984.           "WIDTH=\"28\" HEIGHT=20 ".
  2985.           "ALT=\"GID\">".
  2986.           "</A></TD>\n";
  2987.     }
  2988.  
  2989.     print "  <TD BACKGROUND=\"$YEL_PIX\">$sp</TD>\n";
  2990.  
  2991.     # Inode
  2992.     if ($sort == $SORT_INODE) {
  2993.         print "  <TD ALIGN=\"LEFT\" BACKGROUND=\"$YEL_PIX\">".
  2994.           "<IMG BORDER=\"0\" ".
  2995.           "SRC=\"pict/file_h_meta_cur.jpg\" ".
  2996.           "WIDTH=\"62\" HEIGHT=20 ".
  2997.           "ALT=\"Meta\">".
  2998.           "</TD>\n";
  2999.     } else {
  3000.         $iurl = $url."&sort=$SORT_INODE";
  3001.         print "  <TD ALIGN=\"LEFT\" BACKGROUND=\"$YEL_PIX\">".
  3002.           "<A HREF=\"$iurl\" TARGET=\"_parent\">".
  3003.           "<IMG BORDER=\"0\" ".
  3004.           "SRC=\"pict/file_h_meta_link.jpg\" ".
  3005.           "WIDTH=\"41\" HEIGHT=20 ".
  3006.           "ALT=\"Meta\">".
  3007.           "</A></TD>\n";
  3008.     }
  3009.     print "</TR>\n";
  3010.  
  3011.  
  3012.  
  3013.  
  3014.     my $cnt = 0;
  3015.  
  3016.     # sort into arrays
  3017.     while (<OUT>) {
  3018.         if (/^([\?dfcbrlsw-])\/([\?dfcbrlsw-])\s*(\*?)\s*($REG_INODE)(\(realloc\))?:\t(.+?)\t($REG_DATE)\t($REG_DATE)\t($REG_DATE)\t(\d+)\t(\d+)\t(\d+)$/o) {
  3019.  
  3020.             my $lcldir = $args{'dir'};
  3021.             $dtype[$cnt] = $1;
  3022.             $itype[$cnt] = $2;
  3023.             $del[$cnt] = $3;
  3024.             $inode[$cnt] = $4;
  3025.             $realloc[$cnt] = "";
  3026.             $realloc[$cnt] = $5 if (defined $5);
  3027.             $name[$cnt] = $6;
  3028.             $mod[$cnt] = $7;
  3029.             $acc[$cnt] = $8;
  3030.             $chg[$cnt] = $9;
  3031.             $size[$cnt] = $10;
  3032.             $gid[$cnt] = $11;
  3033.             $uid[$cnt] = $12;
  3034.  
  3035.             if ($inode[$cnt] =~ /^(\d+)(-\d+(-\d+)?)?$/) {
  3036.                 $inode_int[$cnt] = $1;
  3037.             } else {
  3038.                 $inode_int[$cnt] = $inode[$cnt];
  3039.             }
  3040.  
  3041.             # We must adjust the dir for directories
  3042.             if ($itype[$cnt] eq 'd') {
  3043.                 # special cases for .. and .
  3044.                 if ($name[$cnt] eq '..') {
  3045.                     my @dirs = split ('/', $lcldir);
  3046.                     my $i;
  3047.                     $lcldir = "";
  3048.                     for ($i = 0; $i < $#dirs; $i++) {
  3049.                         $lcldir .= ($dirs[$i].'/');
  3050.                     }
  3051.                 }
  3052.                 elsif ($name[$cnt] ne '.') {
  3053.                     $lcldir .= ($name[$cnt].'/');
  3054.                 }
  3055.                 $name[$cnt] .= '/';
  3056.             }
  3057.             else {
  3058.                 $lcldir .= $name[$cnt];
  3059.             }
  3060.  
  3061.  
  3062.             # format the date so that the time and time zone are on the
  3063.             # same line
  3064.             $mod[$cnt] = "$1 $2"  
  3065.               if ($mod[$cnt] =~ /($REG_DAY\s+$REG_TIME)\s+($REG_ZONE2)/o);
  3066.  
  3067.             $acc[$cnt] = "$1 $2"  
  3068.               if ($acc[$cnt] =~ /($REG_DAY\s+$REG_TIME)\s+($REG_ZONE2)/o);
  3069.  
  3070.             $chg[$cnt] = "$1 $2"  
  3071.               if ($chg[$cnt] =~ /($REG_DAY\s+$REG_TIME)\s+($REG_ZONE2)/o);
  3072.  
  3073.             $dir[$cnt] = url_encode($lcldir);
  3074.             $entry[$cnt] = $cnt;
  3075.             $cnt++;
  3076.  
  3077.         } 
  3078.         # We missed it for some reason
  3079.         else {
  3080.             print "<TR><TD COLSPAN=10>Error Parsing File (Invalid Characters?):<BR>$_</TD></TR>\n";
  3081.         }
  3082.     }
  3083.  
  3084.     if ($cnt == 0) {
  3085.         print "</TABLE>\n<CENTER>No Contents</CENTER>\n";
  3086.         return 0;
  3087.     }
  3088.  
  3089.     close (OUT);
  3090.  
  3091.     # Sort the above array based on the sort argument
  3092.     my @sorted;    # an array of indices
  3093.  
  3094.     if ($sort == $SORT_DTYPE) {
  3095.         @sorted = sort {
  3096.             $dtype[$a] cmp $dtype[$b] or
  3097.             lc($name[$a]) cmp lc($name[$b])
  3098.         } @entry;
  3099.     } elsif ($sort == $SORT_ITYPE) {
  3100.         @sorted = sort {
  3101.             $itype[$a] cmp $itype[$b] or
  3102.             lc($name[$a]) cmp lc($name[$b])
  3103.         } @entry;
  3104.     } elsif ($sort == $SORT_NAME) {
  3105.         @sorted = sort {
  3106.             lc($name[$a]) cmp lc($name[$b])
  3107.         } @entry;
  3108.     } elsif ($sort == $SORT_MOD) {
  3109.         @sorted = sort {
  3110.             $mod[$a] cmp $mod[$b] or
  3111.             lc($name[$a]) cmp lc($name[$b])
  3112.         } @entry;
  3113.     } elsif ($sort == $SORT_ACC) {
  3114.         @sorted = sort {
  3115.             $acc[$a] cmp $acc[$b] or
  3116.             lc($name[$a]) cmp lc($name[$b])
  3117.         } @entry;
  3118.     } elsif ($sort == $SORT_CHG) {
  3119.         @sorted = sort {
  3120.             $chg[$a] cmp $chg[$b] or
  3121.             lc($name[$a]) cmp lc($name[$b])
  3122.         } @entry;
  3123.     } elsif ($sort == $SORT_SIZE) {
  3124.         @sorted = sort {
  3125.             $size[$a] <=> $size[$b] or
  3126.             lc($name[$a]) cmp lc($name[$b])
  3127.         } @entry;
  3128.     } elsif ($sort == $SORT_UID) {
  3129.         @sorted = sort {
  3130.             $uid[$a] <=> $uid[$b] or
  3131.             lc($name[$a]) cmp lc($name[$b])
  3132.         } @entry;
  3133.     } elsif ($sort == $SORT_GID) {
  3134.         @sorted = sort {
  3135.             $gid[$a] <=> $gid[$b] or
  3136.             lc($name[$a]) cmp lc($name[$b])
  3137.         } @entry;
  3138.     } elsif ($sort == $SORT_INODE) {
  3139.         @sorted = sort {
  3140.             $inode_int[$a] <=> $inode_int[$b] or
  3141.             lc($name[$a]) cmp lc($name[$b])
  3142.         } @entry;
  3143.     } elsif ($sort == $SORT_DEL) {
  3144.         @sorted = sort {
  3145.             $del[$b] cmp $del[$a] or
  3146.             lc($name[$a]) cmp lc($name[$b])
  3147.         } @entry;
  3148.     }
  3149.  
  3150.     # print them based on sorting
  3151.     my $row = 0;
  3152.     foreach my $i (@sorted) {
  3153.         my $url;
  3154.         my $target;
  3155.         my $func;
  3156.         my $color;
  3157.         my $lcolor;
  3158.         if ($del[$i] eq '*') {
  3159.             $color = "<FONT COLOR=\"".$DEL_COLOR[$realloc[$i] ne ""]."\">";
  3160.             $lcolor = $color;
  3161.         } else {
  3162.             $color = "<FONT COLOR=\"$NORM_COLOR\">";
  3163.             $lcolor = "<FONT COLOR=\"$LINK_COLOR\">";
  3164.         }
  3165.  
  3166.         # directories have different targets and func values
  3167.         if ($itype[$i] eq 'd') {
  3168.             $target = "list";
  3169.             $url="$PROGNAME?func=$FIL_LIST&$baseargs&inode=$inode_int[$i]".
  3170.               "&sort=$sort&dir=$dir[$i]&dmode=$enc_args{'dmode'}";
  3171.         }
  3172.         else {
  3173.             $target = "content";
  3174.             $url="$PROGNAME?func=$FIL_CMENU_FR&$baseargs&inode=$inode[$i]".
  3175.                "&sort=$sort&dir=$dir[$i]&dmode=$enc_args{'dmode'}";
  3176.         }
  3177.  
  3178.         if (($row % 2) == 0) {
  3179.             print "<TR VALIGN=\"TOP\" BGCOLOR=\"$BACK_COLOR\">\n  <TD ALIGN=\"CENTER\">";
  3180.         } else {
  3181.             print "<TR VALIGN=\"TOP\" BGCOLOR=\"$BACK_COLOR_TABLE\">\n  <TD ALIGN=\"CENTER\">";
  3182.         }
  3183.  
  3184.         print "<IMG SRC=\"pict/file_b_check.jpg\" BORDER=\"0\">\n"
  3185.           if ($del[$i] eq '*') ;
  3186.  
  3187.         print "</TD>\n".
  3188.           "  <TD>$sp</TD>\n".
  3189.           "  <TD ALIGN=\"CENTER\">${color}$dtype[$i] / $itype[$i]</TD>\n".
  3190.           "  <TD>$sp</TD>\n";
  3191.  
  3192.         # for valid files and directories make a link
  3193.         if ( ($inode_int[$i] >= $first_inode{$ftype}) && 
  3194.          ($size[$i] > 0) && 
  3195.          (($itype[$i] eq 'r') || ($itype[$i] eq 'd'))) {
  3196.             print "  <TD><A HREF=\"$url\" TARGET=\"$target\">$lcolor";
  3197.         } 
  3198.         else {
  3199.             print "  <TD>$color";
  3200.         }
  3201.         print "<TT>$name[$i]</TT></TD>\n".
  3202.           "  <TD>$sp</TD>\n".
  3203.           "  <TD>${color}$mod[$i]</TD>\n".
  3204.           "  <TD>$sp</TD>\n".
  3205.           "  <TD>${color}$acc[$i]</TD>\n".
  3206.           "  <TD>$sp</TD>\n".
  3207.           "  <TD>${color}$chg[$i]</TD>\n".
  3208.           "  <TD>$sp</TD>\n".
  3209.           "  <TD>${color}$size[$i]</TD>\n".
  3210.           "  <TD>$sp</TD>\n".
  3211.           "  <TD>${color}$uid[$i]</TD>\n".
  3212.           "  <TD>$sp</TD>\n".
  3213.           "  <TD>${color}$gid[$i]</TD>\n".
  3214.           "  <TD>$sp</TD>\n";
  3215.           
  3216.         # for a valid inode, make a link to inode browsing mode
  3217.         if ($inode_int[$i] >= $first_inode{$ftype}) {
  3218.             my $iurl="$PROGNAME?func=$MAIN_FR&mode=$INO_MAIN&$baseargs&inode=$inode[$i]";
  3219.             print "<TD><A HREF=\"$iurl\" TARGET=\"_blank\">$lcolor";
  3220.         }
  3221.         else {
  3222.             print "<TD>$color";
  3223.         }
  3224.         print "$inode[$i]</A> $realloc[$i]</TD>\n</TR>\n";
  3225.  
  3226.         $row++;
  3227.     }
  3228.  
  3229.     print "</TABLE>\n";
  3230.     return 0;
  3231.  
  3232. }; #end of FIL_LIST
  3233.  
  3234.  
  3235. # This takes a directory name as an argument and converts it to
  3236. # the inode value and calls FIL_LIST
  3237. #
  3238. # The inode value can be anything when this is run, it will be 
  3239. # overwritten
  3240. $funcs[$FIL_NAME] = sub {
  3241.     check_dir(); 
  3242.  
  3243.     my $ftype = get_ftype();
  3244.     my $img = get_img('img');
  3245.     my $dir = get_dir();
  3246.  
  3247.     log_host_inv ("$args{'img'}: Finding meta data address for $dir");
  3248.  
  3249.     # Use 'ifind -n' to get the inode
  3250.     local *OUT;    
  3251.     exec_pipe(*OUT, "'${TASKDIR}ifind' -f $ftype -n '$dir' '$img'");
  3252.     my $inode;
  3253.     while (<OUT>) {
  3254.         $inode = $1
  3255.             if (/^($REG_INODE)$/);
  3256.     }
  3257.     close (OUT);
  3258.  
  3259.     unless ($inode =~ /^$REG_INODE$/) {
  3260.         print_check_err ("Error finding meta data address for $dir: $inode");
  3261.     }
  3262.  
  3263.     # Verify it is a directory with istat
  3264.     exec_pipe(*OUT, "'${TASKDIR}istat' -f $ftype '$img' $inode");
  3265.  
  3266.     while (<OUT>) {
  3267.  
  3268.  
  3269.         # This is a directory 
  3270.         if ((/mode:\s+d/)  || (/DOS Mode: Directory/)) {
  3271.             close (OUT);
  3272.  
  3273.             # Set the inode variables
  3274.             $enc_args{'inode'} = $args{'inode'} = $inode;
  3275.  
  3276.             $args{'dir'} .= "/"
  3277.                 unless ($args{'dir'} =~ /.*?\/$/);
  3278.             $enc_args{'dir'} .= "/"
  3279.                 unless ($enc_args{'dir'} =~ /.*?\/$/);
  3280.  
  3281.             # List the directory contents
  3282.             & {$funcs[$FIL_LIST]};
  3283.             
  3284.             return 0;
  3285.         }
  3286.     }
  3287.     close (OUT);
  3288.  
  3289.     # This is not a directory, so just give a link
  3290.     print_html_header("");
  3291.  
  3292. print <<EOF;
  3293.  
  3294. <TT>$dir</TT> (
  3295. <A HREF=\"$PROGNAME?func=$MAIN_FR&mode=$INO_MAIN&$baseargs&inode=$inode\" TARGET=_blank>
  3296. inode $inode</A>) is not a directory.
  3297.  
  3298. <P>
  3299. <A HREF=\"$PROGNAME?func=$FIL_CMENU_FR&$baseargs&inode=$inode&dir=$dir\" TARGET=\"content\">
  3300.   <IMG SRC=\"pict/but_view.jpg\" HEIGHT=20 WIDTH=123 ALT=\"view contents\" BORDER=\"0\">
  3301. </A>
  3302.  
  3303. EOF
  3304.     return 1;
  3305.  
  3306. };
  3307.  
  3308.  
  3309. # Content Frame
  3310. # This creates two frames for the lower rhs frame
  3311. #
  3312. $funcs[$FIL_CMENU_FR] = sub {
  3313.     check_inode('inode'); check_dir();
  3314.  
  3315.     print_html_header_frameset("");
  3316.  
  3317.     print "<FRAMESET ROWS=\"65,*\">\n";
  3318.  
  3319.     print "<FRAME SRC=\"$PROGNAME?func=$FIL_CMENU&$baseargs".
  3320.       "&dir=$enc_args{'dir'}&inode=$enc_args{'inode'}".
  3321.       "&sort=$FIL_SORT_ASC\">\n";
  3322.  
  3323.     print "<FRAME SRC=\"$PROGNAME?func=$FIL_CONT&$baseargs".
  3324.       "&dir=$enc_args{'dir'}&inode=$enc_args{'inode'}".
  3325.       "&sort=$FIL_SORT_ASC\" NAME=\"cont2\">\n</FRAMESET>";
  3326.  
  3327.     return 0;
  3328. };
  3329.  
  3330.  
  3331. # This is the index for the lower rhs frame
  3332. # Choose the content display type here
  3333. $funcs[$FIL_CMENU] = sub {
  3334.     check_inode('inode'); check_dir(); check_sort(); 
  3335.  
  3336.     print_html_header("");
  3337.  
  3338.     my $inode = get_inode('inode');
  3339.     my $img = get_img('img');
  3340.     my $ftype = get_ftype();
  3341.  
  3342.     # get the type of contents
  3343.     local *OUT;    
  3344.     exec_pipe(*OUT, 
  3345.       "'${TASKDIR}icat' -f $ftype '$img' $inode | '${TASKDIR}file' -z -b -");
  3346.  
  3347.  
  3348.     my $file_type = <OUT>;
  3349.     close (OUT);
  3350.  
  3351.     $file_type = "Error getting file type"
  3352.       if ((!defined $file_type) || ($file_type eq ""));
  3353.  
  3354.     # We already have the path in the content window below, so save space
  3355.     # print "<CENTER><TT>$args{'mnt'}$args{'dir'}</TT>\n";
  3356.     print "<CENTER>\n";
  3357.     my $url = "&$baseargs&dir=$enc_args{'dir'}&inode=$enc_args{'inode'}";
  3358.  
  3359.     # Print the options for output display
  3360.     print "<TABLE CELLSPACING=\"0\" CELLPADDING=\"2\">\n<TR>\n".
  3361.       "<TD>ASCII (<A HREF=\"$PROGNAME?func=$FIL_CONT&sort=$FIL_SORT_ASC$url\"".
  3362.        "TARGET=\"cont2\">display</A> - ".
  3363.       "<A HREF=\"$PROGNAME?func=$FIL_REP&sort=$FIL_SORT_ASC$url\"".
  3364.       "TARGET=\"_blank\">report</A>)</TD>\n".
  3365.       "<TD>*</TD>\n".
  3366.       "<TD>Strings (".
  3367.       "<A HREF=\"$PROGNAME?func=$FIL_CONT&sort=$FIL_SORT_STR$url\"".
  3368.        "TARGET=\"cont2\">display</A> - ".
  3369.       "<A HREF=\"$PROGNAME?func=$FIL_REP&sort=$FIL_SORT_STR$url\"".
  3370.       "TARGET=\"_blank\">report</A>)</TD>\n".
  3371.       "<TD>*</TD>\n".
  3372.       "<TD><A HREF=\"$PROGNAME?func=$FIL_SAVE&$url\">".
  3373.       "Export</A></TD>\n";
  3374.  
  3375.     # if the file is either image or HTML, then let them view it 
  3376.     if (($file_type =~ /image data/) || ($file_type =~ /HTML document text/) ||
  3377.      ($file_type =~ /PC bitmap data/)) {
  3378.       print "<TD>*</TD>\n<TD><A HREF=\"$PROGNAME?func=$CELL_MAIN$url\"".
  3379.       "TARGET=\"_blank\">View</A></TD>\n";
  3380.     }
  3381.  
  3382.     print "<TD>*</TD>\n".
  3383.       "<TD><A HREF=\"$PROGNAME?func=$NOTES_ENT$url\" TARGET=\"_blank\">".
  3384.       "Add Note</A></TD>\n" if ($USE_NOTES == 1);
  3385.  
  3386.     print "</TR></TABLE>\n";
  3387.  
  3388.     print "File Type: $file_type";
  3389.     print "</CENTER>";
  3390.  
  3391.     return 0;
  3392. };
  3393.  
  3394. # display deleted files only
  3395. #
  3396. # Sorting should be added to this
  3397. $funcs[$FIL_DEL] = sub {
  3398.     check_inode('inode'); check_dir(); check_sort(); 
  3399.  
  3400.     print_html_header("Deleted files on $args{'img'} $args{'mnt'}");
  3401.  
  3402.     my $inode = get_inode('inode');
  3403.     my $img = get_img('img');
  3404.     my $ftype = get_ftype();
  3405.     my $sort = get_sort();
  3406.  
  3407.     my $sp = "  ";
  3408.  
  3409.     log_host_inv ("$args{'img'}: Listing all deleted files");
  3410.  
  3411.     local *OUT;
  3412.     exec_pipe(*OUT, 
  3413.       "'${TASKDIR}fls' -f $ftype -ldr -z '$tz' -s $ts '$img' $inode");
  3414.  
  3415.  
  3416.     print "<TABLE CELLSPACING=\"0\" CELLPADDING=\"2\"  BORDER=0>\n".
  3417.       "<TR VALIGN=\"MIDDLE\" ALIGN=\"LEFT\" ".
  3418.       "BACKGROUND=\"$YEL_PIX\">\n";
  3419.  
  3420.     # Type
  3421.     print "<TH ALIGN=\"CENTER\">  Type  <BR>".
  3422.       "dir / in</TH>".
  3423.       "<TD>$sp</TD>\n";
  3424.  
  3425.  
  3426.     # Name
  3427.     print "  <TD><IMG BORDER=\"0\" ".
  3428.       "SRC=\"pict/file_h_nam_link.jpg\" ".
  3429.       "WIDTH=\"50\" HEIGHT=20 ".
  3430.       "ALT=\"File Name\">".
  3431.       "</TD>\n".
  3432.       "<TD>$sp</TD>\n";
  3433.  
  3434.     # Mod / Written
  3435.     print "  <TD><IMG BORDER=\"0\" ";
  3436.     if ($mtime_str{$ftype} eq 'Modified') {
  3437.         print "SRC=\"pict/file_h_mod_link.jpg\" ".
  3438.           "WIDTH=\"62\" HEIGHT=20 ".
  3439.           "ALT=\"Modified Time\">";
  3440.     } else {
  3441.         print "SRC=\"pict/file_h_wr_link.jpg\" ".
  3442.           "WIDTH=\"60\" ".
  3443.           "ALT=\"Written Time\">";
  3444.     }
  3445.     print "</TD>\n".
  3446.       "<TD>$sp</TD>\n";
  3447.  
  3448.     # Access
  3449.     print "  <TD><IMG BORDER=\"0\" ".
  3450.       "SRC=\"pict/file_h_acc_link.jpg\" ".
  3451.       "WIDTH=\"66\" HEIGHT=20 ".
  3452.       "ALT=\"Access Time\">".
  3453.       "</TD>\n".
  3454.       "<TD>$sp</TD>\n";
  3455.  
  3456.     # Change / Create
  3457.     print "  <TD><IMG BORDER=\"0\" ";
  3458.     if ($ctime_str{$ftype} eq 'Changed') {    
  3459.         print "SRC=\"pict/file_h_chg_link.jpg\" ".
  3460.           "WIDTH=\"62\" HEIGHT=20 ".
  3461.           "ALT=\"Change Time\">";
  3462.     } else {
  3463.         print  "SRC=\"pict/file_h_cre_link.jpg\" ".
  3464.           "WIDTH=\"59\" HEIGHT=20 ".
  3465.           "ALT=\"Create Time\">";
  3466.     }
  3467.     print "</TD>\n".
  3468.       "<TD>$sp</TD>\n";
  3469.  
  3470.     # Size
  3471.     print "  <TD><IMG BORDER=\"0\" ".
  3472.       "SRC=\"pict/file_h_siz_link.jpg\" ".
  3473.       "WIDTH=\"31\" HEIGHT=20 ".
  3474.       "ALT=\"Size\">".
  3475.       "</TD>\n".
  3476.       "<TD>$sp</TD>\n";
  3477.  
  3478.     # UID
  3479.     print "  <TD><IMG BORDER=\"0\" ".
  3480.       "SRC=\"pict/file_h_uid_link.jpg\" ".
  3481.       "WIDTH=\"27\" HEIGHT=20 ".
  3482.       "ALT=\"UID\">".
  3483.       "</TD>\n".
  3484.       "<TD>$sp</TD>\n";
  3485.  
  3486.     # GID
  3487.     print "  <TD><IMG BORDER=\"0\" ".
  3488.       "SRC=\"pict/file_h_gid_link.jpg\" ".
  3489.       "WIDTH=\"28\" HEIGHT=20 ".
  3490.       "ALT=\"GID\">".
  3491.       "</TD>\n".
  3492.       "<TD>$sp</TD>\n";
  3493.  
  3494.     # Inode
  3495.     print "  <TD><IMG BORDER=\"0\" ".
  3496.       "SRC=\"pict/file_h_meta_link.jpg\" ".
  3497.       "WIDTH=\"41\" HEIGHT=20 ".
  3498.       "ALT=\"Meta\">".
  3499.       "</TD>\n".
  3500.       "<TD>$sp</TD>\n";
  3501.  
  3502.  
  3503.     my $row = 0;
  3504.     while (<OUT>) {
  3505.  
  3506.         if (/^([\?dfcbrlsw-])\/([\?dfcbrlsw-])\s*(\*?)\s*($REG_INODE)(\(realloc\))?:\t(.+?)\t($REG_DATE)\t($REG_DATE)\t($REG_DATE)\t(\d+)\t(\d+)\t(\d+)$/o) {
  3507.  
  3508.             # We have to remove the / from the beginning of the file name so
  3509.             # save all values so they aren't lost
  3510.             my $dt = $1;
  3511.             my $it = $2;
  3512.             my $d = $3;
  3513.             my $i = $4;
  3514.             my $r = 0;
  3515.             $r = 1 if (defined $5);
  3516.             my $n = $6;
  3517.             my $m = $7;
  3518.             my $a = $8;
  3519.             my $c = $9;
  3520.             my $s = $10;
  3521.             my $g = $11; 
  3522.             my $u = $12;
  3523.  
  3524.             if ($n =~ /^\/(.*)/) {
  3525.                 $n = $1;
  3526.             }
  3527.             my $enc_n = url_encode($n);
  3528.             my $iurl="$PROGNAME?func=$INO_CONT&$baseargs&inode=$i";
  3529.  
  3530.             my $i_int = $i;
  3531.             $i_int = $1 if ($i =~ /(\d+)-\d+-\d+/);
  3532.  
  3533.             if (($row % 2) == 0) {
  3534.                 print "<TR VALIGN=\"TOP\" BGCOLOR=\"$BACK_COLOR\">\n";
  3535.             } else {
  3536.                 print "<TR VALIGN=\"TOP\" BGCOLOR=\"$BACK_COLOR_TABLE\">\n";
  3537.             }
  3538.  
  3539.             print "<TD ALIGN=\"CENTER\"><FONT COLOR=\"$DEL_COLOR[$r]\">".
  3540.               "$dt / $it</TD>".
  3541.               "<TD>$sp</TD>\n";
  3542.  
  3543.             if ($it eq 'd') {
  3544.                 my $url="$PROGNAME?func=$FIL_LIST&$baseargs&inode=$i".
  3545.                     "&sort=$sort&dir=$enc_n";
  3546.  
  3547.                 print "<TD>";
  3548.                 if ($i_int >= $first_inode{$ftype}) {
  3549.                     print "<A HREF=\"$url\" target=\"_self\">";
  3550.                 } 
  3551.                 print "<FONT COLOR=\"$DEL_COLOR[$r]\"><TT>".
  3552.                   "$args{'mnt'}$n</TT></TD>".
  3553.                   "<TD>$sp</TD>\n";
  3554.             }
  3555.             else {
  3556.                 my $url="$PROGNAME?func=$FIL_CMENU_FR&$baseargs&inode=$i".
  3557.                     "&sort=$sort&dir=$enc_n";
  3558.             
  3559.                 print "<TD>";
  3560.                 if (($i_int >= $first_inode{$ftype}) && ($it eq 'r')) {
  3561.                     print "<A HREF=\"$url\" target=\"content\">";
  3562.                 } 
  3563.                 print "<FONT COLOR=\"$DEL_COLOR[$r]\"><TT>".
  3564.                   "$args{'mnt'}$n</TT></TD>".
  3565.                   "<TD>$sp</TD>\n";
  3566.             }
  3567.  
  3568.  
  3569.             $m = "$1 $2"  
  3570.               if ($m =~ /($REG_DAY\s+$REG_TIME)\s+($REG_ZONE2)/o);
  3571.             $a = "$1 $2"  
  3572.               if ($a =~ /($REG_DAY\s+$REG_TIME)\s+($REG_ZONE2)/o);
  3573.             $c = "$1 $2"  
  3574.               if ($c =~ /($REG_DAY\s+$REG_TIME)\s+($REG_ZONE2)/o);
  3575.  
  3576.             print "<TD><FONT COLOR=\"$DEL_COLOR[$r]\">$m</TD>".
  3577.               "<TD>$sp</TD>\n".
  3578.               "<TD><FONT COLOR=\"$DEL_COLOR[$r]\">$a</TD>".
  3579.               "<TD>$sp</TD>\n".
  3580.               "<TD><FONT COLOR=\"$DEL_COLOR[$r]\">$c</TD>".
  3581.               "<TD>$sp</TD>\n".
  3582.               "<TD><FONT COLOR=\"$DEL_COLOR[$r]\">$s</TD>".
  3583.               "<TD>$sp</TD>\n".
  3584.               "<TD><FONT COLOR=\"$DEL_COLOR[$r]\">$g</TD>".
  3585.               "<TD>$sp</TD>\n".
  3586.               "<TD><FONT COLOR=\"$DEL_COLOR[$r]\">$u</TD>".
  3587.               "<TD>$sp</TD>\n";
  3588.  
  3589.             print "<TD>";
  3590.             if ($i_int >= $first_inode{$ftype}) {
  3591.                 print "<A HREF=\"$iurl\" target=\"content\">";
  3592.             }
  3593.             print "<FONT COLOR=\"$DEL_COLOR[$r]\">$i</A>";
  3594.             print " (realloc)" if $r;
  3595.             print "</TD></TR>\n";
  3596.         }
  3597.         else {
  3598.             print "Error Parsing File (invalid characters?)<BR>: $_\n<BR>";
  3599.         }
  3600.  
  3601.         $row++;
  3602.     }
  3603.     close(OUT);
  3604.     print "</TABLE>\n";
  3605.  
  3606.     if ($row == 0) {
  3607.         print "<CENTER>None</CENTER>\n";
  3608.         return 0;
  3609.     }
  3610. };
  3611.  
  3612.  
  3613. #
  3614. # Display the actual content here
  3615. #
  3616. # NOTE: This has a media type of raw text
  3617. #
  3618. $funcs[$FIL_CONT] = sub {
  3619.     check_inode('inode'); check_dir(); check_sort(); 
  3620.  
  3621.     print_text_header();
  3622.     print "\n";
  3623.  
  3624.     my $sort = get_sort();
  3625.     my $inode = get_inode('inode');
  3626.     my $img = get_img('img');
  3627.     my $ftype = get_ftype();
  3628.  
  3629.     my $fname = "$args{'mnt'}$args{'dir'}";
  3630.  
  3631.     local *OUT;    
  3632.     if ($sort == $FIL_SORT_ASC) {
  3633.         log_host_inv ("$args{'img'}: Viewing $fname ($inode) as ASCII");
  3634.  
  3635.         exec_pipe(*OUT, "'${TASKDIR}icat' -f $ftype -H '$img' $inode");
  3636.  
  3637.         print "Contents Of File: $fname\n\n\n\n";
  3638.         print_output ($_) while (<OUT>);
  3639.         close (OUT);
  3640.  
  3641.     } elsif ($sort == $FIL_SORT_STR) {
  3642.         log_host_inv ("$args{'img'}: Viewing $fname ($inode) as strings");
  3643.  
  3644.         exec_pipe(*OUT, "'${TASKDIR}icat' -f $ftype -H '$img' $inode | '$STRINGS_EXE' -a");
  3645.  
  3646.         print "String Contents Of File: $fname\n\n\n\n";
  3647.         print_output ($_) while (<OUT>);
  3648.         close (OUT);
  3649.     }
  3650.  
  3651.     return 0;
  3652. };
  3653.  
  3654. # Export the contents of a file
  3655. $funcs[$FIL_SAVE] = sub {
  3656.     check_inode('inode'); check_dir(); 
  3657.  
  3658.  
  3659.     my $inode = get_inode('inode');
  3660.     my $img = get_img('img');
  3661.     my $ftype = get_ftype();
  3662.     my $fname = "$args{'mnt'}$args{'dir'}";
  3663.     
  3664.     log_host_inv ("$args{'img'}: Saving contents of $fname ($inode)");
  3665.  
  3666.     local *OUT;    
  3667.     exec_pipe(*OUT, "'${TASKDIR}icat'  -f $ftype '$img' $inode");
  3668.  
  3669.  
  3670.     print_oct_header();
  3671.  
  3672.     # We can't trust the mnt and dir values (since there 
  3673.     # could be bad ASCII values, so only allow basic chars into name
  3674.     $fname =~ tr/a-zA-Z0-9\_\-\@\,/\./c;
  3675.     $fname = $1 if ($fname =~ /^\.(.*)$/); 
  3676.  
  3677.     print "Content-Disposition: inline; ".
  3678.       "filename=${args{'img'}}-${fname};\n\n";
  3679.  
  3680.     print "$_" while(<OUT>);
  3681.  
  3682.     close (OUT);
  3683.     # we exit instead of return so that we don't get two \n\n at the end
  3684.     exit(0);
  3685. };
  3686.  
  3687.  
  3688.  
  3689.  
  3690. # Display a report for a file
  3691. # This is intended to have its own window
  3692. #
  3693. $funcs[$FIL_REP] = sub {
  3694.     check_inode('inode'); check_dir(); check_sort();
  3695.  
  3696.     print_text_header();
  3697.  
  3698.     my $sort = get_sort();
  3699.     my $img = get_img('img');
  3700.     my $inode = get_inode('inode');
  3701.     my $ftype = get_ftype();
  3702.     my $type;
  3703.     my $fname = "$args{'mnt'}$args{'dir'}";
  3704.  
  3705.  
  3706.     # We can't trust the mnt and dir values (since there 
  3707.     # could be bad ASCII values, so only allow basic chars into name
  3708.     $fname =~ tr/a-zA-Z0-9\_\-\@\,/\./c;
  3709.     $fname = $1 if ($fname =~ /^\.+(.*)$/); 
  3710.     $fname = $1 if ($fname =~ /^(.*?)\.+$/); 
  3711.  
  3712.     print "Content-Disposition: inline; ".
  3713.       "filename=${args{'img'}}-${fname}.txt;\n\n";
  3714.  
  3715.     $fname = "$args{'mnt'}$args{'dir'}";
  3716.     if ($sort == $FIL_SORT_ASC) {
  3717.         log_host_inv ("$args{'img'}: Generating ASCII report for $fname ($inode)");
  3718.         $type = "ascii";
  3719.     }elsif ($sort == $FIL_SORT_STR) {
  3720.         log_host_inv ("$args{'img'}: Generating strings report for $fname ($inode)");
  3721.         $type = "string";
  3722.     } else {
  3723.         print "\n\ninvalid sort value";
  3724.         return 1;
  3725.     }
  3726.  
  3727.  
  3728.     # NOTE: There is a space in the beginning of the separator lines in
  3729.     # order to make clear@stamper.itconsult.co.uk time stamping happy
  3730.     # I think it confuses the lines that begin at the lhs with PGP 
  3731.     # headers and will remove the second line.
  3732.     #
  3733.     print "           Autopsy $type Report (ver $VER)\n\n".
  3734.           "-" x 62 ."\n".
  3735.         "File: $fname\n";
  3736.  
  3737.     local *OUT;    
  3738.     exec_pipe(*OUT, 
  3739.       "'${TASKDIR}icat' -f $ftype -H '$img' $inode | '${TASKDIR}md5'");
  3740.     my $md5 = <OUT>;
  3741.     close (OUT);
  3742.  
  3743.     $md5 = "Error getting MD5 Value"
  3744.       if ((!defined $md5) || ($md5 eq ""));
  3745.  
  3746.     chomp $md5;
  3747.     print "MD5 of file: $md5\n";
  3748.  
  3749.     if ($sort == $FIL_SORT_STR) {
  3750.         exec_pipe(*OUT, 
  3751.           "'${TASKDIR}icat' -f $ftype -H '$img' $inode | '$STRINGS_EXE' -a | '${TASKDIR}md5'");
  3752.         $md5 = <OUT>;
  3753.         close (OUT);
  3754.  
  3755.         $md5 = "Error getting MD5 Value"
  3756.           if ((!defined $md5) || ($md5 eq ""));
  3757.  
  3758.         chomp $md5;
  3759.         print "MD5 of strings: $md5\n";
  3760.     }
  3761.  
  3762.     print "Image: $img\n";
  3763.     print "Image Type: $ftype\n";
  3764.  
  3765.     my $date = localtime();
  3766.     print "Date Generated: $date\n".
  3767.         "Investigator: $args{'inv'}\n".
  3768.         "-" x 62 ."\n";
  3769.  
  3770.     # Get the inode details 
  3771.     exec_pipe(*OUT, 
  3772.       "'${TASKDIR}istat' -f $ftype -z '$tz' -s $ts '$img' $inode");
  3773.     print "$_" while (<OUT>);
  3774.     close (OUT);
  3775.  
  3776.  
  3777.     # File Type
  3778.     exec_pipe(*OUT, 
  3779.       "'${TASKDIR}icat' -f $ftype '$img' $inode | '${TASKDIR}file' -z -b -");
  3780.     my $file_type = <OUT>;
  3781.     close (OUT);
  3782.  
  3783.     $file_type = "Error getting file type"
  3784.       if ((!defined $file_type) || ($file_type eq ""));
  3785.  
  3786.     print "\nFile Type: $file_type";
  3787.  
  3788.     print "\n"."-" x 62 ."\n";
  3789.  
  3790.     if ($sort == $FIL_SORT_ASC) {
  3791.         exec_pipe (*OUT,
  3792.           "'${TASKDIR}icat' -f $ftype -H '$img' $inode");
  3793.     } elsif ($sort == $FIL_SORT_STR) {
  3794.         exec_pipe (*OUT,
  3795.           "'${TASKDIR}icat' -f $ftype -H '$img' $inode | '$STRINGS_EXE' -a");
  3796.     }
  3797.  
  3798.     print_output($_) while (<OUT>);
  3799.     close (OUT);
  3800.     return 0;
  3801. };
  3802.  
  3803.  
  3804. # Generate the MD5 value for every file in a given directory and save
  3805. # them to a text file
  3806. $funcs[$FIL_MD5] = sub {
  3807.     check_inode('inode'); check_dir();
  3808.  
  3809.     print_text_header();
  3810.  
  3811.     my $img = get_img('img');
  3812.     my $inode = get_inode('inode');
  3813.     my $ftype = get_ftype();
  3814.     my $fname = "$args{'mnt'}$args{'dir'}";
  3815.     $fname = 'root' if ($fname eq '/');
  3816.  
  3817.     # We can't trust the mnt and dir values (since there 
  3818.     # could be bad ASCII values, so only allow basic chars into name
  3819.     $fname =~ tr/a-zA-Z0-9\_\-\@\,/\./c;
  3820.  
  3821.     # remove .'s at beginning and end
  3822.     $fname = $1 if ($fname =~ /^\.+(.*)$/); 
  3823.     $fname = $1 if ($fname =~ /^(.*?)\.+$/); 
  3824.     
  3825.     print "Content-Disposition: inline; ".
  3826.       "filename=$fname.md5;\n\n";
  3827.  
  3828.     $fname = "$args{'mnt'}$args{'dir'}";
  3829.  
  3830.     local *OUT;    
  3831.     exec_pipe(*OUT, "'${TASKDIR}fls' -f $ftype -Fu '$img' $inode");
  3832.  
  3833.     print "MD5 Values for files in $fname ($args{'img'})\n\n";
  3834.  
  3835.     while (<OUT>) {
  3836.         # area for allocated files
  3837.         if ((/r\/[\w\-]\s+([\d\-]+):\s+(.*)$/) ||
  3838.           (/-\/r\s+([\d\-]+):\s+(.*)$/)) {
  3839.             my $in = $1;
  3840.             my $name = $2;
  3841.  
  3842.             local *OUT_MD5;
  3843.             exec_pipe(*OUT_MD5, 
  3844.               "'${TASKDIR}icat' -f $ftype '$img' $in | '${TASKDIR}md5'");
  3845.             my $md5out = <OUT_MD5>;
  3846.  
  3847.             $md5out = "Error getting MD5" 
  3848.               if ((!defined $md5out) || ($md5out eq ""));
  3849.  
  3850.             chomp $md5out;
  3851.             print "$md5out\t$name\n";
  3852.             close (OUT_MD5);
  3853.         }
  3854.         elsif (/[\w\-]\/[\w\-]\s+([\d\-]+):\s+(.*)$/) {
  3855.         # ignore, non-file types such as sockets or symlinks that do not have
  3856.         # MD5 values that make sense
  3857.         }
  3858.         # Hmmmm
  3859.         else {
  3860.             print "Error parsing file (invalid characters?): $_\n";
  3861.         }
  3862.     }
  3863.     close (OUT);
  3864.  
  3865. };
  3866.  
  3867.  
  3868. ################# BLOCKS ##########################
  3869.  
  3870. # Generate the 2 frames for block browsing
  3871. $funcs[$BLK_MAIN] = sub {
  3872.  
  3873.     print_html_header_frameset("Data Browse on $args{'img'}");
  3874.  
  3875.     print "<FRAMESET COLS=\"20%,80%\">\n";
  3876.  
  3877.     # Data: Listings
  3878.     print "<FRAME SRC=\"$PROGNAME?func=$BLK_ENT&$baseargs".
  3879.       "&block=$enc_args{'block'}\">\n";
  3880.  
  3881.     # Data Contents
  3882.     if (exists $args{'block'}) {
  3883.         my $len = get_len();
  3884.  
  3885.         print "<FRAME SRC=\"$PROGNAME?func=$BLK_CMENU_FR&".
  3886.           "block=$enc_args{'block'}&$baseargs&len=$len\" ".
  3887.           "NAME=\"content\">\n</FRAMESET>\n";
  3888.     } 
  3889.     else {
  3890.         print "<FRAME SRC=\"$PROGNAME?func=$BLANK&$baseargs\" ".
  3891.           "NAME=\"content\">\n</FRAMESET>\n";
  3892.     }
  3893.  
  3894.     return 0;
  3895. };
  3896.  
  3897. # Frame to enter the data into
  3898. $funcs[$BLK_ENT] = sub {
  3899.  
  3900.     print_html_header("");
  3901.  
  3902.     my $ftype = get_ftype();
  3903.     my $bs = get_unitsize();
  3904.  
  3905.     print  "<FORM ACTION=\"$PROGNAME\" METHOD=\"GET\" ".
  3906.       "TARGET=\"content\">\n".
  3907.       "<INPUT TYPE=\"hidden\" NAME=\"func\" VALUE=\"$BLK_CMENU_FR\">\n".
  3908.       "<INPUT TYPE=\"hidden\" NAME=\"img\" VALUE=\"$args{'img'}\">\n".
  3909.       make_hidden().
  3910.  
  3911.     # Address
  3912.       "<B>$addr_unit{$ftype} Number:</B><BR>    ".
  3913.       "<INPUT TYPE=\"text\" NAME=\"block\" SIZE=12 MAXLENGTH=12";
  3914.     print " VALUE=\"$enc_args{'block'}\"" if (exists $args{'block'});
  3915.     print ">\n";
  3916.  
  3917.     # Number of units
  3918.     print "<P><B>Number of ${addr_unit{$ftype}}s:</B>".
  3919.       "<BR>    ".
  3920.       "<INPUT TYPE=\"text\" NAME=\"len\" VALUE=\"1\" SIZE=6 MAXLENGTH=6>\n";
  3921.  
  3922.     print "<P><B>${addr_unit{$ftype}} Size:</B>".
  3923.       " $bs\n";
  3924.  
  3925.     # dls images do not get to select this
  3926.     if (($ftype ne 'dls') && ($ftype ne 'swap') && ($ftype ne 'raw')) {
  3927.     print 
  3928.       "<P><B>Address Type:</B><BR>    ".
  3929.       "<SELECT NAME=\"btype\" SIZE=1>\n".
  3930.       "<OPTION VALUE=\"$BTYPE_DD\" SELECTED>Regular (dd)</OPTION>\n".
  3931.       "<OPTION VALUE=\"$BTYPE_DLS\">Unallocated (dls)</OPTION>\n".
  3932.       "</SELECT>\n";
  3933.     }
  3934.     else {
  3935.       print "<INPUT TYPE=\"hidden\" NAME=\"btype\" VALUE=\"$BTYPE_DD\">\n";
  3936.     }
  3937.  
  3938.  
  3939.     # Lazarus
  3940.     print "<P><B>Lazarus Addr:</B> ".
  3941.       "<INPUT TYPE=\"checkbox\" NAME=\"btype2\">\n".
  3942.       "<P><INPUT TYPE=\"IMAGE\" SRC=\"pict/but_ok.jpg\" ".
  3943.       "WIDTH=43 HEIGHT=20 ALT=\"Ok\" BORDER=\"0\">\n".
  3944.       "</FORM>\n";
  3945.  
  3946.     print "<P>".
  3947.       "<A HREF=\"$PROGNAME?func=$BLK_DLS&$baseargs\" TARGET=\"content\">".
  3948.       "<IMG SRC=\"pict/but_alloc_list.jpg\" BORDER=\"0\" ".
  3949.       "WIDTH=113 HEIGHT=20 ALT=\"Allocation List\"></A><BR>\n"
  3950.       unless (($ftype eq 'dls') || ($ftype eq 'swap') || ($ftype eq 'raw'));
  3951.  
  3952.     if ( ($ftype ne 'dls') && (exists $img2dls{$args{'img'}}) ) {
  3953.     print "<FORM ACTION=\"$PROGNAME\" METHOD=\"GET\" TARGET=\"_top\">\n".
  3954.       "<INPUT TYPE=\"hidden\" NAME=\"func\" VALUE=\"$MAIN_FR\">\n".
  3955.       "<INPUT TYPE=\"hidden\" NAME=\"mode\" VALUE=\"$BLK_MAIN\">\n".
  3956.       "<INPUT TYPE=\"hidden\" NAME=\"img\" VALUE=\"$img2dls{$args{'img'}}\">\n".
  3957.       make_hidden().
  3958.       "<P><INPUT TYPE=\"IMAGE\" SRC=\"pict/srch_b_lun.jpg\" ".
  3959.       "ALT=\"Load Unallocated Image\" BORDER=\"0\">\n<BR></FORM>\n";
  3960.     }
  3961.  
  3962.     elsif ( ($ftype eq 'dls') && (exists $mod2img{$args{'img'}}) ) {
  3963.     print "<FORM ACTION=\"$PROGNAME\" METHOD=\"GET\" TARGET=\"_top\">\n".
  3964.       "<INPUT TYPE=\"hidden\" NAME=\"func\" VALUE=\"$MAIN_FR\">\n".
  3965.       "<INPUT TYPE=\"hidden\" NAME=\"mode\" VALUE=\"$BLK_MAIN\">\n".
  3966.       "<INPUT TYPE=\"hidden\" NAME=\"img\" VALUE=\"$mod2img{$args{'img'}}\">\n".
  3967.       make_hidden().
  3968.       "<P><INPUT TYPE=\"IMAGE\" SRC=\"pict/srch_b_lorig.jpg\" ".
  3969.       "ALT=\"Load Original Image\" BORDER=\"0\">\n<BR></FORM>\n";
  3970.     }
  3971.  
  3972.  
  3973.     return 0;
  3974. };
  3975.  
  3976. # generate frame for block content
  3977. $funcs[$BLK_CMENU_FR] = sub {
  3978.     check_block();
  3979.  
  3980.     print_html_header_frameset("");
  3981.  
  3982.     my $sort = $BLK_SORT_ASC;
  3983.     $sort = $1 if ((exists $args{'sort'}) && ($args{'sort'} =~ /^(\d+)$/));
  3984.  
  3985.     my $len = get_len();
  3986.  
  3987.     my $blk;
  3988.  
  3989.     my $ifind = get_ifind();
  3990.  
  3991.     # off is 1 if a lazarus block number as they are off by one
  3992.     my $off = 0;
  3993.     $off = -1 if (exists $args{'btype2'});
  3994.  
  3995.     # Do we need to convert from dls value to dd value ? 
  3996.     if ((exists $args{'btype'}) && ($args{'btype'} == $BTYPE_DLS)) {
  3997.  
  3998.         my $img = get_img('img');
  3999.         my $b = get_block() + $off;
  4000.         my $ftype = get_ftype();
  4001.  
  4002.         local *OUT;    
  4003.         exec_pipe(*OUT, "'${TASKDIR}dcalc' -f $ftype -u $b '$img'");
  4004.         $blk = <OUT>;
  4005.         close (OUT);
  4006.  
  4007.         $blk = "Error getting block" 
  4008.           if ((!defined $blk) || ($blk eq ""));
  4009.  
  4010.         if ($blk !~ /^\d+$/) {
  4011.             print "$blk\n";
  4012.             return 1;
  4013.         }
  4014.     }
  4015.     else {
  4016.         $blk = get_block() + $off;
  4017.     }
  4018.  
  4019.     print "<FRAMESET ROWS=\"25%,75%\">\n".
  4020.       "<FRAME SRC=\"$PROGNAME?func=$BLK_CMENU&$baseargs".
  4021.       "&block=$blk&sort=$sort&len=$len&ifind=$ifind\">\n".
  4022.       "<FRAME SRC=\"$PROGNAME?func=$BLK_CONT&$baseargs".
  4023.       "&block=$blk&sort=$sort&len=$len\" NAME=\"cont2\">\n".
  4024.       "</FRAMESET>";
  4025.  
  4026.     return 0;
  4027. };
  4028.  
  4029. sub print_ifind {
  4030.     my $block = get_block();
  4031.  
  4032.     my $img = get_img('img');
  4033.     my $ftype = get_ftype();
  4034.  
  4035.     log_host_inv ("$args{'img'}: Finding $meta_str{$ftype} for data unit $block");
  4036.  
  4037.     local *OUT;    
  4038.     exec_pipe (*OUT, "'${TASKDIR}ifind' -f $ftype -d $block '$img'");
  4039.     my $inode = <OUT>;
  4040.     close (OUT);
  4041.  
  4042.     $inode = "Error getting inode" 
  4043.       if ((!defined $inode) || ($inode eq ""));
  4044.       
  4045.     if ($inode =~ /^($REG_INODE)$/o) {
  4046.         $inode = $1;
  4047.         my $tmpr = $args{'mnt'};
  4048.         print "<B>Pointed to by $meta_str{$ftype}:</B> ".
  4049.           "<A HREF=\"$PROGNAME?func=$MAIN_FR&mode=$INO_MAIN&$baseargs&".
  4050.           "inode=$inode\" TARGET=\"_blank\">$inode</A><BR>\n";
  4051.  
  4052.         print "<B>Pointed to by file:</B><BR>\n";
  4053.         exec_pipe(*OUT, "'${TASKDIR}ffind' -f $ftype -a '$img' $inode");
  4054.         while (<OUT>) {
  4055.             chop ;
  4056.             # Make it red if it is deleted
  4057.             if (/^(\*)\s+\/*(.*)$/) {
  4058.                 print_output("<TT><FONT COLOR=\"$DEL_COLOR[0]\">$tmpr$2</FONT></TT> (deleted)<BR>\n");
  4059.             # If it starts with a '/' then it must be a file
  4060.             } elsif (/^\/(.*)$/) {
  4061.                 print_output("<TT>$tmpr$1</TT><BR>\n");
  4062.             # this must be an error
  4063.             } else {
  4064.                 print_output("$_<BR>\n");
  4065.             }
  4066.         }
  4067.         close (OUT);
  4068.     }
  4069.     else {
  4070.         print "$inode\n";
  4071.     }
  4072. }
  4073.  
  4074.  
  4075.  
  4076. # Generate index for block content
  4077. $funcs[$BLK_CMENU] = sub {
  4078.     check_block(); 
  4079.  
  4080.     print_html_header("");
  4081.  
  4082.     my $block = get_block();
  4083.     my $prev = $block - 1;
  4084.     my $next = $block + 1;
  4085.  
  4086.     my $sort = get_sort();
  4087.     my $ftype = get_ftype();
  4088.     my $img = get_img('img');
  4089.     my $ifind = get_ifind();
  4090.  
  4091.     my $len = get_len();
  4092.     my $bs = get_unitsize();
  4093.     my $len_str = $bs * $len;
  4094.  
  4095.     print "<CENTER><FONT SIZE=3>";
  4096.     my $url = "$PROGNAME?func=$BLK_CMENU_FR&$baseargs&sort=$sort&len=$len".
  4097.       "&ifind=$ifind";
  4098.  
  4099.     # Next and Previous pointers
  4100.     print "<TABLE CELLSPACING=\"0\" CELLPADDING=\"2\">\n".
  4101.       "<TR>\n";
  4102.  
  4103.  
  4104.     # Previous
  4105.     if ($prev < $first_addr{$ftype}) {
  4106.         print "<TD ALIGN=\"right\"> </TD>\n";
  4107.     }
  4108.     else {
  4109.         print "<TD ALIGN=\"right\">".
  4110.           "<A HREF=\"$url&block=$prev\" TARGET=\"_parent\">\n".
  4111.           "<IMG SRC=\"pict/but_prev.jpg\" ALT=\"previous\" ".
  4112.           "WIDTH=\"89\" HEIGHT=20 BORDER=\"0\"></A></TD>\n";
  4113.     }
  4114.  
  4115.     # Next
  4116.     print "<TD ALIGN=\"left\"><A HREF=\"$url&block=$next\"".
  4117.       " TARGET=\"_parent\">".
  4118.       "<IMG SRC=\"pict/but_next.jpg\" ALT=\"next\" ".
  4119.       "WIDTH=\"89\" HEIGHT=20 BORDER=\"0\"></A></TD>\n</TR>\n";
  4120.  
  4121.     print
  4122.       "<TR><TD ALIGN=\"right\"><A HREF=\"$PROGNAME?func=$BLK_SAVE&$baseargs&".
  4123.       "block=$block&len=$len\">".
  4124.       "<IMG SRC=\"pict/but_export.jpg\" BORDER=\"0\" ALT=\"Export\" ".
  4125.       "WIDTH=123 HEIGHT=20></A></TD>\n";
  4126.  
  4127.     if ($USE_NOTES == 1) {
  4128.         print 
  4129.           "<TD ALIGN=\"left\">".
  4130.           "<A HREF=\"$PROGNAME?func=$NOTES_ENT&$baseargs&block=$block&len=$len\" ".
  4131.           "TARGET=\"_blank\">".
  4132.           "<IMG SRC=\"pict/but_addnote.jpg\" BORDER=\"0\" ".
  4133.           "WIDTH=\"89\" HEIGHT=20 ALT=\"Add Note\"></A></TD>\n";
  4134.     }
  4135.     else {
  4136.         print "<TD ALIGN=\"left\"> </TD>\n";
  4137.     }
  4138.  
  4139.     print "</TR></TABLE>\n";
  4140.  
  4141.     # Display formats
  4142.     print "<TABLE CELLSPACING=\"0\" CELLPADDING=\"2\">\n".
  4143.       "<TR><TD>ASCII (";
  4144.     if ($sort == $BLK_SORT_ASC) {
  4145.         print "display - ";
  4146.     } else {
  4147.         print "<A HREF=\"$PROGNAME?func=$BLK_CMENU_FR&$baseargs&".
  4148.           "sort=$BLK_SORT_ASC&block=$block&len=$len\" TARGET=\"_parent\">".
  4149.           "display</A> - \n";
  4150.     }
  4151.  
  4152.     print "<A HREF=\"$PROGNAME?func=$BLK_REP&$baseargs&sort=$BLK_SORT_ASC".
  4153.       "&block=$block&len=$len\" TARGET=\"_blank\">report</A>)</TD>\n".
  4154.       "<TD>*</TD>\n";
  4155.  
  4156.     print "<TD>Hex (";
  4157.     if ($sort == $BLK_SORT_HEX) {
  4158.         print "display - ";
  4159.     } else {
  4160.         print "<A HREF=\"$PROGNAME?func=$BLK_CMENU_FR&$baseargs&".
  4161.           "sort=$BLK_SORT_HEX&block=$block&len=$len\" TARGET=\"_parent\">".
  4162.           "display</A> - \n";
  4163.     }
  4164.  
  4165.     print "<A HREF=\"$PROGNAME?func=$BLK_REP&$baseargs&sort=$BLK_SORT_HEX".
  4166.       "&block=$block&len=$len\" TARGET=\"_blank\">report</A>)</TD>\n".
  4167.       "<TD>*</TD>\n";
  4168.  
  4169.     print "<TD>Strings (";
  4170.     if ($sort == $BLK_SORT_STR) {
  4171.         print "display - ";
  4172.     } else {
  4173.         print "<A HREF=\"$PROGNAME?func=$BLK_CMENU_FR&$baseargs&".
  4174.           "sort=$BLK_SORT_STR&block=$block&len=$len\" TARGET=\"_parent\">".
  4175.           "display</A> - \n";
  4176.     }
  4177.  
  4178.     print "<A HREF=\"$PROGNAME?func=$BLK_REP&$baseargs&sort=$BLK_SORT_STR".
  4179.       "&block=$block&len=$len\" TARGET=\"_blank\">report</A>)</TD>\n".
  4180.       "</TR></TABLE>\n";
  4181.  
  4182.     # Special case for 'dls' b.c. dcat does not have a dls type
  4183.     local *OUT;
  4184.     if ($ftype eq 'dls') {
  4185.           exec_pipe(*OUT, "'${TASKDIR}dcat' -f raw '$img' $block | '${TASKDIR}file' -z -b -");
  4186.     } else {
  4187.         exec_pipe(*OUT, "'${TASKDIR}dcat' -f $ftype '$img' $block | '${TASKDIR}file' -z -b -");
  4188.     }
  4189.     my $file_type = <OUT>;
  4190.     close (OUT);
  4191.  
  4192.     $file_type = "Error getting file type" 
  4193.       if ((!defined $file_type) || ($file_type eq ""));
  4194.  
  4195.     print "<B>File Type:</B> $file_type<BR></CENTER>\n";
  4196.  
  4197.     print "<B>$addr_unit{$ftype}</B> $block<BR>\n";
  4198.     if (($ftype ne "swap") && ($ftype ne "raw") && ($ftype ne "dls")) {
  4199.  
  4200.         exec_pipe(*OUT, "'${TASKDIR}dstat' -f $ftype '$img' $block");
  4201.  
  4202.         my $cnt = 0;
  4203.         while (<OUT>) {
  4204.  
  4205.             if ($_ =~ /((Not )?Allocated)/) {
  4206.                 print "<FONT COLOR=\"$DEL_COLOR[0]\">" if (defined $2);
  4207.                 print "<B>$1</B><BR>";
  4208.                 print "</FONT>" if (defined $2);
  4209.             }
  4210.             elsif ($_ =~ /Group: (\d+)/) {
  4211.                 print "<B>Group:</B> $1<BR>\n";
  4212.             }
  4213.             $cnt++;
  4214.         }
  4215.         close (OUT);
  4216.         if ($cnt == 0) {
  4217.             print "Invalid $addr_unit{$ftype} address<BR>\n";
  4218.             return;
  4219.         }
  4220.  
  4221.  
  4222.         # Make ifind an option
  4223.         $url = "$PROGNAME?func=$BLK_CMENU&$baseargs&sort=$sort&len=$len&".
  4224.           "block=$block";
  4225.         if ($ifind == 0) {
  4226.             print "<A HREF=\"$url&ifind=1\">Find Meta Data Address</A><BR>\n";
  4227.         } else {
  4228.             print "<A HREF=\"$url&ifind=0\">Hide Meta Data Address</A><BR>\n";
  4229.             print_ifind();
  4230.         }
  4231.     }
  4232.  
  4233.     if ($ftype eq 'dls') {
  4234.         if (exists $mod2img{$args{'img'}}) {
  4235.             print "<A HREF=\"$PROGNAME?func=$BLK_CMENU_FR&".
  4236.               "${baseargs_noimg}".
  4237.               "mnt=&img=$mod2img{$args{'img'}}&".
  4238.               "block=$block&sort=$sort&len=$len&btype=$BTYPE_DLS\" ".
  4239.               "TARGET=\"_parent\">View Original</A><BR>\n";
  4240.         }
  4241.     }
  4242.  
  4243.     return 0;
  4244. };
  4245.  
  4246. #Display actual block content
  4247. $funcs[$BLK_CONT] = sub {
  4248.     check_block(); check_sort();
  4249.  
  4250.     print_text_header();
  4251.     print "\n";
  4252.  
  4253.     my $sort = get_sort();
  4254.     my $block = get_block();
  4255.     my $img = get_img('img');
  4256.     my $ftype = get_ftype();
  4257.  
  4258.     my $len = get_len();
  4259.     my $bs = get_unitsize();
  4260.     my $len_str = $bs * $len;
  4261.  
  4262.     my $str = "Contents of $addr_unit{$ftype} $block ($len_str bytes) in $args{'img'}\n\n\n";
  4263.  
  4264.     my $log_str = "contents of $addr_unit{$ftype} $block ($len_str bytes)";
  4265.  
  4266.     local *OUT;
  4267.     if ($sort == $BLK_SORT_HEX) {
  4268.         print "Hex ".$str;
  4269.         log_host_inv ("$args{'img'}: Displaying Hex $log_str");
  4270.         exec_pipe(*OUT,"'${TASKDIR}dcat' -f $ftype -h '$img' $block $len_str");
  4271.     } 
  4272.     elsif ($sort == $BLK_SORT_ASC) {
  4273.         print "ASCII ".$str;
  4274.         log_host_inv ("$args{'img'}: Displaying ASCII $log_str");
  4275.         exec_pipe(*OUT,"'${TASKDIR}dcat' -f $ftype -a '$img' $block $len_str");
  4276.     }
  4277.     elsif ($sort == $BLK_SORT_STR) {
  4278.         print "String ".$str;
  4279.         log_host_inv ("$args{'img'}: Displaying string $log_str");
  4280.         exec_pipe(*OUT,"'${TASKDIR}dcat' -f $ftype '$img' $block $len_str | '$STRINGS_EXE' -a");
  4281.     }
  4282.     print $_ while (<OUT>);
  4283.     close (OUT);
  4284.  
  4285.     return 0;
  4286. };
  4287.  
  4288. $funcs[$BLK_REP] = sub {
  4289.     check_block(); check_sort();
  4290.  
  4291.     print_text_header();
  4292.  
  4293.     my $sort = get_sort();
  4294.     my $img = get_img('img');
  4295.     my $block = get_block();
  4296.     my $ftype = get_ftype();
  4297.     my $len = get_len();
  4298.     my $type;
  4299.  
  4300.     my $bs = get_unitsize();
  4301.     my $len_str = $len * $bs;
  4302.  
  4303.  
  4304.     print "Content-Disposition: inline; ".
  4305.       "filename=$args{'img'}-$addr_unit{$ftype}$args{'block'}.txt;\n\n";
  4306.  
  4307.     if ($sort == $BLK_SORT_ASC) {
  4308.         log_host_inv ("$args{'img'}: Generating ASCII report on data unit $block");
  4309.         $type = "ascii";
  4310.     } elsif ($sort == $BLK_SORT_STR) {
  4311.         log_host_inv ("$args{'img'}: Generating strings report on data unit $block");
  4312.         $type = "string";
  4313.     } elsif ($sort == $BLK_SORT_HEX) {
  4314.         log_host_inv ("$args{'img'}: Generating hex report on data unit $block");
  4315.         $type = "hex";
  4316.     } else {
  4317.         print "\n\n";
  4318.         print "invalid sort value";
  4319.         return 1;
  4320.     }
  4321.  
  4322.  
  4323.  
  4324.     print "           Autopsy $type $addr_unit{$ftype} Report (ver $VER)\n\n".
  4325.       "-" x 62 ."\n";
  4326.  
  4327.     
  4328.  
  4329.     if (($ftype ne 'dls') && ($ftype ne 'raw') && ($ftype ne 'swap')) {
  4330.       
  4331.         print "$addr_unit{$ftype}: $args{'block'}\n";
  4332.         print "Length: $len_str bytes\n";
  4333.  
  4334.  
  4335.         local *OUT;
  4336.         exec_pipe(*OUT, "'${TASKDIR}ifind' -f $ftype -d $block '$img'");
  4337.         my $inode = <OUT>;
  4338.         close (OUT);
  4339.  
  4340.         $inode = "Error getting inode" 
  4341.           if ((!defined $inode) || ($inode eq ""));
  4342.  
  4343.         if ($inode =~ /^($REG_INODE)$/o) {
  4344.             my $tmpi = $1;
  4345.             print "Pointed to by $meta_str{$ftype}: $tmpi\n";
  4346.  
  4347.             my $tmpr = $args{'mnt'};
  4348.             print "Pointed to by files:\n";
  4349.             exec_pipe(*OUT, "'${TASKDIR}ffind' -f $ftype -a '$img' $tmpi");
  4350.             while (<OUT>) {
  4351.                 chop ;
  4352.                 if (/^(\*)\s+\/*(.*)$/) {
  4353.                     print_output("  $tmpr$2 (deleted)\n");
  4354.                 } elsif (/^\/(.*)$/) {
  4355.                     print_output("  $tmpr$1\n");
  4356.                 } else {
  4357.                     print_output("  $_\n");
  4358.                 }
  4359.             }
  4360.             close(OUT);
  4361.         } else {
  4362.             print "Not allocated to any meta data structures\n";
  4363.         }
  4364.     } # not dls
  4365.     else {
  4366.         print "$args{'block'}\n";
  4367.         print "Length: $len_str bytes\n";
  4368.     }
  4369.  
  4370.  
  4371.     exec_pipe(*OUT, "'${TASKDIR}dcat' -f $ftype '$img' $block $len_str | '${TASKDIR}md5'");
  4372.     my $md5 = <OUT>;
  4373.     close(OUT);
  4374.  
  4375.     $md5 = "Error getting md5" 
  4376.       if ((!defined $md5) || ($md5 eq ""));
  4377.  
  4378.     chop $md5;
  4379.     print "MD5 of raw $addr_unit{$ftype}: $md5\n";
  4380.  
  4381.     if ($sort == $BLK_SORT_HEX) {
  4382.         exec_pipe(*OUT, "'${TASKDIR}dcat' -f $ftype -h '$img' $block $len_str | '${TASKDIR}md5'");
  4383.     } elsif ($sort == $BLK_SORT_ASC) {
  4384.         exec_pipe(*OUT, "'${TASKDIR}dcat' -f $ftype -a '$img' $block $len_str | '${TASKDIR}md5'");
  4385.     } elsif ($sort == $BLK_SORT_STR) {
  4386.         exec_pipe(*OUT, "'${TASKDIR}dcat' -f $ftype '$img' $block $len_str | '$STRINGS_EXE' -a | '${TASKDIR}md5'");
  4387.     }
  4388.  
  4389.     $md5 = <OUT>;
  4390.     close(OUT);
  4391.  
  4392.     $md5 = "Error getting md5" 
  4393.       if ((!defined $md5) || ($md5 eq ""));
  4394.  
  4395.     chop $md5;
  4396.     print "MD5 of $type output: $md5\n";
  4397.  
  4398.     print "Image: $img\n";
  4399.     print "Image Type: $ftype\n";
  4400.  
  4401.     my $date = localtime();
  4402.  
  4403.     print "Date Generated: $date\n".
  4404.       "Investigator: $args{'inv'}\n".
  4405.       "-" x 62 ."\n";
  4406.  
  4407.  
  4408.     if ($sort == $BLK_SORT_HEX) {
  4409.         exec_pipe(*OUT, "'${TASKDIR}dcat' -f $ftype -h '$img' $block $len_str");
  4410.     } 
  4411.     elsif ($sort == $BLK_SORT_ASC) {
  4412.         exec_pipe(*OUT, "'${TASKDIR}dcat' -f $ftype -a '$img' $block $len_str");
  4413.     }
  4414.     elsif ($sort == $BLK_SORT_STR) {
  4415.         exec_pipe(*OUT, "'${TASKDIR}dcat' -f $ftype '$img' $block $len_str | '$STRINGS_EXE' -a");
  4416.     }
  4417.     print_output($_) while (<OUT>);
  4418.     close (OUT);
  4419.  
  4420.     return 0;
  4421. };
  4422.  
  4423.  
  4424. #
  4425. # Display the block allocation list
  4426. #
  4427. $funcs[$BLK_DLS] = sub {
  4428.     print_html_header("Block Allocation List");
  4429.  
  4430.     my $DLS_GAP = 500;
  4431.  
  4432.     my $img = get_img('img');
  4433.     my $ftype = get_ftype();
  4434.  
  4435.     my $min = 0;
  4436.     $min = get_min() if (exists $args{'min'});
  4437.     my $max = $min + $DLS_GAP - 1;
  4438.  
  4439.     # set fmin to the minimum for the file system
  4440.     my $fmin = $min;
  4441.     $fmin = $first_addr{$ftype} if ($min < $first_addr{$ftype});
  4442.  
  4443.     log_host_inv ("$args{'img'}: Block Allocation List for $min to $max");
  4444.     print "<CENTER><H2>$addr_unit{$ftype}: $min - $max</H2>";
  4445.  
  4446.     my $tmp;
  4447.     print "<FONT SIZE=3>\n";
  4448.     if ($min - $DLS_GAP >= 0) {
  4449.         $tmp = $min - $DLS_GAP;
  4450.         print "<A HREF=\"$PROGNAME?func=$BLK_DLS&$baseargs&min=$tmp\">".
  4451.            "<IMG SRC=\"pict/but_prev.jpg\" ALT=\"previous\" ".
  4452.            "WIDTH=\"89\" HEIGHT=20 BORDER=\"0\"></A> ";
  4453.     }
  4454.     $tmp = $min + $DLS_GAP;
  4455.     print " <A HREF=\"$PROGNAME?func=$BLK_DLS&$baseargs&min=$tmp\">".
  4456.       "<IMG SRC=\"pict/but_next.jpg\" ALT=\"next\" ".
  4457.       "WIDTH=\"89\" HEIGHT=20 BORDER=\"0\"></A><BR>";
  4458.     print "</FONT></CENTER>\n";
  4459.  
  4460.     local *OUT;
  4461.     exec_pipe(*OUT, "'${TASKDIR}dls' -elb -f $ftype '$img' $fmin-$max");
  4462.     while (<OUT>) {
  4463.         if (/^(\d+)\|([af])/) {
  4464.             print "<A HREF=\"$PROGNAME?func=$BLK_CMENU_FR&$baseargs&block=$1\">".
  4465.               "$1:</A> ";
  4466.             if ($2 eq "a") {
  4467.                 print "allocated<BR>\n";
  4468.             } else {
  4469.                 print "<FONT COLOR=\"$DEL_COLOR[0]\">free</FONT><BR>\n";
  4470.             }
  4471.         }
  4472.     }
  4473.     close (OUT);
  4474.  
  4475.     print "<CENTER><FONT SIZE=3>\n";
  4476.     if ($min - $DLS_GAP >= 0) {
  4477.         $tmp = $min - $DLS_GAP;
  4478.         print "<A HREF=\"$PROGNAME?func=$BLK_DLS&$baseargs&min=$tmp\">".
  4479.            "<IMG SRC=\"pict/but_prev.jpg\" ALT=\"previous\" ".
  4480.            "WIDTH=\"89\" HEIGHT=20 BORDER=\"0\"></A> ";
  4481.     }
  4482.     $tmp = $min + $DLS_GAP;
  4483.     print " <A HREF=\"$PROGNAME?func=$BLK_DLS&$baseargs&min=$tmp\">".
  4484.       "<IMG SRC=\"pict/but_next.jpg\" ALT=\"next\" ".
  4485.       "WIDTH=\"89\" HEIGHT=20 BORDER=\"0\"></A><BR>";
  4486.     print "</FONT></CENTER>\n";
  4487. };
  4488.  
  4489. $funcs[$BLK_SAVE] = sub {
  4490.     check_block(); 
  4491.  
  4492.     print_oct_header();
  4493.  
  4494.     my $block = get_block();
  4495.     my $img = get_img('img');
  4496.     my $ftype = get_ftype();
  4497.     my $len = get_len();
  4498.     my $bs = get_unitsize();
  4499.     my $len_str = $len * $bs;
  4500.  
  4501.     log_host_inv ("$args{'img'}: Saving contents of data unit $block ($len_str bytes)");
  4502.  
  4503.     print "Content-Disposition: inline; filename=$args{'img'}".
  4504.       "-$addr_unit{$ftype}$block.raw;\n\n";
  4505.  
  4506.     local *OUT;
  4507.     exec_pipe(*OUT, "'${TASKDIR}dcat' -f $ftype '$img' $block $len_str");
  4508.     print "$_" while (<OUT>);
  4509.     close (OUT);
  4510.  
  4511.     # we exit instead of return so that we don't get two \n\n at the end
  4512.     exit(0);
  4513. };
  4514.  
  4515.  
  4516. ########################### INODE ####################
  4517. $funcs[$INO_MAIN] = sub {
  4518.  
  4519.     print_html_header_frameset("Meta Data Browse on $args{'img'}");
  4520.     print "<FRAMESET COLS=\"20%,80%\">\n";
  4521.  
  4522.     # Inode Enter Location
  4523.     print "<FRAME SRC=\"$PROGNAME?func=$INO_ENT&$baseargs".
  4524.       "&inode=$enc_args{'inode'}\">\n";
  4525.  
  4526.     # Inode Contents
  4527.     if (exists $enc_args{'inode'}) {
  4528.         print "<FRAME SRC=\"$PROGNAME?func=$INO_CONT&".
  4529.           "inode=$enc_args{'inode'}&$baseargs\" ".
  4530.           "NAME=\"content\">\n</FRAMESET>\n";
  4531.     }
  4532.     else {
  4533.         print "<FRAME SRC=\"$PROGNAME?func=$BLANK&$baseargs\" ".
  4534.           "NAME=\"content\">\n</FRAMESET>\n";
  4535.     }
  4536.  
  4537.     return 0;
  4538. };
  4539.  
  4540. # Generate the frame to enter the data into
  4541. $funcs[$INO_ENT] = sub {
  4542.     print_html_header("");
  4543.  
  4544.     my $ftype = get_ftype();
  4545.  
  4546.     # Address
  4547.     print "<FORM ACTION=\"$PROGNAME\" METHOD=\"GET\" TARGET=\"content\">\n".
  4548.       "<B>$meta_str{$ftype} Number:</B><BR>    ".
  4549.       "<INPUT TYPE=\"text\" NAME=\"inode\" SIZE=12 MAXLENGTH=12";
  4550.  
  4551.     print " VALUE=\"$enc_args{'inode'}\"" if exists ($args{'inode'});
  4552.  
  4553.     print ">\n".
  4554.       "<INPUT TYPE=\"hidden\" NAME=\"func\" VALUE=\"$INO_CONT\">\n".
  4555.       "<INPUT TYPE=\"hidden\" NAME=\"img\" VALUE=\"$args{'img'}\">\n".
  4556.       make_hidden().
  4557.  
  4558.     # Ok Button
  4559.       "<P><INPUT TYPE=\"IMAGE\" SRC=\"pict/but_ok.jpg\" ".
  4560.       "WIDTH=43 HEIGHT=20 ALT=\"Ok\" BORDER=\"0\"></FORM>\n";
  4561.  
  4562.     # Allocation List
  4563.     print "<P>".
  4564.       "<A HREF=\"$PROGNAME?func=$INO_ILS&$baseargs\" TARGET=\"content\">".
  4565.       "<IMG SRC=\"pict/but_alloc_list.jpg\" BORDER=\"0\" ".
  4566.       "WIDTH=113 HEIGHT=20 ALT=\"Allocation List\">".
  4567.       "</A>\n";
  4568.  
  4569.     return 0;
  4570. };
  4571.  
  4572. # Display the contents of inode
  4573. $funcs[$INO_CONT] = sub {
  4574.     check_inode('inode'); 
  4575.  
  4576.     print_html_header("");
  4577.  
  4578.     my $inode = get_inode('inode');
  4579.     my $img = get_img('img');
  4580.     my $ftype = get_ftype();
  4581.  
  4582.     log_host_inv ("$args{'img'}: Displaying details of $meta_str{$ftype} $inode");
  4583.  
  4584.     my $inode_int = $inode;
  4585.     $inode_int = $1 if ($inode =~ /^(\d+)-\d+(-\d)?/);
  4586.  
  4587.     my $prev = $inode_int - 1;
  4588.     my $next = $inode_int + 1;
  4589.  
  4590.     print "<FONT SIZE=3><CENTER>\n";
  4591.     print "<A HREF=\"$PROGNAME?func=$INO_CONT&$baseargs&inode=$prev\">".
  4592.       "<IMG SRC=\"pict/but_prev.jpg\" ALT=\"previous\" ".
  4593.       "WIDTH=\"89\" HEIGHT=20 BORDER=\"0\"></A>\n" 
  4594.       unless ($prev < $first_inode{$ftype});
  4595.  
  4596.     print "<A HREF=\"$PROGNAME?func=$INO_CONT&$baseargs&inode=$next\">".
  4597.       "<IMG SRC=\"pict/but_next.jpg\" ALT=\"next\" ".
  4598.       "WIDTH=\"89\" HEIGHT=20 BORDER=\"0\"></A>\n<BR>";
  4599.  
  4600.     print "<TABLE CELLSPACING=\"0\" CELLPADDING=\"2\">\n<TR>".
  4601.       "<TD><A HREF=\"$PROGNAME?func=$INO_REP&$baseargs&inode=$inode\"".
  4602.       " TARGET=\"_blank\">".
  4603.       "<IMG SRC=\"pict/but_report.jpg\" ALT=\"report\" ".
  4604.       "WIDTH=88 HEIGHT=20 BORDER=\"0\">".
  4605.       "</A></TD>\n".
  4606.       "<TD><A HREF=\"$PROGNAME?func=$FIL_CMENU_FR&$baseargs&inode=$inode&".
  4607.       "dir=$args{'img'}-inode-$inode\" TARGET=\"_blank\">".
  4608.       "<IMG SRC=\"pict/but_view.jpg\" ALT=\"view contents\" ".
  4609.       "WIDTH=123 HEIGHT=20 BORDER=\"0\">".
  4610.       "</A></TD>\n".
  4611.       "<TD><A HREF=\"$PROGNAME?func=$INO_SAVE&$baseargs&inode=$inode&\">".
  4612.       "<IMG SRC=\"pict/but_export.jpg\" ALT=\"export\" ".
  4613.       "WIDTH=123 HEIGHT=20 BORDER=\"0\">".
  4614.       "</A></TD>";
  4615.  
  4616.     print 
  4617.       "<TD><A HREF=\"$PROGNAME?func=$NOTES_ENT&$baseargs&inode=$inode&\" ".
  4618.       "TARGET=\"_blank\">".
  4619.       "<IMG SRC=\"pict/but_addnote.jpg\" ALT=\"Add Note\" ".
  4620.       "WIDTH=\"89\" HEIGHT=20 BORDER=\"0\">".
  4621.       "</A></TD>" if ($USE_NOTES == 1);
  4622.  
  4623.     print "</TR></TABLE>\n</FONT></CENTER>\n<FONT SIZE=3>";
  4624.  
  4625.     my $tmpr = $args{'mnt'};
  4626.  
  4627.  
  4628.  
  4629.     if ($ftype =~ /fat/) {
  4630.         print "<A HREF=\"$PROGNAME?func=$INO_FFIND&$baseargs&".
  4631.           "inode=$inode\" TARGET=\"_blank\">Find File</A><BR>";
  4632.     } else {
  4633.  
  4634.         print "<B>Pointed to by file:</B><BR>\n"; 
  4635.  
  4636.         local *OUT;
  4637.         exec_pipe(*OUT, "'${TASKDIR}ffind' -f $ftype -a '$img' $inode");
  4638.         my $cnt = 0;
  4639.         while (<OUT>) {
  4640.             chop ;
  4641.             if (/^(\*)\s+\/*(.*)$/) {
  4642.                 print_output("<TT><FONT COLOR=\"$DEL_COLOR[0]\">$tmpr$2</FONT></TT> (deleted)<BR>\n");
  4643.             } elsif (/^\/(.*)$/) {
  4644.                 print_output("<TT>$tmpr$1</TT><BR>\n");
  4645.             } else {
  4646.                 print_output("$_<BR>\n");
  4647.             }
  4648.             $cnt++;
  4649.         }
  4650.         close (OUT);
  4651.         if ($cnt == 0) {
  4652.             print "<BR>Invalid $meta_str{$ftype} value<BR>\n";
  4653.             return;
  4654.         }
  4655.     }
  4656.  
  4657.     exec_pipe(*OUT, 
  4658.       "'${TASKDIR}icat' -f $ftype '$img' $inode | '${TASKDIR}file' -z -b -");
  4659.     my $file_type = <OUT>;
  4660.     close (OUT);
  4661.  
  4662.     $file_type = "Error getting file type"
  4663.       if ((!defined $file_type) || ($file_type eq ""));
  4664.  
  4665.     print "<B>File Type:</B><BR>$file_type<BR>\n";
  4666.  
  4667.     # MD5 Value
  4668.     exec_pipe(*OUT, 
  4669.       "'${TASKDIR}icat' -f $ftype '$img' $inode | '${TASKDIR}md5'");
  4670.     my $md5out = <OUT>;
  4671.     close (OUT);
  4672.  
  4673.     $md5out = "Error getting MD5" 
  4674.       if ((!defined $md5out) || ($md5out eq ""));
  4675.  
  4676.     chomp $md5out;
  4677.     print "<B>MD5:</B><BR><TT>$md5out</TT><BR>\n";
  4678.  
  4679.  
  4680.     # Hash Database Lookups
  4681.     if ((($NSRLDB ne "") || ($alert_db ne "") || ($exclude_db ne "")) &&
  4682.       ($md5out =~ /^$REG_MD5$/o)) {
  4683.  
  4684.         print "<FORM ACTION=\"$PROGNAME\" METHOD=\"GET\" TARGET=\"_blank\">\n".
  4685.           make_hidden().
  4686.           "<INPUT TYPE=\"hidden\" NAME=\"md5\" VALUE=\"$md5out\">\n".
  4687.           "<INPUT TYPE=\"hidden\" NAME=\"func\" VALUE=\"$HASH_LOOKUP\">\n".
  4688.           "<TABLE CELLPADDING=\"2\" CELLSPACING=\"8\"><TR>\n";
  4689.  
  4690.         if ($NSRLDB ne "") {
  4691.               print "<TD ALIGN=\"left\">".
  4692.               "<INPUT TYPE=\"checkbox\" NAME=\"hash_nsrl\" VALUE=\"1\" CHECKED>".
  4693.               "NSRL</TD>\n";
  4694.         }
  4695.         if ($alert_db ne "") {
  4696.               print "<TD ALIGN=\"left\">".
  4697.               "<INPUT TYPE=\"checkbox\" NAME=\"hash_alert\" VALUE=\"1\" CHECKED>".
  4698.               "Alert Database</TD>\n";
  4699.         }
  4700.         if ($exclude_db ne "") {
  4701.               print "<TD ALIGN=\"left\">".
  4702.               "<INPUT TYPE=\"checkbox\" NAME=\"hash_exclude\" VALUE=\"1\" CHECKED>".
  4703.               "Exclude Database</TD>\n";
  4704.         }
  4705.         print "<TD ALIGN=\"left\">".
  4706.           "<INPUT TYPE=\"IMAGE\" SRC=\"pict/but_ok.jpg\" ".        
  4707.           "WIDTH=43 HEIGHT=20 ALT=\"Ok\" BORDER=\"0\">".
  4708.           "</TD></TR></TABLE>\n</FORM>\n";
  4709.     }
  4710.  
  4711.  
  4712.     # istat output
  4713.     print "<B>Details:</B><BR>\n";
  4714.     my $mode = 0;    # set to 1 when showing blocks
  4715.     my $force = 0;    # set to 1 if size of inode is 0 
  4716.  
  4717.     my @output;
  4718.     if (exists ($args{'force'})) {
  4719.         my $f = get_force();
  4720.         exec_pipe(*OUT,
  4721.           "'${TASKDIR}istat' -f $ftype -z '$tz' -s $ts -b $f '$img' $inode");
  4722.     } else {
  4723.         exec_pipe(*OUT, 
  4724.           "'${TASKDIR}istat' -f $ftype -z '$tz' -s $ts '$img' $inode");
  4725.     }
  4726.     while (<OUT>) {
  4727.         if ($mode == 1) {
  4728.             if (/^Indirect Blocks/) {
  4729.                 print "$_<BR>\n";
  4730.                 next;
  4731.             }
  4732.             elsif (/^Type: (\S+) \((\d+\-\d+)\) (.*)$/) {
  4733.                 print "Type: $1 (".
  4734.                   "<A HREF=\"$PROGNAME?func=$FIL_CMENU_FR&$baseargs".
  4735.                   "&inode=$inode_int-$2&dir=$args{'img'}-inode-$inode_int-$2\" ".
  4736.                   "TARGET=\"_blank\">$2</A>) $3<BR>\n";
  4737.                 next;
  4738.             }
  4739.  
  4740.             my $blk;
  4741.             foreach $blk (split (/ /, $_)) {
  4742.                 print "<A HREF=\"$PROGNAME?func=$MAIN_FR&mode=$BLK_MAIN&".
  4743.                   "$baseargs&block=$blk\" TARGET=\"_blank\">$blk</A>  ";
  4744.             }
  4745.             print "<BR>\n";
  4746.         }
  4747.         else {
  4748.             if (/^Not Allocated$/) {
  4749.                 print "<FONT COLOR=\"$DEL_COLOR[0]\">$_</FONT><BR>\n";
  4750.             }
  4751.             else {
  4752.                 print "$_<BR>\n";
  4753.             }
  4754.             $mode = 1 if (/^Direct Blocks|^Sectors/);
  4755.             $mode = 1 if (/^Attributes/);
  4756.  
  4757.             if ((/^size: (\d+)/) && ($1 == 0)) {
  4758.                 $force = 1;
  4759.             }
  4760.         }
  4761.     }
  4762.     close (OUT);
  4763.  
  4764.     # display a text box to force X number of blocks to be displayed
  4765.     if ($force == 1)  {
  4766.         print "<FORM ACTION=\"$PROGNAME\" METHOD=\"GET\">\n".
  4767.           make_hidden().
  4768.           "<INPUT TYPE=\"hidden\" NAME=\"img\" VALUE=\"$args{'img'}\">\n".
  4769.           "<INPUT TYPE=\"hidden\" NAME=\"inode\" VALUE=\"$inode\">\n".
  4770.           "<INPUT TYPE=\"hidden\" NAME=\"func\" VALUE=\"$INO_CONT\">\n";
  4771.  
  4772.         print "Enter number of $addr_unit{$ftype}s to display: <INPUT TYPE=\"TEXT\" ".
  4773.           "VALUE=5 NAME=\"force\" SIZE=\"3\">\n";
  4774.  
  4775.         print "<INPUT TYPE=\"IMAGE\" SRC=\"pict/but_force.jpg\" ".
  4776.               "WIDTH=53 HEIGHT=20 ALT=\"Force\" BORDER=\"0\"> (because the size is 0)\n</FORM>\n";
  4777.     }
  4778.  
  4779. };
  4780.  
  4781. $funcs[$INO_FFIND] = sub {
  4782.  
  4783.     check_inode('inode'); 
  4784.  
  4785.     print_html_header("Find File");
  4786.  
  4787.     my $inode = get_inode('inode');
  4788.     my $img = get_img('img');
  4789.     my $ftype = get_ftype();
  4790.  
  4791.     my $tmpr = $args{'mnt'};
  4792.     print "<B>Pointed to by file:</B><BR>\n"; 
  4793.  
  4794.     local *OUT;
  4795.     exec_pipe(*OUT, "'${TASKDIR}ffind' -f $ftype -a '$img' $inode");
  4796.     while (<OUT>) {
  4797.         chop ;
  4798.         if (/(\*)\s+\/*(.*)/) {
  4799.             print_output("<TT><FONT COLOR=\"$DEL_COLOR[0]\">$tmpr$2</FONT></TT> (deleted)<BR>\n");
  4800.         } elsif (/^\/(.*)$/) {
  4801.             print_output("<TT>$tmpr$1</TT><BR>\n");
  4802.         } else {
  4803.             print_output("$_<BR>\n");
  4804.         }
  4805.     }
  4806.     close (OUT);
  4807. };
  4808.  
  4809.  
  4810. $funcs[$INO_SAVE] = sub {
  4811.     check_inode('inode'); 
  4812.  
  4813.     print_oct_header();
  4814.  
  4815.     my $inode = get_inode('inode');
  4816.     my $img = get_img('img');
  4817.     my $ftype = get_ftype();
  4818.  
  4819.     log_host_inv ("$args{'img'}: Saving contents of $meta_str{$ftype} $inode");
  4820.  
  4821.     print "Content-Disposition: inline; filename=$args{'img'}".
  4822.       "-inode$inode.raw;\n\n";
  4823.  
  4824.     local *OUT;
  4825.     exec_pipe(*OUT, 
  4826.       "'${TASKDIR}icat' -f $ftype '$img' $inode");
  4827.     print "$_" while (<OUT>);
  4828.     close (OUT);
  4829.  
  4830.     # exit instead of return so we don't get \n\n at the end
  4831.     exit(0);
  4832. };
  4833.  
  4834. $funcs[$INO_REP] = sub {
  4835.     check_inode('inode'); 
  4836.  
  4837.     print_text_header();
  4838.  
  4839.     my $inode = get_inode('inode');
  4840.     my $img = get_img('img');
  4841.     my $ftype = get_ftype();
  4842.  
  4843.     log_host_inv ("$args{'img'}: Generating report for $meta_str{$ftype} $inode");
  4844.  
  4845.     print "Content-Disposition: inline; ".
  4846.       "filename=$args{'img'}-inode$inode.txt;\n\n";
  4847.  
  4848.     print "           Autopsy $meta_str{$ftype} Report (ver $VER)\n\n".
  4849.       "-" x 62 ."\n".
  4850.       "$meta_str{$ftype}: $args{'inode'}\n";
  4851.  
  4852.     print "Pointed to by file:\n"; 
  4853.     my $tmpr = $args{'mnt'};
  4854.     local *OUT;
  4855.  
  4856.     exec_pipe(*OUT, "'${TASKDIR}ffind' -f $ftype -a '$img' $inode");
  4857.     while (<OUT>) {
  4858.         chop ;
  4859.         if (/^(\*)\s+\/*(.*)$/) {
  4860.             print_output("  $tmpr$2 (deleted)\n");
  4861.         } elsif (/^\/(.*)$/) {
  4862.             print_output("  $tmpr$1\n");
  4863.         } else {
  4864.             print_output("  $_\n");
  4865.         }
  4866.     }
  4867.     close(OUT);
  4868.  
  4869.     
  4870.     exec_pipe(*OUT, "'${TASKDIR}istat' -f $ftype -z '$tz' -s $ts '$img' $inode | '${TASKDIR}md5'");
  4871.     my $md5 = <OUT>;
  4872.     close (OUT);
  4873.  
  4874.     $md5 = "Error getting MD5 Value"
  4875.       if ((!defined $md5) || ($md5 eq ""));
  4876.  
  4877.     chop $md5;
  4878.     print "MD5 of istat output: $md5\n";
  4879.  
  4880.     print "Image: $img\n";
  4881.     print "Image Type: $ftype\n";
  4882.  
  4883.     my $date = localtime();
  4884.     print "Date Generated: $date\n".
  4885.       "Investigator: $args{'inv'}\n".
  4886.       "-" x 62 ."\n";
  4887.  
  4888.     exec_pipe(*OUT,
  4889.       "'${TASKDIR}istat' -f $ftype -z '$tz' -s $ts '$img' $inode");
  4890.     while (<OUT>) {
  4891.            print "$_";
  4892.     }
  4893.     close (OUT);
  4894.  
  4895.     exec_pipe (*OUT,
  4896.       "'${TASKDIR}icat' -f $ftype '$img' $inode | '${TASKDIR}file' -z -b -");
  4897.     my $file_type = <OUT>;
  4898.     close (OUT);
  4899.  
  4900.     $file_type = "Error getting file type"
  4901.       if ((!defined $file_type) || ($file_type eq ""));
  4902.  
  4903.     print "\nFile Type: $file_type";
  4904.  
  4905.     print "\n"."-" x 62 ."\n";
  4906.  
  4907.     return 0;
  4908. };
  4909.  
  4910.  
  4911. # Display the Inode Allocation Table
  4912. $funcs[$INO_ILS] = sub {
  4913. my $ILS_GAP = 500;
  4914.  
  4915.     my $ftype = get_ftype();
  4916.     my $img = get_img('img');
  4917.  
  4918.     my $min = 0;
  4919.  
  4920.     $min = get_min() if (exists $args{'min'});
  4921.     my $max = $min + $ILS_GAP - 1;  
  4922.  
  4923.     # Because we can not use inodes 0 and 1 for most FS, set fmin to the
  4924.     # minimum for this fs
  4925.     my $fmin = $min;
  4926.     $fmin = $first_inode{$ftype} if ($min < $first_inode{$ftype});
  4927.         
  4928.     print_html_header("$meta_str{$ftype} Allocation List $fmin -> $max");
  4929.  
  4930.     log_host_inv ("$args{'img'}: $meta_str{$ftype} Allocation List for $min to $max");
  4931.  
  4932.     print "<CENTER><H2>$meta_str{$ftype}: $fmin - $max</H2>";
  4933.         
  4934.     # Display next and previous links
  4935.     my $tmp;
  4936.     print "<FONT SIZE=3>\n";
  4937.     if ($min > $first_inode{$ftype}) {
  4938.         $tmp = $min - $ILS_GAP;
  4939.         print "<A HREF=\"$PROGNAME?func=$INO_ILS&$baseargs&min=$tmp\">".
  4940.            "<IMG SRC=\"pict/but_prev.jpg\" ALT=\"previous\" ".
  4941.            "WIDTH=\"89\" HEIGHT=20 BORDER=\"0\"></A> ";
  4942.     }
  4943.     $tmp = $min + $ILS_GAP;
  4944.     print " <A HREF=\"$PROGNAME?func=$INO_ILS&$baseargs&min=$tmp\">".
  4945.       "<IMG SRC=\"pict/but_next.jpg\" ALT=\"next\" ".
  4946.       "WIDTH=\"89\" HEIGHT=20 BORDER=\"0\"></A><BR>";
  4947.     print "</FONT></CENTER>\n";
  4948.  
  4949.     # The list
  4950.     local *OUT;
  4951.     exec_pipe (*OUT,
  4952.       "'${TASKDIR}ils' -e -s $ts -f $ftype '$img' $fmin-$max");
  4953.     while (<OUT>) {
  4954.         if (/^($REG_INODE)\|([af])\|\d+\|\d+\|\d+\|\d+\|\d+\|/o) {
  4955.             print "<A HREF=\"$PROGNAME?func=$INO_CONT&$baseargs&inode=$1\">".
  4956.               "$1:</A> ";
  4957.             if ($2 eq "a") {
  4958.                 print "allocated<BR>\n";
  4959.             } else {
  4960.                 print "<FONT COLOR=\"$DEL_COLOR[0]\">free</FONT><BR>\n";
  4961.             }
  4962.         }
  4963.     }
  4964.     close (OUT);
  4965.  
  4966.     # Display next and previous links
  4967.     print "<CENTER><FONT SIZE=3>\n";
  4968.     if ($min > $first_inode{$ftype}) {
  4969.         $tmp = $min - $ILS_GAP;
  4970.         print "<A HREF=\"$PROGNAME?func=$INO_ILS&$baseargs&min=$tmp\">".
  4971.            "<IMG SRC=\"pict/but_prev.jpg\" ALT=\"previous\" ".
  4972.            "WIDTH=\"89\" HEIGHT=20 BORDER=\"0\"></A> ";
  4973.     }
  4974.     $tmp = $min + $ILS_GAP;
  4975.     print " <A HREF=\"$PROGNAME?func=$INO_ILS&$baseargs&min=$tmp\">".
  4976.       "<IMG SRC=\"pict/but_next.jpg\" ALT=\"next\" ".
  4977.       "WIDTH=\"89\" HEIGHT=20 BORDER=\"0\"></A><BR>";
  4978.     print "</FONT></CENTER>\n";
  4979.  
  4980. };
  4981.  
  4982. ############ SEARCHING ##################
  4983.  
  4984.  
  4985. my $CASE_INSENS = 1;
  4986. my $CASE_SENS = 0;
  4987.  
  4988. my $REG_EXP = 1;
  4989. my $STRING = 0;
  4990.  
  4991. # Form to enter search data
  4992. $funcs[$SRCH_ENT] = sub {
  4993.     print_html_header("Search on $args{'img'}");
  4994.  
  4995.     print "<CENTER><H3>Keyword Search on <TT>$args{'img'}</TT></H3>\n";
  4996.  
  4997.     print "<FORM ACTION=\"$PROGNAME\" METHOD=\"GET\">\n".
  4998.       "Enter String: <INPUT TYPE=\"text\" NAME=\"str\"><BR><BR>\n".
  4999.       make_hidden().
  5000.       "<INPUT TYPE=\"hidden\" NAME=\"func\" VALUE=\"$SRCH_RMAIN\">\n".
  5001.       "<INPUT TYPE=\"hidden\" NAME=\"img\" VALUE=\"$args{'img'}\">\n".
  5002.       "<INPUT TYPE=\"checkbox\" NAME=\"srch_case\" VALUE=\"$CASE_INSENS\">".
  5003.       "Case Insensitive\n".
  5004.       "<INPUT TYPE=\"checkbox\" NAME=\"regexp\" VALUE=\"$REG_EXP\">".
  5005.       "Regular Expression<BR><BR>\n".
  5006.       "<INPUT TYPE=\"IMAGE\" SRC=\"pict/srch_b_srch.jpg\" ".
  5007.       "ALT=\"Search\" BORDER=\"0\">\n</FORM>\n";
  5008.  
  5009.     my $ftype = get_ftype();
  5010.  
  5011.     print "<TABLE WIDTH=600><TR>\n";
  5012.  
  5013.     # If we are a non-dls image and one exists - make a button to load it
  5014.     if ( ($ftype ne 'dls') && (exists $img2dls{$args{'img'}}) ) {
  5015.     print 
  5016.       "<TD ALIGN=CENTER WIDTH=200>".
  5017.       "<FORM ACTION=\"$PROGNAME\" METHOD=\"GET\" TARGET=\"_top\">\n".
  5018.       "<INPUT TYPE=\"hidden\" NAME=\"func\" VALUE=\"$MAIN_FR\">\n".
  5019.       "<INPUT TYPE=\"hidden\" NAME=\"mode\" VALUE=\"$SRCH_MAIN\">\n".
  5020.       "<INPUT TYPE=\"hidden\" NAME=\"img\" VALUE=\"$img2dls{$args{'img'}}\">\n".
  5021.       make_hidden().
  5022.       "<INPUT TYPE=\"IMAGE\" SRC=\"pict/srch_b_lun.jpg\" ".
  5023.       "ALT=\"Load Unallocated Image\" BORDER=\"0\">\n<BR></FORM></TD>\n";
  5024.     }
  5025.  
  5026.     # If we are a dls and the original exists - make a button to load it
  5027.     elsif ( ($ftype eq 'dls') && (exists $mod2img{$args{'img'}}) ) {
  5028.     print 
  5029.       "<TD ALIGN=CENTER WIDTH=200>".
  5030.       "<FORM ACTION=\"$PROGNAME\" METHOD=\"GET\" TARGET=\"_top\">\n".
  5031.       "<INPUT TYPE=\"hidden\" NAME=\"func\" VALUE=\"$MAIN_FR\">\n".
  5032.       "<INPUT TYPE=\"hidden\" NAME=\"mode\" VALUE=\"$SRCH_MAIN\">\n".
  5033.       "<INPUT TYPE=\"hidden\" NAME=\"img\" VALUE=\"$mod2img{$args{'img'}}\">\n".
  5034.       make_hidden().
  5035.       "<INPUT TYPE=\"IMAGE\" SRC=\"pict/srch_b_lorig.jpg\" ". 
  5036.       "ALT=\"Load Original Image\" BORDER=\"0\">\n<BR></FORM></TD>\n";
  5037.     }
  5038.  
  5039.     # Strings Button
  5040.     if (!(exists $img2str{$args{'img'}})) {
  5041.  
  5042.         my $dest_img = $args{'img'};
  5043.         $dest_img = $mod2img{$args{'img'}} if exists ($mod2img{$args{'img'}});
  5044.  
  5045.         print 
  5046.           "<TD ALIGN=CENTER WIDTH=200>".
  5047.           "<FORM ACTION=\"$PROGNAME\" METHOD=\"GET\" TARGET=\"_top\">\n".
  5048.           "<INPUT TYPE=\"hidden\" NAME=\"func\" VALUE=\"$IMG_DETAILS\">\n".
  5049.           "<INPUT TYPE=\"hidden\" NAME=\"img\" VALUE=\"$dest_img\">\n".
  5050.           make_hidden().
  5051.           "<INPUT TYPE=\"IMAGE\" SRC=\"pict/srch_b_str.jpg\" ". 
  5052.           "ALT=\"Extract Strings\" BORDER=\"0\">\n<BR></FORM></TD>\n";
  5053.     }
  5054.  
  5055.     # Unallocated Space Button
  5056.     if (($ftype ne 'dls') && ($ftype ne 'swap') && ($ftype ne 'raw') && 
  5057.       (!(exists $img2dls{$args{'img'}}))) {
  5058.         print 
  5059.           "<TD ALIGN=CENTER WIDTH=200>".
  5060.           "<FORM ACTION=\"$PROGNAME\" METHOD=\"GET\" TARGET=\"_top\">\n".
  5061.           "<INPUT TYPE=\"hidden\" NAME=\"func\" VALUE=\"$IMG_DETAILS\">\n".
  5062.           "<INPUT TYPE=\"hidden\" NAME=\"img\" VALUE=\"$args{'img'}\">\n".
  5063.           make_hidden().
  5064.           "<INPUT TYPE=\"IMAGE\" SRC=\"pict/srch_b_un.jpg\" ". 
  5065.           "ALT=\"Extract Unallocated Space\" BORDER=\"0\">\n<BR></FORM></TD>\n";
  5066.     }
  5067.  
  5068.     print "</TR></TABLE>\n";
  5069.  
  5070.     print "<A HREF=\"help/grep.html\" TARGET=\"_new\">".
  5071.       "grep cheat sheet</A>\n<BR><BR>\n";
  5072.  
  5073.     print "<P><FONT COLOR=\"red\">NOTE:</FONT> The keyword search runs ".
  5074.       "<TT>grep</TT> on the image.<BR>\n".
  5075.       "A list of what will and ".
  5076.       "what will not be found is available ".
  5077.       "<A HREF=\"help/grep_lim.html\" TARGET=\"_new\">here</A>.<BR>\n";
  5078.  
  5079.  
  5080.     # Section for previous searches
  5081.     my $srch_name = get_srch_file(0);
  5082.     if (-e $srch_name) {
  5083.         print "<HR><H3>Previous Searches</H3>\n".
  5084.           "<TABLE WIDTH=600>\n";
  5085.         my $row_idx = 0;
  5086.  
  5087.         # Cycle through the files
  5088.         for (my $srch_idx = 0; ;$srch_idx++) {
  5089.  
  5090.             $srch_name = get_srch_file($srch_idx);
  5091.             
  5092.             last unless (-e $srch_name);
  5093.  
  5094.             # Open the file to get the string and count
  5095.             unless (open (SRCH, "$srch_name")) {
  5096.                 print "Error opening search file: $srch_name\n";
  5097.                 return 1;
  5098.             }
  5099.             my $prev_str = "";
  5100.             my $prev_cnt = 0;
  5101.             while (<SRCH>) {
  5102.                 unless (/^(\d+)\|(.*?)?\|(.*)$/) {
  5103.                     print "Error pasing header of search file: $srch_name\n";
  5104.                     return 1;
  5105.                 }
  5106.                 $prev_cnt = $1;
  5107.                 $prev_str = $3;
  5108.                 if (length ($prev_str) > 32) {
  5109.                     $prev_str = substr($prev_str, 0, 32);
  5110.                     $prev_str .= "...";
  5111.                 }
  5112.  
  5113.                 last;
  5114.             }
  5115.             close (SRCH);
  5116.  
  5117.             print "<TR>\n" if ($row_idx == 0); 
  5118.  
  5119.             print "  <TD ALIGN=CENTER WIDTH=150>\n".
  5120.                 "<FORM ACTION=\"$PROGNAME\" METHOD=\"GET\">\n".
  5121.                 "<INPUT TYPE=\"hidden\" NAME=\"func\" VALUE=\"$SRCH_RMAIN\">\n".
  5122.                 "<INPUT TYPE=\"hidden\" NAME=\"img\" VALUE=\"$args{'img'}\">\n".
  5123.                 "<INPUT TYPE=\"hidden\" NAME=\"srchidx\" VALUE=\"$srch_idx\">\n".
  5124.               make_hidden();
  5125.  
  5126.             print "<INPUT TYPE=\"SUBMIT\" VALUE=\"$prev_str ($prev_cnt)\">".
  5127.               "<BR></FORM>\n";
  5128.  
  5129.             if ($row_idx == 3) {
  5130.                 print "</TR>\n";
  5131.                 $row_idx = 0;
  5132.             } else {
  5133.                 $row_idx++;
  5134.             }
  5135.         }
  5136.         print "</TABLE>\n";
  5137.     }
  5138.  
  5139.     # Predefined expressions from search.pl
  5140.     print "<HR><H3>Predefined Searches</H3>\n";
  5141.     print "<TABLE WIDTH=600>\n";
  5142.     my $row_idx = 0;
  5143.     my $r;
  5144.     foreach $r (keys %auto_srch) {
  5145.  
  5146.         $auto_srch_reg{$r} = 0 unless (defined $auto_srch_reg{$r});
  5147.         $auto_srch_csense{$r} = 1 unless (defined $auto_srch_csense{$r});
  5148.  
  5149.         print "<TR>\n" if ($row_idx == 0); 
  5150.  
  5151.         print "  <TD ALIGN=CENTER WIDTH=150>\n".
  5152.             "<FORM ACTION=\"$PROGNAME\" METHOD=\"GET\">\n".
  5153.             "<INPUT TYPE=\"hidden\" NAME=\"func\" VALUE=\"$SRCH_RMAIN\">\n".
  5154.             "<INPUT TYPE=\"hidden\" NAME=\"img\" VALUE=\"$args{'img'}\">\n".
  5155.             "<INPUT TYPE=\"hidden\" NAME=\"str\" VALUE=\"$auto_srch{$r}\">\n".
  5156.           make_hidden();
  5157.  
  5158.         if ($auto_srch_reg{$r} == 1) {
  5159.               print 
  5160.               "<INPUT TYPE=\"hidden\" NAME=\"regexp\" VALUE=\"$REG_EXP\">\n";
  5161.         } 
  5162.         if ($auto_srch_csense{$r} == 0) {
  5163.               print
  5164.               "<INPUT TYPE=\"hidden\" NAME=\"srch_case\" VALUE=\"$CASE_INSENS\">\n";
  5165.         }
  5166.           print "<INPUT TYPE=\"SUBMIT\" VALUE=\"$r\"><BR></FORM>\n".
  5167.           "  </TD>\n";
  5168.         
  5169.         if ($row_idx == 3) {
  5170.             print "</TR>\n";
  5171.             $row_idx = 0;
  5172.         } else {
  5173.             $row_idx++;
  5174.         }
  5175.     }
  5176.     print "</TABLE>\n";
  5177.  
  5178.  
  5179.     return 0;
  5180. };
  5181.  
  5182. # MAIN WITH RESULTS
  5183. # Page that makes frame with the results on left and data units on right
  5184. $funcs[$SRCH_RMAIN] = sub {
  5185.  
  5186.     # A string was given for a new search
  5187.     if (exists $args{'str'}) {
  5188.         check_str();
  5189.  
  5190.         print_html_header_frameset("Search on $args{'img'} for $args{'str'}");
  5191.  
  5192.         print "<FRAMESET COLS=\"35%,65%\">\n";
  5193.  
  5194.         my $srch_case = "";
  5195.         $srch_case = "&srch_case=$args{'srch_case'}" 
  5196.           if (exists $args{'srch_case'});
  5197.  
  5198.         my $regexp = "";
  5199.         $regexp = "®exp=$args{'regexp'}" 
  5200.           if (exists $args{'regexp'});
  5201.  
  5202.         # Block List
  5203.         print "<FRAME SRC=\"$PROGNAME?func=$SRCH_DOSRCH&".
  5204.           "$baseargs$srch_case$regexp&str=$enc_args{'str'}\">\n";
  5205.     }
  5206.     elsif (exists $args{'srchidx'}) {
  5207.         check_srchidx();
  5208.  
  5209.         print_html_header_frameset("Search on $args{'img'} for Index $args{'idx'}");
  5210.  
  5211.         print "<FRAMESET COLS=\"35%,65%\">\n";
  5212.  
  5213.         # Block List
  5214.         print "<FRAME SRC=\"$PROGNAME?func=$SRCH_READSRCH&".
  5215.           "$baseargs&srchidx=$enc_args{'srchidx'}\">\n";
  5216.     }
  5217.  
  5218.     # Block Contents
  5219.     print "<FRAME SRC=\"$PROGNAME?func=$BLANK&$baseargs\" NAME=\"content\">\n".
  5220.       "</FRAMESET>\n";
  5221.  
  5222.     return 0;
  5223. };
  5224.  
  5225.  
  5226.  
  5227. # Find an empty file to save the keyword searches to
  5228. sub find_srch_file {
  5229.     my $tmp_img = $args{'img'};
  5230.     $tmp_img =~ tr/\//\-/;
  5231.  
  5232.     my $out_name = "${host_dir}${DATADIR}/$tmp_img";
  5233.     my $i;
  5234.     for ($i = 0; -e "${out_name}-${i}.srch"; $i++) { }
  5235.  
  5236.     return "${out_name}-${i}.srch";
  5237. }
  5238.  
  5239. # Pass the index and get the full path of the file returned
  5240. sub get_srch_file {
  5241.     my $idx = shift;
  5242.     my $tmp_img = $args{'img'};
  5243.     $tmp_img =~ tr/\//\-/;
  5244.     return "${host_dir}${DATADIR}/$tmp_img-${idx}.srch";
  5245. }
  5246.  
  5247. $funcs[$SRCH_READSRCH] = sub {
  5248.     check_srchidx(); 
  5249.  
  5250.     print_html_header("");
  5251.  
  5252.     my $srch_name = get_srch_file($args{'srchidx'});
  5253.     unless (open (SRCH, "$srch_name")) {
  5254.         print "Error opening search file: $srch_name\n";
  5255.         return 1;
  5256.     }
  5257.  
  5258.     my @results;
  5259.     my $prev_str = "";
  5260.     my $grep_flag = "";
  5261.  
  5262.     while (<SRCH>) {
  5263.         if ($. == 1) {
  5264.             unless (/^(\d+)\|(.*?)?\|(.*)$/) {
  5265.                 print "Error pasing header of search file: $srch_name\n";
  5266.                 return 1;
  5267.             }
  5268.             $grep_flag = $2;
  5269.             $prev_str = $3;
  5270.         } else {
  5271.             push @results, "$_";
  5272.         }
  5273.     }
  5274.     close (SRCH);
  5275.     print_srch_results($prev_str, $grep_flag, \@results, $srch_name);
  5276.  
  5277.     return 0;
  5278. };
  5279.  
  5280.  
  5281. # performs actual search, saves hits to file, and calls method to print
  5282. $funcs[$SRCH_DOSRCH] = sub {
  5283.     check_str(); 
  5284.  
  5285.     print_html_header("");
  5286.  
  5287.     my $img = get_img('img');
  5288.     my $ftype = get_ftype();
  5289.  
  5290.     my $orig_str = get_str();
  5291.     my $grep_str = $orig_str;   # we will escape some values in the grep ver
  5292.  
  5293.  
  5294.     # Check for a search string 
  5295.     if ($orig_str eq "") {
  5296.         print "You must enter a string value to search<BR>\n";
  5297.         print "<B><A HREF=\"$PROGNAME?func=$SRCH_ENT&$baseargs\" ".
  5298.           "TARGET=\"_parent\">New Search</A></B>\n<P>";
  5299.         return 1;
  5300.     }
  5301.  
  5302.  
  5303.     my $log = "";            # Log entry string
  5304.     my $grep_flag = "";        # Flags to pass to grep
  5305.  
  5306.     # Check if search is case insensitive
  5307.     my $case = 0;
  5308.     if ((exists $args{'srch_case'}) && ($args{'srch_case'} == $CASE_INSENS)) {
  5309.         $grep_flag = "-i";
  5310.         $case = 1;
  5311.         $log .= "Case Insensitive ";
  5312.     }
  5313.  
  5314.     # Check if search is a regular expression
  5315.     my $regexp = 0;
  5316.     if ((exists $args{'regexp'}) && ($args{'regexp'} == $REG_EXP)) {
  5317.         $grep_flag .= " -E";
  5318.         $regexp = 1;
  5319.         $log .= "Regular Expression ";
  5320.     }
  5321.  
  5322.     # if not a reg-exp, we need to escape some special values that
  5323.     # 'grep' will misinterpret
  5324.     else {
  5325.         $grep_str =~ s/\\/\\\\/g;    # \
  5326.         $grep_str =~ s/\./\\\./g;    # .
  5327.         $grep_str =~ s/\[/\\\[/g;    # [
  5328.         $grep_str =~ s/\^/\\\^/g;    # ^
  5329.         $grep_str =~ s/\$/\\\$/g;    # $
  5330.         $grep_str =~ s/\*/\\\*/g;    # *
  5331.         # We need to add ' to end begin and end of the search as well
  5332.         if ($grep_str =~ /\'/) {
  5333.             $grep_str =~ s/\'/\\\'/g;    # '
  5334.             $grep_str = "'$grep_str'";
  5335.         }
  5336.         $grep_str =~ s/^\-/\\\-/;    # starting with - (mistakes for an arg)
  5337.     }
  5338.  
  5339.  
  5340.     log_host_inv ("$args{'img'}: ${log}search for $grep_str");
  5341.  
  5342.     # Get the addressable unit of image
  5343.     my $bs = get_unitsize();
  5344.  
  5345.     local *OUT;
  5346.  
  5347.     my $hit_cnt = 0;
  5348.     $SIG{ALRM} = sub {
  5349.         if (($hit_cnt++ % 5) == 0) {
  5350.             print "+";
  5351.         } else {
  5352.             print "-";
  5353.         }
  5354.         alarm(5);
  5355.     };
  5356.  
  5357.     alarm(5);
  5358.     print "<B>Searching</B>: ";
  5359.  
  5360.     # if the string is less than 4 chars, then it will not be in the
  5361.     # strings file so it will be searched for the slow way
  5362.     if (length($orig_str) < 4) {
  5363.         my $ltmp = length ($orig_str);
  5364.         exec_pipe (*OUT, 
  5365.           "'$STRINGS_EXE' -t d -n $ltmp '$img' | '$GREP_EXE' $grep_flag '$grep_str'");
  5366.     }
  5367.     # Use the strings file if it exists
  5368.     elsif (defined $img2str{$args{'img'}}) {
  5369.         my $str_img = "${host_dir}/$img2str{$args{'img'}}";
  5370.         exec_pipe (*OUT, 
  5371.           "'$GREP_EXE' $grep_flag '$grep_str' '$str_img'");
  5372.     }
  5373.     # Run strings on the image first and then grep that
  5374.     else {
  5375.         exec_pipe (*OUT, 
  5376.           "'$STRINGS_EXE' -a -t d '$img' | '$GREP_EXE' $grep_flag '$grep_str'");
  5377.     } 
  5378.  
  5379.  
  5380.     # $norm_str is normalized to find the "hit" in the output
  5381.     my $norm_str = $orig_str;
  5382.  
  5383.     # make this lowercase if we are doing case insens 
  5384.     $norm_str =~ tr/[A-Z]/[a-z]/ if ($case == 1);
  5385.  
  5386.     my $norm_str_len = length ($norm_str);
  5387.  
  5388.     # array to pass to printing method
  5389.     my @results;
  5390.  
  5391.     # Cycle through the results and put them in an array
  5392.     while (<OUT>) {
  5393.  
  5394.         # print "." if (scalar (@results) % $STATUS == 0);
  5395.  
  5396.         # Parse out the byte offset and hit string
  5397.         if (/^\s*(\d+)\s+(.+)$/)  {
  5398.             my $off = $1;
  5399.             my $hit_str_orig = $2;
  5400.             my $idx = 0;
  5401.  
  5402.             # Make a copy that we can modify & play with
  5403.             my $hit_str = $hit_str_orig;
  5404.             $hit_str =~ tr/[A-Z]/[a-z]/ if ($case == 1);
  5405.  
  5406.             # How long was the string that we hit?
  5407.             my $hit_str_len = length ($hit_str);
  5408.  
  5409.             # I'm not sure how to find a grep re in the hit yet, so 
  5410.             # for now we do not get the exact offset
  5411.             if ($regexp) {
  5412.                 my $b = int ($off / $bs);
  5413.                 my $o = int ($off % $bs);
  5414.  
  5415.                 # $hit =~ s/\n//g;
  5416.                 push @results, "${b}|${o}|";
  5417.                 next;
  5418.             }
  5419.  
  5420.  
  5421.             # There could be more than one keyword in the string
  5422.             # so cylcle through all of them
  5423.             my $psize = scalar (@results);
  5424.             while (($idx = index ($hit_str, $norm_str, $idx)) > -1) {
  5425.  
  5426.                 my $b = int (($off + $idx) / $bs);
  5427.                 my $o = int (($off + $idx) % $bs);
  5428.  
  5429.                 # The summary of the hit starts 5 chars before it
  5430.                 my $sum_min = $idx - 5;
  5431.                 $sum_min = 0 if ($sum_min < 0);
  5432.  
  5433.                 # Goto 5 after, if there is still space
  5434.                 my $sum_max = $idx + $norm_str_len + 5;
  5435.                 $sum_max = $hit_str_len if ($sum_max > $hit_str_len);
  5436.  
  5437.                 my $sum_hit = substr ($hit_str_orig, $sum_min, $sum_max - $sum_min);
  5438.                 # remove new lines
  5439.                 $sum_hit =~ s/\n/ /g;
  5440.  
  5441.                 push @results, "${b}|${o}|$sum_hit";
  5442.  
  5443.                 # advance index to find next hit
  5444.                 $idx++;
  5445.             }
  5446.             # If we did not find a term, then just print what
  5447.             # was found-this occurs bc index does not find it
  5448.             # sometimes.
  5449.             if ($psize == scalar(@results)) {
  5450.  
  5451.                 my $b = int ($off / $bs);
  5452.                 my $o = int ($off % $bs);
  5453.  
  5454.                 # $hit =~ s/\n//g;
  5455.                 push @results, "${b}|${o}|";
  5456.                 next;
  5457.             }
  5458.         }
  5459.         # A negative offset is common on FreeBSD with large images
  5460.         elsif (/^\s*(\-\d+):?\s*(.+)$/) {
  5461.             print "ERROR: Negative byte offset ($1) Your version of ".
  5462.               "strings likely does not support large files: $2<BR>\n";
  5463.         }
  5464.         else {
  5465.             print "Error parsing grep result: $_<BR>\n";
  5466.         }
  5467.     }
  5468.     close (OUT);
  5469.     $SIG{ALRM} = 'DEFAULT';
  5470.  
  5471.     print " <B>Done</B><BR>";
  5472.  
  5473.     print "<B>Saving</B>: ";
  5474.     # Find a file to save the results to
  5475.     my $srch_name = find_srch_file();
  5476.     unless (open(IDX, ">$srch_name")) {
  5477.         print "Error opening $srch_name\n";
  5478.         return (1);
  5479.     }
  5480.  
  5481.     # Print the header 
  5482.     my $cnt = scalar(@results);
  5483.     print IDX "$cnt|${grep_flag}|${orig_str}\n";
  5484.  
  5485.     for (my $i = 0; $i < $cnt; $i++) {
  5486. #        print "." if ($i % $STATUS == 0);
  5487.         print IDX "$results[$i]\n";
  5488.     }
  5489.     close (IDX);
  5490.     print " <B>Done</B><HR>\n";
  5491.  
  5492.     print_srch_results($grep_str, $grep_flag, \@results, $srch_name);
  5493.  
  5494.     return 0;
  5495. };
  5496.  
  5497.  
  5498. # Args are search string, grep flags, and array of hits
  5499. sub print_srch_results {
  5500.  
  5501.     if (scalar (@_) != 4) {
  5502.         print "Missing Args for print_srch_results()\n";
  5503.         return 1;
  5504.     }
  5505.  
  5506.     my $grep_str = shift();
  5507.     my $grep_flag = shift();
  5508.     my @results = @{shift()};
  5509.     my $srch_name = shift();
  5510.     my $cnt = scalar(@results);
  5511.  
  5512.     my $ftype = get_ftype();
  5513.     my $addr_str = $addr_unit{$ftype};
  5514.  
  5515.     print "<B><A HREF=\"$PROGNAME?func=$SRCH_ENT&$baseargs\" ".
  5516.       "TARGET=\"_parent\">New Search</A></B>\n<P>";
  5517.  
  5518.     my $grep_str_html = html_encode($grep_str);
  5519.     if ($cnt == 0) {    
  5520.         print "<B><TT>$grep_str_html</TT> was not found</B><BR>\n";
  5521.     } elsif ($cnt == 1) {
  5522.         print "<B>1 occurrence of <TT>$grep_str_html</TT> was found</B><BR>\n";
  5523.     } else {
  5524.         print "<B>$cnt occurrences of <TT>$grep_str_html</TT> were found</B><BR>\n";
  5525.     }
  5526.  
  5527.     print "Search Options:<BR>\n";
  5528.     if ($grep_flag =~ /\-i/) {
  5529.         print "  Case Insensitive<BR>\n";
  5530.     } else {
  5531.         print "  Case Sensitive<BR>\n";
  5532.     }
  5533.     if ($grep_flag =~ /\-E/) {
  5534.         print "  Regular Expression<BR>\n";
  5535.     }
  5536.  
  5537.     print "<HR>\n";
  5538.  
  5539.     if ($cnt > 1000) {
  5540.         print "There were more than <U>1000</U> hits.<BR>\n";
  5541.         print "Please revise the search to a managable amount.\n";
  5542.         print "<P>The $cnt hits can be found in: <TT>$srch_name</TT><BR>\n";
  5543.         print "<P><B><A HREF=\"$PROGNAME?func=$SRCH_ENT&$baseargs\" ".
  5544.           "TARGET=\"_parent\">New Search</A></B>\n<P>";
  5545.         return 0;
  5546.     }
  5547.  
  5548.     my $prev = -1;
  5549.     for (my $i = 0; $i < $cnt; $i++) {
  5550.  
  5551.         unless ($results[$i] =~ /^(\d+)\|(\d+)\|(.*)?$/) {
  5552.             print "Error parsing search array: $results[$i]\n";
  5553.             return 1;
  5554.         }
  5555.  
  5556.         my $blk = $1;
  5557.         my $off = $2;
  5558.         my $str = $3;
  5559.  
  5560.         if ($blk != $prev) {
  5561.             my $url="$PROGNAME?func=$BLK_CMENU_FR&$baseargs&block=$blk";
  5562.             
  5563.             print "<BR>\n$addr_str $blk (<A HREF=\"$url&sort=$BLK_SORT_HEX\" ". 
  5564.               "TARGET=content>Hex</A> - ".
  5565.               "<A HREF=\"$url&sort=$BLK_SORT_ASC\" TARGET=content>".
  5566.               "Ascii</A>";
  5567.  
  5568.             print " - <A HREF=\"$PROGNAME?$baseargs&func=$BLK_CMENU_FR&".
  5569.               "mnt=$enc_args{'mnt'}&img=$mod2img{$args{'img'}}&".
  5570.               "btype=$BTYPE_DLS&block=$blk\" TARGET=content>Original</A>"
  5571.               if (($ftype eq 'dls') && (exists $mod2img{$args{'img'}}));
  5572.  
  5573.             print ")<BR>";
  5574.             $prev = $blk;
  5575.         }
  5576.  
  5577.         my $occ = $i + 1;
  5578.         if ($str ne "")  {
  5579.             $str = html_encode($str);    
  5580.             print "$occ: $off (<TT>$str</TT>)<BR>\n";
  5581.         } else {
  5582.             print "$occ: $off<BR>\n";
  5583.         }
  5584.     }
  5585.  
  5586.  
  5587.     return 0;
  5588. }
  5589.  
  5590.  
  5591. # Make a strings -t d file for the image to decrease the search time
  5592. $funcs[$IMG_MAKESTR] = sub {
  5593.     check_fname(); check_fname_mode(); 
  5594.  
  5595.     print_html_header("");
  5596.  
  5597.     my $fname = get_fname();
  5598.     my $fname_rel = get_fname_rel();
  5599.     my $mode = $args{'fname_mode'};
  5600.     my $ftype = get_ftype();
  5601.  
  5602.     if ((-e "$fname") && ($FNAME_MODE_INIT == $mode)) {
  5603.         print "File Already Exists: $fname_rel\n";
  5604.  
  5605.         my $hidden = 
  5606.           "<INPUT TYPE=\"hidden\" NAME=\"func\" VALUE=\"$IMG_MAKESTR\">\n".
  5607.           "<INPUT TYPE=\"hidden\" NAME=\"img\" VALUE=\"$args{'img'}\">\n".
  5608.           make_hidden();
  5609.  
  5610.         $hidden .= "<INPUT TYPE=\"hidden\" NAME=\"md5\" VALUE=\"$args{'md5'}\">\n" 
  5611.             if (exists $args{'md5'});
  5612.  
  5613.         print "<FORM ACTION=\"$PROGNAME\" METHOD=\"GET\">\n".
  5614.           "New Name: <INPUT TYPE=\"text\" NAME=\"fname\">\n".
  5615.           "<TABLE CELLSPACING=\"30\" CELLPADDING=\"2\"><TR><TD>".
  5616.           "$hidden".
  5617.           "<INPUT TYPE=\"hidden\" NAME=\"fname_mode\" VALUE=\"$FNAME_MODE_INIT\">\n".
  5618.           "<INPUT TYPE=\"IMAGE\" SRC=\"pict/but_new_name.jpg\" ". 
  5619.           "WIDTH=79 HEIGHT=20 ALT=\"Use New Name\" BORDER=\"0\">\n".
  5620.           "</FORM></TD>\n";
  5621.  
  5622.         print "<TD><FORM ACTION=\"$PROGNAME\" METHOD=\"GET\">\n".
  5623.           "$hidden".
  5624.           "<INPUT TYPE=\"hidden\" NAME=\"fname\" VALUE=\"$args{'fname'}\">\n".
  5625.           "<INPUT TYPE=\"hidden\" NAME=\"fname_mode\" VALUE=\"$FNAME_MODE_OVER\">\n".
  5626.           "<INPUT TYPE=\"IMAGE\" SRC=\"pict/but_replace.jpg\" ". 
  5627.           "WIDTH=66 HEIGHT=20 ALT=\"Replace\" BORDER=\"0\">\n".
  5628.           "</FORM></TD></TR></TABLE>";
  5629.  
  5630.           return 0;
  5631.     }
  5632.  
  5633.     my $img = get_img('img');
  5634.  
  5635.     print "Extracting strings from <TT>$args{'img'}</TT> and saving to ".
  5636.       "<TT>$args{'fname'}</TT><BR><BR>\n";
  5637.  
  5638.     log_host_inv ("$args{'img'}: Saving ASCII strings to $fname_rel");
  5639.  
  5640.     local *OUT;
  5641.     exec_pipe (*OUT,
  5642.       "'$STRINGS_EXE' -a -t d '$img' > '$fname'");
  5643.     print $_ while (<OUT>);
  5644.     close (OUT);
  5645.  
  5646.     # Verify that it worked
  5647.     unless (open (STR, "$fname")) { 
  5648.         print "Error opening $fname<BR>\n".
  5649.           "Either an error occurred while generating the file or ".
  5650.           "no ASCII strings exist";
  5651.         return (1);
  5652.     }
  5653.  
  5654.     my $sz = 0;
  5655.     while (<STR>) {
  5656.         unless (/^\s*\d+\s+\S.*$/) {
  5657.             print ("Error making strings file: $_");
  5658.             return (1);
  5659.         }
  5660.         $sz = 1;
  5661.         last;
  5662.     }
  5663.  
  5664.     if ($sz == 0) {
  5665.         print "Strings file has no valid entries, there could be no ASCII".
  5666.           " strings in the original image";
  5667.  
  5668.         print "<FORM ACTION=\"$PROGNAME\" METHOD=\"GET\">\n".
  5669.           "<INPUT TYPE=\"hidden\" NAME=\"img\" VALUE=\"$args{'img'}\">\n".
  5670.           "<INPUT TYPE=\"hidden\" NAME=\"func\" VALUE=\"$IMG_DETAILS\">\n".
  5671.           make_hidden().
  5672.           "<INPUT TYPE=\"IMAGE\" SRC=\"pict/but_ok.jpg\" ".        
  5673.           "WIDTH=43 HEIGHT=20 ALT=\"Ok\" BORDER=\"0\">\n</FORM>";
  5674.         return (1);
  5675.     }
  5676.  
  5677.     close (STR);
  5678.  
  5679.     # append to config
  5680.     update_host_config("strings", $fname_rel, 
  5681.       "$args{'img'}");
  5682.     print "<TT>$fname_rel</TT> added to host config file<BR><BR>";
  5683.  
  5684.  
  5685.     $img2ftype{$fname_rel} = "strings";
  5686.     $mod2img{$fname_rel} = $args{'img'};
  5687.     $img2str{$args{'img'}} = $fname_rel;
  5688.  
  5689.     # Calculate MD5
  5690.     if ((exists $args{'md5'}) && ($args{'md5'} == 1)) {
  5691.         print "Calculating MD5 Value<BR><BR>\n";
  5692.         my $m = int_create_wrap ($fname, $fname_rel);
  5693.         print "MD5 Value: <TT>$m</TT><BR><BR>\n";
  5694.     }
  5695.  
  5696.     my $dest_img = $args{'img'};
  5697.     # We need to return with a real image to IMG_DETAILS so check the mod
  5698.     $dest_img = $mod2img{$args{'img'}}
  5699.       if (defined $mod2img{$args{'img'}});
  5700.  
  5701.  
  5702.     print "<A HREF=\"$PROGNAME?$baseargs_noimg&func=$IMG_DETAILS&".
  5703.       "img=$dest_img\" TARGET=_top>Image Details</A><P>\n";
  5704.     
  5705.     print "<A HREF=\"$PROGNAME?func=$MAIN_FR&mode=$SRCH_MAIN&$baseargs\"".
  5706.           " TARGET=\"_top\">Keyword Search</A>\n";
  5707.  
  5708.     return 0;
  5709. };
  5710.  
  5711. $funcs[$IMG_MAKEDLS] = sub {
  5712.     check_fname(); check_fname_mode(); 
  5713.  
  5714.     print_html_header("");
  5715.  
  5716.     my $fname = get_fname();
  5717.     my $fname_rel = get_fname_rel();
  5718.     my $mode = $args{'fname_mode'};
  5719.  
  5720.     if ((-e "$fname") && ($FNAME_MODE_INIT == $mode)) {
  5721.         print "File Already Exists: $fname_rel\n";
  5722.         my $hidden = 
  5723.           "<INPUT TYPE=\"hidden\" NAME=\"func\" VALUE=\"$IMG_MAKEDLS\">\n".
  5724.           "<INPUT TYPE=\"hidden\" NAME=\"img\" VALUE=\"$args{'img'}\">\n".
  5725.           make_hidden();
  5726.  
  5727.         $hidden .= "<INPUT TYPE=\"hidden\" NAME=\"md5\" VALUE=\"$args{'md5'}\">\n" 
  5728.             if (exists $args{'md5'});
  5729.  
  5730.         print "<FORM ACTION=\"$PROGNAME\" METHOD=\"GET\">\n".
  5731.           "New Name: <INPUT TYPE=\"text\" NAME=\"fname\"> ".
  5732.           "<TABLE CELLSPACING=\"30\" CELLPADDING=\"2\"><TR><TD>".
  5733.           "$hidden".
  5734.           "<INPUT TYPE=\"hidden\" NAME=\"fname_mode\" VALUE=\"$FNAME_MODE_INIT\">\n".
  5735.           "<INPUT TYPE=\"IMAGE\" SRC=\"pict/but_new_name.jpg\" ".               
  5736.           "WIDTH=79 HEIGHT=20 ALT=\"Use New Name\" BORDER=\"0\">\n".
  5737.           "</FORM></TD>\n";
  5738.  
  5739.         print "<TD><FORM ACTION=\"$PROGNAME\" METHOD=\"GET\">\n".
  5740.           "<INPUT TYPE=\"IMAGE\" SRC=\"pict/but_replace.jpg\" ".               
  5741.           "WIDTH=66 HEIGHT=20 ALT=\"Replace\" BORDER=\"0\"><BR>\n".
  5742.           "$hidden".
  5743.           "<INPUT TYPE=\"hidden\" NAME=\"fname\" VALUE=\"$args{'fname'}\">\n".
  5744.           "<INPUT TYPE=\"hidden\" NAME=\"fname_mode\" VALUE=\"$FNAME_MODE_OVER\">\n".
  5745.           "</FORM></TD></TR></FORM>";
  5746.  
  5747.           return 0;
  5748.     }
  5749.  
  5750.     my $img = get_img('img');
  5751.     my $ftype = get_ftype();
  5752.  
  5753.     log_host_inv ("$args{'img'}: Saving unallocated data to $fname_rel");
  5754.  
  5755.     print "Extracting unallocated data from <TT>$args{'img'}</TT> and ".
  5756.       "saving to <TT>$fname_rel</TT><BR><BR>\n";
  5757.  
  5758.     local *OUT;
  5759.     exec_pipe (*OUT, 
  5760.       "'${TASKDIR}dls' -f $ftype '$img' > '$fname'");
  5761.     print "$_" while (<OUT>);
  5762.     close (OUT);
  5763.  
  5764.  
  5765.     # append to fsmorgue 
  5766.     update_host_config("dls", $fname_rel, $args{'img'}); 
  5767.  
  5768.     print "<TT>$fname_rel</TT> added to host config file<BR><BR>";
  5769.  
  5770.     $img2ftype{$fname_rel} = "dls";
  5771.     $mod2img{$fname_rel} = $args{'img'};
  5772.     $img2dls{$args{'img'}} = $fname_rel;
  5773.  
  5774.     # Calculate MD5
  5775.     if ((exists $args{'md5'}) && ($args{'md5'} == 1)) {
  5776.         print "Calculating MD5 Value<BR><BR>\n";
  5777.         my $m = int_create_wrap ($fname, $fname_rel);
  5778.         print "MD5 Value: <TT>$m</TT><BR><BR>\n";
  5779.     }
  5780.     
  5781.     print "<A HREF=\"$PROGNAME?$baseargs&func=$IMG_DETAILS\"".
  5782.       " TARGET=_top>Image Details</A><P>\n";
  5783.     
  5784.     print "<A HREF=\"$PROGNAME?func=$MAIN_FR&mode=$SRCH_MAIN&$baseargs_noimg&".
  5785.           "img=$fname_rel\" TARGET=\"_top\">Keyword Search</A>\n";
  5786.  
  5787.     return 0;
  5788. };
  5789.  
  5790.  
  5791.  
  5792. ############ FILE SYSTEM ##################
  5793.  
  5794. $funcs[$FS_STAT] = sub {
  5795.     print_html_header("File System Status");
  5796.  
  5797.     log_host_inv ("$args{'img'}: Displaying file system details");
  5798.  
  5799.     my $img = get_img('img');
  5800.     my $ftype = get_ftype();
  5801.     my $fat = 0;
  5802.     local *OUT;
  5803.     exec_pipe (*OUT, 
  5804.       "'${TASKDIR}fsstat' -f $ftype  '$img'");
  5805.     while (<OUT>) {
  5806.  
  5807.         # Special case for FAT
  5808.         # We will be giving hyperlinks in the FAT table dump
  5809.         if ($fat == 1) {
  5810.             # Ignore the divider
  5811.             if (/\-\-\-\-\-\-\-\-\-\-/) {
  5812.                 print "$_<BR>";
  5813.                 next;
  5814.             }
  5815.  
  5816.             if (/^((\d+)\-\d+\s+\((\d+)\)) \-\> ([\w]+)$/) {
  5817.                 my $full = $1;
  5818.                 my $blk = $2;
  5819.                 my $len = $3;
  5820.                 my $next = $4;
  5821.  
  5822.                 # Print the tag so that other FAT entries can link to it
  5823.                 print "<A NAME=\"$blk\">\n";
  5824.  
  5825.                 print "<A HREF=\"$PROGNAME?$baseargs&func=$MAIN_FR&mode=$BLK_MAIN&".
  5826.                   "block=$blk&len=$len\" TARGET=\"_blank\">$full</A> -> ";
  5827.  
  5828.                 if ($next eq 'EOF') {
  5829.                     print "EOF<BR>\n";
  5830.                 }
  5831.                 else {
  5832.                   print "<A HREF=\"#$next\">$next</A><BR>\n";
  5833.                 }
  5834.             }
  5835.             else {
  5836.                 $fat = 0;
  5837.                 print "$_<BR>";
  5838.             }
  5839.         }
  5840.         else {
  5841.             print "$_<BR>";
  5842.         }
  5843.  
  5844.         # Set the flag if we reach the FAT 
  5845.         $fat = 1 if (($ftype =~ /fat/) && ($_ =~ /FAT CONTENTS/));
  5846.     }
  5847.     close (OUT);
  5848. };
  5849.  
  5850.  
  5851. ############ INTEGRITY CHECKS ##################
  5852.  
  5853.  
  5854. # Special func for printing integrity check menu
  5855. # We show any file that we have a reference for
  5856.  
  5857. # pass the md5 hash (from md5.txt) and then the sorted array
  5858. sub int_menu_print {
  5859.     my %md5s = %{$_[0]};
  5860.     my @sort = @{$_[1]};
  5861.  
  5862.     for (my $i = 0; $i <= $#sort; $i++) {
  5863.  
  5864.         print "<TR><TD ALIGN=\"right\"><TT><B>$sort[$i]</B></TT></TD>\n";
  5865.  
  5866.         # It already exists, so make verify button
  5867.         if (exists $md5s{$sort[$i]}) {
  5868.             print "<TD><TT>$md5s{$sort[$i]}</TT></TD>".
  5869.               "<FORM ACTION=\"$PROGNAME\" METHOD=\"GET\" TARGET=\"cont\">\n".
  5870.               "<INPUT TYPE=\"hidden\" NAME=\"img\" VALUE=\"$sort[$i]\">\n".
  5871.               make_hidden().
  5872.               "<TD><INPUT TYPE=\"hidden\" NAME=\"func\" VALUE=\"$INT_CHECK\">\n".
  5873.               "<INPUT TYPE=\"IMAGE\" SRC=\"pict/int_b_valid.jpg\" ".               
  5874.               "ALT=\"Validate\" BORDER=\"0\">\n".
  5875.               "</FORM></TD></TR>\n";
  5876.         }
  5877.         # Generate New button
  5878.         else {
  5879.             print "<TD> </TD><TD>".
  5880.               "<FORM ACTION=\"$PROGNAME\" METHOD=\"GET\" TARGET=\"cont\">\n".
  5881.               "<INPUT TYPE=\"hidden\" NAME=\"img\" VALUE=\"$sort[$i]\">\n".
  5882.               make_hidden().
  5883.               "<INPUT TYPE=\"hidden\" NAME=\"func\" VALUE=\"$INT_CREATE\">\n".
  5884.               "<INPUT TYPE=\"IMAGE\" SRC=\"pict/int_b_calc.jpg\" ".               
  5885.               "ALT=\"Calculate\" BORDER=\"0\">\n".
  5886.               "</FORM></TD></TR>\n";
  5887.         }
  5888.     }
  5889.  
  5890.     return;
  5891. };
  5892.  
  5893.  
  5894. # Create a frame with two rows, one with the list of images to check
  5895. # and then the bottom actually does it.  
  5896. $funcs[$INT_LIST_FR] = sub {
  5897.     print_html_header_frameset("$args{'case'}:$args{'host'} Integrity Check");
  5898.  
  5899.     print "<FRAMESET ROWS=\"80%,20%\">\n";
  5900.  
  5901.     # Block List
  5902.     print "<FRAME SRC=\"$PROGNAME?func=$INT_LIST&$baseargs\">\n";
  5903.     print "<FRAME SRC=\"$PROGNAME?func=$BLANK\" NAME=\"cont\">\n";
  5904.  
  5905.     print "</FRAMESET>\n";
  5906.  
  5907.     return 0;
  5908. };
  5909.  
  5910. # Reads the MD5 file to fill in the MENU list for the integrity
  5911. # check mode
  5912. $funcs[$INT_LIST] = sub {
  5913.     print_html_header("Image Integrity Menu");
  5914.  
  5915.     my %md5s;
  5916.     my @dls;
  5917.     my @str;
  5918.     my @fs;
  5919.     my @body;
  5920.     my @tl;
  5921.  
  5922.     # Read the known values if the file exists
  5923.     if (open (FILE, "${host_dir}${IMGDIR}/$MD5_FILE")) { 
  5924.         # Read the md5 values into a hash
  5925.         while (<FILE>) {
  5926.             s/^\s+//;
  5927.             s/\s+$//;
  5928.  
  5929.             if (/($REG_MD5)\s+(.*)/o) {
  5930.                 $md5s{"$2"} = $1;
  5931.                 $md5s{"$2"} =~ tr/[a-f]/[A-F]/;
  5932.             }
  5933.             else {
  5934.                 print "Error reading line $. of $MD5_FILE: $_<BR>\n";
  5935.                 return 1;
  5936.             }
  5937.         }
  5938.         close (FILE);
  5939.     }
  5940.  
  5941.     if (open (FILE, "${host_dir}${DATADIR}/$MD5_FILE")) { 
  5942.         # Read the md5 values into a hash
  5943.         while (<FILE>) {
  5944.             s/^\s+//;
  5945.             s/\s+$//;
  5946.  
  5947.             if (/($REG_MD5)\s+(.*)/o) {
  5948.                 $md5s{"$2"} = $1;
  5949.                 $md5s{"$2"} =~ tr/[a-f]/[A-F]/;
  5950.             }
  5951.             else {
  5952.                 print "Error reading line $. of $MD5_FILE: $_<BR>\n";
  5953.                 return 1;
  5954.             }
  5955.         }
  5956.         close (FILE);
  5957.     }
  5958.  
  5959.     # sort the images into the different types
  5960.     foreach my $k (keys %img2ftype) {
  5961.         if ($img2ftype{$k} eq "dls") {
  5962.             push @dls, $k;
  5963.         } 
  5964.         elsif ($img2ftype{$k} eq "strings") {
  5965.             push @str, $k;
  5966.         } 
  5967.         elsif ($img2ftype{$k} eq "body") {
  5968.             push @body, $k;
  5969.         } 
  5970.         elsif ($img2ftype{$k} eq "timeline") {
  5971.             push @tl, $k;
  5972.         } 
  5973.         else {
  5974.             push @fs, $k;
  5975.         }
  5976.     }
  5977.  
  5978.  
  5979.     print "<CENTER><TABLE CELLSPACING=\"10\" CELLPADDING=\"2\">";
  5980.  
  5981.     # File system images
  5982.     if (scalar @fs > 0) {
  5983.         print "<TR><TH COLSPAN=3>".
  5984.           "<IMG SRC=\"pict/int_h_img.jpg\" ALT=\"File System Images\">".
  5985.           "</TH></TR>\n";
  5986.         my @sort = sort {$a cmp $b} @fs;
  5987.         int_menu_print (\%md5s, \@sort);
  5988.     }
  5989.  
  5990.     # Unallocated (dls) images
  5991.     if (scalar @dls > 0) {
  5992.         print  "<TR><TH COLSPAN=3> </TH></TR>\n".
  5993.           "<TR><TH COLSPAN=3>".
  5994.           "<IMG SRC=\"pict/int_h_unalloc.jpg\" ALT=\"Unallocated Data Files\">".
  5995.           "</TH></TR>\n";
  5996.         my @sort = sort {$a cmp $b} @dls;
  5997.         int_menu_print (\%md5s, \@sort);
  5998.     }
  5999.  
  6000.     # Strings files (of dls or fs images)
  6001.     if (scalar @str > 0) {
  6002.         print "<TR><TH COLSPAN=3> </TH></TR>\n".
  6003.           "<TR><TH COLSPAN=3>".
  6004.           "<IMG SRC=\"pict/int_h_str.jpg\" ALT=\"Strings of Images\">".
  6005.           "</TH></TR>\n";
  6006.         my @sort = sort {$a cmp $b} @str;
  6007.         int_menu_print (\%md5s, \@sort);
  6008.  
  6009.     }
  6010.  
  6011.     # timeline body files
  6012.     if (scalar @body > 0) {
  6013.         print "<TR><TH COLSPAN=3> </TH></TR>\n".
  6014.           "<TR><TH COLSPAN=3>".
  6015.           "<IMG SRC=\"pict/int_h_data.jpg\" ALT=\"Timeline Data Files\">".
  6016.           "</TH></TR>\n";
  6017.         my @sort = sort {$a cmp $b} @body;
  6018.         int_menu_print (\%md5s, \@sort);
  6019.     }
  6020.  
  6021.     # timeline files
  6022.     if (scalar @tl > 0) {
  6023.         print "<TR><TH COLSPAN=3> </TH></TR>\n".
  6024.           "<TR><TH COLSPAN=3>".
  6025.           "<IMG SRC=\"pict/int_h_tl.jpg\" ALT=\"Timelines\">".
  6026.           "</TH></TR>\n";
  6027.         my @sort = sort {$a cmp $b} @tl;
  6028.         int_menu_print (\%md5s, \@sort);
  6029.     }
  6030.  
  6031.  
  6032. print <<EOF;
  6033. </TABLE>
  6034. <P>
  6035. <TABLE CELLSPACING=20 WIDTH=600 CELLPADDING=2>
  6036. <TR>
  6037.   <TD><A HREF=\"$PROGNAME?$baseargs&func=$IMG_OPEN\" TARGET=\"_top\">
  6038.     <IMG SRC=\"pict/menu_b_ok.jpg\" ALT=\"Ok\" 
  6039.     WIDTH=\"167\" HEIGHT=20 BORDER=\"0\">
  6040.   </A>
  6041.   </TD>
  6042.   <TD><A HREF=\"$PROGNAME?$baseargs&func=$INT_LIST_FR\" TARGET=\"_top\">
  6043.     <IMG SRC=\"pict/menu_b_ref.jpg\" ALT=\"Refresh\" 
  6044.     WIDTH=\"167\" HEIGHT=20 BORDER=\"0\">
  6045.   </A>
  6046.   </TD>
  6047.   <TD ALIGN=CENTER>
  6048.     <A HREF=\"$HELP_URL\" TARGET=\"_blank\">
  6049.     <IMG SRC=\"pict/menu_b_help.jpg\" ALT=\"Help\" 
  6050.     WIDTH=\"167\" HEIGHT=20 BORDER=0>
  6051.   </A>
  6052.   </TD>
  6053. </TR>
  6054. </TABLE>
  6055.  
  6056. EOF
  6057.     return;
  6058. };
  6059.  
  6060.  
  6061. # Pass the relative path (images/xyz) of the file.  The MD5 is
  6062. # returned (or NULL) (in all caps)
  6063. sub lookup_md5 {
  6064.     my $img = shift;
  6065.     my $md5 = "";
  6066.  
  6067.     (my $img_dir) = split (/\//,$img);
  6068.     my $md5_file = "${host_dir}${img_dir}/$MD5_FILE";
  6069.  
  6070.     if (-e "$md5_file") {
  6071.         unless (open (FILE, $md5_file)) { 
  6072.             print "Error opening $md5_file<BR>\n";
  6073.             return "";
  6074.         }
  6075.  
  6076.         while (<FILE>) {
  6077.             s/^\s+//;
  6078.             s/\s+$//;
  6079.  
  6080.             if (/($REG_MD5)\s+(.*)/o) {
  6081.                 my $m = $1;
  6082.                 if ($2 =~ /$img$/) {
  6083.                     $md5 = $m;
  6084.                     $md5 =~ tr/[a-f]/[A-F]/;
  6085.                     last;
  6086.                 }
  6087.             }
  6088.             else {
  6089.                 print "Error reading line $. of $md5_file: $_<BR>\n";
  6090.                 return "";
  6091.             }
  6092.         }
  6093.         close (FILE);
  6094.     }
  6095.  
  6096.     return $md5;
  6097. };
  6098.  
  6099.  
  6100. $funcs[$INT_CHECK] = sub {
  6101.     # we do a check_img because it was skipped in the main function
  6102.     check_img('img');
  6103.     print_html_header("Image Integrity Check");
  6104.  
  6105.     my $md5 = lookup_md5($args{'img'});
  6106.  
  6107.     if ($md5 eq "") {
  6108.         print "The MD5 value of <TT>$args{'img'}</TT> was not found<BR>".
  6109.           "It can be calculated by pressing the button below.".
  6110.           "<BR><BR>\n<FORM ACTION=\"$PROGNAME\" METHOD=\"GET\">\n".
  6111.           "<INPUT TYPE=\"hidden\" NAME=\"func\" VALUE=\"$INT_CREATE\">\n".
  6112.           "<INPUT TYPE=\"hidden\" NAME=\"img\" VALUE=\"$args{'img'}\">\n".
  6113.           make_hidden().
  6114.           "<INPUT TYPE=\"IMAGE\" SRC=\"pict/int_b_calc.jpg\" ".               
  6115.           "ALT=\"Calculate\" BORDER=\"0\">\n</FORM>";
  6116.         return 1;
  6117.     }
  6118.  
  6119.     log_host_inv ("$args{'img'}: Checking image integrity");
  6120.  
  6121.     print "<FONT SIZE=3>Original MD5: <TT>$md5</TT><BR>\n";
  6122.  
  6123.     # We have the original value, now get the new one
  6124.     my $img = get_img('img');
  6125.     my $cur = calc_md5($img);
  6126.  
  6127.     if ($cur =~ /^$REG_MD5$/o) {
  6128.         print "Current MD5: <TT>$cur</TT><BR><BR>\n";
  6129.  
  6130.         if ($cur eq $md5) {
  6131.             print "Pass<BR>\n";
  6132.             log_host_inv ("$args{'img'}: Image integrity check PASSED");
  6133.         } else {
  6134.             print "<FONT COLOR=\"$DEL_COLOR[0]\">Fail: Restore from backup".
  6135.               "</FONT><BR>\n";
  6136.  
  6137.             log_host_inv ("$args{'img'}: Image integrity check FAILED");
  6138.         }
  6139.         return 0;
  6140.     }
  6141.     else {
  6142.         print "$cur<BR>\n";
  6143.         return 1;
  6144.     }
  6145. };
  6146.  
  6147. # Calculate the MD5 value of a file (given the full path)
  6148. # return the value in upper case
  6149. sub calc_md5 {
  6150.     my $img = shift;
  6151.  
  6152.     my $hit_cnt = 0;
  6153.     $SIG{ALRM} = sub {
  6154.         if (($hit_cnt++ % 5) == 0) {
  6155.             print "+";
  6156.         } else {
  6157.             print "-";
  6158.         }
  6159.         alarm(5);
  6160.     };
  6161.  
  6162.     alarm(5);
  6163.     local *OUT;
  6164.     exec_pipe (*OUT, "'${TASKDIR}md5' '$img'");
  6165.     my $out = <OUT>;
  6166.     close (OUT);
  6167.  
  6168.     $SIG{ALRM} = 'DEFAULT';
  6169.     print "\n"
  6170.       if ($hit_cnt > 0);
  6171.  
  6172.     $out = "Error getting MD5" 
  6173.       if ((!defined $out) || ($out eq ""));
  6174.  
  6175.     if ($out =~ /($REG_MD5)\s+$img/) {
  6176.         my $m = $1;
  6177.         $m =~ tr/[a-f]/[A-F]/;
  6178.         return $m;
  6179.     } else {
  6180.         return $out;
  6181.     }
  6182. }
  6183.  
  6184.  
  6185. # Pass it the full path and the short name
  6186. # and it adds it to md5.txt and returns the MD5
  6187. sub int_create_wrap  {
  6188.     my $img = shift;
  6189.     my $name = shift;
  6190.  
  6191.     my $m = calc_md5 ($img);
  6192.     update_md5 ($name, $m) if ($m =~ /^$REG_MD5$/o); 
  6193.     return $m;
  6194. }
  6195.  
  6196. $funcs[$INT_CREATE] = sub {
  6197.     print_html_header("Image Integrity Creation");
  6198.     print "Calculating MD5 value for <TT>$args{'img'}</TT><BR>\n";
  6199.     log_host_inv ("$args{'img'}: Calculating MD5 value");
  6200.  
  6201.     my $img = get_img('img');
  6202.     my $m = int_create_wrap ($img, $args{'img'});
  6203.  
  6204.     print "MD5: <TT>$m</TT><BR>\n";
  6205.     (my $img_dir) = split (/\//,$args{'img'});
  6206.     print "<BR>Value added to <TT>${host_dir}${img_dir}/$MD5_FILE</TT><BR><BR>\n";
  6207. };
  6208.  
  6209.  
  6210. ####################################################################
  6211. # TIME LINE
  6212.  
  6213. my %m2d = ("Jan", 1, "Feb", 2, "Mar", 3, "Apr", 4, "May", 5, "Jun", 6,
  6214.     "Jul", 7, "Aug", 8, "Sep", 9, "Oct", 10, "Nov", 11, "Dec", 12);
  6215. my @d2m = ("", "Jan","Feb","Mar","Apr", "May", "Jun", "Jul", "Aug",
  6216.   "Sep", "Oct", "Nov", "Dec");
  6217.  
  6218. # Call the appropriate function based on the value of sort
  6219. $funcs[$TL_MAIN] = sub {
  6220.     print_html_header_frameset("Timeline: $args{'case'}:$args{'host'}");
  6221.  
  6222.     print "<FRAMESET ROWS=\"38,*\">\n";
  6223.  
  6224.     my $mode = $TL_MAIN;
  6225.     $mode = get_mode() if (exists $args{'mode'});
  6226.  
  6227.     # Listing
  6228.     print "<FRAME SRC=\"$PROGNAME?func=$TL_TABS&$baseargs&mode=$mode\">\n";
  6229.  
  6230.     my $str = "";
  6231.  
  6232.     # Contents
  6233.     if ($mode == $TL_MAIN) {
  6234.         print "<FRAME SRC=\"$PROGNAME?func=$BLANK\" ".
  6235.           "NAME=\"content\">\n</FRAMESET>\n";
  6236.  
  6237.         return;
  6238.     }
  6239.     # elsif ($mode == $TL_BODY_ENT) 
  6240.     elsif ($mode == $TL_TL_ENT) {
  6241.         $str .= "&body=$args{'body'}" if (exists $args{'body'});
  6242.     }
  6243.     elsif ($mode == $TL_VIEW_FR) {
  6244.         $str .= "&tl=$args{'tl'}" if (exists $args{'tl'});
  6245.     }
  6246.     # elsif ($mode == $NOTES_MAIN) 
  6247.  
  6248.     print "<FRAME SRC=\"$PROGNAME?func=$mode&$baseargs$str\" ".
  6249.       "NAME=\"content\">\n</FRAMESET>\n";
  6250.  
  6251.     return 0;
  6252. };
  6253.  
  6254.  
  6255.  
  6256. $funcs[$TL_BODY_ENT] = sub {
  6257.     print_html_header("");
  6258.  
  6259.     my $i;
  6260.     my %mnt2img;
  6261.  
  6262.     # Cycle through each image we read from fsmorgue
  6263.     foreach $i (keys %img2mnt) {
  6264.         next if (($img2ftype{$i} eq "strings") || ($img2ftype{$i} eq "dls") ||
  6265.           ($img2ftype{$i} eq "raw") || ($img2ftype{$i} eq "swap"));
  6266.  
  6267.         $mnt2img{"$img2mnt{$i}--$i"} = $i;
  6268.     }
  6269.  
  6270.     # sort via ftype and then mount point (which includes the name)
  6271.     my @mnt = sort {
  6272.         lc($img2ftype{$mnt2img{$a}}) cmp lc($img2ftype{$mnt2img{$b}}) or
  6273.         lc($a) cmp lc($b)
  6274.     } keys %mnt2img; 
  6275.  
  6276.     print "<FORM ACTION=\"$PROGNAME\" METHOD=\"GET\">\n".
  6277.       "<INPUT TYPE=\"hidden\" NAME=\"func\" VALUE=\"$TL_BODY_DOIT\">\n".
  6278.       make_hidden().
  6279.       "<P>1.  Select one or more of the following images to collect data from:\n".
  6280.       "<TABLE CELLSPACING=\"8\" CELLPADDING=\"2\">";
  6281.  
  6282.     for (my $i = 0; $i <= $#mnt; $i++) {
  6283.         my $img = $mnt2img{$mnt[$i]};
  6284.  
  6285.         print "<TR><TD><INPUT TYPE=\"checkbox\" NAME=\"$img\" VALUE=\"1\">".
  6286.           "</TD><TD><TT>$img2mnt{$img}</TT></TD><TD><TT>$img</TT></TD>".
  6287.           "<TD>$img2ftype{$img}</TD>\n";
  6288.     }
  6289.  
  6290.  
  6291.     print "</TABLE><P>2.  Select the data types to gather:<BR>\n". 
  6292.       "<TABLE CELLSPACING=\"8\" CELLPADDING=\"2\"><TR>".
  6293.       "<TD><INPUT TYPE=\"checkbox\" NAME=\"al_file\" VALUE=\"1\" CHECKED>".
  6294.       "</TD><TD>Allocated Files</TD>".
  6295.       "<TD><INPUT TYPE=\"checkbox\" NAME=\"unal_file\" VALUE=\"1\" CHECKED>".
  6296.       "</TD><TD>Unallocated Files</TD>".
  6297.       "<TD><INPUT TYPE=\"checkbox\" NAME=\"unal_inode\" VALUE=\"1\" CHECKED>".
  6298.       "</TD><TD>Unallocated Meta Data Structures</TD></TR></TABLE>\n".
  6299.       "<P>3.   Enter name of output file (<TT>body</TT>):<BR>".
  6300.       "<TT>$DATADIR/</TT>".
  6301.       "<INPUT TYPE=\"text\" NAME=\"fname\" VALUE=\"body\">\n".
  6302.       "<INPUT TYPE=\"hidden\" NAME=\"fname_mode\" VALUE=\"$FNAME_MODE_INIT\">\n".
  6303.       "<P>4.   Generate MD5 Value? ".
  6304.       "<INPUT TYPE=\"checkbox\" NAME=\"md5\" VALUE=\"1\" CHECKED>";
  6305.  
  6306.     print "<P><INPUT TYPE=\"IMAGE\" SRC=\"pict/but_ok.jpg\" ".
  6307.       "WIDTH=43 HEIGHT=20 ALT=\"Ok\" BORDER=\"0\"></FORM>\n";
  6308. };
  6309.  
  6310. $funcs[$TL_BODY_DOIT] = sub {
  6311.     check_fname(); check_fname_mode();
  6312.     print_html_header("");
  6313.  
  6314.     my $fname_rel = get_fname_rel();
  6315.     my $fname = get_fname();
  6316.  
  6317.     my $mode = $args{'fname_mode'};
  6318.  
  6319.     if ((-e "$fname") && ($FNAME_MODE_INIT == $mode)) {
  6320.         print "File Already Exists: $fname_rel\n";
  6321.   
  6322.         my $hidden = make_hidden();
  6323.  
  6324.         $hidden .= "<INPUT TYPE=\"hidden\" NAME=\"func\" ".
  6325.           "VALUE=\"$TL_BODY_DOIT\">\n";
  6326.  
  6327.         my $i;
  6328.         foreach $i (%img2mnt) {
  6329.               $hidden .= "<INPUT TYPE=\"hidden\" NAME=\"$i\" VALUE=\"1\">\n"
  6330.               if (exists $args{$i});
  6331.         }
  6332.  
  6333.         $hidden .= "<INPUT TYPE=\"hidden\" NAME=\"al_file\" ".
  6334.           "VALUE=\"$args{'al_file'}\">\n" if (exists $args{'al_file'});
  6335.         $hidden .= "<INPUT TYPE=\"hidden\" NAME=\"unal_file\" ".
  6336.           "VALUE=\"$args{'unal_file'}\">\n" if (exists $args{'unal_file'});
  6337.         $hidden .= "<INPUT TYPE=\"hidden\" NAME=\"unal_inode\" ".
  6338.           "VALUE=\"$args{'unal_inode'}\">\n" if (exists $args{'unal_inode'});
  6339.         $hidden .= "<INPUT TYPE=\"hidden\" NAME=\"md5\" ".
  6340.           "VALUE=\"$args{'md5'}\">\n" if (exists $args{'md5'});
  6341.  
  6342.  
  6343.         # Make a new name 
  6344.         print "<FORM ACTION=\"$PROGNAME\" METHOD=\"GET\">\n".
  6345.           "New Name: <INPUT TYPE=\"text\" NAME=\"fname\">".
  6346.           "<TABLE CELLSPACING=\"30\" CELLPADDING=\"2\"><TR><TD>".
  6347.           "<INPUT TYPE=\"hidden\" NAME=\"fname_mode\" VALUE=\"$FNAME_MODE_INIT\"
  6348. >\n".
  6349.           "$hidden".
  6350.           "<INPUT TYPE=\"IMAGE\" SRC=\"pict/but_new_name.jpg\" ".               
  6351.           "WIDTH=79 HEIGHT=20 ALT=\"Use New Name\" BORDER=\"0\">\n".
  6352.           "</FORM></TD>\n";
  6353.  
  6354.  
  6355.  
  6356.         # Overwrite it
  6357.         print "<TD><FORM ACTION=\"$PROGNAME\" METHOD=\"GET\">\n".
  6358.           "<INPUT TYPE=\"IMAGE\" SRC=\"pict/but_replace.jpg\" ".               
  6359.           "WIDTH=66 HEIGHT=20 ALT=\"Replace\" BORDER=\"0\"><BR>\n".
  6360.           "<INPUT TYPE=\"hidden\" NAME=\"fname\" VALUE=\"$args{'fname'}\">\n".
  6361.           "<INPUT TYPE=\"hidden\" NAME=\"fname_mode\" VALUE=\"$FNAME_MODE_OVER\"
  6362. >\n".
  6363.           "$hidden".
  6364.           "</FORM></TD></TR></TABLE>";
  6365.  
  6366.           return 0;
  6367.     }
  6368.  
  6369.     # we will be appending to the file so we should del it now
  6370.     if (-e "$fname") {
  6371.         unlink ($fname);
  6372.     }    
  6373.  
  6374.  
  6375.     my $log_files = "";
  6376.     my $log_type = "";
  6377.  
  6378.     my $al_file = 0;
  6379.     if (exists $args{'al_file'}) {
  6380.         $al_file = $args{'al_file'}; 
  6381.         $log_type .= "Allocated Files";
  6382.     }
  6383.  
  6384.     my $unal_file = 0;
  6385.     if (exists $args{'unal_file'}) {
  6386.         $unal_file = $args{'unal_file'};
  6387.         $log_type .= ", " if ($log_type ne "");
  6388.         $log_type .= "Unallocated Files";
  6389.     }
  6390.  
  6391.     my $unal_inode = 0;
  6392.     if (exists $args{'unal_inode'}) {
  6393.         $unal_inode = $args{'unal_inode'}; 
  6394.         $log_type .= ", " if ($log_type ne "");
  6395.         $log_type .= "Unallocated Meta Data Structures";
  6396.     }
  6397.  
  6398.  
  6399.  
  6400.     if (($unal_inode == 0) && ($unal_file == 0) && ($al_file == 0)) {
  6401.         print "No data types were selected.  You must select at least one.<BR>\n";
  6402.         return 1;
  6403.     }
  6404.  
  6405.  
  6406.     my $i;
  6407.     my $found = 0;
  6408.     local *OUT;
  6409.     foreach $i (keys %img2mnt) {
  6410.         if (exists $args{$i}) {
  6411.  
  6412.             $found = 1;
  6413.             my $ftype = $img2ftype{$i};
  6414.             my $img = $host_dir.$i;
  6415.             my $mnt = $img2mnt{$i};
  6416.         
  6417.             $log_files .= ", " if ($log_files ne "");
  6418.             $log_files .= "$i";
  6419.  
  6420.             if (($al_file) && ($unal_file)) {
  6421.                 print "Running <TT>fls -r -m</TT> on <TT>$i</TT><BR>\n";
  6422.                 exec_pipe (*OUT, 
  6423.                   "'${TASKDIR}fls' -z '$tz' -s $ts -m '$mnt' -f $ftype -r '$img' >> '$fname'");
  6424.                 print "$_<BR>\n" while (<OUT>);
  6425.                 close (OUT);
  6426.             }
  6427.             elsif ($al_file) {
  6428.                 print "Running <TT>fls -ru -m</TT> on <TT>$i</TT><BR>\n";
  6429.                 exec_pipe (*OUT, 
  6430.                   "'${TASKDIR}fls' -z '$tz' -s $ts -m '$mnt' -f $ftype -ru '$img' >> '$fname'");
  6431.                 print "$_<BR>\n" while (<OUT>);
  6432.                 close (OUT);
  6433.             }
  6434.             elsif ($unal_file) {
  6435.                 print "Running <TT>fls -rd -m</TT> on <TT>$i</TT><BR>\n";
  6436.                 exec_pipe (*OUT,
  6437.                   "'${TASKDIR}fls' -z '$tz' -s $ts -m '$mnt' -f $ftype -rd '$img' >> '$fname'");
  6438.                 print "$_<BR>\n" while (<OUT>);
  6439.                 close (OUT);
  6440.             }
  6441.  
  6442.              if ($unal_inode) {
  6443.                 print "Running <TT>ils -m</TT> on <TT>$i</TT><BR>\n";
  6444.                 my $tz_back = "";
  6445.                 $tz_back = $ENV{TZ} if (exists $ENV{TZ});
  6446.  
  6447.                 $ENV{TZ} = $tz;
  6448.                 POSIX::tzset();
  6449.  
  6450.                 exec_pipe (*OUT, 
  6451.                   "'${TASKDIR}ils' -s $ts -m -f $ftype '$img' >> '$fname'");
  6452.                 print "$_<BR>\n" while (<OUT>);
  6453.                 close (OUT);
  6454.                 $ENV{TZ} = $tz_back;
  6455.                 POSIX::tzset();
  6456.             }
  6457.         }
  6458.     }
  6459.  
  6460.     unless ($found) {
  6461.         print "No images were given for analysis.  At least one must be selected.<BR>\n";
  6462.         return 1;
  6463.     }
  6464.  
  6465.     
  6466.     log_host_inv ("Saving timeline data for $log_type for $log_files to $fname_rel");
  6467.  
  6468.     # append to  host config
  6469.     update_host_config ("body", $fname_rel);
  6470.  
  6471.     print "<BR>Body file saved to <TT>$fname</TT><BR><BR>\n".
  6472.       "Entry added to host config file<BR><BR>\n";
  6473.  
  6474.     # Calculate MD5
  6475.     if ((exists $args{'md5'}) && ($args{'md5'} == 1)) {
  6476.         print "Calculating MD5 Value<BR><BR>\n";
  6477.         my $m = int_create_wrap ($fname, $fname_rel);
  6478.         print "MD5 Value: <TT>$m</TT><BR><BR>\n";
  6479.     }
  6480.  
  6481.     print "<FORM ACTION=\"$PROGNAME\" METHOD=\"GET\" TARGET=\"_top\">\n".
  6482.       "<INPUT TYPE=\"hidden\" NAME=\"body\" VALUE=\"$args{'fname'}\">\n".
  6483.       "<INPUT TYPE=\"hidden\" NAME=\"func\" VALUE=\"$TL_MAIN\">\n".
  6484.       "<INPUT TYPE=\"hidden\" NAME=\"mode\" VALUE=\"$TL_TL_ENT\">\n".
  6485.       make_hidden().
  6486.       "<INPUT TYPE=\"IMAGE\" SRC=\"pict/but_ok.jpg\" ".
  6487.       "WIDTH=43 HEIGHT=20 ALT=\"Ok\" BORDER=\"0\">\n</FORM>\n";
  6488.  
  6489.     return 0;
  6490. };
  6491.  
  6492. $funcs[$TL_TL_ENT] = sub {
  6493.     print_html_header("");
  6494.     
  6495.     my @body;
  6496.     # Find the body files if we will be looking for them
  6497.     unless (exists $args{'body'}) {
  6498.         foreach my $k (keys %img2ftype) {
  6499.             if ($img2ftype{$k} eq "body") {
  6500.                 push @body, $k;
  6501.             }
  6502.         }
  6503.  
  6504.         if (scalar(@body) == 0) {
  6505.             print "There are currently no <TT>body</TT> files ".
  6506.               "for this host.<BR>You must create the intermediate ".
  6507.               "data file before you can perform this step<BR>\n".
  6508.               "<P><A TARGET=\"_top\"  ".
  6509.               "HREF=\"$PROGNAME?$baseargs&func=$TL_MAIN&mode=$TL_BODY_ENT\">".
  6510.               "<IMG SRC=\"pict/but_ok.jpg\" ALT=\"Ok\" ".
  6511.               "WIDTH=\"43\" HEIGHT=20 BORDER=\"0\">".
  6512.               "</A>\n";
  6513.             return 1;
  6514.         }
  6515.     }
  6516.     print "<FORM ACTION=\"$PROGNAME\" METHOD=\"GET\">\n".
  6517.       "<INPUT TYPE=\"hidden\" NAME=\"func\" VALUE=\"$TL_TL_DOIT\">\n".
  6518.       make_hidden().
  6519.       "1.  Select the data input file (<TT>body</TT>):\n".
  6520.       "<TABLE CELLSPACING=\"0\" CELLPADDING=\"2\">";
  6521.  
  6522.     # if the body file was specified then just print it
  6523.     if (exists $args{'body'}) {
  6524.         print "<TR><TD><INPUT TYPE=\"radio\" NAME=\"body\" ".
  6525.           "VALUE=\"$args{'body'}\" CHECKED>".
  6526.           "</TD><TD>$args{'body'}</TD>\n";
  6527.     }
  6528.     else {
  6529.         my @body_sort = sort {lc($a) cmp lc($b)} @body;
  6530.         for (my $i = 0; $i <= $#body_sort; $i++) {
  6531.             (my $img_dir, my $str_img) = split (/\//,$body_sort[$i]);
  6532.  
  6533.             print "<TR><TD><INPUT TYPE=\"radio\" NAME=\"body\" ".
  6534.               "VALUE=\"$str_img\"></TD><TD>$str_img</TD>\n";
  6535.         }
  6536.     }
  6537.  
  6538.     my $cur_mon = 1 + (localtime())[4];
  6539.     my $cur_year = 1900 + (localtime())[5];
  6540.  
  6541.     # STARTING DATE
  6542.     print "</TABLE>\n".
  6543.       "<P>2.  Enter the starting date:<BR>\n".
  6544.       "None: <INPUT TYPE=\"radio\" NAME=\"st_none\" VALUE=\"1\" CHECKED><BR>".
  6545.       "Specify: <INPUT TYPE=\"radio\" NAME=\"st_none\" VALUE=\"0\">  ".
  6546.       "<SELECT NAME=\"st_mon\" SIZE=\"1\">";
  6547.  
  6548.     for my $i (1 .. 12) {
  6549.         if ($i == $cur_mon) {
  6550.             print "<OPTION SELECTED VALUE=\"$i\">$d2m[$i]</OPTION>\n";
  6551.         } else {
  6552.             print "<OPTION VALUE=\"$i\">$d2m[$i]</OPTION>\n";
  6553.         }
  6554.     }
  6555.  
  6556.     print "</SELECT>".
  6557.       "<SELECT NAME=\"st_day\" SIZE=\"1\">".
  6558.       "<OPTION SELECTED>1</OPTION>\n";
  6559.  
  6560.     for my $i (2 .. 31) {
  6561.         print "<OPTION VALUE=\"$i\">$i</OPTION>\n";
  6562.     }
  6563.  
  6564.  
  6565.     print "</SELECT>".
  6566.       "<INPUT TYPE=\"text\" NAME=\"st_year\" SIZE=\"6\" VALUE=\"$cur_year\">\n";
  6567.  
  6568.  
  6569.     # END DATE
  6570.     print "<P>3.   Enter the ending date:<BR>\n".
  6571.       "None: <INPUT TYPE=\"radio\" NAME=\"end_none\" VALUE=\"1\" CHECKED><BR>\n".
  6572.       "Specify: <INPUT TYPE=\"radio\" NAME=\"end_none\" VALUE=\"0\">  \n".
  6573.       "<SELECT NAME=\"end_mon\" SIZE=\"1\">\n";
  6574.  
  6575.     for my $i (1 .. 12) {
  6576.         if ($i == $cur_mon) {
  6577.             print "<OPTION SELECTED VALUE=\"$i\">$d2m[$i]</OPTION>\n";
  6578.         } else {
  6579.             print "<OPTION VALUE=\"$i\">$d2m[$i]</OPTION>\n";
  6580.         }
  6581.     }
  6582.  
  6583.     print "</SELECT>\n".
  6584.       "<SELECT NAME=\"end_day\" SIZE=\"1\">\n".
  6585.       "<OPTION SELECTED VALUE=\"1\">1</OPTION>\n";
  6586.  
  6587.     for my $i (2 .. 31) {
  6588.         print "<OPTION VALUE=\"$i\">$i</OPTION>\n";
  6589.     }
  6590.  
  6591.     print "</SELECT>".
  6592.       "<INPUT TYPE=\"text\" NAME=\"end_year\" SIZE=\"6\" VALUE=\"$cur_year\">\n";
  6593.  
  6594.  
  6595.     # FILE NAME
  6596.     print "<P>4.   Enter the file name to save as:<BR>".
  6597.       "<TT>$DATADIR/</TT><INPUT TYPE=\"text\" SIZE=36 NAME=\"fname\"><BR>\n".
  6598.       "<INPUT TYPE=\"hidden\" NAME=\"fname_mode\" VALUE=\"$FNAME_MODE_INIT\">\n";
  6599.  
  6600.  
  6601.     # Get only the UNIX images - since only they have /etc/passwd and group
  6602.     my @unix_imgs;
  6603.     my $root_img = "";
  6604.     foreach my $i (keys %img2ftype) {
  6605.         my $f = $img2ftype{$i};
  6606.  
  6607.         next unless (($f =~ /^linux/) || ($f =~ /bsd$/) ||
  6608.           ($f =~ /^solaris$/) || ($f =~ /^bsdi$/)) ;
  6609.  
  6610.         push @unix_imgs, $i;
  6611.  
  6612.         # Keep a reference to an image with '/' as the mounting point
  6613.         $root_img = $i 
  6614.           if ($img2mnt{$i} eq '/');
  6615.     }
  6616.  
  6617.     if (scalar @unix_imgs > 0) {
  6618.  
  6619.         print "<P>5.  Select the UNIX image that contains the /etc/passwd and /etc/group files:<BR>\n";
  6620.  
  6621.         print "<SELECT NAME=\"pw_img\">\n";
  6622.  
  6623.         # If we did not find an image that has a / mounting point, then
  6624.         # we will use none as the default.  
  6625.         if ($root_img eq "") {    
  6626.             print "<OPTION VALUE=\"\" SELECTED>None</OPTION>\n";
  6627.         } else {
  6628.             print "<OPTION VALUE=\"\">None</OPTION>\n";
  6629.         }
  6630.  
  6631.         foreach my $img (@unix_imgs) {
  6632.             if ($root_img eq $img) {    
  6633.                 print 
  6634.                   "<OPTION VALUE=\"$img\" SELECTED>$img ($img2mnt{$img})".
  6635.                   "</OPTION>\n";
  6636.             } else {
  6637.                 print 
  6638.                   "<OPTION VALUE=\"$img\">$img ($img2mnt{$img})</OPTION>\n";
  6639.             }
  6640.         }
  6641.  
  6642.         print "</SELECT>\n";
  6643.         print "<P>6.  Generate MD5 Value? ";
  6644.     }
  6645.     else {
  6646.         print "<P>5.  Generate MD5 Value? ";
  6647.     }
  6648.  
  6649.     print "<INPUT TYPE=\"checkbox\" NAME=\"md5\" VALUE=\"1\" CHECKED>\n";
  6650.  
  6651.     # Create Button
  6652.     print "<P><INPUT TYPE=\"IMAGE\" SRC=\"pict/but_ok.jpg\" ".
  6653.       "WIDTH=43 HEIGHT=20 ALT=\"Ok\" BORDER=\"0\">\n</FORM>\n";
  6654.  
  6655.     return 0;
  6656. };
  6657.  
  6658.  
  6659. $funcs[$TL_TL_DOIT] = sub {
  6660.     check_fname(); check_body(); 
  6661.  
  6662.     print_html_header("");
  6663.  
  6664.     my $body = get_body();
  6665.  
  6666.     my $fname = get_fname();
  6667.     my $fname_rel = get_fname_rel();
  6668.  
  6669.     my $mode = $args{'fname_mode'};
  6670.                 
  6671.     if ((-e "$fname") && ($FNAME_MODE_INIT == $mode)) {
  6672.         print "File Already Exists: <TT>$fname_rel</TT><BR>\n";
  6673.  
  6674.         my $hidden = "<INPUT TYPE=\"hidden\" NAME=\"body\" VALUE=\"$args{'body'}\">".
  6675.         make_hidden();
  6676.  
  6677.         $hidden .= "<INPUT TYPE=\"hidden\" NAME=\"st_none\" ".
  6678.           "VALUE=\"$args{'st_none'}\">\n" if (exists $args{'st_none'});
  6679.         $hidden .= "<INPUT TYPE=\"hidden\" NAME=\"st_year\" ".
  6680.           "VALUE=\"$args{'st_year'}\">\n" if (exists $args{'st_year'});
  6681.         $hidden .= "<INPUT TYPE=\"hidden\" NAME=\"st_day\" ".
  6682.           "VALUE=\"$args{'st_day'}\">\n" if (exists $args{'st_day'});
  6683.         $hidden .= "<INPUT TYPE=\"hidden\" NAME=\"st_mon\" ".
  6684.           "VALUE=\"$args{'st_mon'}\">\n" if (exists $args{'st_mon'});
  6685.         $hidden .= "<INPUT TYPE=\"hidden\" NAME=\"end_none\" ".
  6686.           "VALUE=\"$args{'end_none'}\">\n" if (exists $args{'end_none'});
  6687.         $hidden .= "<INPUT TYPE=\"hidden\" NAME=\"end_year\" ".
  6688.           "VALUE=\"$args{'end_year'}\">\n" if (exists $args{'end_year'});
  6689.         $hidden .= "<INPUT TYPE=\"hidden\" NAME=\"end_day\" ".
  6690.           "VALUE=\"$args{'end_day'}\">\n" if (exists $args{'end_day'});
  6691.         $hidden .= "<INPUT TYPE=\"hidden\" NAME=\"end_mon\" ".
  6692.           "VALUE=\"$args{'end_mon'}\">\n" if (exists $args{'end_mon'});
  6693.         $hidden .= "<INPUT TYPE=\"hidden\" NAME=\"tz\" ".
  6694.           "VALUE=\"$args{'tz'}\">\n" if (exists $args{'tz'});
  6695.         $hidden .= "<INPUT TYPE=\"hidden\" NAME=\"pw_img\" ".
  6696.           "VALUE=\"$args{'pw_img'}\">\n" if (exists $args{'pw_img'});
  6697.         $hidden .= "<INPUT TYPE=\"hidden\" NAME=\"md5\" ".
  6698.           "VALUE=\"$args{'md5'}\">\n" if (exists $args{'md5'});
  6699.    
  6700.         # Make a new name 
  6701.         print "<FORM ACTION=\"$PROGNAME\" METHOD=\"GET\">\n".
  6702.           "New Name: <INPUT TYPE=\"text\" NAME=\"fname\">".
  6703.           "<TABLE CELLSPACING=\"30\" CELLPADDING=\"2\"><TR><TD>".
  6704.           "<INPUT TYPE=\"hidden\" NAME=\"func\" VALUE=\"$TL_TL_DOIT\">\n".
  6705.           "<INPUT TYPE=\"hidden\" NAME=\"fname_mode\" VALUE=\"$FNAME_MODE_INIT\">\n".
  6706.           "$hidden\n".
  6707.           "<INPUT TYPE=\"IMAGE\" SRC=\"pict/but_new_name.jpg\" ".               
  6708.           "WIDTH=79 HEIGHT=20 ALT=\"Use New Name\" BORDER=\"0\">\n".
  6709.           "</FORM></TD>\n";
  6710.  
  6711.  
  6712.  
  6713.         # Overwrite it
  6714.         print "<TD><FORM ACTION=\"$PROGNAME\" METHOD=\"GET\">\n".
  6715.           "<INPUT TYPE=\"IMAGE\" SRC=\"pict/but_replace.jpg\" ".               
  6716.           "WIDTH=66 HEIGHT=20 ALT=\"Replace\" BORDER=\"0\"><BR>\n".
  6717.           "<INPUT TYPE=\"hidden\" NAME=\"func\" VALUE=\"$TL_TL_DOIT\">\n".
  6718.           "<INPUT TYPE=\"hidden\" NAME=\"fname\" VALUE=\"$args{'fname'}\">\n".
  6719.           "<INPUT TYPE=\"hidden\" NAME=\"fname_mode\" VALUE=\"$FNAME_MODE_OVER\"
  6720. >\n".
  6721.           "$hidden\n".
  6722.           "</FORM></TD></TR></TABLE>";
  6723.  
  6724.         return 0;
  6725.     }
  6726.  
  6727.     my $mon;
  6728.     my $day;
  6729.     my $year;
  6730.  
  6731.     my $date = "";
  6732.  
  6733.     # Get the start date
  6734.     unless ((exists $args{'st_none'}) && ($args{'st_none'} == 1)) {
  6735.  
  6736.         if (exists $args{'st_mon'}) {
  6737.             check_st_mon();
  6738.             $mon = get_st_mon();
  6739.         }
  6740.         if (exists $args{'st_year'}) {
  6741.             check_st_year();
  6742.             $year = get_st_year();
  6743.         }
  6744.         if ((exists $args{'st_day'}) && ($args{'st_day'} =~ /^(\d\d?)$/)) {
  6745.             $day = $1;
  6746.             if (($day < 1) || ($day > 31)) {
  6747.                 print ("Invalid start day\n");
  6748.                 return 1;
  6749.             }
  6750.         } else {
  6751.             print ("Invalid start day\n");
  6752.             return 1;
  6753.         }
  6754.  
  6755.         $date = "$mon/$day/$year";
  6756.     }
  6757.  
  6758.     unless ((exists $args{'end_none'}) && ($args{'end_none'} == 1)) {
  6759.         
  6760.         if ($date eq "") {
  6761.             print "Begin date must be given if ending date is given<BR>";
  6762.             return 1;
  6763.         }
  6764.  
  6765.         if ((exists $args{'end_mon'}) && ($args{'end_mon'} =~ /^(\d\d?)$/)) {
  6766.             $mon = $1;
  6767.             if (($mon < 1) || ($mon > 12)) {
  6768.                 print ("Invalid end month\n");
  6769.                 return 1;
  6770.             }
  6771.         } else {
  6772.             print ("Invalid end month\n");
  6773.             return 1;
  6774.         }
  6775.         if ((exists $args{'end_year'}) && ($args{'end_year'} =~ /^(\d\d\d\d)$/)) {
  6776.             $year = $1;
  6777.             if (($year < 1970) || ($year > 2020)) {
  6778.                 print ("Invalid ending year\n");
  6779.                 return 1;
  6780.             }
  6781.  
  6782.         } else {
  6783.             print ("Invalid end year\n");
  6784.             return 1;
  6785.         }
  6786.         if ((exists $args{'end_day'}) && ($args{'end_day'} =~ /^(\d\d?)$/)) {
  6787.             $day = $1;
  6788.             if (($day < 1) || ($day > 31)) {
  6789.                 print ("Invalid end day\n");
  6790.                 return 1;
  6791.             }
  6792.         } else {
  6793.             print ("Invalid end day\n");
  6794.             return 1;
  6795.         }
  6796.  
  6797.         $date .= "-$mon/$day/$year";
  6798.     }
  6799.  
  6800.  
  6801.     # temp strings for the password and group files
  6802.     my $pw_tmp = "";
  6803.     my $gr_tmp = "";
  6804.     my $mac_args = "";
  6805.     my $log = "";
  6806.  
  6807.     local *OUT;
  6808.  
  6809.     # Password and Group Files
  6810.     if ((exists $args{'pw_img'}) && ($args{'pw_img'} ne "")) {
  6811.         check_img('pw_img');
  6812.         my $pw_img = get_img('pw_img');
  6813.  
  6814.         my $ftype = $img2ftype {$args{'pw_img'}};
  6815.  
  6816.         $log .= "Password & Group File ($pw_img) ";
  6817.  
  6818.         # Get the passwd file inode and copy the file
  6819.         exec_pipe (*OUT, 
  6820.           "'${TASKDIR}ifind' -f $ftype -n 'etc/passwd' '$pw_img'");
  6821.         my $pwi = <OUT>;
  6822.         close (OUT);
  6823.  
  6824.         $pwi = "Error getting inode for passwd" 
  6825.           if ((!defined $pwi) || ($pwi eq ""));
  6826.  
  6827.         # Do the Taint Checking
  6828.         if ($pwi =~ /^($REG_INODE)$/) {
  6829.             $pwi = $1; 
  6830.  
  6831.             $log .= "Password Inode ($pwi) ";
  6832.             # Find a temp name that we can call it
  6833.             my $i;
  6834.             for ($i = 0; ; $i++) {
  6835.                 unless (-e "$fname.pw-$i") {
  6836.                     $pw_tmp = "$fname.pw-$i";                
  6837.                     last;
  6838.                 }
  6839.             }
  6840.  
  6841.             exec_sys("'${TASKDIR}icat' -f $ftype '$pw_img' $pwi > '$pw_tmp'");
  6842.             $mac_args .= " -p \'$pw_tmp\' ";
  6843.  
  6844.         } else {
  6845.             print ("Error finding /etc/passwd inode in $pw_img ($pwi)<BR>");
  6846.             log_host_inv ("$pw_img: /etc/passwd file not found for timeline");
  6847.         }
  6848.  
  6849.         # Get the group file inode and copy the file
  6850.         exec_pipe (*OUT, 
  6851.           "'${TASKDIR}ifind' -f $ftype -n 'etc/group' '$pw_img'");
  6852.         my $gri = <OUT>;
  6853.         close (OUT);
  6854.  
  6855.         $gri = "Error getting inode for group" 
  6856.           if ((!defined $gri) || ($gri eq ""));
  6857.  
  6858.         # Do the Taint Checking
  6859.         if ($gri =~ /^($REG_INODE)$/) {
  6860.             $gri = $1; 
  6861.  
  6862.             $log .= "Group Inode ($gri) ";
  6863.  
  6864.             # Find a temp name that we can call it
  6865.             my $i;
  6866.             for ($i = 0; ; $i++) {
  6867.                 unless (-e "$fname.gr-$i") {
  6868.                     $gr_tmp = "$fname.gr-$i";                
  6869.                     last;
  6870.                 }
  6871.             }
  6872.             exec_sys("'${TASKDIR}icat' -f $ftype '$pw_img' $gri > '$gr_tmp'");
  6873.             $mac_args .= " -g \'$gr_tmp\' ";
  6874.         } else {
  6875.             print ("Error finding /etc/group inode in $pw_img ($gri)<BR>");
  6876.             log_host_inv ("$pw_img: /etc/group file not found for timeline");
  6877.         }
  6878.     }
  6879.  
  6880.     if ($date eq "") {
  6881.         print "Creating Timeline using all dates (Time Zone: $tz)<BR>\n";
  6882.         log_host_inv ("$args{'body'}: Creating timeline using all dates (TZ: $tz) ${log}to $fname_rel");
  6883.     } else {
  6884.         print "Creating Timeline for $date (Time Zone: $tz)<BR>\n";
  6885.         log_host_inv ("$args{'body'}: Creating timeline for $date (TZ: $tz) ${log}to $fname_rel");
  6886.     }
  6887.  
  6888.     # mactime needs the path to run the 'date' command
  6889.     $ENV{PATH} = "/bin:/usr/bin";
  6890.     local *OUT;
  6891.     exec_pipe (*OUT,
  6892.       "LANG=C LC_ALL=C '${TASKDIR}mactime' -b '$body' -z '$tz' -i day '${fname}.sum' $mac_args $date > '$fname'");
  6893.     print "$_<BR>\n" while (<OUT>);
  6894.     close (OUT);
  6895.     $ENV{PATH} = "";
  6896.  
  6897.  
  6898.     # Remove the password and group files
  6899.     unlink ("$pw_tmp") if ($pw_tmp ne "");
  6900.     unlink ("$gr_tmp") if ($gr_tmp ne "");
  6901.  
  6902.     print "<BR>Timeline saved to <TT>$fname</TT><BR><BR>\n";
  6903.  
  6904.     # append to fsmorgue 
  6905.     update_host_config ("timeline", $fname_rel);
  6906.     print "Entry added to host config file<BR><BR>\n";
  6907.  
  6908.  
  6909.     # Calculate MD5
  6910.     if ((exists $args{'md5'}) && ($args{'md5'} == 1)) {
  6911.         print "Calculating MD5 Value<BR><BR>\n";
  6912.         my $m = int_create_wrap ($fname, $fname_rel);
  6913.         print "MD5 Value: <TT>$m</TT><BR><BR>\n";
  6914.     }
  6915.  
  6916.     print "<FORM ACTION=\"$PROGNAME\" METHOD=\"GET\" TARGET=\"_top\">\n".
  6917.       "<INPUT TYPE=\"hidden\" NAME=\"tl\" VALUE=\"$args{'fname'}\">\n".
  6918.       "<INPUT TYPE=\"hidden\" NAME=\"func\" VALUE=\"$TL_MAIN\">\n".
  6919.       "<INPUT TYPE=\"hidden\" NAME=\"mode\" VALUE=\"$TL_VIEW_FR\">\n".
  6920.       make_hidden().
  6921.       "<INPUT TYPE=\"IMAGE\" SRC=\"pict/but_ok.jpg\" ".
  6922.       "WIDTH=43 HEIGHT=20 ALT=\"Ok\" BORDER=\"0\">\n</FORM>\n".
  6923.       "(NOTE: It is easier to view the timeline in a text editor than here)";
  6924.  
  6925.     return 0;
  6926. };
  6927.  
  6928. $funcs[$TL_VIEW_MENU] = sub {
  6929.     print_html_header("");
  6930.  
  6931.     my @tl;
  6932.     # Find the timelines in the images hash
  6933.     foreach my $k (keys %img2ftype) {
  6934.         if ($img2ftype{$k} eq "timeline") {
  6935.             push @tl, $k;
  6936.         }
  6937.     }
  6938.  
  6939.  
  6940.     if (scalar(@tl) == 0) {
  6941.         print "There are currently no timeline files in the ".
  6942.         "host config file.<BR>One must first be created before you ".
  6943.         "can view it<BR>\n";
  6944.  
  6945.         print "<P><A TARGET=\"_top\"  ".
  6946.           "HREF=\"$PROGNAME?$baseargs&func=$TL_MAIN&mode=$TL_TL_ENT\">".
  6947.           "<IMG SRC=\"pict/but_ok.jpg\" ALT=\"Ok\" ".
  6948.           "WIDTH=\"43\" HEIGHT=20 BORDER=\"0\">".
  6949.           "</A>\n";
  6950.  
  6951.         return 1;
  6952.     }
  6953.  
  6954.     print "<FORM ACTION=\"$PROGNAME\" METHOD=\"GET\">\n".
  6955.       "<INPUT TYPE=\"hidden\" NAME=\"func\" VALUE=\"$TL_VIEW_FR\">\n".
  6956.       make_hidden().
  6957.       "1.  Select the timeline file:\n".
  6958.       "<TABLE CELLSPACING=\"0\" CELLPADDING=\"2\">\n";
  6959.  
  6960.     my @tl_sort = sort {lc($a) cmp lc($b)} @tl;
  6961.     for (my $i = 0; $i <= $#tl_sort; $i++) {
  6962.         (my $img_dir, my $str_img) = split (/\//,$tl_sort[$i]);
  6963.  
  6964.         print "<TR><TD><INPUT TYPE=\"radio\" NAME=\"tl\" ".
  6965.           "VALUE=\"$str_img\"></TD><TD>$str_img</TD>\n";
  6966.     }
  6967.  
  6968.  
  6969.     print "</TABLE>\n".
  6970.       "<INPUT TYPE=\"IMAGE\" SRC=\"pict/but_ok.jpg\" ".
  6971.       "WIDTH=43 HEIGHT=20 ALT=\"Ok\" BORDER=\"0\">\n</FORM>\n";
  6972.     
  6973.     return 0;
  6974. };
  6975.  
  6976.  
  6977. $funcs[$TL_VIEW_FR] = sub {
  6978.     check_tl();
  6979.  
  6980.     print_html_header_frameset("");
  6981.     my $tl = get_tl();
  6982.     my $url = "";
  6983.  
  6984.     unless (exists $args{'st_mon'}) {
  6985.         # get the start point (this design is not efficient at ALL)
  6986.         if (-z "$tl") {
  6987.             print("Timeline has no entries");
  6988.             return (1);
  6989.         }
  6990.  
  6991.         unless (open (TL, "$tl")) {
  6992.             print("Error opening $tl");
  6993.             return (1);
  6994.         }
  6995.  
  6996.         my $beg_mon;
  6997.         my $beg_year;
  6998.         while (<TL>) {
  6999.             if (/^(?:\w\w\w )?(\w\w\w)\s+\d\d\s+(\d\d\d\d)\s+\d\d:\d\d:\d\d/) {
  7000.                 $url = "tl=$enc_args{'tl'}&st_mon=$m2d{$1}&st_year=$2";
  7001.             }
  7002.             last;
  7003.         }
  7004.         close (TL);
  7005.  
  7006.         if ($url eq "") {
  7007.             print "Invalid Timeline<BR>\n";
  7008.             return 1;
  7009.         }
  7010.     }
  7011.     else {
  7012.         $url = "tl=$enc_args{'tl'}&st_mon=$enc_args{'st_mon'}&".
  7013.             "st_year=$enc_args{'st_year'}";
  7014.     }
  7015.  
  7016.     print "<FRAMESET ROWS=\"65,*\">\n".
  7017.       "<FRAME SRC=\"$PROGNAME?$baseargs&func=$TL_VIEW_IDX&$url\">\n".
  7018.       "<FRAME SRC=\"$PROGNAME?$baseargs&func=$TL_VIEW&$url\">\n</FRAMESET>";
  7019.  
  7020.     return 0;
  7021. };
  7022.  
  7023. $funcs[$TL_VIEW_IDX] = sub {
  7024.     check_st_mon(); check_st_year();check_tl();
  7025.  
  7026.     print_html_header("");
  7027.  
  7028.     my $mon = get_st_mon();
  7029.     my $year = get_st_year();
  7030.     my $tl = get_tl();
  7031.  
  7032.     print "<CENTER><FONT SIZE=3>";
  7033.     my $url = "$PROGNAME?$baseargs&func=$TL_VIEW_FR&tl=$enc_args{'tl'}";
  7034.  
  7035.     # Next and Previous pointers
  7036.     my $pyear = $year;
  7037.     my $pmon = $mon - 1;
  7038.     if ($pmon == 0) {
  7039.         $pmon = 12;
  7040.         $pyear--;
  7041.     }
  7042.     print "<TABLE CELLSPACING=\"0\" CELLPADDING=\"2\">\n".
  7043.       "<TR><TD ALIGN=\"CENTER\">".
  7044.       "<A HREF=\"$url&st_mon=$pmon&st_year=$pyear\" TARGET=\"_parent\">".
  7045.       "<- $d2m[$pmon] $pyear</A></TD>\n".
  7046.       "<TD> </TD>\n";
  7047.  
  7048.     if (-e "${tl}.sum") {
  7049.         print "<TD><A HREF=\"$PROGNAME?$baseargs&func=$TL_VIEW_SUM&".
  7050.           "tl=$enc_args{'tl'}\" TARGET=\"_parent\">".
  7051.           "Summary</TD>\n".
  7052.           "<TD> </TD>\n";
  7053.     }
  7054.  
  7055.     my $nyear = $year;
  7056.     my $nmon = $mon + 1;
  7057.     if ($nmon == 13) {
  7058.         $nmon = 1;
  7059.         $nyear++;
  7060.     }
  7061.  
  7062.     print "<TD ALIGN=\"CENTER\">".
  7063.       "<A HREF=\"$url&st_mon=$nmon&st_year=$nyear\" TARGET=\"_parent\">".
  7064.       "$d2m[$nmon] $nyear -></A></TD></TR></TABLE>\n";
  7065.  
  7066.     # Make a form to enter the next month and year to show.  
  7067.     # it defaults to the current location
  7068.     print "<FORM ACTION=\"$PROGNAME\" METHOD=\"GET\" TARGET=\"_parent\">\n".
  7069.       "<INPUT TYPE=\"hidden\" NAME=\"func\" VALUE=\"$TL_VIEW_FR\">\n".
  7070.       "<INPUT TYPE=\"hidden\" NAME=\"tl\" VALUE=\"$enc_args{'tl'}\">\n".
  7071.       make_hidden().
  7072.  
  7073.       "<TABLE CELLSPACING=\"0\" CELLPADDING=\"2\">\n".
  7074.       "<TR><TD ALIGN=\"CENTER\"><SELECT NAME=\"st_mon\" SIZE=\"1\">\n";
  7075.  
  7076.     for my $i (1 .. 12) {
  7077.         if ($i == $mon) {
  7078.             print "<OPTION SELECTED VALUE=\"$i\">$d2m[$i]</OPTION>\n";
  7079.         } else {
  7080.             print "<OPTION VALUE=\"$i\">$d2m[$i]</OPTION>\n"; 
  7081.         }
  7082.     }
  7083.  
  7084.     print "</SELECT></TD>".
  7085.       "<TD ALIGN=\"CENTER\">".
  7086.       "<INPUT TYPE=\"text\" NAME=\"st_year\" SIZE=\"6\" VALUE=\"$year\">".
  7087.       "</TD>".
  7088.       "<TD ALIGN=\"CENTER\">".
  7089.       "<INPUT TYPE=\"IMAGE\" SRC=\"pict/but_ok.jpg\" ALT=\"Ok\" ".
  7090.       "WIDTH=43 HEIGHT=20 BORDER=\"0\"></TD>\n".
  7091.       "</TR></TABLE></FORM>\n";
  7092.  
  7093.     return 0;
  7094. };
  7095.  
  7096.  
  7097. # Display the contents of the summary file (hits per day) and show
  7098. # it as hits per month
  7099. $funcs[$TL_VIEW_SUM] = sub {
  7100.     check_tl();
  7101.  
  7102.     print_html_header("");
  7103.     
  7104.     my $tl = get_tl();
  7105.  
  7106.     $tl .= ".sum";
  7107.  
  7108.     unless (-e "$tl") {
  7109.         print_err ("Summary of timeline file not found (<TT>$tl</TT>)<BR>The timeline must be created with The Sleuth Kit version 1.61 or greater to have a summary\n");
  7110.     }
  7111.  
  7112.     open (TL, "<$tl") or die "Can not open $tl";
  7113.     my $url = "$PROGNAME?$baseargs&func=$TL_VIEW_FR&tl=$enc_args{'tl'}";
  7114.  
  7115.     print "<P>This page provides a monthly summary of activity.".
  7116.       "Each day that has activity is noted with the number of events<BR>\n";
  7117.  
  7118.     my $p_year = "";
  7119.     my $p_mon = "";
  7120.  
  7121.     print "<P><TABLE CELLSPACING=2 BORDER=0>\n";
  7122.  
  7123.     while (<TL>) {
  7124.         my @a = split(/ /, $_);
  7125.         next unless (scalar (@a) == 5);
  7126.         my $mon = $m2d{$a[1]};
  7127.         my $year = $a[3];
  7128.         $year = $1 if ($year =~ /^(\d{4,4}):$/);
  7129.  
  7130.         if (($p_year ne $year) || ($p_mon ne $mon)) {
  7131.             print "<TR><TD COLSPAN=6 ALIGN=LEFT>".
  7132.               "<A HREF=\"$url&st_mon=$mon&st_year=$year\">".
  7133.                 "$a[1] $year</A></TD></TR>\n";
  7134.  
  7135.             $p_year = $year;
  7136.             $p_mon = $mon;
  7137.         }
  7138.         print "<TR><TD>  </TD><TD>$a[0]</TD>".
  7139.           "<TD>$a[1]</TD><TD>$a[2]</TD><TD>$year</TD><TD>($a[4])</TD></TR>\n";
  7140.     }
  7141.     print "</TABLE>\n";
  7142.  
  7143.     close (TL);
  7144.  
  7145.     return 0;
  7146. };
  7147.  
  7148. # display a given month of the timeline
  7149. $funcs[$TL_VIEW] = sub {
  7150.     check_tl(); check_st_mon(); check_st_year();
  7151.     print_html_header("");
  7152.  
  7153.     my $tl = get_tl();
  7154.     my $st_mon = get_st_mon();
  7155.     my $st_year = get_st_year();
  7156.  
  7157.  
  7158.     unless (open (TL, "$tl")) {
  7159.         print("Error opening $tl");
  7160.         return (1);
  7161.     }
  7162.  
  7163.     log_host_inv ("$args{'tl'}: Viewing timeline for $d2m[$st_mon] $st_year");
  7164.  
  7165.     print "<TABLE CELLSPACING=\"5\" CELLPADDING=\"2\" WIDTH=100%>\n";
  7166.  
  7167.     # zone identifies if we should be printing or not
  7168.     my $zone = 0;
  7169.     my $row = 0;
  7170.     while (<TL>) {
  7171.         if (/^(?:(\w\w\w\s+)?(\w\w\w\s+\d\d\s+\d\d\d\d)\s+(\d\d:\d\d:\d\d))?\s+(\d+)\s+([mac\.]+)\s+([-\/\?\w]+)\s+([\d\w\/]+)\s+([\d\w\/]+)\s+($REG_INODE)\s+(.*)$/o) {
  7172.         
  7173.             my $day = "";
  7174.             $day = $1 if (defined $1);
  7175.             my $date = "";
  7176.             $date = $2 if (defined $2);
  7177.             my $time = "";
  7178.             $time = $3 if (defined $3);
  7179.             my $sz = $4;
  7180.             my $mac = $5;
  7181.             my $p = $6;
  7182.             my $u = $7;
  7183.             my $g = $8;
  7184.             my $i = $9;
  7185.             my $f = $10;
  7186.  
  7187.             # we must break this down to see if we can skip it or not
  7188.             if ($date ne "") {
  7189.                 if ($date =~ /^(\w\w\w)\s+\d\d\s+(\d\d\d\d)$/) {
  7190.                     if ($2 < $st_year) {
  7191.                         next;
  7192.                     } elsif (($2 == $st_year) && ($m2d{$1} < $st_mon)) {
  7193.                         next;
  7194.                     } elsif ($2 > $st_year) {
  7195.                         last;
  7196.                     } elsif (($2 == $st_year) && ($m2d{$1} > $st_mon)) {
  7197.                         last;
  7198.                     } else {
  7199.                         $zone = 1;
  7200.                     }
  7201.                 }
  7202.             }
  7203.  
  7204.             # we need to print this entry
  7205.             if ($zone) {
  7206.  
  7207.                 # the deleted inode <blah-dead-2> entries screw up in HTML
  7208.                 $f = "<$1 >" if ($f =~ /^<(.*?)>$/);
  7209.  
  7210.                 if (($row % 2) == 0) {
  7211.                     print "<TR VALIGN=\"TOP\" BGCOLOR=\"$BACK_COLOR\">\n";
  7212.                 } else {
  7213.                     print "<TR VALIGN=\"TOP\" BGCOLOR=\"$BACK_COLOR_TABLE\">\n";
  7214.                 }
  7215.  
  7216.                 print "<TD>$day $date $time</TD>".
  7217.                   "<TD>$sz</TD><TD>$mac</TD><TD>$p</TD>".
  7218.                   "<TD>$u</TD><TD>$g</TD><TD>$i</TD><TD>$f</TD></TR>\n";
  7219.  
  7220.                 $row++;
  7221.             } 
  7222.         } 
  7223.         else {
  7224.             print "Error parsing timeline: $_<BR>\n";
  7225.         }
  7226.     }
  7227.     close (TL);
  7228.     print "</TABLE>";
  7229.  
  7230.     return 0;
  7231. };
  7232.  
  7233.  
  7234.  
  7235. ############ Notes ##################
  7236.  
  7237. # window that allows one to make a note
  7238. # use the vars that were passed to determine what a comment is being
  7239. # made about (file, inode, block)
  7240. #
  7241. $funcs[$NOTES_ENT] = sub {
  7242.  
  7243.     my $str;
  7244.     my $hidden;
  7245.  
  7246.     if ($USE_NOTES == 0) {
  7247.         print_html_header("Error");
  7248.         print "Notes Option is not enabled\n";
  7249.         return;
  7250.     }
  7251.  
  7252.     my $ftype = get_ftype();
  7253.  
  7254.     # if the inode arg exists, it is either an inode note or a file name note
  7255.     if (exists $args{'inode'}) {
  7256.         my $inode = get_inode('inode');
  7257.         my $fname = "";
  7258.  
  7259.         if (exists $args{'dir'}) {
  7260.             my $fname = "$args{'mnt'}$args{'dir'}";
  7261.             print_html_header("Notes for file $fname");
  7262.             print 
  7263.               "<CENTER><B>Enter a note for <TT>$fname</TT> ($inode):</B>".
  7264.               "<BR><BR>\n";
  7265.         } else {
  7266.             print_html_header("Notes for $meta_str{$ftype} $inode");
  7267.             print 
  7268.               "<CENTER><B>Enter a note for $meta_str{$ftype} $inode:</B>".
  7269.               "<BR><BR>\n";
  7270.         }
  7271.  
  7272.         print 
  7273.           "<FORM ACTION=\"$PROGNAME\" METHOD=\"GET\">\n".
  7274.           "<TEXTAREA ROWS=10 COLS=50 WRAP=\"virtual\" NAME=\"note\">".
  7275.           "</TEXTAREA><BR>\n".
  7276.           "<INPUT TYPE=\"hidden\" NAME=\"func\" VALUE=\"$NOTES_WRITE\">\n".
  7277.           "<INPUT TYPE=\"hidden\" NAME=\"img\" VALUE=\"$args{'img'}\">\n".
  7278.             "<INPUT TYPE=\"hidden\" NAME=\"inode\" VALUE=\"$inode\">\n".
  7279.           make_hidden();
  7280.  
  7281.           print 
  7282.             "<INPUT TYPE=\"hidden\" NAME=\"dir\" VALUE=\"$args{'dir'}\">\n"
  7283.             if (exists $args{'dir'});
  7284.  
  7285.  
  7286.         # Option to add a normal note
  7287.         print 
  7288.           "<INPUT TYPE=\"checkbox\" NAME=\"norm_note\" VALUE=\"1\" CHECKED>\n".
  7289.           "  Add a Standard Note<BR>\n";
  7290.  
  7291.         # Sequencer notes
  7292.         $ENV{TZ} = $tz;
  7293.         POSIX:tzset();
  7294.  
  7295.         my $ftype = get_ftype();
  7296.         my $img_path = get_img('img');
  7297.         my $inode_int = $inode;
  7298.         $inode_int = $1 if ($inode_int =~ /(\d+)-\d+(-\d+)?/);
  7299.         local *OUT;
  7300.         exec_pipe (*OUT,
  7301.           "'${TASKDIR}ils' -f $ftype -e '$img_path' $inode_int");
  7302.         # Get the fourth line
  7303.         my $tmp = <OUT>;
  7304.         $tmp = <OUT>;
  7305.         $tmp = <OUT>;
  7306.         $tmp = <OUT>;
  7307.         unless ((defined $tmp) && ($tmp =~ /^$REG_INODE\|\w\|\d+\|\d+\|(\d+)\|(\d+)\|(\d+)\|/o)) {
  7308.             print "Error parsing 'ils' output:<BR>\n";
  7309.             return 1;
  7310.         }
  7311.         my $mtime = $1;
  7312.         my $atime = $2;
  7313.         my $ctime = $3;
  7314.         close (OUT);
  7315.  
  7316.         $mtime = localtime($mtime);
  7317.         $atime = localtime($atime);
  7318.         $ctime = localtime($ctime);
  7319.  
  7320.         print 
  7321.           "<BR><B>Add a Sequencer Event:</B><BR>\n".
  7322.           "<INPUT TYPE=\"checkbox\" NAME=\"mtime\" VALUE=\"1\">".
  7323.           "  M-Time (<TT>$mtime</TT>)<BR>\n".
  7324.           "<INPUT TYPE=\"checkbox\" NAME=\"atime\" VALUE=\"1\">".
  7325.           "  A-Time (<TT>$atime</TT>)<BR>\n".
  7326.           "<INPUT TYPE=\"checkbox\" NAME=\"ctime\" VALUE=\"1\">".
  7327.           "  C-Time (<TT>$ctime</TT>)<BR>\n";
  7328.  
  7329.         print 
  7330.           "<BR><INPUT TYPE=\"IMAGE\" SRC=\"pict/but_ok.jpg\" ".
  7331.           "WIDTH=43 HEIGHT=20 ALT=\"Ok\" BORDER=\"0\">\n</FORM>\n";
  7332.     }
  7333.  
  7334.     # data unit comment
  7335.     elsif (exists $args{'block'}) {
  7336.         my $block = get_block();
  7337.         my $len = get_len();
  7338.         print_html_header("Notes for $addr_unit{$ftype} $block");
  7339.  
  7340.         print 
  7341.           "<CENTER><B>Enter a note for $addr_unit{$ftype} $block</B><BR><BR>\n".
  7342.           "<FORM ACTION=\"$PROGNAME\" METHOD=\"GET\">\n".
  7343.           "<TEXTAREA ROWS=10 COLS=50 WRAP=\"virtual\" NAME=\"note\">".
  7344.           "</TEXTAREA><BR>\n".
  7345.           "<INPUT TYPE=\"hidden\" NAME=\"func\" VALUE=\"$NOTES_WRITE\">\n".
  7346.           "<INPUT TYPE=\"hidden\" NAME=\"img\" VALUE=\"$args{'img'}\">\n".
  7347.             "<INPUT TYPE=\"hidden\" NAME=\"block\" VALUE=\"$block\">\n".
  7348.             "<INPUT TYPE=\"hidden\" NAME=\"len\" VALUE=\"$len\">\n".
  7349.             "<INPUT TYPE=\"hidden\" NAME=\"norm_note\" VALUE=\"1\">\n".
  7350.           make_hidden().
  7351.           "<BR><INPUT TYPE=\"IMAGE\" SRC=\"pict/but_ok.jpg\" ".
  7352.           "WIDTH=43 HEIGHT=20 ALT=\"Ok\" BORDER=\"0\">\n</FORM>\n";
  7353.     }
  7354.  
  7355.     else {
  7356.         print_html_header ("ERROR");
  7357.         print "Unknown note type\n";
  7358.         return;
  7359.     }
  7360.  
  7361.     return;
  7362. };
  7363.  
  7364.  
  7365. # Write the note to the note file
  7366. # we tell what kind of note it is based on what args are passed
  7367. #
  7368. # if inode is passed it is either a dir, file, or inode and if block is
  7369. # passed it is a block
  7370. # If the dir arg is passed it is a file or directory and if the dir arg
  7371. # ends with a '/' then it is a directory
  7372. #
  7373. # This function also writes the sequencer events from files and inodes
  7374. # but the NOTES_SEQ_WRITE does the manual ones
  7375. #
  7376. $funcs[$NOTES_WRITE] = sub {
  7377.  
  7378.     if ($USE_NOTES == 0) {
  7379.         print_html_header("Error");
  7380.         print "Notes Option is not enabled\n";
  7381.         return;
  7382.     }
  7383.  
  7384.     check_note();
  7385.  
  7386.     # Get rid of carriage returns that Netscape adds 
  7387.     $args{'note'} =~ tr/\r//d;
  7388.  
  7389.  
  7390.     my $ftype = get_ftype();
  7391.     my $inode = "";
  7392.     my $fname = "";
  7393.     my $block = "";
  7394.     my $len = "";
  7395.     my $type = "";
  7396.  
  7397.     if (exists $args{'inode'}) {
  7398.         $inode = get_inode('inode');
  7399.  
  7400.  
  7401.         if (exists $args{'dir'}) {
  7402.             $args{'dir'} .= "/"
  7403.               if ($args{'dir'} eq "");
  7404.             $fname = "$args{'mnt'}$args{'dir'}";
  7405.  
  7406.             if (($args{'dir'} =~ /\/$/) || ($args{'dir'} eq "")) {
  7407.                 log_host_inv ("$args{'img'}: Creating note for directory $fname ($inode)");
  7408.                 $type = "dir";
  7409.             } else {
  7410.                 log_host_inv ("$args{'img'}: Creating note for file $fname ($inode)");
  7411.                 $type = "file";
  7412.             }
  7413.         }
  7414.         else {
  7415.             log_host_inv ("$args{'img'}: Creating note for $meta_str{$ftype} $inode");
  7416.             $type = "$meta_str{$ftype}";
  7417.         }
  7418.     }
  7419.     elsif (exists $args{'block'}) {
  7420.         $block = get_block();
  7421.         $len = get_len();
  7422.  
  7423.         log_host_inv ("$args{'img'}: Creating note for $addr_unit{$ftype} $block");
  7424.         $type = "$addr_unit{$ftype}";
  7425.     }
  7426.     else {
  7427.         print_html_header ("ERROR");
  7428.         print "Unknown note type\n";
  7429.         return;
  7430.     }
  7431.  
  7432.     print_text_header();
  7433.     print "\n";
  7434.  
  7435.     # Create the notes
  7436.     # Create a "normal" note
  7437.     if ((exists $args{'norm_note'}) && ($args{'norm_note'} == 1)) {
  7438.  
  7439.         my $notes_file = investig_notes_fname();
  7440.         open NOTES, ">>$notes_file" or die "Can't open log: $notes_file";
  7441.         print "Note added to $notes_file:\n\n";
  7442.  
  7443.         # Date
  7444.         my $tmp = localtime();
  7445.         print NOTES "$tmp\n";
  7446.         print "$tmp\n";
  7447.  
  7448.         # We have a file name
  7449.         if ($fname ne "") {
  7450.             if ($type eq 'dir') {
  7451.                 print NOTES "Directory: $fname\n";
  7452.                 print "Directory: $fname\n";
  7453.             }
  7454.             else {
  7455.                 print NOTES "File: $fname\n";
  7456.                 print "File: $fname\n";
  7457.             }
  7458.         }
  7459.         if ($inode ne "") {
  7460.             print NOTES "Image: $args{'img'}  Inode: $inode\n";
  7461.             print "Image: $args{'img'}  Inode: $inode\n";
  7462.         }
  7463.         if ($block ne "") {
  7464.             print NOTES "Image: $args{'img'}  $addr_unit{$ftype}: $block  Len: $len\n";
  7465.             print "Image: $args{'img'}  $addr_unit{$ftype}: $block  Len: $len\n";
  7466.         }
  7467.  
  7468.         # The actual notes and a line at the bottom
  7469.         print NOTES "\n$args{'note'}\n\n".
  7470.           "-" x 62 ."\n";
  7471.         print "\n$args{'note'}\n\n";
  7472.  
  7473.         close (NOTES);
  7474.     }
  7475.  
  7476.     return 0
  7477.       unless (exists $args{'inode'});
  7478.  
  7479.  
  7480.     # Create a sequencer event
  7481.     return 0 
  7482.       unless ( ((exists $args{'mtime'}) && ($args{'mtime'} == 1)) ||
  7483.         ((exists $args{'atime'}) && ($args{'atime'} == 1)) ||
  7484.         ((exists $args{'ctime'}) && ($args{'ctime'} == 1)) );
  7485.  
  7486.     my $img_path = get_img('img');
  7487.  
  7488.     # Get the times for the inode
  7489.     # Set the timezone to the host zone
  7490.     $ENV{TZ} = "$tz";
  7491.     POSIX::tzset();
  7492.  
  7493.     my $inode_int = $inode;
  7494.     $inode_int = $1 if ($inode_int =~ /(\d+)-\d+(-\d+)?/);
  7495.     local *OUT;
  7496.     exec_pipe (*OUT,
  7497.       "'${TASKDIR}ils' -f $ftype -e '$img_path' $inode_int");
  7498.  
  7499.     # Skip to the fourth line
  7500.     my $tmp = <OUT>;
  7501.     $tmp = <OUT>;
  7502.     $tmp = <OUT>;
  7503.     $tmp = <OUT>;
  7504.     unless ((defined $tmp) && ($tmp =~ /^$REG_INODE\|\w\|\d+\|\d+\|(\d+)\|(\d+)\|(\d+)\|/o)) {
  7505.         print "Error parsing 'ils' output<BR>\n";
  7506.         return 1;
  7507.     }
  7508.     my $mtime = $1;
  7509.     my $atime = $2;
  7510.     my $ctime = $3;
  7511.     close (OUT);
  7512.  
  7513.     # Get rid of the carriage returns
  7514.     $args{'note'} =~ s/\n/<BR>/gs;
  7515.  
  7516.     my $notes_file = investig_seq_notes_fname();
  7517.     open NOTES, ">>$notes_file" or die "Can't open log: $notes_file";
  7518.  
  7519.  
  7520.     if ((exists $args{'mtime'}) && ($args{'mtime'} == 1)) {
  7521.  
  7522.         my ($sec,$min,$hour,$mday,$mon,$year,$wday,$yday,$isdst) =
  7523.           localtime($mtime);
  7524.         $year += 1900;
  7525.         $mon += 1;
  7526.         $mday = "0$mday" if ($mday < 10);
  7527.         $hour = "0$hour" if ($hour < 10);
  7528.         $min = "0$min" if ($min < 10);
  7529.         $sec = "0$sec" if ($sec < 10);
  7530.     
  7531.         print NOTES "'$year','$mon','$mday','$hour','$min','$sec',".
  7532.           "'$args{'host'}','$args{'img'}','$fname','$inode','$block',".
  7533.           "'$type','[M-Time]$args{'note'}'\n";
  7534.  
  7535.         log_host_inv ("$args{'img'}: M-Time note added for inode $args{'inode'}");
  7536.         print "M-Time sequence event added\n";
  7537.     }
  7538.     if ((exists $args{'atime'}) && ($args{'atime'} == 1)) {
  7539.         my ($sec,$min,$hour,$mday,$mon,$year,$wday,$yday,$isdst) =
  7540.           localtime($atime);
  7541.         $year += 1900;
  7542.         $mon += 1;
  7543.         $mday = "0$mday" if ($mday < 10);
  7544.         $hour = "0$hour" if ($hour < 10);
  7545.         $min = "0$min" if ($min < 10);
  7546.         $sec = "0$sec" if ($sec < 10);
  7547.     
  7548.         print NOTES "'$year','$mon','$mday','$hour','$min','$sec',".
  7549.           "'$args{'host'}','$args{'img'}','$fname','$inode','$block',".
  7550.           "'$type','[A-Time]$args{'note'}'\n";
  7551.  
  7552.         log_host_inv ("$args{'img'}: A-Time note added for inode $args{'inode'}");
  7553.         print "A-Time sequence event added\n";
  7554.     }
  7555.     if ((exists $args{'ctime'}) && ($args{'ctime'} == 1)) {
  7556.         my ($sec,$min,$hour,$mday,$mon,$year,$wday,$yday,$isdst) =
  7557.           localtime($ctime);
  7558.         $year += 1900;
  7559.         $mon += 1;
  7560.         $mday = "0$mday" if ($mday < 10);
  7561.         $hour = "0$hour" if ($hour < 10);
  7562.         $min = "0$min" if ($min < 10);
  7563.         $sec = "0$sec" if ($sec < 10);
  7564.     
  7565.         print NOTES "'$year','$mon','$mday','$hour','$min','$sec',".
  7566.           "'$args{'host'}','$args{'img'}','$fname','$inode','$block',".
  7567.           "'$type','[C-Time]$args{'note'}'\n";
  7568.  
  7569.         log_host_inv ("$args{'img'}: C-Time note added for inode $args{'inode'}");
  7570.         print "C-Time sequence event added\n";
  7571.     }
  7572.  
  7573.     close (NOTES);
  7574.  
  7575.     return 0;
  7576. };
  7577.  
  7578.  
  7579.  
  7580. # Display the contents of the "normal" notes file
  7581. $funcs[$NOTES_READ] = sub {
  7582.  
  7583.     if ($USE_NOTES == 0) {
  7584.         print_html_header("Error");
  7585.         print "Notes Option is not enabled\n";
  7586.         return;
  7587.     }
  7588.  
  7589.     print_html_header("Contents of Notes File");
  7590.  
  7591.     my $notes_file = investig_notes_fname();
  7592.  
  7593.     log_host_inv ("Viewing contents of notes file ($notes_file)");
  7594.     if ((!(-e "$notes_file")) || (-z "$notes_file")) {
  7595.         print "No notes have been entered yet<BR>\n";
  7596.         return;
  7597.     }
  7598.  
  7599.     open NOTES, "<$notes_file" or die "Can't open log: $notes_file";
  7600.  
  7601.     my $file = "";
  7602.     my $dir = "";
  7603.  
  7604.     print "<TABLE WIDTH=100%>\n".
  7605.       "<TR BGCOLOR=$BACK_COLOR><TD ALIGN=LEFT>\n";
  7606.  
  7607.     my $row=0;
  7608.     # This will need to change whenever the log format changes
  7609.     while (<NOTES>) {
  7610.  
  7611.         # we need to extract mnt from here
  7612.         $file = $1 if (/File: (.*)/);
  7613.         $dir = $1 if (/Directory: (.*)/);
  7614.  
  7615.         # Reset the $file if we are at the end of the current note
  7616.         if (/^\-+$/) {
  7617.             $file = "";
  7618.             $dir = "";
  7619.             if (($row++ % 2) == 0) {
  7620.                   print "</TD></TR>\n<TR BGCOLOR=$BACK_COLOR_TABLE><TD ALIGN=LEFT>\n";
  7621.             } else {
  7622.                   print "</TD></TR>\n<TR BGCOLOR=$BACK_COLOR><TD ALIGN=LEFT>\n";
  7623.             }
  7624.         }
  7625.         else {
  7626.             print "$_<BR>";
  7627.         }
  7628.  
  7629.         if (/Image: ($REG_IMG)  Inode: ([0-9\-]+)/o) {
  7630.  
  7631.             my $img = $1;
  7632.             my $inode = $2;
  7633.  
  7634.             # if we can't find this image, then it likely means that the
  7635.             # comment pertains to a different case, so we can not give
  7636.             # any links
  7637.             unless (exists $img2mnt{$img}) {
  7638.                 next;
  7639.             }
  7640.             
  7641.             # file note
  7642.             if ($file ne "") {
  7643.                 # extract the prepended mnt value
  7644.                 my $mnt = $img2mnt{$img};
  7645.                 my $fname = "";
  7646.                 $fname = $1 if ($file =~ /^$mnt\/?(.*)$/);
  7647.                 print "<A HREF=\"$PROGNAME?$baseargs&func=$FIL_CMENU_FR".
  7648.                   "&img=$img&inode=$inode&dir=$fname\" TARGET=\"_blank\">View</A><BR>\n";
  7649.             }
  7650.             # directory note
  7651.             elsif ($dir ne "") {
  7652.                 # extract the prepended mnt value
  7653.                 my $mnt = $img2mnt{$img};
  7654.                 my $fname = "";
  7655.                 $fname = $1 if ($dir =~ /^$mnt\/?(.*)$/);
  7656.                 print "<A HREF=\"$PROGNAME?func=$MAIN_FR&".
  7657.                   "mode=$FIL_MAIN&img=$img&".
  7658.                   "$baseargs&inode=$inode&dir=$fname\" TARGET=\"_blank\">".
  7659.                   "View</A><BR>\n";
  7660.  
  7661.             }
  7662.             # inode note
  7663.             else {
  7664.                 print "<A HREF=\"$PROGNAME?func=$MAIN_FR&".
  7665.                   "mode=$INO_MAIN&img=$img".
  7666.                   "&$baseargs&inode=$inode\" TARGET=\"_blank\">View</A><BR>\n";
  7667.             }
  7668.         }
  7669.  
  7670.         # block note
  7671.         elsif (/Image: ($REG_IMG)  \w+: ([0-9]+)  Len: (\d+)/o) {
  7672.             print "<A HREF=\"$PROGNAME?func=$MAIN_FR&".
  7673.               "mode=$BLK_MAIN&img=$1&".
  7674.               "block=$2&len=$3&$baseargs\"".
  7675.               " TARGET=\"_blank\">View</A><BR>\n";
  7676.         }
  7677.     }
  7678.  
  7679.     print "</TR></TABLE>\n";
  7680.  
  7681.     # Ok and refresh buttons    
  7682.     print 
  7683.       "<P><CENTER><TABLE WIDTH=600>\n".
  7684.       "<TR><TD WIDTH=300 ALIGN=CENTER>\n".
  7685.       "<A HREF=\"$PROGNAME?func=$IMG_OPEN&$baseargs\">".
  7686.       "<IMG BORDER=0 SRC=\"pict/menu_b_ok.jpg\" ".
  7687.       "WIDTH=167 HEIGHT=20></A>\n".
  7688.       "</TD><TD WIDTH=300 ALIGN=CENTER>\n".
  7689.       "<A HREF=\"$PROGNAME?func=$NOTES_READ&$baseargs\">".
  7690.       "<IMG BORDER=0 SRC=\"pict/menu_b_ref.jpg\" ".
  7691.       "WIDTH=167 HEIGHT=20></A>\n".
  7692.       "</TD></TR></TABLE>\n";
  7693.  
  7694.     close (NOTES);
  7695.     return;
  7696. };
  7697.  
  7698.  
  7699. #########################################################################
  7700. # Sequencer Code
  7701.  
  7702. # Write a sequence event that was manually entered 
  7703. $funcs[$NOTES_SEQ_WRITE] = sub {
  7704.  
  7705.     if ($USE_NOTES == 0) {
  7706.         print_html_header("Error");
  7707.         print "Notes Option is not enabled\n";
  7708.         return;
  7709.     }
  7710.  
  7711.     check_note();
  7712.  
  7713.     print_html_header("Writing Sequencer Event");
  7714.  
  7715.     # Get rid of carriage returns that Netscape adds 
  7716.     $args{'note'} =~ tr/\r//d;
  7717.     $args{'note'} =~ s/\n/<BR>/gs;
  7718.  
  7719.     if ($args{'note'} eq "") {
  7720.         print "A comment must be given for the event<BR>\n".
  7721.           "<P><A HREF=\"$PROGNAME?func=$NOTES_SEQ_READ&$baseargs\">".
  7722.           "<IMG BORDER=0 SRC=\"pict/menu_b_ok.jpg\" ".
  7723.           "WIDTH=167 HEIGHT=20></A>\n"; 
  7724.         return 1;
  7725.     }
  7726.  
  7727.     # Check the args and add them to the final string that will be written
  7728.     my $str = "";
  7729.     unless ((exists $args{'year'}) && ($args{'year'} =~ /^(\d\d\d\d)$/))  {
  7730.         print "Invalid year<BR>\n";
  7731.         return 1;
  7732.     }
  7733.     $str .= "'$1',";
  7734.  
  7735.     unless ((exists $args{'mon'}) && ($args{'mon'} =~ /^(\d\d?)$/))  {
  7736.         print "Invalid month<BR>\n";
  7737.         return 1;
  7738.     }
  7739.     $str .= "'$1',";
  7740.  
  7741.     unless ((exists $args{'day'}) && ($args{'day'} =~ /^(\d\d?)$/))  {
  7742.         print "Invalid day<BR>\n";
  7743.         return 1;
  7744.     }
  7745.     $str .= "'$1',";
  7746.  
  7747.     unless ((exists $args{'hour'}) && ($args{'hour'} =~ /^(\d\d?)$/))  {
  7748.         print "Invalid hour<BR>\n";
  7749.         return 1;
  7750.     }
  7751.     $str .= "'$1',";
  7752.  
  7753.     unless ((exists $args{'min'}) && ($args{'min'} =~ /^(\d\d?)$/))  {
  7754.         print "Invalid min<BR>\n";
  7755.         return 1;
  7756.     }
  7757.     $str .= "'$1',";
  7758.  
  7759.     unless ((exists $args{'sec'}) && ($args{'sec'} =~ /^(\d\d?)$/))  {
  7760.         print "Invalid sec<BR>\n";
  7761.         return 1;
  7762.     }
  7763.     $str .= "'$1',";
  7764.  
  7765.     # There are no image, inode, file name, or data unit for this type
  7766.     $str .= "'$args{'host'}','','','','',";
  7767.  
  7768.     unless ((exists $args{'src'}) && ($args{'src'} =~ /^(\w+)$/))  {
  7769.         print "Invalid src<BR>\n";
  7770.         return 1;
  7771.     }
  7772.     $str .= "'$1','$args{'note'}'\n";
  7773.  
  7774.     # Write the string to the notes file
  7775.     my $notes_file = investig_seq_notes_fname();
  7776.     open NOTES, ">>$notes_file" or die "Can't open log: $notes_file";
  7777.     print NOTES $str;
  7778.     close (NOTES);
  7779.  
  7780.     # Send a message to the user
  7781.     print "Event Added to Sequencer file:<BR><BR>\n".
  7782.       "$d2m[$args{'mon'}] $args{'day'}, $args{'year'} ".
  7783.       "$args{'hour'}:$args{'min'}:$args{'sec'}<BR><BR>\n".
  7784.       "$args{'note'}<BR>\n".
  7785.       "<P><A HREF=\"$PROGNAME?func=$NOTES_SEQ_READ&$baseargs&".
  7786.       "year=$enc_args{'year'}&mon=$enc_args{'mon'}&day=$enc_args{'day'}&".
  7787.       "hour=$enc_args{'hour'}&min=$enc_args{'min'}&sec=$enc_args{'sec'}\">".
  7788.       "<IMG BORDER=0 SRC=\"pict/but_ok.jpg\" ALT=\"Ok\" ".
  7789.       "WIDTH=43 HEIGHT=20></A>\n"; 
  7790.  
  7791.     return 0;
  7792. };
  7793.  
  7794.  
  7795. # View the sequencer file
  7796. $funcs[$NOTES_SEQ_READ] = sub {
  7797.  
  7798.     if ($USE_NOTES == 0) {
  7799.         print_html_header("Error");
  7800.         print "Notes Option is not enabled\n";
  7801.         return;
  7802.     }
  7803.  
  7804.     print_html_header("Event Sequencer");
  7805.  
  7806.     print "<CENTER>\n".
  7807.       "<H3>Event Sequencer</H3>\n";
  7808.  
  7809.  
  7810.     my $cnt = 0;
  7811.     my @entry;
  7812.     my (@year, @mon, @day, @hour, @min, @sec, @host, @img, @fname, @inode, @data, @type, @note);
  7813.  
  7814.     # Read the sequencer file into arrays that will be sorted
  7815.     my $notes_file = investig_seq_notes_fname();
  7816.     if (-e $notes_file) {
  7817.  
  7818.     open NOTES, "$notes_file" or die "Can't open log: $notes_file";
  7819.     while (<NOTES>) {
  7820.  
  7821.         unless (/^'?(\d+)'?,'?(\d+)'?,'?(\d+)'?,'?(\d+)'?,'?(\d+)'?,'?(\d+)'?,'?($REG_HOST)'?,'?($REG_IMG)?'?,'?(.*?)?'?,'?($REG_INODE)?'?,'?(\d+)?'?,'?([\w\s]+)'?,'?(.*?)'?$/) {
  7822.             print "Error parsing sequence event entry: $_\n";
  7823.             return 1;
  7824.         }
  7825.  
  7826.         $year[$cnt] = $1;
  7827.         $mon[$cnt] = $2;
  7828.         $day[$cnt] = $3;
  7829.         $hour[$cnt] = $4;
  7830.         $min[$cnt] = $5;
  7831.         $sec[$cnt] = $6;
  7832.         $host[$cnt] = $7;
  7833.         $img[$cnt] = $8;
  7834.         $fname[$cnt] = $9;
  7835.         $inode[$cnt] = $10;
  7836.         $data[$cnt] = $11;
  7837.         $type[$cnt] = $12;
  7838.         $note[$cnt] = $13;
  7839.  
  7840.         $entry[$cnt] = $cnt;
  7841.         $cnt++;
  7842.     }
  7843.  
  7844.     close (NOTES);
  7845.  
  7846.     # Sort the values by date, source, and then note
  7847.     my @sorted = sort {
  7848.         $year[$a] <=> $year[$b] or
  7849.         $mon[$a] <=> $mon[$b] or
  7850.         $day[$a] <=> $day[$b] or
  7851.         $hour[$a] <=> $hour[$b] or
  7852.         $min[$a] <=> $min[$b] or
  7853.         $sec[$a] <=> $sec[$b] or
  7854.         lc($type[$a]) cmp lc($type[$b]) or
  7855.         lc($note[$a]) cmp lc($note[$b])
  7856.     } @entry;
  7857.  
  7858.  
  7859.     # Table and header
  7860.     print "<TABLE WIDTH=800 BORDER=1>\n".
  7861.       "<TR BACKGROUND=\"$YEL_PIX\">\n".
  7862.       "<TH>Date & Time</TH>\n".
  7863.       "<TH>Source</TH>\n".
  7864.       "<TH>Event & Note</TH></TR>\n";
  7865.  
  7866.     # Cycle through the sorted events
  7867.     my $row = 0;
  7868.     foreach my $i (@sorted) {
  7869.  
  7870.         # Alternate row colors
  7871.         if (($row % 2) == 0) {
  7872.             print "<TR BGCOLOR=\"$BACK_COLOR\">\n";
  7873.         } else {
  7874.             print "<TR BGCOLOR=\"$BACK_COLOR_TABLE\">\n";
  7875.         }
  7876.  
  7877.         # Date & Time
  7878.         print "<TD ALIGN=LEFT VALIGN=TOP>\n".
  7879.           "$d2m[$mon[$i]] $day[$i], $year[$i]".
  7880.           " $hour[$i]:$min[$i]:$sec[$i]</TD>";
  7881.  
  7882.         my $img;
  7883.         if (defined $img[$i]) {
  7884.             $img = $img[$i];
  7885.         } else {
  7886.             $img = "";
  7887.         }
  7888.  
  7889.         print "<TD ALIGN=LEFT VALIGN=TOP>\n";
  7890.         # IF there is as name, then we will show it
  7891.         if ((defined $fname[$i]) && ($fname[$i] ne "")) {
  7892.  
  7893.             if (($img ne "") && (exists $img2mnt{$img}) && 
  7894.               (defined $inode[$i])) {
  7895.                 # extract the prepended mnt value
  7896.                 my $mnt = $img2mnt{$img};
  7897.                 my $fname = "";
  7898.                 $fname = $1 if ($fname[$i] =~ /^$mnt\/?(.*)$/);
  7899.  
  7900.                 # Check if it is a directory 
  7901.                 if ($type[$i] eq 'dir') {
  7902.                     print "<A HREF=\"$PROGNAME?func=$MAIN_FR&".
  7903.                       "mode=$FIL_MAIN&img=$img[$i]&".
  7904.                       "$baseargs&inode=$inode[$i]&dir=$fname\" ".
  7905.                       "TARGET=\"_blank\">\n".
  7906.                       "<TT>$fname[$i]</TT></A>\n";
  7907.                 } else {
  7908.                     print "<A HREF=\"$PROGNAME?func=$FIL_CMENU_FR&".
  7909.                       "img=$img[$i]&".
  7910.                       "$baseargs&inode=$inode[$i]&dir=$fname\" ".
  7911.                       "TARGET=\"_blank\">\n".
  7912.                       "<TT>$fname[$i]</TT></A>\n";
  7913.                 }
  7914.             }
  7915.             else {
  7916.                 print "<TT>$fname[$i]</TT>\n";
  7917.             }
  7918.         }
  7919.  
  7920.         # Display the inode value if there was no name
  7921.         elsif (($img ne "") && (defined $inode[$i]) && ($inode[$i] ne "")) {
  7922.             my $ftype = $img2ftype{$img};
  7923.  
  7924.             # Include a link if we can
  7925.             if (exists $img2mnt{$img}) {
  7926.                 print "<A HREF=\"$PROGNAME?func=$MAIN_FR&".
  7927.                   "mode=$INO_MAIN&img=$img".
  7928.                   "&$baseargs&inode=$inode[$i]\" TARGET=\"_blank\">\n".
  7929.                   "$meta_str{$ftype}: $inode[$i]</A>\n";
  7930.             }
  7931.             else {
  7932.                 print "$meta_str{$ftype}: $inode[$i]\n";
  7933.             }
  7934.         }
  7935.  
  7936.         # Otherwise, just give the source type
  7937.         else {
  7938.             print "$type[$i]\n";
  7939.         }
  7940.         print "</TD>\n";
  7941.  
  7942.         # Print the actual note
  7943.         $note[$i] = " " if ($note[$i] eq "");
  7944.         print "<TD ALIGN=LEFT>$note[$i]</TD></TR>\n";
  7945.  
  7946.         $row++;
  7947.     }
  7948.  
  7949.     print "</TABLE>\n";
  7950.  
  7951.     } 
  7952.     # End of if file exists
  7953.     else {
  7954.         print "No events currently exist<BR>\n";
  7955.     }
  7956.  
  7957.     # Ok and refresh buttons 
  7958.     print 
  7959.       "<P><TABLE WIDTH=600>\n".
  7960.       "<TR><TD WIDTH=300 ALIGN=CENTER>\n".
  7961.       "<A HREF=\"$PROGNAME?func=$IMG_OPEN&$baseargs\">".
  7962.       "<IMG BORDER=0 SRC=\"pict/menu_b_ok.jpg\" ".
  7963.       "WIDTH=167 HEIGHT=20></A>\n".
  7964.       "</TD><TD WIDTH=300 ALIGN=CENTER>\n".
  7965.       "<A HREF=\"$PROGNAME?func=$NOTES_SEQ_READ&$baseargs\">".
  7966.       "<IMG BORDER=0 SRC=\"pict/menu_b_ref.jpg\" ".
  7967.       "WIDTH=167 HEIGHT=20></A>\n".
  7968.       "</TD></TR></TABLE>\n";
  7969.  
  7970.  
  7971.     # Manually add a new event
  7972.     print "<HR>\n".
  7973.       "<B>Add a New Event</B><BR><BR>\n".
  7974.       "<FORM ACTION=\"$PROGNAME\" METHOD=\"GET\">\n".
  7975.       "<TEXTAREA ROWS=10 COLS=50 WRAP=\"virtual\" NAME=\"note\">".
  7976.       "</TEXTAREA><BR>\n".
  7977.       "<INPUT TYPE=\"hidden\" NAME=\"func\" VALUE=\"$NOTES_SEQ_WRITE\">\n".
  7978.       make_hidden();
  7979.  
  7980.     # Month
  7981.     print
  7982.       "<P>Date: ".
  7983.       "<SELECT NAME=\"mon\" SIZE=\"1\">\n";
  7984.  
  7985.     my $prev = 1;
  7986.     $prev = $args{'mon'} 
  7987.       if ((exists $args{'mon'}) && ($args{'mon'} =~ /^\d+$/));
  7988.  
  7989.     for my $i (1 .. 12) {
  7990.         if ($i == $prev) {
  7991.           print "<OPTION VALUE=$i SELECTED>$d2m[$i]</OPTION>\n";
  7992.         } else {
  7993.         print "<OPTION VALUE=\"$i\">$d2m[$i]</OPTION>\n";
  7994.         }
  7995.     }
  7996.  
  7997.     print "</SELECT>\n";
  7998.  
  7999.     # Day
  8000.     print " <SELECT NAME=\"day\" SIZE=\"1\">\n";
  8001.  
  8002.     $prev = 1;
  8003.     $prev = $args{'day'} 
  8004.       if ((exists $args{'day'}) && ($args{'day'} =~ /^\d+$/));
  8005.  
  8006.     for my $i (1 .. 31) {
  8007.         my $dstr = $i;
  8008.         $dstr = "0$i" if ($i < 10);
  8009.  
  8010.         if ($prev eq $dstr) {
  8011.               print "<OPTION VALUE=\"$dstr\" SELECTED>$dstr</OPTION>\n";
  8012.         } else {
  8013.             print "<OPTION VALUE=\"$dstr\">$dstr</OPTION>\n";
  8014.         }
  8015.     }
  8016.     print "</SELECT>\n";
  8017.  
  8018.     # Year
  8019.     $prev = 1900 + (localtime())[5];
  8020.     $prev = $args{'year'} 
  8021.       if ((exists $args{'year'}) && ($args{'year'} =~ /^\d+$/));
  8022.  
  8023.     print 
  8024.       " <INPUT TYPE=\"text\" VALUE=\"$prev\" ".
  8025.       "NAME=\"year\" SIZE=\"6\">\n";
  8026.  
  8027.     # Hour
  8028.     print "  <SELECT NAME=\"hour\" SIZE=\"1\">\n";
  8029.     $prev = 0;
  8030.     $prev = $args{'hour'} 
  8031.       if ((exists $args{'hour'}) && ($args{'hour'} =~ /^\d+$/));
  8032.  
  8033.     for my $i (0 .. 23) {
  8034.         my $hstr = $i;
  8035.         $hstr = "0$i" if ($i < 10);
  8036.  
  8037.         if ($prev eq $hstr) {
  8038.             print "<OPTION VALUE=\"$hstr\" SELECTED>$hstr</OPTION>\n";
  8039.         } else {
  8040.             print "<OPTION VALUE=\"$hstr\">$hstr</OPTION>\n";
  8041.         }
  8042.     }
  8043.     print "</SELECT>\n";
  8044.  
  8045.     # Min
  8046.     print ":<SELECT NAME=\"min\" SIZE=\"1\">\n";
  8047.     $prev = 0;
  8048.     $prev = $args{'min'} 
  8049.       if ((exists $args{'min'}) && ($args{'min'} =~ /^\d+$/));
  8050.  
  8051.     for my $i (0 .. 59) {
  8052.         my $mstr = $i;
  8053.         $mstr = "0$i" if ($i < 10);
  8054.         if ($prev eq $mstr) {
  8055.             print "<OPTION VALUE=\"$mstr\" SELECTED>$mstr</OPTION>\n";
  8056.         } else {
  8057.             print "<OPTION VALUE=\"$mstr\">$mstr</OPTION>\n";
  8058.         }
  8059.     }
  8060.     print "</SELECT>\n";
  8061.  
  8062.     # Sec
  8063.     print ":<SELECT NAME=\"sec\" SIZE=\"1\">\n";
  8064.     $prev = 0;
  8065.     $prev = $args{'sec'}
  8066.       if ((exists $args{'sec'}) && ($args{'sec'} =~ /^\d+$/));
  8067.  
  8068.     for my $i (0 .. 59) {
  8069.         my $sstr = $i;
  8070.         $sstr = "0$i" if ($i < 10);
  8071.  
  8072.         if ($prev eq $sstr) {
  8073.             print "<OPTION VALUE=\"$sstr\" SELECTED>$sstr</OPTION>\n";
  8074.         } else {
  8075.             print "<OPTION VALUE=\"$sstr\">$sstr</OPTION>\n";
  8076.         }
  8077.     }
  8078.     print "</SELECT>\n";
  8079.  
  8080.     # Type
  8081.     print "<BR><BR>Source of Event: <SELECT NAME=\"src\" SIZE=1>\n".
  8082.       "<OPTION VALUE=\"firewall\">firewall</OPTION>\n".
  8083.       "<OPTION VALUE=\"ids\">ids</OPTION>\n".
  8084.       "<OPTION VALUE=\"isp\">isp</OPTION>\n".
  8085.       "<OPTION VALUE=\"log\">log</OPTION>\n".
  8086.       "<OPTION VALUE=\"other\" SELECTED>other</OPTION>\n".
  8087.       "<OPTION VALUE=\"person\">person</OPTION>\n".
  8088.       "</SELECT>\n";
  8089.  
  8090.     print "<P><INPUT TYPE=\"IMAGE\" SRC=\"pict/menu_b_ok.jpg\" ".
  8091.       "WIDTH=167 HEIGHT=20 ALT=\"Ok\" BORDER=\"0\">\n</FORM>\n";
  8092.  
  8093.     return 0;
  8094. };
  8095.  
  8096.  
  8097.  
  8098.  
  8099.  
  8100. #########################################################################
  8101. # sorter
  8102. #
  8103.  
  8104. # sorter frameset
  8105. $funcs[$SORTER_MAIN] = sub {
  8106.     print_html_header_frameset("Sorter on $args{'img'}");
  8107.  
  8108.     print "<FRAMESET COLS=\"20%,80%\">\n";        
  8109.  
  8110.     # Block List
  8111.     print "<FRAME SRC=\"$PROGNAME?func=$SORTER_LIST&$baseargs\">\n";
  8112.  
  8113.     # Blank
  8114.     print "<FRAME SRC=\"$PROGNAME?func=$BLANK&$baseargs\" NAME=\"content\">\n".
  8115.       "</FRAMESET>\n";
  8116.  
  8117.     return 0;
  8118. };
  8119.  
  8120.  
  8121. # The left-hand frame for running sorter
  8122. $funcs[$SORTER_LIST] = sub {
  8123.     print_html_header("sorter menu");
  8124.  
  8125.     print "<P><A HREF=\"$PROGNAME?func=$SORTER_ENT&$baseargs\" ".
  8126.       "TARGET=\"content\">Sort Files by Type</A>";
  8127.  
  8128.     return 0;
  8129. };
  8130.  
  8131.  
  8132. # Get the data and print the form so that sorter can be run
  8133. $funcs[$SORTER_ENT] = sub {
  8134.     print_html_header("sorter - enter data to create");
  8135.  
  8136.     print "<CENTER>".
  8137.       "<H3>File Type Sortings</H3></CENTER><BR>".
  8138.       "<FORM ACTION=\"$PROGNAME\" METHOD=\"GET\">\n".
  8139.       "<INPUT TYPE=\"hidden\" NAME=\"func\" VALUE=\"$SORTER_DOIT\">\n".
  8140.       "<INPUT TYPE=\"hidden\" NAME=\"img\" VALUE=\"$args{'img'}\">\n".
  8141.       make_hidden();
  8142.  
  8143.     print <<EOF1;
  8144. <P>The <B>sorter</B> tool will process an image and organize the
  8145. files based on their file type.  The files are organized into categories
  8146. that are defined in configuration files.  The categories will be saved
  8147. in the <TT>${DATADIR}</TT> directory.  
  8148. <HR>
  8149. EOF1
  8150.  
  8151.     my $sort_dir = get_sorter_dir();
  8152.     if (-d "$sort_dir") {
  8153.         print "WARNING: This will overwrite any existing data in:<BR>".
  8154.         "    <TT>$sort_dir</TT><BR>\n";
  8155.     }
  8156.  
  8157.  
  8158.     my $tab = "        ";
  8159.  
  8160.     print <<EOF2;
  8161.  
  8162. <P>
  8163. <INPUT TYPE=\"checkbox\" NAME=\"sorter_cat\" VALUE=\"1\" CHECKED>
  8164. Sort files into categories by type
  8165.  
  8166.   <P>$tab
  8167.   <INPUT TYPE=\"checkbox\" NAME=\"sorter_unk\" VALUE=\"1\">
  8168.   Do not save data about <TT>unknown</TT> file types
  8169.  
  8170.   <P>$tab
  8171.   <INPUT TYPE=\"checkbox\" NAME=\"sorter_save\" VALUE=\"1\">
  8172.   Save a copy of files in category directory (may require lots of disk space)
  8173.  
  8174.   <P>$tab
  8175.   <INPUT TYPE=\"checkbox\" NAME=\"sorter_img\" VALUE=\"1\">
  8176.   Save ONLY graphic images and make thumbnails <BR>
  8177.   $tab (may require lots of disk space and will save to a different directory than sorting all file types)
  8178.  
  8179. <P>
  8180. <INPUT TYPE=\"checkbox\" NAME=\"sorter_ext\" VALUE=\"1\" CHECKED>
  8181. Extension and File Type Validation
  8182.  
  8183. EOF2
  8184.  
  8185.     if (($NSRLDB ne "") && (-e "$NSRLDB")) {
  8186.     # @@@ Removed until it is easier to identify the known bad files in
  8187.     # NSRL
  8188. #        print 
  8189. #          "<P><INPUT TYPE=\"checkbox\" NAME=\"sorter_nsrl\" VALUE=\"1\" CHECKED>".
  8190. #          "Exclude files in the <B>NIST NSRL</B>\n";
  8191.  
  8192.         print "<P>The <B>NIST NSRL</B> option has been removed from this mode\n";
  8193.     }
  8194.  
  8195.     if (($alert_db ne "") && (-e "$alert_db")) {
  8196.         print 
  8197.           "<P><INPUT TYPE=\"checkbox\" NAME=\"sorter_alert\" VALUE=\"1\" CHECKED>".
  8198.           "Alert files that are found in the <B>Alert Hash Database</B>\n";
  8199.     }
  8200.  
  8201.     if (($exclude_db ne "") && (-e "$exclude_db")) {
  8202.         print 
  8203.           "<P><INPUT TYPE=\"checkbox\" NAME=\"sorter_exclude\" VALUE=\"1\" CHECKED>".
  8204.           "Ignore files that are found in the <B>Exclude Hash Database</B>\n";
  8205.     }
  8206.  
  8207.     print 
  8208.       "<P><INPUT TYPE=\"IMAGE\" SRC=\"pict/but_ok.jpg\" ".
  8209.       "WIDTH=43 HEIGHT=20 ALT=\"Ok\" BORDER=\"0\">\n</FORM>\n";
  8210.  
  8211.     return;
  8212. };
  8213.  
  8214.  
  8215. # Run sorter on the image 
  8216. $funcs[$SORTER_DOIT] = sub {
  8217.     print_html_header("sorter - create");
  8218.  
  8219.     my $sort_args = "";
  8220.     my $ext = 0;
  8221.     my $cat = 0;
  8222.  
  8223.     log_host_inv ("Running 'sorter' on ($args{'img'}");
  8224.  
  8225.     $ext = 1 if ((exists $args{'sorter_ext'}) && ($args{'sorter_ext'} == 1));
  8226.     $cat = 1 if ((exists $args{'sorter_cat'}) && ($args{'sorter_cat'} == 1));
  8227.  
  8228.     if (($cat == 0) && ($ext == 0)) {
  8229.         print "At least one action must be selected\n".
  8230.           "<P><A HREF=\"$PROGNAME?func=$SORTER_ENT&$baseargs\">".
  8231.           "<IMG BORDER=0 SRC=\"pict/but_ok.jpg\" ALT=\"Ok\" ".
  8232.           "WIDTH=43 HEIGHT=20></A>\n";
  8233.  
  8234.         return;
  8235.     }
  8236.  
  8237.     # If both actions are wanted then no flags are needed
  8238.     $sort_args .= "-e " if (($ext == 1) && ($cat == 0));
  8239.     $sort_args .= "-i " if (($ext == 0) && ($cat == 1));
  8240.  
  8241.     my $sort_dir = get_sorter_dir();
  8242.  
  8243.     if ($cat == 1) {
  8244.         if ((exists $args{'sorter_img'}) && ($args{'sorter_img'} == 1)) {
  8245.             my $config = "${TASKDIR}/../share/sorter/images.sort";
  8246.  
  8247.             print_err ("images configuration file not found ($config)")
  8248.               unless (-e "$config");
  8249.  
  8250.             $sort_args .= "-C $config -s -U ";
  8251.  
  8252.             $sort_dir = get_sorter_graphics_dir();
  8253.  
  8254.         } else {
  8255.             $sort_args .= "-s " 
  8256.               if ((exists $args{'sorter_save'}) && ($args{'sorter_save'} == 1));
  8257.  
  8258.             $sort_args .= "-U " 
  8259.               if ((exists $args{'sorter_unk'}) && ($args{'sorter_unk'} == 1));
  8260.         }
  8261.     }
  8262.  
  8263.     if ($NSRLDB ne "") {
  8264.         # @@@ Removed until the known bad can be identified in NSRL
  8265.         # $sort_args .= "-n \'$NSRLDB\' "
  8266.         # if ((exists $args{'sorter_nsrl'}) && ($args{'sorter_nsrl'} == 1));
  8267.     }
  8268.  
  8269.     if ($alert_db ne "") {
  8270.         $sort_args .= "-a \'$alert_db\' "
  8271.           if ((exists $args{'sorter_alert'}) && ($args{'sorter_alert'} == 1));
  8272.     }
  8273.  
  8274.     if ($exclude_db ne "") {
  8275.         $sort_args .= "-x \'$exclude_db\' "
  8276.           if ((exists $args{'sorter_exclude'}) && ($args{'sorter_exclude'} == 1));
  8277.     }
  8278.  
  8279.     my $mnt = get_mnt();
  8280.     my $fstype = get_ftype();
  8281.     my $img = get_img('img');
  8282.  
  8283.     unless (-d "$sort_dir") {
  8284.         unless (mkdir "$sort_dir", $MKDIR_MASK) {
  8285.             print_err ("Error making $sort_dir");
  8286.         }
  8287.     }
  8288.     if (-e "$sort_dir/index.html") {
  8289.         unlink ("$sort_dir/index.html");
  8290.     }
  8291.  
  8292.     my $exec = "-h -m '$mnt' -d '$sort_dir' -f $fstype $sort_args '$img'";
  8293.     print "Executing: <TT>sorter $exec</TT><P>\n";
  8294.  
  8295.     # Execute Sorter
  8296.     my $hit_cnt = 0;
  8297.     $SIG{ALRM} = sub {
  8298.         if (($hit_cnt++ % 5) == 0) {
  8299.             print "+";
  8300.         } else {
  8301.             print "-";
  8302.         }
  8303.         alarm(5);
  8304.     };
  8305.     alarm(5);
  8306.  
  8307.     local *OUT;
  8308.     exec_pipe (*OUT, 
  8309.       "LANG=C LC_ALL=C '${TASKDIR}sorter' $exec");
  8310.  
  8311.     while (<OUT>) {
  8312.         print "$_<BR>\n";
  8313.         $hit_cnt = 0;
  8314.     }
  8315.  
  8316.     $SIG{ALRM} = 'DEFAULT';
  8317.  
  8318.     if (-e "$sort_dir/index.html") {
  8319.         print "<P>Output can be found by viewing: <TT>$sort_dir/index.html</TT><P>\n".
  8320.           "(Future versions of Autopsy will have built-in viewing capabilities)<BR>\n";
  8321.  
  8322.  
  8323.         # Print the index.html file from the output
  8324.         print "<HR><CENTER><H3>Results Summary</H3></CENTER>\n";
  8325.         open INDEX, "<$sort_dir/index.html" 
  8326.           or die "Can't open sorter index file ($sort_dir/index.html)";
  8327.  
  8328.         while (<INDEX>) {
  8329.             next if ((/^<HTML><HEAD><TITLE>/i) || 
  8330.               (/^<BODY><CENTER><H2>/i));
  8331.  
  8332.             # Extract out the symlinks to the categories
  8333.             if (/^\s*<li><A HREF="\.\/[\w\.]+">([\w\s]+)<\/a> \((\d+)\)\s*$/i) {
  8334.                 print "<LI>$1 ($2)\n";
  8335.             }
  8336.             # Skip the link on the thumbnails link
  8337.             elsif (/^\s*\(<A HREF=[\"\.\/\w]+>thumbnails<\/A>\)\s*$/) {
  8338.                 print "(thumbnails)\n";
  8339.             }
  8340.             else {
  8341.                 print "$_";
  8342.             }
  8343.         }
  8344.         close (INDEX);
  8345.     }
  8346.  
  8347.     return;
  8348. };
  8349.  
  8350.  
  8351. #########################################################################
  8352. # Hash Databases
  8353. #
  8354. sub hash_index_md5sum {
  8355.     my $db = shift;
  8356.     local *OUT;
  8357.     exec_pipe (*OUT, 
  8358.       "'${TASKDIR}hfind' -i md5sum '$db'");
  8359.     while (<OUT>) {
  8360.         print "$_<BR>\n";
  8361.     }
  8362.     close (OUT);
  8363. };
  8364.  
  8365. sub hash_index_nsrl {
  8366.     local *OUT;
  8367.     exec_pipe (*OUT, 
  8368.       "'${TASKDIR}hfind' -i nsrl-md5 '$NSRLDB'");
  8369.     while (<OUT>) {
  8370.         print "$_<BR>\n";
  8371.     }
  8372.     close (OUT);
  8373. };
  8374.  
  8375.  
  8376. # Window from HOST Manager
  8377. $funcs[$HASH_MAIN] = sub {
  8378.     print_html_header("Hash Database Manager");
  8379.  
  8380. print <<EOF;
  8381.  
  8382. Hash databases allow Autopsy to quickly identify known files.  This includes
  8383. files that are known to be good and those that are known to be bad.  The
  8384. 'hfind' tool is used to lookup entries in the databases and it needs an
  8385. index file for each database.  This window allows one to re-index the
  8386. database after it has been updated.  
  8387.  
  8388. <P>
  8389. To edit the location of the databases, you must manually edit the 
  8390. <TT>host.aut</TT> file in the host directory.  
  8391.  
  8392. <HR>
  8393. <CENTER>
  8394. <IMG SRC=\"pict/hashdb_h_alert.jpg\" ALT=\"Alert Database\" BORDER=\"0\">
  8395. </CENTER>
  8396. <P><B>Overview</B><BR>
  8397. These files are known to be <U>bad</U> and are the ones that you want to
  8398. know about if they are in the image you are analyzing.  For example,
  8399. this database would include hashes of known attacker tools, rootkits,
  8400. or photographs.  
  8401.  
  8402. EOF
  8403.     print "<P><B>Details</B><BR>\n";
  8404.     if ($alert_db eq "") {
  8405.         print "Location: <TT>Not Configured</TT><BR>\n";
  8406.     }
  8407.     elsif (-e "$alert_db") {
  8408.         print "Location: <TT>$alert_db</TT><BR>\n";
  8409.         if (-e "${alert_db}-md5.idx") {
  8410.             print "Status: MD5 Index File Exists<BR>\n";
  8411.         } else {
  8412.             print "Status: Database has not been MD5 indexed<BR>\n";
  8413.         }
  8414.  
  8415.         # Index Button
  8416.         print
  8417.           "<P><A HREF=\"$PROGNAME?func=$HASH_INDEX&hash_alert=1&$baseargs\">".
  8418.           "<IMG SRC=\"pict/but_indexdb.jpg\" ALT=\"Index DB\" ".
  8419.           "WIDTH=116 HEIGHT=20 BORDER=\"0\">".
  8420.           "</A>\n";
  8421.  
  8422.         # Lookup Button
  8423.         if (-e "${alert_db}-md5.idx") {
  8424.             print
  8425.                  "<P><B>Lookup</B><BR>".
  8426.               "<FORM ACTION=\"$PROGNAME\" METHOD=\"GET\">".
  8427.               "<INPUT TYPE=\"hidden\" NAME=\"func\" VALUE=\"$HASH_LOOKUP\">\n".
  8428.               "<INPUT TYPE=\"hidden\" NAME=\"hash_alert\" VALUE=\"1\">\n".
  8429.               make_hidden().
  8430.                 "<TABLE CELLSPACING=\"10\" CELLPADDING=\"2\">\n<TR>\n".
  8431.               "<TD ALIGN=\"LEFT\">Enter MD5 Value: ".
  8432.               "<INPUT TYPE=\"text\" NAME=\"md5\" SIZE=40 MAXLENGTH=32></TD>\n".
  8433.               "<TD ALIGN=\"LEFT\">".
  8434.               "<INPUT TYPE=\"IMAGE\" SRC=\"pict/but_lookup.jpg\" ALT=\"Ok\" ".
  8435.               "WIDTH=116 HEIGHT=20 BORDER=\"0\">\n".
  8436.               "</TD></TR>\n</TABLE>\n".
  8437.               "</FORM>";
  8438.         }
  8439.     }
  8440.     else {
  8441.         print "Location: <TT>$alert_db</TT><BR>\n".
  8442.           "ERROR: Database not found<BR>\n";
  8443.     }
  8444.  
  8445.  
  8446. print <<EOF2;
  8447. <HR>
  8448. <CENTER>
  8449. <IMG SRC=\"pict/hashdb_h_ig.jpg\" ALT=\"Ignore Database\" BORDER=\"0\">
  8450. </CENTER>
  8451. <P><B>Overview</B><BR>
  8452. These files are known to be <U>good</U> and are the ones that you
  8453. can ignore if they are found in the image you are analyzing.  For
  8454. example, this database would include hashes of known system binaries
  8455. and other documents that you do not want to waste time on when running
  8456. 'sorter' or files that you want to confirm were not modified by an 
  8457. attacker.  
  8458.  
  8459. EOF2
  8460.  
  8461.     print "<P><B>Details</B><BR>\n";
  8462.     if ($exclude_db eq "") {
  8463.         print "Location: <TT>Not Configured</TT><BR>\n";
  8464.     }
  8465.     elsif (-e "$exclude_db") {
  8466.         print "Location: <TT>$exclude_db</TT><BR>\n";
  8467.         if (-e "${exclude_db}-md5.idx") {
  8468.             print "Status: MD5 Index File Exists<BR>\n";
  8469.         } else {
  8470.             print "Status: Database has not been MD5 indexed<BR>\n";
  8471.         }
  8472.  
  8473.         # Index Button
  8474.         print 
  8475.           "<P><A HREF=\"$PROGNAME?func=$HASH_INDEX&hash_exclude=1&$baseargs\">".
  8476.           "<IMG SRC=\"pict/but_indexdb.jpg\" ALT=\"Index DB\" ".
  8477.           "WIDTH=116 HEIGHT=20 BORDER=\"0\">".
  8478.           "</A>\n";
  8479.  
  8480.         # Lookup Button
  8481.         if (-e "${exclude_db}-md5.idx") {
  8482.             print
  8483.               "<P><B>Lookup</B><BR>".
  8484.               "<FORM ACTION=\"$PROGNAME\" METHOD=\"GET\">".
  8485.               "<INPUT TYPE=\"hidden\" NAME=\"func\" VALUE=\"$HASH_LOOKUP\">\n".
  8486.               "<INPUT TYPE=\"hidden\" NAME=\"hash_exclude\" VALUE=\"1\">\n".
  8487.               make_hidden().
  8488.                 "<TABLE CELLSPACING=\"10\" CELLPADDING=\"2\">\n<TR>\n".
  8489.               "<TD ALIGN=\"LEFT\">Enter MD5 Value: ".
  8490.               "<INPUT TYPE=\"text\" NAME=\"md5\" SIZE=40 MAXLENGTH=32></TD>\n".
  8491.               "<TD ALIGN=\"LEFT\">".
  8492.               "<INPUT TYPE=\"IMAGE\" SRC=\"pict/but_lookup.jpg\" ALT=\"Ok\" ".
  8493.               "WIDTH=116 HEIGHT=20 BORDER=\"0\">\n".
  8494.               "</TD></TR>\n</TABLE>\n".
  8495.               "</FORM>";
  8496.         }
  8497.     }
  8498.     else {
  8499.         print "Location: <TT>$exclude_db</TT><BR>\n".
  8500.           "ERROR: Database not found<BR>\n";
  8501.     }
  8502.  
  8503. print <<EOF3;
  8504. <HR>
  8505. <CENTER>
  8506. <IMG SRC=\"pict/hashdb_h_nsrl.jpg\" ALT=\"NSRL Database\" BORDER=\"0\">
  8507. </CENTER>
  8508. <P><B>Overview</B><BR>
  8509. These files are known to be <U>good</U> and <U>bad</U>.  It is currently
  8510. difficult to distinguish between known good and known bad and therefore
  8511. the NSRL is no longer used much in Autopsy until a better solution can
  8512. be found.
  8513.  
  8514. EOF3
  8515.  
  8516.     print "<P><B>Details</B><BR>\n";
  8517.     if ($NSRLDB eq "") {
  8518.         print "Location: <TT>Not Configured</TT><BR>\n";
  8519.     }
  8520.     elsif (-e "$NSRLDB") {
  8521.         print "Location: <TT>$NSRLDB</TT><BR>\n";
  8522.         if (-e "${NSRLDB}-md5.idx") {
  8523.             print "Status: MD5 Index File Exists<BR>\n";
  8524.         } else {
  8525.             print "Status: Database has not been MD5 indexed<BR>\n";
  8526.         }
  8527.  
  8528.         # Index Button
  8529.         print 
  8530.           "<P><A HREF=\"$PROGNAME?func=$HASH_INDEX&hash_nsrl=1&$baseargs\">".
  8531.           "<IMG SRC=\"pict/but_indexdb.jpg\" ALT=\"Index DB\" ".
  8532.           "WIDTH=116 HEIGHT=20 BORDER=\"0\">".
  8533.           "</A>\n";
  8534.  
  8535.         # Lookup Button
  8536.         if (-e "${NSRLDB}-md5.idx") {
  8537.             print
  8538.               "<P><B>Lookup</B><BR>".
  8539.               "<FORM ACTION=\"$PROGNAME\" METHOD=\"GET\">".
  8540.               "<INPUT TYPE=\"hidden\" NAME=\"func\" VALUE=\"$HASH_LOOKUP\">\n".
  8541.               "<INPUT TYPE=\"hidden\" NAME=\"hash_nsrl\" VALUE=\"1\">\n".
  8542.               make_hidden().
  8543.                 "<TABLE CELLSPACING=\"10\" CELLPADDING=\"2\">\n<TR>\n".
  8544.               "<TD ALIGN=\"LEFT\">Enter MD5 Value: ".
  8545.               "<INPUT TYPE=\"text\" NAME=\"md5\" SIZE=40 MAXLENGTH=32></TD>\n".
  8546.               "<TD ALIGN=\"LEFT\">".
  8547.               "<INPUT TYPE=\"IMAGE\" SRC=\"pict/but_lookup.jpg\" ".
  8548.               "ALT=\"Lookup\" WIDTH=116 HEIGHT=20 BORDER=0>\n".
  8549.               "</TD></TR>\n</TABLE>\n".
  8550.               "</FORM>";
  8551.         }
  8552.     }
  8553.     else {
  8554.         print "Location: <TT>$NSRLDB</TT><BR>\n".
  8555.           "ERROR: Database not found<BR>\n";
  8556.     }
  8557.  
  8558. print <<EOF4;
  8559.  
  8560. <HR><CENTER>
  8561. <TABLE WIDTH=600 CELLSPACING=\"0\" CELLPADDING=\"2\">
  8562. <TR>
  8563.   <TD ALIGN=CENTER>
  8564.     <A HREF=\"$PROGNAME?func=$IMG_OPEN&$baseargs\">
  8565.     <IMG SRC=\"pict/menu_b_ok.jpg\" ALT=\"Ok\" WIDTH=\"167\" HEIGHT=20 BORDER=\"0\">
  8566.     </A>
  8567.   </TD>
  8568.   <TD ALIGN=CENTER>
  8569.     <A HREF=\"$HELP_URL\" TARGET=\"_blank\">
  8570.     <IMG SRC=\"pict/menu_b_help.jpg\" ALT=\"Help\" 
  8571.     WIDTH=\"167\" HEIGHT=20 BORDER=0>
  8572.     </A>
  8573.   </TD>
  8574. </TR>
  8575. </TABLE>
  8576. EOF4
  8577.  
  8578.     return;
  8579. };
  8580.  
  8581. $funcs[$HASH_INDEX] = sub {
  8582.     print_html_header("Hash Database Indexing");
  8583.  
  8584.     if ((exists $args{'hash_exclude'}) && ($args{'hash_exclude'} == 1) && 
  8585.       ($exclude_db ne "")) {
  8586.         log_host_info ("Exclude Database Re-Indexed");
  8587.         print "<HR><B>Exclude Database Indexing</B><P>\n";
  8588.         hash_index_md5sum($exclude_db);
  8589.     }
  8590.  
  8591.     if ((exists $args{'hash_alert'}) && ($args{'hash_alert'} == 1) && 
  8592.       ($alert_db ne "")) {
  8593.         log_host_info ("Alert Database Re-Indexed");
  8594.         print "<HR><B>Alert Database Indexing</B><P>\n";
  8595.         hash_index_md5sum($alert_db);
  8596.     }
  8597.  
  8598.     if ((exists $args{'hash_nsrl'}) && ($args{'hash_nsrl'} == 1) && 
  8599.       ($NSRLDB ne "")) {
  8600.         log_host_info ("NSRL Database Re-Indexed");
  8601.         print "<HR><B>NSRL Database Indexing</B><P>\n";
  8602.         hash_index_nsrl();
  8603.     }
  8604.  
  8605.     print "<P>Indexing Complete<BR>\n".
  8606.       "<HR><P>\n<A HREF=\"$PROGNAME?func=$HASH_MAIN&$baseargs\">\n".
  8607.       "<IMG SRC=\"pict/menu_b_hashdb.jpg\" WIDTH=\"167\" ".
  8608.       "HEIGHT=20 ALT=\"Hash Databases\" BORDER=\"0\"></A>\n";
  8609.  
  8610.     return;
  8611. };
  8612.  
  8613. # Lookup hashes in database
  8614. $funcs[$HASH_LOOKUP] = sub {
  8615.     print_html_header("Hash Database Lookup");
  8616.  
  8617.     unless ((exists $args{'md5'}) && ($args{'md5'} =~ /^$REG_MD5$/o)) {
  8618.         print_err("Invalid MD5 Argument");
  8619.     }
  8620.     
  8621.     if ((exists $args{'hash_nsrl'}) && ($args{'hash_nsrl'} == 1) && 
  8622.       ($NSRLDB ne "")) {
  8623.         print "<HR><B>NSRL Lookup</B><P>\n";
  8624.  
  8625.         if (-e "$NSRLDB") {
  8626.             local *OUT;
  8627.             exec_pipe (*OUT, 
  8628.               "'${TASKDIR}hfind' '$NSRLDB' $args{'md5'}");
  8629.             print "$_<BR>\n" while (<OUT>);
  8630.             close (OUT);
  8631.             log_host_inv ("NSRL Lookup ($args{'md5'})");
  8632.         }
  8633.         else {
  8634.             print "NSRL Database Missing<BR>\n";
  8635.             log_host_inv ("NSRL Lookup ($args{'md5'}) - Database Missing");
  8636.         }
  8637.     }
  8638.  
  8639.     if ((exists $args{'hash_exclude'}) && ($args{'hash_exclude'} == 1) && 
  8640.       ($exclude_db ne "")) {
  8641.         print "<HR><B>Exclude Database Lookup</B><P>\n";
  8642.  
  8643.         if (-e "$exclude_db") {
  8644.             local *OUT;
  8645.             exec_pipe (*OUT, 
  8646.               "'${TASKDIR}hfind' '$exclude_db' $args{'md5'}");
  8647.             print "$_<BR>\n" while (<OUT>);
  8648.             close (OUT);
  8649.             log_host_inv ("Exclude Database Lookup ($args{'md5'})");
  8650.         }
  8651.         else {
  8652.             print "Exclude Database Missing<BR>\n";
  8653.             log_host_inv ("Exclude Database Lookup ($args{'md5'}) - Database Missing");
  8654.         }
  8655.     }
  8656.  
  8657.     if ((exists $args{'hash_alert'}) && ($args{'hash_alert'} == 1) && 
  8658.       ($alert_db ne "")) {
  8659.         print "<HR><B>Alert Database Lookup</B><P>\n";
  8660.  
  8661.         if (-e "$alert_db") {
  8662.             local *OUT;
  8663.             exec_pipe (*OUT, 
  8664.               "'${TASKDIR}hfind' '$alert_db' $args{'md5'}");
  8665.             print "$_<BR>\n" while (<OUT>);
  8666.             close (OUT);
  8667.             log_host_inv ("Alert Database Lookup ($args{'md5'})");
  8668.         }    
  8669.         else {
  8670.             print "Alert Database Missing<BR>\n";
  8671.             log_host_inv ("Alert Database Lookup ($args{'md5'}) - Database Missing");
  8672.         }
  8673.     }
  8674.  
  8675.     print "<HR><P>\n".
  8676.       "If any of the hash databases need to be re-indexed, use the ".
  8677.       "<U>Hash Database Manager</U><P>".
  8678.       "<A HREF=\"$PROGNAME?func=$HASH_MAIN&$baseargs\" TARGET=\"_blank\">\n".
  8679.       "<IMG SRC=\"pict/menu_b_hashdb.jpg\" WIDTH=\"167\" ".
  8680.       "HEIGHT=20 ALT=\"Hash Databases\" BORDER=\"0\"></A>\n";
  8681.  
  8682.     return 0;
  8683. };
  8684.  
  8685.  
  8686. #########################################################################
  8687. # CELL - Sanitized Environment
  8688. #
  8689.  
  8690. my $CELL_MODE_SANIT = 1;
  8691. my $CELL_MODE_NORM = 2;
  8692.  
  8693. $funcs[$CELL_MAIN] = sub {
  8694.     check_inode('inode'); check_dir(); 
  8695.     my $fname = "$args{'mnt'}$args{'dir'}";
  8696.     print_html_header_frameset("Autopsy Cell");
  8697.  
  8698.     print "<FRAMESET ROWS=\"15%,85%\">\n";        
  8699.  
  8700.     # if a mode was not given, then choose the Sanitized by default
  8701.     $args{'cell_mode'} = $CELL_MODE_SANIT 
  8702.       unless ((exists $args{'cell_mode'}) && ($args{'cell_mode'} =~ /^\d$/));
  8703.  
  8704.     my $url = "&$baseargs&inode=$enc_args{'inode'}&dir=$enc_args{'dir'}&".
  8705.       "cell_mode=$args{'cell_mode'}";
  8706.  
  8707.     print "<FRAME SRC=\"$PROGNAME?func=${CELL_MENU}${url}\">\n".
  8708.       "<FRAME SRC=\"$PROGNAME?func=${CELL_CONT}${url}\">\n".
  8709.       "</FRAMESET>\n";
  8710.  
  8711.     return 0;
  8712. };
  8713.  
  8714. # Print the menu on top.  This allows one to export the file and change modes
  8715. $funcs[$CELL_MENU] = sub {
  8716.     check_inode('inode'); check_dir(); check_cell_mode();
  8717.     print_html_header ("Cell Header");
  8718.  
  8719.     my $cell_mode = $args{'cell_mode'};
  8720.  
  8721.     my $url = "&$baseargs&inode=$enc_args{'inode'}&".
  8722.       "dir=$enc_args{'dir'}";
  8723.  
  8724.     if ($cell_mode == $CELL_MODE_SANIT) {
  8725.  
  8726. print <<EOF1;
  8727. <CENTER>
  8728. This file is currently being viewed in a <B>sanitized environment</B><BR>
  8729. HTML files have been edited to disable scripts and links.  
  8730. Pictures have been replaced by place holders<BR>
  8731.  
  8732. <TABLE WIDTH=300 CELLSPACING=\"0\" CELLPADDING=\"2\">
  8733. <TR>
  8734.   <TD ALIGN=CENTER>
  8735.     <A HREF=\"$PROGNAME?func=$CELL_MAIN$url&cell_mode=$CELL_MODE_NORM\" 
  8736.       TARGET=\"_top\">
  8737.       <IMG SRC=\"pict/sanit_b_norm.jpg\" ALT=\"Normal\" BORDER=\"0\">
  8738.     </A>
  8739.   </TD>
  8740. EOF1
  8741.  
  8742.     }
  8743.  
  8744.     elsif ($cell_mode == $CELL_MODE_NORM) {
  8745. print <<EOF2;
  8746. <CENTER>
  8747. This file is currently being viewed in a <B>normal environment</B><BR>
  8748. HTML files are being viewed without modification.<BR>
  8749.  
  8750. <TABLE WIDTH=300 CELLSPACING=\"0\" CELLPADDING=\"2\">
  8751. <TR>
  8752.   <TD ALIGN=CENTER>
  8753.     <A HREF=\"$PROGNAME?func=$CELL_MAIN$url&cell_mode=$CELL_MODE_SANIT\" 
  8754.       TARGET=\"_top\">
  8755.       <IMG SRC=\"pict/sanit_b_san.jpg\" ALT=\"Sanitized\" BORDER=\"0\">
  8756.     </A>
  8757.   </TD>
  8758. EOF2
  8759.     }
  8760.  
  8761.     # Export the file
  8762.     print "<TD ALIGN=CENTER>\n".
  8763.       "<A HREF=\"$PROGNAME?func=$FIL_SAVE&$url\">".
  8764.       "<IMG SRC=\"pict/but_export.jpg\" ALT=\"export\" BORDER=\"0\" ".
  8765.       "WIDTH=123 HEIGHT=20>".
  8766.       "</A></TD></TR></TABLE>";
  8767.  
  8768.     return;
  8769. };
  8770.  
  8771.  
  8772. # Display safe and common things in the browser (pictures, basic html)
  8773. $funcs[$CELL_CONT] = sub {
  8774.     check_inode('inode'); check_dir(); check_cell_mode();
  8775.  
  8776.     my $inode = get_inode('inode');
  8777.     my $img = get_img('img');
  8778.     my $ftype = get_ftype();
  8779.     my $fname = "$args{'mnt'}$args{'dir'}";
  8780.  
  8781.     # identify what type it is
  8782.     local *OUT;
  8783.     exec_pipe (*OUT,
  8784.       "'${TASKDIR}icat' -f $ftype '$img' $inode | '${TASKDIR}file' -b -");
  8785.     my $file_type = <OUT>;
  8786.     close (OUT);
  8787.  
  8788.     $file_type = "Error getting file type"
  8789.       if ((!defined $file_type) || ($file_type eq ""));
  8790.  
  8791.     if ($file_type =~ /JPEG image data/) {
  8792.         log_host_inv ("$args{'img'}: Viewing $fname ($inode) as JPEG");
  8793.         print "Content-type: image/jpeg${HTTP_NL}${HTTP_NL}";
  8794.     }
  8795.     elsif ($file_type =~ /GIF image data/) {
  8796.         log_host_inv ("$args{'img'}: Viewing $fname ($inode) as GIF");
  8797.         print "Content-type: image/gif${HTTP_NL}${HTTP_NL}";
  8798.     }
  8799.     elsif ($file_type =~ /PNG image data/) {
  8800.         log_host_inv ("$args{'img'}: Viewing $fname ($inode) as PNG");
  8801.         print "Content-type: image/png${HTTP_NL}${HTTP_NL}";
  8802.     }
  8803.     elsif ($file_type =~ /PC bitmap data/) {
  8804.         log_host_inv ("$args{'img'}: Viewing $fname ($inode) as BMP");
  8805.         print "Content-type: image/bmp${HTTP_NL}${HTTP_NL}";
  8806.     }
  8807.     elsif ($file_type =~ /HTML document text/) {
  8808.         log_host_inv ("$args{'img'}: Viewing $fname ($inode) as HTML");
  8809.         print "Content-type: text/html${HTTP_NL}${HTTP_NL}";
  8810.     }
  8811.     else {
  8812.         log_host_inv ("$args{'img'}: Unknown format of inode $inode ");
  8813.         print_html_header("");
  8814.         print "Unknown File Type for Viewing: $file_type\n";
  8815.         return 1;
  8816.     }
  8817.  
  8818.     local *OUT;
  8819.     exec_pipe (*OUT, 
  8820.       "'${TASKDIR}icat' -f $ftype '$img' $inode");
  8821.  
  8822.     while (<OUT>) {
  8823.         # Parse out bad "stuff"
  8824.         if (($file_type =~ /HTML document text/) && 
  8825.           ($args{'cell_mode'} == $CELL_MODE_SANIT)) {
  8826.             $_ =~ s/\bSRC=/SRC=$SANITIZE_TAG\?/ig;
  8827.             $_ =~ s/\bHREF=/HREF=$SANITIZE_TAG\?/ig;
  8828.             $_ =~ s/<script/<$SANITIZE_TAG-script/ig;
  8829.             $_ =~ s/\bBACKGROUND=/BACKGROUND=$SANITIZE_TAG\?/ig;
  8830.         }
  8831.         print "$_";
  8832.     }
  8833.     close (OUT);
  8834.     return 0;
  8835. };
  8836.  
  8837.  
  8838. ##### Begin main ############
  8839.  
  8840. sub autopsy_main {
  8841.     # Parse arguments
  8842.     my $args = shift;
  8843.     foreach my $nam_val (split (/&/, $args)) {
  8844.         my ($name, $value) = split (/=/, $nam_val);
  8845.         if (defined $value) {
  8846.             my $dec_name = url_decode($name);
  8847.             $enc_args{$dec_name} = $value;
  8848.             $args{$dec_name} = url_decode($value);
  8849.         }
  8850.     }
  8851.  
  8852.     if (exists $args{'case'}) {
  8853.         check_case();
  8854.         $case_dir = "${LOCKDIR}/".get_case()."/";
  8855.  
  8856.         if (exists $args{'host'}) {
  8857.             check_host();
  8858.             $host_dir = "$case_dir".get_host()."/";
  8859.             read_host_config() if ($args{'func'} != $HOST_ADD_DOIT);
  8860.         }
  8861.     }
  8862.  
  8863.  
  8864.     if (check_func()) {
  8865.         # No func value was given or an invalid one was given
  8866.  
  8867.         if (exists $args{'func'}) {
  8868.             print_html_header();
  8869.             print "Invalid func argument (positive numbers only)<BR>\n";
  8870.         }
  8871.         else {
  8872.             # give the main menu if no func value was given
  8873.             & {$funcs[$WELCOME]};
  8874.         }
  8875.  
  8876.         print "${HTTP_NL}${HTTP_NL}";
  8877.         return 0;
  8878.     }
  8879.  
  8880.     # These functions do not need any arguments
  8881.     if (
  8882.         ($args{'func'} == $WELCOME) || 
  8883.         ($args{'func'} == $BLANK) || 
  8884.         (($args{'func'} >= $CASE_LO) && ($args{'func'} <= $CASE_HI)) ) {
  8885.  
  8886.     }
  8887.  
  8888.     # need the case value
  8889.     elsif (($args{'func'} >= $HOST_LO) && ($args{'func'} <= $HOST_HI)) {
  8890.         check_case();
  8891.     }
  8892.  
  8893.     # need the case and host
  8894.     elsif ( (($args{'func'} >= $IMG_LO) && ($args{'func'} <= $IMG_HI)) ||
  8895.       (($args{'func'} >= $NOTES_LO) && ($args{'func'} <= $NOTES_HI)) ||
  8896.       (($args{'func'} >= $TL_LO) && ($args{'func'} <= $TL_HI))  ||
  8897.       (($args{'func'} >= $HASH_LO) && ($args{'func'} <= $HASH_HI))  ||
  8898.       ($args{'func'} == $INT_LIST)  || ($args{'func'} == $INT_LIST_FR)) {
  8899.         check_case();
  8900.         check_inv();
  8901.         check_host();
  8902.     }
  8903.     # Int doesn't need the ftype because it gets messed up with body and
  8904.     # timelines and such
  8905.     elsif(($args{'func'} >= $INT_LO) && ($args{'func'} <= $INT_HI)) {
  8906.         check_case();
  8907.         check_inv();
  8908.         check_host();
  8909.         check_img('img'); 
  8910.     }
  8911.     # FIL, BLK, SRCH, INO, FS, INT, CASE
  8912.     else {
  8913.         check_case();
  8914.         check_inv();
  8915.         check_host();
  8916.         check_img('img'); 
  8917.         check_ftype();
  8918.  
  8919.     }
  8920.  
  8921.     # special case of the strings and dls output
  8922.     if ((exists $img2ftype{$args{'img'}}) && 
  8923.       (($img2ftype{$args{'img'}} eq "strings") || 
  8924.       ($img2ftype{$args{'img'}} eq "raw") || 
  8925.       ($img2ftype{$args{'img'}} eq "swap") || 
  8926.       ($img2ftype{$args{'img'}} eq "dls")) ) {
  8927.  
  8928.         unless (
  8929.           (($args{'func'} >= $SRCH_LO) && ($args{'func'} <= $SRCH_HI)) ||
  8930.           (($args{'func'} >= $BLK_LO) && ($args{'func'} <= $BLK_HI)) ||
  8931.           (($args{'func'} >= $NOTES_LO) && ($args{'func'} <= $NOTES_HI)) ||
  8932.           (($args{'func'} >= $MAIN_LO) && ($args{'func'} <= $MAIN_HI)) ||
  8933.           (($args{'func'} >= $IMG_LO) && ($args{'func'} <= $IMG_HI)) ||
  8934.           ($args{'func'} == $BLANK) ||
  8935.           (($args{'func'} >= $INT_LO) && ($args{'func'} <= $INT_HI)) ) {
  8936.  
  8937.             print_html_header();
  8938.             print "Error: You selected a non-file system image ".
  8939.               "that can only be used for Searching and data unit browsing<BR>\n";
  8940.     
  8941.             make_baseargs();
  8942.  
  8943.             print "<BR><A HREF=\"$PROGNAME?$baseargs&func=$IMG_OPEN\"".
  8944.               "TARGET=\"_top\">Return to Host Manager</A><BR>";
  8945.  
  8946.             exit 1;
  8947.         }
  8948.         $enc_args{'mnt'} = "";
  8949.     }
  8950.     elsif ((exists $img2ftype{$args{'img'}}) && 
  8951.       (($img2ftype{$args{'img'}} eq "body") || 
  8952.       ($img2ftype{$args{'img'}} eq "timeline")) ) {
  8953.  
  8954.         # this is just a dummy section to exclude the timeline files
  8955.         # from the next check of mounting point 
  8956.     }
  8957.  
  8958.     #  if the mounting point was not found, then look it up
  8959.     elsif ((exists $args{'img'}) && (!exists $args{'mnt'})) {
  8960.         unless (exists $img2mnt{$args{'img'}}) {
  8961.             print_html_header();
  8962.             print "Mounting point not found: $args{'img'}\n";
  8963.             exit 1;
  8964.         }
  8965.         $args{'mnt'} = $img2mnt{$args{'img'}};
  8966.         $enc_args{'mnt'} = url_encode($img2mnt{$args{'img'}});
  8967.     }
  8968.  
  8969.     make_baseargs();
  8970.     & {$funcs[$args{'func'}]};
  8971.  
  8972.     print "\n</BODY>\n" if ($is_body == 1);
  8973.     print "\n</HTML>\n" if ($is_html == 1);
  8974.  
  8975.     print "${HTTP_NL}${HTTP_NL}";
  8976.     return 0;
  8977. }
  8978.  
  8979. # This assumes that the checking of the types has been done and this just
  8980. # makes a string of the key values if they exist
  8981. #
  8982. #  case
  8983. #  host
  8984. #  img
  8985.  
  8986. # Must add & after
  8987. sub make_baseargs {
  8988.     $baseargs = "";
  8989.  
  8990.     $baseargs .= "case=$enc_args{'case'}&" 
  8991.       if ((exists $enc_args{'case'}) && ($enc_args{'case'} ne ""));
  8992.     $baseargs .= "host=$enc_args{'host'}&" 
  8993.       if ((exists $enc_args{'host'}) && ($enc_args{'host'} ne ""));
  8994.     $baseargs .= "inv=$enc_args{'inv'}&" 
  8995.       if ((exists $enc_args{'inv'}) && ($enc_args{'inv'} ne ""));
  8996.     
  8997.     $baseargs_noimg = $baseargs;
  8998.  
  8999.     $baseargs .= "img=$enc_args{'img'}&" 
  9000.       if ((exists $enc_args{'img'}) && ($enc_args{'img'} ne ""));
  9001.     $baseargs .= "ftype=$enc_args{'ftype'}&" 
  9002.       if ((exists $enc_args{'ftype'}) && ($enc_args{'ftype'} ne ""));
  9003.     $baseargs .= "mnt=$enc_args{'mnt'}&" 
  9004.       if ((exists $enc_args{'mnt'}) && ($enc_args{'mnt'} ne ""));
  9005.  
  9006.     # remove the final '&'
  9007.     $baseargs_noimg = $1 if ($baseargs_noimg =~ /^(.*?)&$/);
  9008.     $baseargs = $1 if ($baseargs =~ /^(.*?)&$/);
  9009.  
  9010.     return;
  9011. };
  9012.  
  9013.  
  9014.  
  9015. # Does not do mnt or img
  9016. sub make_hidden {
  9017.     my $str = "";
  9018.  
  9019.     $str .= "<INPUT TYPE=\"hidden\" NAME=\"host\" VALUE=\"$args{'host'}\">\n"
  9020.       if ((exists $args{'host'}) && ($args{'host'} ne ""));
  9021.  
  9022.     $str .= "<INPUT TYPE=\"hidden\" NAME=\"case\" VALUE=\"$args{'case'}\">\n"
  9023.       if ((exists $args{'case'}) && ($args{'case'} ne ""));
  9024.  
  9025.     $str .= "<INPUT TYPE=\"hidden\" NAME=\"inv\" VALUE=\"$args{'inv'}\">\n"
  9026.       if ((exists $args{'inv'}) && ($args{'inv'} ne ""));
  9027.  
  9028.     return $str;
  9029. }
  9030.  
  9031.  
  9032. #########################################################################3
  9033. #
  9034. # Config Files
  9035. #
  9036. #
  9037.  
  9038. # Return a hash of the keywords and the values
  9039. sub read_case_config {
  9040.     my $case;
  9041.  
  9042.     if (scalar (@_) == 1) {
  9043.         $case = shift;
  9044.     } else {
  9045.         $case = get_case();
  9046.     }
  9047.  
  9048.     my $fname = case_config_fname($case);
  9049.  
  9050.     open CONFIG, "<$fname" 
  9051.       or die "Can't open case config file ($fname)";
  9052.  
  9053.     my %vals;
  9054.  
  9055.     while (<CONFIG>) {
  9056.         next if ((/^\#/) || (/^\s+$/));
  9057.         s/^\s+//;
  9058.         s/\s+$//;
  9059.         $vals{$1} = $2 if (/^(\S+)\s+(.*)$/);
  9060.     }
  9061.     close (CONFIG);
  9062.  
  9063.     $vals{'desc'} = "None Provided" unless (exists $vals{'desc'});
  9064.     $vals{'created'} = "unknown" unless (exists $vals{'created'});
  9065.  
  9066.     $vals{'images'} = $IMGDIR unless (exists $vals{'images'});
  9067.     $vals{'data'} = $DATADIR unless (exists $vals{'data'});
  9068.     $vals{'log'} = $LOGDIR unless (exists $vals{'log'});
  9069.     $vals{'reports'} = $REPDIR unless (exists $vals{'reports'});
  9070.  
  9071.     return %vals;
  9072. };
  9073.  
  9074.  
  9075. # reads host config file and sets global hash values for images and other
  9076. sub read_host_config {
  9077.     my $host = get_host();
  9078.  
  9079.     my $cfile = host_config_fname();
  9080.  
  9081.     unless (open (FILE, $cfile)) { 
  9082.         print_check_err("Error opening $cfile");
  9083.     }
  9084.  
  9085.     %img2mnt = ();
  9086.     %img2ftype = ();
  9087.     %mod2img = ();
  9088.     %img2str = ();
  9089.     %img2dls = ();
  9090.     
  9091.     $tz = "";
  9092.     $ts = 0;
  9093.     $host_desc = "";
  9094.     $exclude_db = "";
  9095.     $alert_db = "";
  9096.  
  9097.     while (<FILE>) {
  9098.         next if ((/^\#/) || (/^\s+$/));
  9099.  
  9100.         # remove whitespace
  9101.         s/^\s+//;      
  9102.         s/\s+$//;
  9103.  
  9104.         # normal file system image entry
  9105.         #
  9106.         # 'image    images/hda1.dd        openbsd        /usr
  9107.         if (/^image\s+($REG_IMG)\s+([\w\-]+)\s+([\w\-\_\.\/:\\]+)$/o) {
  9108.             my $i = $1;
  9109.             my $t = $2;
  9110.             my $r = $3;
  9111.  
  9112.             unless (defined $root_inode{$t}) {
  9113.                 print_check_err("Error: unknown type: $t in host config: $.".
  9114.                   "<BR>Edit the file and refresh your browser");
  9115.             }
  9116.  
  9117.             unless ((-e "${host_dir}${i}") || (-l "${host_dir}${i}")) {
  9118.                 print_check_err("Error: image in ${host}.host:$. not found: ".
  9119.                   "${host_dir}${i}<BR>Edit the config file and refresh your browser".
  9120.                   "<BR>(Or your version of Perl does not support large files)");
  9121.             }
  9122.  
  9123.             $img2ftype{$i} = $t;
  9124.  
  9125.             # Add trailing / to original mount point if needed
  9126.             if (($r !~ /.*?\/$/) && ($r !~ /.*?\\$/)) {
  9127.                 $r .= '/';
  9128.             }
  9129.             $img2mnt{$i} = $r;
  9130.         }
  9131.         # entry for a strings or dls file
  9132.         #
  9133.         # strings     data/hda1.str        images/hda1.dd
  9134.         elsif (/^strings\s+($REG_IMG)\s+($REG_IMG)$/o) {
  9135.             my $i = $1;
  9136.             my $o = $2;
  9137.  
  9138.             unless ((-e "${host_dir}${i}") || (-l "${host_dir}${i}")) {
  9139.                 print_check_err("Error: strings file not found: ".
  9140.                   "${host_dir}${i}<BR>Edit host config and refresh your browser");
  9141.             }
  9142.  
  9143.             unless ((-e "${host_dir}${o}") || (-l "${host_dir}${o}")) {
  9144.                 print_check_err("Error: strings original not found: ".
  9145.                   "${host_dir}${o}<BR>Edit host config and refresh your browser");
  9146.             }
  9147.  
  9148.             $img2ftype{$i} = "strings";
  9149.             $mod2img{$i} = $o;
  9150.             $img2str{$o} = $i;
  9151.         }
  9152.  
  9153.         # dls entry
  9154.         # dls data/image.dls    [images/image.dd]
  9155.         elsif (/^dls\s+($REG_IMG)\s*($REG_IMG)?$/o) {
  9156.             my $dls = $1;
  9157.  
  9158.             unless ((-e "${host_dir}${dls}") || (-l "${host_dir}${dls}")) {
  9159.                 print_check_err("Error: dls file not found: ".
  9160.                   "${host_dir}${dls}<BR>Edit host config and refresh your browser");
  9161.             }
  9162.      
  9163.             $img2ftype{$dls} = "dls";
  9164.     
  9165.             if (defined $2) {
  9166.                 my $dd = $2;
  9167.                 
  9168.                 unless ((-e "${host_dir}${dd}") || (-l "${host_dir}${dd}")) {
  9169.                     print_check_err("Error: dls original not found: ".
  9170.                       "${host_dir}${dd}<BR>Edit host config and refresh your browser");
  9171.                 }
  9172.  
  9173.                 $mod2img{$dls} = $dd;
  9174.                 $img2dls{$dd} = $dls;
  9175.             }
  9176.  
  9177.         }
  9178.         # swap
  9179.         # swap        images/hda3.dd        
  9180.         elsif (/^swap\s+($REG_IMG)\s*$/o) {
  9181.             my $i = $1;
  9182.  
  9183.             unless ((-e "${host_dir}${i}") || (-l "${host_dir}${i}")) {
  9184.                 print_check_err("Error: swap in ${host}.host:$. not found: ".
  9185.                   "${host_dir}${i}<BR>Edit the config file and refresh your browser".
  9186.                   "<BR>(Or your version of Perl does not support large files)");
  9187.             }
  9188.  
  9189.             $img2ftype{$i} = "swap";
  9190.         }
  9191.         # raw
  9192.         # raw    images/hda3.dd        
  9193.         elsif (/^raw\s+($REG_IMG)\s*$/o) {
  9194.             my $i = $1;
  9195.  
  9196.             unless ((-e "${host_dir}${i}") || (-l "${host_dir}${i}")) {
  9197.                 print_check_err("Error: raw in ${host}.host:$. not found: ".
  9198.                   "${host_dir}${i}<BR>Edit the config file and refresh your browser".
  9199.                   "<BR>(Or your version of Perl does not support large files)");
  9200.             }
  9201.  
  9202.             $img2ftype{$i} = "raw";
  9203.         }
  9204.  
  9205.         # body data/body.txt
  9206.         elsif (/^body\s+($REG_IMG)$/o) {
  9207.             my $i = $1;
  9208.  
  9209.             unless ((-e "${host_dir}${i}") || (-l "${host_dir}${i}")) {
  9210.                 print_check_err("Error: body file not found: ".
  9211.                   "${host_dir}${i}<BR>Edit host config and refresh your browser");
  9212.             }
  9213.  
  9214.             $img2ftype{$i} = "body";
  9215.         }
  9216.         # timeline data/timeline.txt
  9217.         elsif (/^timeline\s+($REG_IMG)$/o) {
  9218.             my $i = $1;
  9219.  
  9220.             unless ((-e "${host_dir}${i}") || (-l "${host_dir}${i}")) {
  9221.                 print_check_err("Error: timeline file not found: ".
  9222.                   "${host_dir}${i}<BR>Edit host config and refresh your browser");
  9223.             }
  9224.  
  9225.             $img2ftype{$i} = "timeline";
  9226.         }
  9227.         # timezone XYZ
  9228.         elsif (/^timezone\s+($REG_ZONE1)$/o) {
  9229.             $tz = $1;    
  9230.         }
  9231.         # timeskew XYZ
  9232.         elsif (/^timeskew\s+($REG_SKEW)$/o) {
  9233.             $ts = $1;    
  9234.         }
  9235.         # desc XYZ
  9236.         elsif (/^desc\s+(.*)$/) {
  9237.             $host_desc = $1;    
  9238.         }
  9239.         # hash databases
  9240.         elsif (/^alert_db\s+'(.*)'$/) {
  9241.             $alert_db = $1;
  9242.         }
  9243.         elsif (/^exclude_db\s+'(.*)'$/) {
  9244.             $exclude_db = $1;
  9245.         }
  9246.         else {
  9247.             my $msg = "Error: invalid entry in $cfile:$.".
  9248.               "<BR>\n".
  9249.               "image    path    fs_type        mnt_point<BR>\n".
  9250.               "strings    path    orig_img<BR>\n".
  9251.               "dls        path    [orig_img]<BR>\n".
  9252.               "body        path<BR>\n".
  9253.               "timeline    path<BR>\n".
  9254.               "timezone    TZ<BR>\n".
  9255.               "desc        DESCRIPTION<BR>\n";
  9256.             print_check_err($msg);
  9257.         }
  9258.     }
  9259.     close (FILE);
  9260.  
  9261.     if ($tz eq "") {
  9262.         print_check_err ("Missing Timezone Variable in Host Config");
  9263.     }
  9264. }
  9265.  
  9266.  
  9267. # Remove any entries with the given image name from the host config
  9268. # and add a new one
  9269. #
  9270. # If type is "", then nothing is written, just removed
  9271. sub update_host_config {
  9272.     my $type = shift;
  9273.     my $img = shift;
  9274.     my $ref = shift;
  9275.  
  9276.     my $read = host_config_fname();
  9277.     my $write = $read."-".rand();
  9278.  
  9279.     unless (open (READ, "<$read")) {
  9280.         print "Error opening $read";
  9281.         exit (1);
  9282.     }
  9283.  
  9284.     unless (open (WRITE, ">$write")) {
  9285.         print "Error opening $write";
  9286.         exit (1);
  9287.     }
  9288.  
  9289.     while (<READ>) {
  9290.         s/^\s+//;
  9291.         s/\s+$//;
  9292.         print WRITE "$_\n" unless ((/^(\w+)\s+($REG_IMG)/o) && ($2 eq $img)
  9293.           && ($1 ne 'desc') && ($1 ne 'timezone'));
  9294.     }
  9295.  
  9296.     if ($type ne "") {
  9297.         if (defined $ref) {
  9298.             print WRITE "$type  $img    $ref\n";
  9299.         } else {
  9300.             print WRITE "$type  $img\n";
  9301.         }
  9302.     }
  9303.  
  9304.     close (READ);
  9305.     close (WRITE);
  9306.     rename $write, $read;
  9307.  
  9308.     return;
  9309. };
  9310.  
  9311.  
  9312.  
  9313. # Given the image and md5, it is saved to the MD5.txt file and any other
  9314. # references to the image are removed
  9315. #
  9316. # if $md5 is "", then nothing is written
  9317. sub update_md5 {
  9318.     my $img = shift;
  9319.     my $md5 = shift;
  9320.     $md5 =~ tr/[a-f]/[A-F]/;
  9321.  
  9322.     (my $img_dir) = split (/\//,$img);
  9323.     my $read = "${host_dir}/$img_dir/${MD5_FILE}";
  9324.     my $write = $read."-".rand();
  9325.     
  9326.     unless (open (WRITE, ">$write")) {
  9327.         print "Error opening $write";
  9328.         exit (1);
  9329.     }
  9330.  
  9331.     if (-e "$read") {
  9332.         unless (open (READ, "<$read")) {
  9333.             print "Error opening $read";
  9334.             exit (1);
  9335.         }
  9336.  
  9337.         while (<READ>) {
  9338.             s/^\s+//;
  9339.             s/\s+$//;
  9340.             print WRITE "$_\n" unless ((/^$REG_MD5\s+($REG_IMG)/o) && ($1 eq $img));
  9341.         }
  9342.         close (READ);
  9343.     }
  9344.  
  9345.     print WRITE "$md5   $img\n" if ($md5 ne "");
  9346.  
  9347.     close (WRITE);
  9348.  
  9349.     rename $write, $read;
  9350.     return;
  9351. }
  9352.  
  9353.  
  9354.  
  9355.  
  9356.  
  9357. # Write the login name to the investigators file
  9358. sub write_invest {
  9359.     my $name = shift;
  9360.     my $fname = investig_fname();
  9361.     open INVES, ">>$fname" or die "Can't open investigators file: $fname";
  9362.     if ($name =~ /^$REG_INVESTIG$/o) {
  9363.         print INVES "$name\n";
  9364.     } else {
  9365.         print_err ("Invalid investigator: $name");
  9366.     }
  9367.     close (INVES);
  9368. }
  9369.  
  9370.  
  9371. # Read the investigators file and return a sorted list
  9372. sub read_invest {
  9373.     my $fname = investig_fname();
  9374.     open INVES, "<$fname" or return;
  9375.  
  9376.     my @investigs;
  9377.     while (<INVES>) {
  9378.         chomp;
  9379.         s/^\s+//;
  9380.         s/\s+$//;
  9381.         push @investigs, $_
  9382.           if (/^$REG_INVESTIG$/o);
  9383.     }
  9384.     close (INVES);
  9385.     sort {lc($a) cmp lc($b)}  @investigs;
  9386. }
  9387.  
  9388.  
  9389. #### END OF MAIN ####
  9390.  
  9391.  
  9392. # if no args are passed, return case config using args{'case'},
  9393. # else use the case value passed
  9394. #
  9395. # Case config:
  9396. # In case directory with case_name.case
  9397. sub case_config_fname {
  9398.     if (scalar (@_) == 1) {
  9399.         my $c = shift;
  9400.         return "${LOCKDIR}$c/case.aut";
  9401.     } else {
  9402.         return "${LOCKDIR}$args{'case'}/case.aut";
  9403.     }
  9404. }
  9405.  
  9406. # Case log
  9407. # In case directory with case_name.log
  9408. sub case_log_fname {
  9409.     return "${case_dir}/case.log";
  9410. }
  9411.  
  9412. # File of investigators name in list
  9413. sub investig_fname {
  9414.     return "${case_dir}/investigators.txt";
  9415. }
  9416.  
  9417.  
  9418. sub investig_notes_fname {
  9419.     return "${host_dir}/logs/".$args{'inv'}.".notes";
  9420. }
  9421.  
  9422. sub investig_seq_notes_fname {
  9423.     return "${host_dir}/logs/".$args{'inv'}.".seq.notes";
  9424. }
  9425.  
  9426. sub investig_log_fname {
  9427.     return "${host_dir}/$LOGDIR/$args{'inv'}.log";
  9428. }
  9429.  
  9430. sub investig_exec_log_fname {
  9431.     return "${host_dir}/$LOGDIR/$args{'inv'}.exec.log";
  9432. }
  9433.  
  9434. sub host_log_fname {
  9435.     return "${host_dir}/$LOGDIR/host.log";
  9436. }
  9437.  
  9438.  
  9439. # if no args are passed, return host config using args{'host'},
  9440. # else use the host value passed
  9441. sub host_config_fname {
  9442.     if (scalar (@_) == 1) {
  9443.         my $h = shift;
  9444.         return "${case_dir}$h/host.aut";
  9445.     } else {
  9446.         return "${host_dir}host.aut";
  9447.     }
  9448. }
  9449. ###################### COMMAND WRAPPERS ######################
  9450.  
  9451. # exec_pipe(HANDLE, CMD);
  9452. sub exec_pipe {
  9453.     my $handle = shift(@_);
  9454.     my $cmd = shift(@_);
  9455.  
  9456.     die "Can't open pipe for exec_pipe" unless 
  9457.       defined(my $pid = open ($handle , "-|") );
  9458.  
  9459.     if ($pid) {
  9460.         # this sucks, but for some reason the buffers don't empty if
  9461.         # this isn't there and the output is missing sometimes
  9462.         sleep(1);
  9463.         return $handle;
  9464.     } else {
  9465.         $| = 1;
  9466.         log_host_inv_exec ("$cmd");
  9467.         exec("$cmd") or die "Can't exec program: $!";
  9468.     }
  9469. }
  9470.  
  9471. sub exec_sys {
  9472.  
  9473.     my $cmd = shift(@_);
  9474.     log_host_inv_exec ("$cmd");
  9475.     system ($cmd);
  9476.     return; 
  9477. }
  9478.  
  9479. ###################### INPUT CHECKS ######################
  9480.  
  9481.  
  9482. #
  9483. # Arguments
  9484. #
  9485. sub check_func {
  9486.     if ((!exists $args{'func'}) || ($args{'func'} !~ /^\d+$/) ||
  9487.        (!(defined $funcs[$args{'func'}])) )  {
  9488.         return 1;
  9489.     }
  9490.     return 0;
  9491. }
  9492.  
  9493. # We don't allow much for the image because this is an argument to
  9494. # the TASK programs.  We keep these files only in one
  9495. # directory and for easy/simple security only allow basic names
  9496. # Symbolic links are allowed if these simple names are not desired
  9497. #
  9498. # Allowed values are A-Za-z0-9_-.
  9499. sub check_img {
  9500.     my $img = shift;
  9501.  
  9502.     if (!exists $args{$img}) {
  9503.         print_check_err ("Missing image ($img) argument");
  9504.     } 
  9505.     elsif ($args{$img} =~ /^$REG_IMG$/o) {
  9506.         # Check for its actual existence
  9507.  
  9508.         print_check_err("Missing image in host dir ($img): $args{$img}")
  9509.           unless ((-e "${host_dir}$args{$img}") 
  9510.           || (-l "${host_dir}$args{$img}"));
  9511.  
  9512.         print_check_err("Invalid directory in image name")
  9513.           if (($args{$img} =~ /^\//) || ($args{$img} =~ /^\.\./));
  9514.     }
  9515.     else {
  9516.         print_check_err ("Invalid image ($img) value (only letters, ".
  9517.           "numbers,-,.,_) [$args{$img}]");
  9518.     }
  9519.  
  9520.     return 0;
  9521. }
  9522.  
  9523.  
  9524. # Return the full path of the image
  9525. sub get_img {
  9526.     my $img_cat = shift;
  9527.     if ($args{$img_cat} =~ /^($REG_IMG)$/o) {
  9528.         return "${host_dir}$1";
  9529.     }
  9530.     print_err("Invalid Image");
  9531. }
  9532.  
  9533.  
  9534. # img_path is used when adding images - it is the full path to the 
  9535. # non-evidence locker copy of the image
  9536. sub check_img_path {
  9537.     if (!exists $args{'img_path'}) {
  9538.         print_check_err ("Missing image (img_path) argument");
  9539.     } 
  9540.     elsif ($args{'img_path'} =~ /^$REG_IMG_PATH$/o) {
  9541.         # Check for its actual existence
  9542.  
  9543.         print_check_err("Image not found at $args{'img_path'}")
  9544.           unless ((-e "$args{'img_path'}") 
  9545.           || (-l "$args{'img_path'}"));
  9546.     }
  9547.     else {
  9548.         print_check_err ("Invalid image path (only letters, ".
  9549.           "numbers,-,.,_/ and start with /) [$args{'img_path'}]");
  9550.     }
  9551.  
  9552.     return 0;
  9553. }
  9554.  
  9555. sub get_img_path {
  9556.     if ($args{'img_path'} =~ /^($REG_IMG_PATH)$/o) {
  9557.         return "$1";
  9558.     }
  9559.     print_err("Invalid Image Path");
  9560. }
  9561.  
  9562.  
  9563. # Case name
  9564. sub check_case {
  9565.     unless (exists $args{'case'}) {
  9566.         print_check_err ("Missing case argument");
  9567.     } 
  9568.     unless ($args{'case'} =~ /^$REG_CASE$/o) {
  9569.         print_check_err ("Invalid case value (letters, num, and symbols only");
  9570.     }
  9571.     return 0;
  9572. }
  9573.  
  9574. sub get_case {
  9575.     if ($args{'case'} =~ /^($REG_CASE)$/o) {
  9576.         return $1;
  9577.     }
  9578.     print_err("Invalid Case Name");
  9579. }
  9580.  
  9581. # Host name
  9582. sub check_host {
  9583.     unless (exists $args{'host'}) {
  9584.         print_check_err ("Missing host argument");
  9585.     } 
  9586.     unless ($args{'host'} =~ /^$REG_HOST$/o) {
  9587.         print_check_err ("Invalid host value");
  9588.     }
  9589.     return 0;
  9590. }
  9591.  
  9592. sub get_host {
  9593.     if ($args{'host'} =~ /^($REG_HOST)$/o) {
  9594.         return $1;
  9595.     }
  9596.     print_err("Invalid Host");
  9597. }
  9598.  
  9599.  
  9600. sub check_inv {
  9601.     unless (exists $args{'inv'}) {
  9602.         print_check_err ("Missing inv argument");
  9603.     } 
  9604.     unless ($args{'inv'} =~ /^$REG_INVESTIG$/o) {
  9605.         print_check_err ("Invalid inv value (letters, num, and symbols only");
  9606.     }
  9607.     return 0;
  9608. }
  9609.  
  9610. sub get_inv {
  9611.     if ($args{'inv'} =~ /^($REG_INVESTIG)$/o) {
  9612.         return $1;
  9613.     }
  9614.     print_err("Invalid Investigator");
  9615. }
  9616.  
  9617.  
  9618.  
  9619. sub check_fname {
  9620.     unless (exists $args{'fname'}) {
  9621.         print_check_err ("Missing fname argument");
  9622.     } 
  9623.     unless ($args{'fname'} =~ /^$REG_FNAME$/o) {
  9624.         print_check_err ("Invalid fname value (only letters, ".
  9625.           "numbers,-,., and _)");
  9626.     }
  9627.     return 0;
  9628. }
  9629.  
  9630. sub get_fname {
  9631.     if ($args{'fname'} =~ /^($REG_FNAME)$/o) {
  9632.         return "${host_dir}${DATADIR}/$1";
  9633.     }
  9634.     print_err("Invalid File Name");
  9635. }
  9636.  
  9637.  
  9638. # Return the relative fname
  9639. sub get_fname_rel {
  9640.     if ($args{'fname'} =~ /^($REG_FNAME)$/o) {
  9641.         return "$DATADIR/$1";
  9642.     }
  9643.     print_err("Invalid Relative File Name");
  9644. }
  9645.  
  9646. sub check_body {
  9647.     unless (exists $args{'body'}) {
  9648.         print_check_err ("Missing body argument");
  9649.     } 
  9650.     unless ($args{'body'} =~ /^$REG_BODY$/o) {
  9651.         print_check_err ("Invalid body value (only letters, ".
  9652.           "numbers,-,., and _)");
  9653.     }
  9654.     return 0;
  9655. }
  9656.  
  9657. sub get_body {
  9658.     if ($args{'body'} =~ /^($REG_BODY)$/o) {
  9659.         return "${host_dir}${DATADIR}/$1";
  9660.     }
  9661.     print_err("Invalid Body");
  9662. }
  9663.  
  9664. sub check_tl {
  9665.     if (!exists $args{'tl'}) {
  9666.         print_check_err ("Missing timeline argument");
  9667.     } 
  9668.     elsif ($args{'tl'} =~ /^($REG_TL)$/o) {
  9669.  
  9670.         # Check for its actual existence
  9671.         unless ((-e "${host_dir}${DATADIR}/$1") || 
  9672.           (-l "${host_dir}${DATADIR}/$1")) {
  9673.             print_check_err("Missing timeline: ${host_dir}${DATADIR}/$1");
  9674.         }
  9675.     }
  9676.     else {
  9677.         print_check_err ("Invalid timeline value (only letters, ".
  9678.           "numbers,-,., and _)");
  9679.     }
  9680.     return 0;
  9681. }
  9682.  
  9683. sub get_tl {
  9684.     if ($args{'tl'} =~ /^($REG_TL)$/o) {
  9685.         return "${host_dir}${DATADIR}/$1";
  9686.     }
  9687.     print_err("Invalid Timeline");
  9688. }
  9689.  
  9690. sub check_fname_mode {
  9691.     if (!exists $args{'fname_mode'}) {
  9692.         print_check_err ("Missing fname_mode argument");
  9693.     } 
  9694.     unless ($args{'fname_mode'} =~ /^\d+$/) {
  9695.         print_check_err ("invalid mode: numbers only");
  9696.     }
  9697.     return 0;
  9698. }
  9699.  
  9700.  
  9701. sub get_sorter_dir {
  9702.     if ($args{'img'} =~ /^.*?\/(.*)$/) {
  9703.         return "${host_dir}${DATADIR}/sorter-$1/";
  9704.     }
  9705.     print_err("Invalid Sorter Directory");
  9706. }
  9707.  
  9708. sub get_sorter_graphics_dir {
  9709.     if ($args{'img'} =~ /^.*?\/(.*)$/) {
  9710.         return "${host_dir}${DATADIR}/sorter-graphics-$1/";
  9711.     }
  9712.     print_err("Invalid Sorter Graphics Directory");
  9713. }
  9714.  
  9715.  
  9716. sub check_dir {
  9717.     if ((!exists $args{'dir'}) ||
  9718.       ($args{'dir'} =~ /\/\.\.\//) ||
  9719.       ($args{'dir'} =~ /\;/) ) {
  9720.         print_check_err("Invalid dir argument (valid file path only)");
  9721.     }
  9722.     return 0;
  9723. }
  9724.  
  9725. sub get_dir {
  9726.     if ($args{'dir'} =~ /([^;]*)/o) {
  9727.         return $1;
  9728.     }
  9729.     print_err("Invalid Directory");
  9730. }
  9731.  
  9732. sub check_mnt {
  9733.     my $ftype = get_ftype();
  9734.     if (($ftype eq "dls") || ($ftype eq "swap") || ($ftype eq "raw")) {
  9735.         $args{'mnt'} = $ftype;
  9736.     }
  9737.     elsif (!exists $args{'mnt'}) {
  9738.         print_check_err("Missing mount point argument");
  9739.     }
  9740.     elsif ($args{'mnt'} =~ /\/\.\.\//) {
  9741.         print_check_err("Invalid mount point argument (valid file path only)");
  9742.     }
  9743.     unless ($args{'mnt'} =~ /^$REG_MNT$/o) {
  9744.         print_check_err("Invalid mount point argument (valid file path only)");
  9745.     }
  9746.     return 0;
  9747. }
  9748.  
  9749. sub get_mnt {
  9750.     if ($args{'mnt'} =~ /($REG_MNT)/o) {
  9751.         return $1;
  9752.     }
  9753.     print_err("Invalid Mounting Point");
  9754. }
  9755.  
  9756. sub check_inode {
  9757.     my $inode = shift;
  9758.     if ((!exists $args{$inode}) || ($args{$inode} !~ /^$REG_INODE$/o) ||
  9759.       ($args{$inode} < 0)) {
  9760.         print_check_err("Invalid inode ($inode) argument (numbers >= 0 only)");
  9761.     }
  9762.     return 0;
  9763. }
  9764.  
  9765. # We can only have positive numbers
  9766. sub get_inode {
  9767.     my $inode = shift;
  9768.     if ($args{$inode} =~ /^($REG_INODE)$/o) {
  9769.         return $1;
  9770.     }
  9771.     print_err("Invalid Inode");
  9772. }
  9773.  
  9774. sub get_force {
  9775.     if ($args{'force'} =~ /^(\d+)$/) {
  9776.         return $1;
  9777.     }
  9778.     print_err("Invalid Force Flag");
  9779. }
  9780.  
  9781. sub check_block {
  9782.     if ((!exists $args{'block'}) || ($args{'block'} !~ /^\d+$/)) {
  9783.         print_check_err("Invalid block argument (positive numbers only)");
  9784.     }
  9785.     return 0;
  9786. }
  9787.  
  9788. sub get_block {
  9789.     if ($args{'block'} =~ /^(\d+)$/) {
  9790.         return $1;
  9791.     }
  9792.     print_err("Invalid Block");
  9793. }
  9794.  
  9795. sub check_cell_mode {
  9796.     if ((!exists $args{'cell_mode'}) || ($args{'cell_mode'} !~ /^\d$/o)) { 
  9797.         print_check_err("Invalid cell_mode argument (numbers >= 0 only)");
  9798.     }
  9799.     return 0;
  9800. }
  9801.  
  9802.  
  9803. sub check_len {
  9804.     if ((!exists $args{'len'}) || ($args{'len'} !~ /^\d+$/)) {
  9805.         print_check_err("Invalid len argument (positive numbers only)");
  9806.     }
  9807.     return 0;
  9808. }
  9809.  
  9810. sub get_len  {
  9811.     if ((exists $args{'len'}) && ($args{'len'} =~ /^(\d+)$/)) {
  9812.         return $1;
  9813.     }
  9814.     # return the default len of 1 if it is not defined
  9815.     return 1;
  9816. }
  9817.  
  9818. sub check_sort {
  9819.     if ((!exists $args{'sort'}) || ($args{'sort'} !~ /^\d+$/)) {
  9820.         print_check_err("Invalid sort argument (positive numbers only)");
  9821.     }
  9822.     return 0;
  9823. }
  9824.  
  9825. sub get_sort {
  9826.     if ($args{'sort'} =~ /^(\d+)$/) {
  9827.         return $1;
  9828.     }
  9829.     print_err("Invalid sort flag");
  9830. }
  9831.  
  9832.  
  9833. # ifind is optional and by default is 0 if not given
  9834. sub get_ifind {
  9835.     if (!exists $args{'ifind'}) {
  9836.         return 0;
  9837.     }
  9838.     elsif ($args{'ifind'} =~ /^(\d+)$/) {
  9839.         return $1;
  9840.     }
  9841.     print_err("Invalid ifind flag");
  9842. }
  9843.  
  9844. sub check_mode {
  9845.     if ((!exists $args{'mode'}) || ($args{'mode'} !~ /^\d+$/)) {
  9846.         print_check_err("Invalid mode argument (positive numbers only)");
  9847.     }
  9848.     return 0;
  9849. }
  9850.  
  9851. sub get_mode {
  9852.     if ($args{'mode'} =~ /^(\d+)$/) {
  9853.         return $1;
  9854.     }
  9855.     print_err("Invalid Mode");
  9856. }
  9857.  
  9858. sub check_dmode {
  9859.     if ((!exists $args{'dmode'}) || ($args{'dmode'} !~ /^\d+$/)) {
  9860.         print_check_err("Invalid dmode argument (positive numbers only)");
  9861.     }
  9862.     return 0;
  9863. }
  9864.  
  9865. sub get_dmode {
  9866.     if ($args{'dmode'} =~ /^(\d+)$/) {
  9867.         return $1;
  9868.     }
  9869.     print_err("Invalid dmode");
  9870. }
  9871.  
  9872. sub get_min {
  9873.     if ($args{'min'} =~ /^(\d+)$/) {
  9874.         return $1;
  9875.     }
  9876.     print_err("Invalid Minute");
  9877. }
  9878.  
  9879. sub check_htype {
  9880.     if ((!exists $args{'htype'}) || ($args{'htype'} !~ /^\d+$/)) {
  9881.         print_check_err("Invalid htype argument (positive numbers only)");
  9882.     }
  9883.     return 0;
  9884. }
  9885.  
  9886. sub get_htype {
  9887.     if ($args{'htype'} =~ /^(\d+)$/) {
  9888.         return $1;
  9889.     }
  9890.     print_err("Invalid htype");
  9891. }
  9892.  
  9893.  
  9894.  
  9895. # This should be made more flexible
  9896. sub check_str {
  9897.     if (!exists $args{'str'}) {
  9898.         print_check_err("Missing string argument");
  9899.     }
  9900.     return 0;
  9901. }
  9902.  
  9903. # Get the string to search for with grep
  9904. # This should be made more flexible
  9905. sub get_str {
  9906.     if ($args{'str'} =~ /^\s*(.*)$/) {
  9907.         return $1;
  9908.     }
  9909.     print_err("Invalid String");
  9910. }
  9911.  
  9912.  
  9913. # Index for previous keyword search
  9914. sub check_srchidx {
  9915.     if ((!exists $args{'srchidx'}) || ($args{'srchidx'} !~ /^\d+$/)) {
  9916.         print_check_err("Invalid srchidx argument (positive numbers only)");
  9917.     }
  9918.     return 0;
  9919. }
  9920.  
  9921.  
  9922. sub check_tz {
  9923.     if ((!exists $args{'tz'}) || ($args{'tz'} !~ /^$REG_ZONE1$/o)) {
  9924.         print_check_err("Missing time zone argument");
  9925.     }
  9926.     return 0;
  9927. }
  9928.  
  9929. sub get_tz {
  9930.     if ($args{'tz'} =~ /^($REG_ZONE1)$/o) {
  9931.         return $1;
  9932.     }
  9933.     print_err("Invalid Timezone");
  9934. }
  9935.  
  9936. sub check_do_md5 {
  9937.     if ((!exists $args{'do_md5'}) || ($args{'do_md5'} !~ /^\d+$/)) {
  9938.         print_check_err("Missing do_md5 argument");
  9939.     }
  9940.     return 0;
  9941. }
  9942.  
  9943. sub get_do_md5 {
  9944.     if ($args{'do_md5'} =~ /^\s*(\d+)$/) {
  9945.         return $1;
  9946.     }
  9947.     print_err("Invalid MD5 Flag");
  9948. }
  9949.  
  9950. sub check_ts {
  9951.     if ((!exists $args{'ts'}) || ($args{'ts'} !~ /^$REG_SKEW$/o)) {
  9952.         print_check_err("Missing time skew argument");
  9953.     }
  9954.     return 0;
  9955. }
  9956.  
  9957. sub get_ts {
  9958.     if ($args{'ts'} =~ /^\s*($REG_SKEW)$/o) {
  9959.         return $1;
  9960.     }
  9961.     print_err("Invalid Time Skew");
  9962. }
  9963.  
  9964. sub check_note {
  9965.     if (!exists $args{'note'}) {
  9966.         print_check_err("Missing note argument");
  9967.     }
  9968.     return 0;
  9969. }
  9970.  
  9971. sub check_ftype {
  9972.     unless (((exists $img2ftype{$args{'img'}}) &&
  9973.       ($img2ftype{$args{'img'}} =~ /^$REG_FTYPE$/o)) || 
  9974.       ((exists $args{'ftype'}) && 
  9975.       ($args{'ftype'} =~ /^$REG_FTYPE$/o)) ) {
  9976.         print_check_err("Missing or invalid ftype value");
  9977.     }
  9978.     return 0;
  9979. }
  9980.  
  9981. sub get_ftype {
  9982.     unless ((exists $args{'img'}) && (exists $img2ftype{$args{'img'}})) {
  9983.         if (exists $args{'ftype'}) {
  9984.             if ($args{'ftype'} =~ /^($REG_FTYPE)$/o) {
  9985.                 return $1;
  9986.             }
  9987.             return 0;
  9988.         }
  9989.         print_check_err("Missing ftype value");
  9990.     }
  9991.     return $img2ftype{$args{'img'}};
  9992. }
  9993.  
  9994.  
  9995. sub check_st_mon {
  9996.     if ((exists $args{'st_mon'}) && ($args{'st_mon'} =~ /^(\d\d?)$/)) {
  9997.         if (($1 < 1) || ($1 > 12)) {
  9998.             print ("Invalid start month\n");
  9999.             return 1;
  10000.         }
  10001.     } else {
  10002.         print ("Invalid start month\n");
  10003.         return 1;
  10004.     }
  10005. }
  10006.  
  10007. sub get_st_mon {
  10008.     if ($args{'st_mon'} =~ /^(\d\d?)$/) {
  10009.         return $1;
  10010.     }
  10011.     print_err("Invalid Month");
  10012. }
  10013.  
  10014.  
  10015. sub check_st_year {
  10016.     if ((exists $args{'st_year'}) && ($args{'st_year'} =~ /^(\d\d\d\d?)$/)) {
  10017.         if (($1 < 1970) || ($1 > 2020)) {
  10018.             print ("Invalid start year\n");
  10019.             return 1;
  10020.         }
  10021.     } else {
  10022.         print ("Invalid start year\n");
  10023.         return 1;
  10024.     }
  10025. }
  10026.  
  10027. sub get_st_year {
  10028.     if ($args{'st_year'} =~ /^(\d\d\d\d)$/) {
  10029.         return $1;
  10030.     }
  10031.     print_err("Invalid Year");
  10032. }
  10033.  
  10034. sub get_unitsize {
  10035.     my $ftype = get_ftype();
  10036.     my $dcat_out;
  10037.  
  10038.     if ($ftype eq 'dls') {      
  10039.         if (exists $mod2img{$args{'img'}}) {
  10040.             my $orig =  $mod2img{$args{'img'}};
  10041.             local *OUT;
  10042.             exec_pipe(*OUT, 
  10043.               "'${TASKDIR}dcat' -f $img2ftype{$orig} -s '$host_dir$orig'");
  10044.             $dcat_out = <OUT>;
  10045.             close (OUT);
  10046.         }
  10047.         # We don't have the original image, so just set the size to 512
  10048.         else {
  10049.             return 512;
  10050.         }
  10051.     }
  10052.     elsif ($ftype eq 'swap') {
  10053.         return 4096;
  10054.     }
  10055.     elsif ($ftype eq 'raw') {
  10056.         return 512;
  10057.     }
  10058.     else {
  10059.         my $img = get_img('img');
  10060.         local *OUT;
  10061.         exec_pipe(*OUT, 
  10062.           "'${TASKDIR}dcat' -f $ftype -s '$img'");
  10063.         $dcat_out = <OUT>;
  10064.         close (OUT);
  10065.     }
  10066.     $dcat_out = "Error getting unit size" 
  10067.       if ((!defined $dcat_out) || ($dcat_out eq ""));
  10068.  
  10069.     if ($dcat_out =~ /(\d+): Size of Addressable Unit/) {
  10070.         return $1;
  10071.     }
  10072.     else {
  10073.         print "Error identifying block size (dcat -s output)<BR>\n";
  10074.         print "$dcat_out<BR>\n";
  10075.         exit(1);
  10076.     }
  10077. };
  10078.  
  10079.  
  10080. ############## URL UTILITIES ##################
  10081.  
  10082. sub html_encode {
  10083.     my $text = shift;
  10084.     $text =~ s/&/&/gs;
  10085.     $text =~ s/</</gs;
  10086.     $text =~ s/>/>/gs;
  10087.  
  10088.     # @@@ LEADING SPACES and TABS
  10089.     # while ($text =~ s/^( )*\t/"$1    "/eig) {}
  10090.     # while ($text =~ s/^( )* /"$1 "/eig) {}
  10091.     return $text;
  10092. }
  10093.  
  10094. sub url_encode {
  10095.     my $text = shift;
  10096.     $text =~ s/([^a-z0-9_.!~*'() -])/sprintf "%%%02X", ord($1)/eig;
  10097.     $text =~ tr/ /+/;
  10098.     return $text;
  10099. }
  10100.  
  10101. sub url_decode {
  10102.     my $text = shift;
  10103.     $text =~ tr/\+/ /;
  10104.     $text =~ s/%([a-f0-9][a-f0-9])/chr( hex( $1 ) )/eig;
  10105.     return $text;
  10106. }
  10107.  
  10108.  
  10109. ############ LOGGING ########################
  10110.  
  10111. sub log_session_info 
  10112. {
  10113.     return unless ($USE_LOG == 1);
  10114.     my $str = shift;
  10115.     chomp $str;
  10116.     my $date = localtime;
  10117.  
  10118.     my $lname = "autopsy.log";       
  10119.     open AUTLOG, ">>${LOCKDIR}/$lname" or die "Can't open log: $lname";
  10120.     print AUTLOG "$date: $str\n";
  10121.     close (AUTLOG);
  10122.  
  10123.     return;
  10124. };
  10125.  
  10126. sub log_case_info {
  10127.     return unless ($USE_LOG == 1);
  10128.     my $str = shift;
  10129.     chomp $str;
  10130.     my $date = localtime;
  10131.     my $fname = case_log_fname();
  10132.  
  10133.     open CASELOG, ">>$fname" or die "Can't open log: $fname";
  10134.     print CASELOG "$date: $str\n";
  10135.     close (CASELOG);
  10136.  
  10137.     return;
  10138. };
  10139.  
  10140.  
  10141. # log data to the general log file for the host
  10142. sub log_host_info {
  10143.     return unless ($USE_LOG == 1);
  10144.     my $str = shift;
  10145.     chomp $str;
  10146.     my $date = localtime;
  10147.     my $fname = host_log_fname();
  10148.  
  10149.     open HOSTLOG, ">>$fname" or die "Can't open log: $fname";
  10150.     print HOSTLOG "$date: $str\n";
  10151.     close (HOSTLOG);
  10152.  
  10153.     return;
  10154. };
  10155.  
  10156.  
  10157. # Log data to the investigators specific log file
  10158. sub log_host_inv {
  10159.     return unless ($USE_LOG == 1);
  10160.     my $str = shift;
  10161.     chomp $str;
  10162.     my $date = localtime;
  10163.     my $fname = investig_log_fname();
  10164.  
  10165.     open HOSTLOG, ">>$fname" or die "Can't open log: $fname";
  10166.     print HOSTLOG "$date: $str\n";
  10167.     close (HOSTLOG);
  10168.  
  10169.     return;
  10170. };
  10171.  
  10172. sub log_host_inv_exec {
  10173.     return unless ($USE_LOG == 1);
  10174.     my $str = shift;
  10175.     chomp $str;
  10176.  
  10177.     # We may not have a full host setup yet so check the reqs for the 
  10178.     # exec log file
  10179.     return unless (defined $host_dir && $host_dir ne "");
  10180.     return unless (exists $args{'inv'} && $args{'inv'} ne "");
  10181.  
  10182.     my $date = localtime;
  10183.     my $fname = investig_exec_log_fname();
  10184.  
  10185.     open HOSTLOG, ">>$fname" or die "Can't open log: $fname";
  10186.     print HOSTLOG "$date: $str\n";
  10187.     close (HOSTLOG);
  10188.  
  10189.     return;
  10190.  
  10191.  
  10192. }
  10193.  
  10194.  
  10195.  
  10196.  
  10197. ############ DISPLAY ########################
  10198. sub print_check_err {
  10199.     print_html_header("");
  10200.     print shift()."<BR>\n";
  10201.     sleep (1);
  10202.     exit 1;
  10203. }
  10204.  
  10205. sub print_err {
  10206.     print shift()."<BR>\n";
  10207.     sleep (1);
  10208.     exit 1;
  10209. }
  10210.  
  10211. # The page that makes the frameset does not have a body statement
  10212. # This routine is used to make the minimum required header statements
  10213. sub print_html_header_frameset {
  10214.     my $text = shift;
  10215.     print "Content-type: text/html${HTTP_NL}${HTTP_NL}";
  10216.  
  10217.     my $time = localtime();
  10218.  
  10219. print <<EOF;
  10220. <HTML>
  10221. <!-- Autopsy ver. $VER Forensic Browser -->
  10222. <!-- Page created at: $time -->
  10223. <HEAD>
  10224.   <TITLE>$text</TITLE>
  10225. </HEAD>
  10226.  
  10227. EOF
  10228.     $is_html = 1;
  10229. }
  10230.  
  10231. # Create the header information with the body tag
  10232. sub print_html_header {
  10233.     print_html_header_frameset(shift);
  10234.     print "<BODY BGCOLOR=\"$BACK_COLOR\">\n\n";
  10235.     $is_body = 1;
  10236. }
  10237.  
  10238. # Print the header with the margins set to 0 so that the tab buttons
  10239. # are flush with the edges of the frame
  10240. sub print_html_header_tabs {
  10241.     print_html_header_frameset(shift);
  10242.     print "<BODY MARGINHEIGHT=0 MARGINWIDTH=0 TOPMARGIN=0 ".
  10243.       "LEFTMARGIN=0 RIGHTMARGIN=0 BOTMARGIN=0 BGCOLOR=\"$BACK_COLOR\">\n\n";
  10244.     $is_body = 1;
  10245. }
  10246.  
  10247.  
  10248. # Header for front page to warn about java script
  10249. sub print_javascript_header {
  10250.     my $text = shift;
  10251.     print "Content-type: text/html${HTTP_NL}${HTTP_NL}";
  10252.  
  10253.     my $time = localtime();
  10254.     # The write line has to stay on one line
  10255. print <<EOF;
  10256. <HTML>
  10257. <!-- Autopsy ver. $VER Forensic Browser -->
  10258. <!-- Page created at: $time -->
  10259. <HEAD>
  10260.   <TITLE>$text</TITLE>
  10261.   <SCRIPT language=\"JavaScript\">
  10262.   <!-- hide script from old browsers
  10263.   document.write(\'<CENTER><FONT COLOR=\"red\"><P>WARNING: Your browser currently has Java Script enabled</FONT><P>You do not need Java Script to use Autopsy and it is recommended that it be turned off for security reasons<HR></CENTER>\');
  10264.   //-->
  10265.   </SCRIPT>
  10266. </HEAD>
  10267.  
  10268. <BODY BGCOLOR=\"$BACK_COLOR\">
  10269.  
  10270. EOF
  10271.  
  10272.     $is_html = 1;
  10273.     $is_body = 1;
  10274. }
  10275.  
  10276.  
  10277. # For raw text outputs
  10278. # This only has ONE newline at the end so that a Content-Disposition
  10279. # can be added. A newline must be added if Disposition is not used.
  10280. sub print_text_header {
  10281.     print "Content-type: text/plain${HTTP_NL}";
  10282. }
  10283.  
  10284. # For forced save outputs
  10285. # This only has ONE newline at the end so that a Content-Disposition
  10286. # can be added. A newline must be added if Disposition is not used.
  10287. sub print_oct_header {
  10288.     print "Content-type: application/octet-stream${HTTP_NL}";
  10289. }
  10290.  
  10291. # remove control chars from printout
  10292. sub print_output {
  10293.     while (my $out = shift) {
  10294.         foreach $_ (split (//, $out)) {
  10295.             if (($_ eq "\n") || ($_ eq "\r") || ($_ eq "\f") ||
  10296.               ($_ eq "\t") ) {
  10297.                 print "$_";
  10298.             }
  10299.             elsif ((ord($_) < 0x20) || (ord($_) > 0x7e)) {
  10300.                 print "^".ord($_);
  10301.             }
  10302.             else {
  10303.                 print "$_";
  10304.             }
  10305.         }
  10306.     }
  10307. }
  10308.