home *** CD-ROM | disk | FTP | other *** search
/ Visual Basic Source Code / Visual Basic Source Code.iso / vbsource / vbdatabs / hexdump.cpp < prev    next >
Encoding:
C/C++ Source or Header  |  1999-03-17  |  18.0 KB  |  646 lines

  1. // ------------------------------- //
  2. // -------- Start of File -------- //
  3. // ------------------------------- //
  4. // ----------------------------------------------------------- // 
  5. // C++ Source Code File Name: hexdump.cpp 
  6. // Compiler Used: MSVC40, DJGPP 2.7.2.1, GCC 2.7.2.1, HP CPP 10.24
  7. // Produced By: Doug Gaer 
  8. // File Creation Date: 02/13/1996 
  9. // Date Last Modified: 03/17/1999
  10. // ----------------------------------------------------------- // 
  11. // ------------- Program description and details ------------- // 
  12. // ----------------------------------------------------------- // 
  13. /*
  14. THIS SOFTWARE IS PROVIDED "AS IS" WITHOUT WARRANTY OF ANY KIND.
  15. THE ENTIRE RISK OF THE QUALITY AND PERFORMANCE OF THIS SOFTWARE
  16. IS WITH YOU. SHOULD ANY ELEMENT OF THIS SOFTWARE PROVE DEFECTIVE,
  17. YOU WILL ASSUME THE COST OF ALL NECESSARY SERVICING, REPAIR, OR
  18. CORRECTION.
  19.   
  20. This program is used to display the contents of a specified
  21. file, in both hexadecimal and ASCII, to the console. 
  22. */
  23. // ----------------------------------------------------------- // 
  24. #include <iostream.h>
  25. #include <fstream.h>
  26. #include <ctype.h>
  27. #include <iomanip.h>
  28. #include <stdio.h>
  29. #include <stdlib.h>
  30. #include <string.h>
  31. #include "hxcrc.h"
  32.  
  33. // Define this macro for DOS file opens (the default is UNIX)
  34. // #ifndef __DOS__
  35. // #define __DOS__
  36. // #endif
  37.  
  38. // Hexdump version number and program name
  39. const double HexdumpVersionNumber = 1031.101;
  40. const char *ProgramName = "hexdump";
  41.  
  42. // Program constants
  43. const int MAX_LINE = 255;  // Maximum characters per line
  44. const int hxBuffSize = 16; // Maximum number of bytes per line
  45. const int decBuffSize = 8; // Maximum number of bytes per line
  46.  
  47. // Constants for text parser
  48. const int MAXWORDLENGTH = 255;
  49. const int MAXWORDS = 255;
  50.  
  51. // Program globals
  52. char in_file[MAX_LINE];    // Input file 
  53. char out_file[MAX_LINE];   // Optional output file name
  54. int prompting = 0;         // Enable prompting during console dump
  55. int use_console = 1;       // Dump to console if no output file is specified
  56. int decimal_mode = 0;      // Display in decimal mode (Default is HEX)
  57. int building_bin_file = 0; // True if building binary file from text file
  58. int strip_comments = 0;    // True if not adding comments
  59. int display_crc32 = 0;     // True if displaying 32-bit crc checksum
  60. int display_crc16 = 0;     // True if displaying 16-bit crc checksum
  61. int NumLines = 8;          // Default maximum number of lines to display
  62.  
  63. // Table for HEX to binary conversions
  64. const char *bintab[16] = {
  65.   "0000", "0001", "0010", "0011", "0100", "0101", "0110", "0111",
  66.   "1000", "1001", "1010", "1011", "1100", "1101", "1110", "1111"
  67. };
  68.  
  69. // Program Functions 
  70. void ProcessArgs(int argc, char *argv[]);
  71. void HelpMessage(const char *program_name, const double version_number);
  72. int HexFileDump(fstream &infile, ostream &stream);
  73. int DecFileDump(fstream &infile, ostream &stream);
  74. void BuildBinaryFile(char *ifname, char *ofname);
  75. void TruncateLine(char *line, char tline[MAX_LINE], char delimiter1 = '\t',
  76.           char delimiter2 = ';');
  77. int text_parse(char *string, char words[MAXWORDS][MAXWORDLENGTH],
  78.            int*numwords, char sepchar1 = ' ', char sepchar2 = ' ');
  79.  
  80. void HelpMessage(const char *program_name, const double version_number)
  81. {
  82.   char vbuffer[255];
  83.   sprintf(vbuffer, "%.3f", version_number);
  84.   cout << endl;
  85.   cout << "Hexadecimal file dump program version "
  86.        << vbuffer  << endl;
  87.   cout << "Usage: " << program_name << " [switches] infile "
  88.        << "outfile (optional)" << endl;
  89.   cout << "Switches:  -?      = Display this help message." << endl;
  90.   cout << "           -c      = Display a 32-bit CRC checksum value." << endl;
  91.   cout << "           -C      = Display a 16-bit CRC checksum value." << endl;
  92.   cout << "           -d      = Display in decimal mode (Default is HEX)."
  93.        << endl;
  94.   cout << "           -p#     = Prompting after displaying # line: -p10"
  95.        << endl;
  96.   cout << "           -r      = Rebuild binary file from hex dump text file.\n"
  97.        << "                     Only works for files created in hex mode."   
  98.        << endl;
  99.   cout << "           -s      = Strip comments from output." << endl;
  100.   cout << endl;
  101.   cout << "           -x      = Convert 32-bit HEX number to DEC: -Xfefe"
  102.        << endl;
  103.   cout << "           -X      = Convert signed 32-bit HEX number to DEC."
  104.        << endl;
  105.   cout << "           -B      = Convert 32-bit HEX number to binary: -Bfefe"
  106.        << endl;
  107.   cout << "           -D      = Convert DEC number to HEX: -D23" << endl;
  108.   cout << endl;
  109.   exit(0);
  110. }
  111.  
  112. void ProcessArgs(int argc, char *argv[])
  113. // Process the program's argument list
  114. {
  115.   int i, ibuf;
  116.   char *sbuf;
  117.   unsigned long ulbuf, bbuf;
  118.   long lbuf;
  119.   
  120.   for(i = 1; i < argc; i++ ) {
  121.     if(*argv[i] == '-') {
  122.       char sw = *(argv[i] +1);
  123.       switch(sw) {
  124.     case '?' :
  125.       HelpMessage(ProgramName, HexdumpVersionNumber);
  126.       break;
  127.  
  128.     case 'c':
  129.       display_crc32 = 1;
  130.       break;
  131.  
  132.     case 'C':
  133.       display_crc16 = 1;
  134.       break;
  135.  
  136.     case 'p' :
  137.       prompting = 1;
  138.       ibuf = atoi(&argv[i][2]);
  139.       if(ibuf > 0) NumLines = ibuf; 
  140.       break;
  141.  
  142.     case 'd' :
  143.       decimal_mode = 1;
  144.       break;
  145.  
  146.     case 'r' :
  147.       building_bin_file = 1;
  148.       break;
  149.  
  150.     case 's' :
  151.       strip_comments = 1;
  152.       break;
  153.  
  154.     case 'x' : {
  155.       sbuf = &argv[i][2];
  156.       cout << endl;
  157.       sscanf(sbuf, "%x", &ulbuf);
  158.       cout.setf(ios::uppercase);
  159.       cout << "0x" << hex << ulbuf << " = " << dec << ulbuf << endl;
  160.       cout << endl;
  161.       exit(0);
  162.       break;
  163.     }
  164.       
  165.     case 'X' : {
  166.       sbuf = &argv[i][2];
  167.       cout << endl;
  168.       sscanf(sbuf, "%x", &lbuf);
  169.       cout.setf(ios::uppercase);
  170.       cout << "0x" << hex << lbuf << " = " << dec << lbuf << endl;
  171.       cout << endl;
  172.       exit(0);
  173.       break;
  174.     }
  175.     
  176.     case 'D' : {
  177.       sbuf = &argv[i][2];
  178.       cout << endl;
  179.       sscanf(sbuf, "%u", &ulbuf);
  180.       cout.setf(ios::uppercase);
  181.       cout << ulbuf << " = " << "0x" << hex << ulbuf << endl;
  182.       cout << endl;
  183.       exit(0);
  184.       break;
  185.     }
  186.  
  187.     case 'B' : {
  188.       sbuf = &argv[i][2];
  189.       cout << endl;
  190.       sscanf(sbuf, "%x", &ulbuf);
  191.       cout.setf(ios::uppercase);
  192.       cout << "0x" << hex << ulbuf << " = ";
  193.       bbuf = (ulbuf & 0xf0000000)>>28;
  194.       cout << bintab[bbuf] << ' ';
  195.       bbuf = (ulbuf & 0xf000000)>>24;
  196.       cout << bintab[bbuf] << ' ';
  197.       bbuf = (ulbuf & 0xf00000)>>20;
  198.       cout << bintab[bbuf] << ' ';
  199.       bbuf = (ulbuf & 0xf0000)>>16;
  200.       cout << bintab[bbuf] << ' ';
  201.       bbuf = (ulbuf & 0xf000)>>12;
  202.       cout << bintab[bbuf] << ' ';
  203.       bbuf = (ulbuf & 0xf00)>>8;
  204.       cout << bintab[bbuf] << ' ';
  205.       bbuf = (ulbuf & 0xf0)>>4;
  206.       cout << bintab[bbuf] << ' '; 
  207.       bbuf = ulbuf & 0x0f;
  208.       cout << bintab[bbuf] << endl; 
  209.       cout << endl;
  210.       exit(0);
  211.       break;
  212.     }
  213.     
  214.     default:
  215.       cerr << endl;
  216.       cerr << "Unknown switch " << argv[i] << endl;
  217.       cerr << "Exiting..." << endl;
  218.       cerr << endl;
  219.       exit(0);
  220.       break;
  221.       }
  222.     }
  223.     else { 
  224.       strcpy(in_file, argv[i]);      // Input file name
  225.       if(argv[i+1]) {
  226.     strcpy(out_file, argv[i+1]); // Output file name
  227.     break;
  228.       }
  229.       else
  230.     break;
  231.     }
  232.   }
  233. }
  234.  
  235. int HexFileDump(fstream &infile, ostream &stream)
  236. {
  237.   register int i, j;
  238.   int count = 0;
  239.   char c[hxBuffSize];
  240.  
  241.   // Print all text in upper case characters
  242.   stream.setf(ios::uppercase);
  243.  
  244.   while(!infile.eof()) {
  245.  
  246.     for(i = 0; i < hxBuffSize && !infile.eof(); i++) {
  247.       infile.get(c[i]);
  248.     }
  249.       
  250.     if(i < hxBuffSize) i--; // Get rid of eof;
  251.       
  252.     for(j = 0; j < i; j++) {
  253.       long xx = (long)c[j];
  254.  
  255.       // Set fill chars and reset first 24 bits for one byte display
  256.       stream << setfill('0') << setw(2) << hex << (xx & 0xFF);
  257.       stream << " "; // Print one space between the bytes
  258.     }
  259.  
  260.     // Set the line spacing to a minimum of bytes per line
  261.     for(; j < hxBuffSize; j++) stream << "   "; // Insert 3 spaces
  262.  
  263.     if(!strip_comments) {
  264.       // Separate hex output by one tab and denote comments
  265.       // with a semicolon.
  266.       stream << "\t" << "; ";
  267.       
  268.       // Filter out any non-printable characters
  269.       for(j = 0; j < i; j++)
  270.     if(isgraph(c[j])) stream << c[j];
  271.     else stream << ".";
  272.     }
  273.     
  274.     stream << endl;
  275.       
  276.     if(use_console == 1 && prompting == 1) {
  277.       count++;
  278.       if(count == NumLines) {
  279.     count = 0;
  280.     stream << endl;
  281.     stream << "Press ENTER to continue: ";
  282.     cin.get();
  283.     stream << endl;
  284.       }
  285.     }
  286.   }
  287.  
  288.   infile.close();
  289.  
  290.   return 1;
  291. }
  292.  
  293. int DecFileDump(fstream &infile, ostream &stream)
  294. {
  295.   register int i, j;
  296.   int count = 0;
  297.   char c[decBuffSize];
  298.   
  299.   // Print all text in upper case characters
  300.   stream.setf(ios::uppercase);
  301.  
  302.   while(!infile.eof()) {
  303.  
  304.     for(i = 0; i < decBuffSize && !infile.eof(); i++) {
  305.       infile.get(c[i]);
  306.     }
  307.       
  308.     if(i < decBuffSize) i--; // Get rid of eof;
  309.       
  310.     for(j = 0; j < i; j++) {
  311.       long xx = (long)c[j];
  312.  
  313.       // Set fill chars and reset first 24 bits for one byte display
  314.     stream << setfill('0') << setw(3) << dec << (xx & 0xFF);
  315.     stream << " "; // Print one space between the bytes
  316.     }
  317.  
  318.     // Set the line spacing to a maximum number of bytes per line
  319.     for(; j < decBuffSize; j++) stream << "    "; // Insert 4 spaces
  320.  
  321.     if(!strip_comments) {
  322.       // Separate hex output by one tab and denote comments
  323.       // with a semicolon.
  324.       stream << "\t" << "; ";
  325.       
  326.       // Filter out any non-printable characters
  327.       for(j = 0; j < i; j++)
  328.     if(isgraph(c[j])) stream << c[j];
  329.     else stream << ".";
  330.     }
  331.     
  332.     stream << endl;
  333.       
  334.     if(use_console == 1 && prompting == 1) {
  335.       count++;
  336.       if(count == NumLines) {
  337.     count = 0;
  338.     stream << endl;
  339.     stream << "Press ENTER to continue: ";
  340.     cin.get();
  341.     stream << endl;
  342.       }
  343.     }
  344.   }
  345.  
  346.   infile.close();
  347.  
  348.   return 1;
  349. }
  350.  
  351. void BuildBinaryFile(char *ifname, char *ofname)
  352. {
  353.   cout << "Building new binary file from hex dump text file..." << endl;
  354.   
  355.   if(ifname[0] == 0) {
  356.     cout << endl;
  357.     cout << "You must specify a valid hex dump text file." << endl;
  358.     cout << endl;
  359.     exit(0);
  360.   }
  361.  
  362.   // Default output file name if none specified on command line
  363.   if(ofname[0] == 0) ofname = "outfile.bin";
  364.  
  365.   ifstream infile(ifname, ios::in|ios::nocreate);
  366.   if(!infile) {
  367.     cerr << "Could not open " << ifname << endl;
  368.     exit(0);
  369.   }
  370.  
  371. #if defined(__DOS__)
  372.   // In MS-DOS/Windows there are two file types, text and binary
  373.   fstream outfile(ofname, ios::out|ios::in|ios::trunc|ios::binary);
  374.   // NOTE: There is no ios::in or ios::out default mode for fstream objects.
  375.   // You must specify both modes for read and write files. 
  376. #elif defined(__DJGPP2721__)
  377.   // DJGPP 2.7.2.1 will not create a file using ios::out|ios::in modes
  378.   fstream outfile(ofname, ios::out|ios::binary);
  379. #else 
  380.   // In UNIX there is only one file type
  381.   fstream outfile(ofname, ios::out|ios::in|ios::trunc);
  382. #endif
  383.  
  384.   if(!outfile) {
  385.     cerr << "Could not create " << ofname << endl;
  386.     exit(0);
  387.   }
  388.  
  389.   char words[MAXWORDS][MAXWORDLENGTH];
  390.   char LineBuffer[MAX_LINE];
  391.   char InputBuffer[MAX_LINE];
  392.   int i, num, byte_count = 0;
  393.   long word_val;
  394.   unsigned char byte_val;
  395.   unsigned long CRC32 = 0xffffffffL;
  396.   unsigned long outfile_CRC32, CRC32_check;
  397.   hxCRC crc;
  398.   
  399.   // Clear the buffers
  400.   for(i = 0; i < MAX_LINE; i++) LineBuffer[i] = '\0';
  401.   for(i = 0; i < MAX_LINE; i++) InputBuffer[i] = '\0';
  402.   
  403.   while(infile) {
  404.     infile.getline(LineBuffer, MAX_LINE);
  405.  
  406.     // Truncate the line when the first tab is found
  407.     TruncateLine(LineBuffer, InputBuffer);
  408.  
  409.     if(text_parse(InputBuffer, words, &num) == 1) {
  410.       cerr << "Parse error! Exiting..." << endl;
  411.       cerr << endl;
  412.       exit(0);
  413.     }
  414.  
  415.     // Write the hex values in the text file to a binary file
  416.     for(i = 0; i < num; i++) {
  417.       if(words[i] != 0 && (strlen(words[i]) == 2)) {
  418.     sscanf(words[i], "%x", &word_val);
  419.     word_val &= 0xFF; // Reset the first 24 bits
  420.     byte_val = (unsigned char) word_val;
  421.  
  422.     // Calculate a 32-bit CRC for each byte value
  423.     CRC32=crc.crc32tab[(CRC32 ^ word_val)&0xFF] ^ ((CRC32>>8)&0x00ffffffL);
  424.  
  425.     outfile.write((unsigned char *) &byte_val, sizeof(byte_val));
  426.     byte_count++;
  427.       }
  428.     }
  429.   
  430.     // Clear the buffers
  431.     for(i = 0; i < MAX_LINE; i++) LineBuffer[i] = '\0';
  432.     for(i = 0; i < MAX_LINE; i++) InputBuffer[i] = '\0';
  433.   }
  434.  
  435.   // Finish 32-bit CRC calculation for each byte value
  436.   CRC32 ^= 0xffffffffL;
  437.  
  438. #ifdef __DJGPP2721__
  439.   // DJGPP 2.7.2.1 will not create a file using ios::out|ios::in modes
  440.   // NOTE: There is no ios::in or ios::out default mode for fstream objects.
  441.   // Both modes must be specifed for read and write files. 
  442.   cout << "Finished." << endl;
  443.   cout << byte_count << " bytes written to " << ofname << endl;
  444.   cout << endl;
  445.   infile.close();
  446.   outfile.close();
  447.   return; // Do not calculate CRC for output file under DJGPP
  448. #endif
  449.   
  450.   // Calculate a 32-bit CRC for the output file 
  451.   outfile_CRC32 = crc.calcCRC32(outfile);
  452.   CRC32_check = CRC32 ^ outfile_CRC32; // XOR the CRC values
  453.   if(CRC32_check != 0) { 
  454.     cout << "Checksum error in " << ofname << endl;   
  455.     cout << "File fails CRC-32 test." << endl;
  456.     cout << "CRC of bytes written = ";
  457.     cout.setf(ios::uppercase);
  458.     cout << "0x" << setfill('0') << setw(8) << hex << CRC32 << endl;
  459.     cout.unsetf(ios::uppercase);
  460.     cout << "File CRC = ";
  461.     cout.setf(ios::uppercase);
  462.     cout << "0x" << setfill('0') << setw(8) << hex << outfile_CRC32 << endl;
  463.     cout.unsetf(ios::uppercase);
  464.     cout << endl;
  465.   }
  466.   else {
  467.     cout << "Finished." << endl;
  468.     cout << byte_count << " bytes written to " << ofname << endl;
  469.     cout << endl;
  470.   }
  471.   infile.close();
  472.   outfile.close();
  473. }
  474.  
  475. void TruncateLine(char *line, char tline[MAX_LINE],
  476.           char delimiter1, char delimiter2)
  477. // Used to truncate a line of text starting at the first occurrence
  478. // of the delimiter characters.
  479. {
  480.   int len = strlen(line);
  481.   int i, offset = 0;
  482.  
  483.   for(i = 0; i < len; i++) {
  484.     if((line[i] == delimiter1) || (line[i] == delimiter2)) {
  485.       offset = i;
  486.       break;
  487.     }
  488.   }
  489.   
  490.   if(!offset) { // Delimiter character was not found
  491.     tline[len] = 0; // Ensure null termination
  492.     strcpy(tline, line);
  493.     return; 
  494.   }
  495.   
  496.   len -= offset;
  497.   tline[offset] = 0; // Ensure null termination
  498.   memmove(tline, line, offset);
  499. }
  500.  
  501. int text_parse(char *string, char words[MAXWORDS][MAXWORDLENGTH],
  502.            int*numwords, char sepchar1, char sepchar2)
  503. // General purpose text parser. Returns 0 if successful or 1 if a
  504. // parse error occurred.
  505. {
  506.   int i = 0;
  507.   char newword[MAXWORDLENGTH];
  508.   *numwords = 0;
  509.  
  510.   // First skip over leading blanks. Stop if an ASCII NULL is seen
  511.   while (1) {
  512.     if (*string == '\0') return 0;
  513.     if (*string != ' ') break;
  514.     string++;
  515.   }
  516.   
  517.   while(1) {
  518.     // Check to see if there is room for another word in the array
  519.     if(*numwords == MAXWORDS) return 1;
  520.  
  521.     i = 0;
  522.     while (i < MAXWORDLENGTH) {
  523.       if(*string == 0 || *string == sepchar1 || *string == sepchar2) break;
  524.       newword[i] = *string;
  525.       string++;
  526.       i++;
  527.     }
  528.  
  529.     newword[i] = 0; // Ensure an ASCII null at end of newword. 
  530.     strcpy (words[*numwords], newword);  // Install into array 
  531.     (*numwords)++;
  532.     
  533.     // If stopped by an ASCII NULL above, exit loop
  534.     if(*string == 0) break;
  535.     
  536.     string++;
  537.     if(*string == 0) break;
  538.   }
  539.   return 0;
  540. }
  541.  
  542. int main(int argc, char *argv[])
  543. {
  544.   // If no argument is given print usage message to the screen 
  545.   if(argc < 2) {
  546.     HelpMessage(ProgramName, HexdumpVersionNumber);
  547.     return 0;
  548.   }
  549.   
  550.   // Process the programs command line arguments
  551.   ProcessArgs(argc, argv);
  552.  
  553.   // If building a binary file from a hex dump text file,
  554.   // execute the build function and terminate the program.
  555.   if(building_bin_file == 1)  {
  556.     BuildBinaryFile(in_file, out_file);
  557.     return 0;
  558.   }
  559.   
  560.   if(in_file[0] == 0 ) {
  561.     cout << endl;
  562.     cout << "You must specify a valid input file name." << endl;
  563.     cout << endl;
  564.     return 0;
  565.   }
  566.  
  567. #if defined(__DOS__)
  568.   // In MS-DOS/Windows there are two file types, text and binary
  569.   fstream infile(in_file, ios::in | ios::binary | ios::nocreate);
  570. #elif defined(__DJGPP2721__)
  571.   fstream infile(in_file, ios::in | ios::binary | ios::nocreate);
  572. #else 
  573.   // In UNIX there is only one file type
  574.   fstream infile(in_file, ios::in | ios::nocreate);
  575. #endif
  576.  
  577.   if(!infile) {
  578.     cerr << endl;
  579.     cerr << "Cannot open file: " << in_file << endl;
  580.     cerr << "Exiting..." << endl;
  581.     cerr << endl;
  582.     return 1;
  583.   }
  584.  
  585.   if(display_crc32) {
  586.     hxCRC crc;
  587.     cout << in_file << endl;
  588.     cout << "CRC-32 = ";
  589.     cout.setf(ios::uppercase);
  590.     unsigned long checksum = crc.calcCRC32(infile);
  591.     cout << "0x" << setfill('0') << setw(8) << hex << checksum << endl;
  592.     cout.unsetf(ios::uppercase);
  593.     return 0;
  594.   }
  595.  
  596.   if(display_crc16) {
  597.     hxCRC crc;
  598.     cout << in_file << endl;
  599.     cout << "CRC-16 = ";
  600.     cout.setf(ios::uppercase);
  601.     unsigned short checksum = crc.calcCRC16(infile);
  602.     cout << "0x" << setfill('0') << setw(4) << hex << checksum << endl;
  603.     cout.unsetf(ios::uppercase);
  604.     cout << "CCITT CRC-16 = ";
  605.     cout.setf(ios::uppercase);
  606.     checksum = crc.calcCRC16(infile, 0);
  607.     cout << "0x" << setfill('0') << setw(4) << hex << checksum << endl;
  608.     cout.unsetf(ios::uppercase);
  609.     return 0;
  610.   }
  611.   
  612.   if(out_file[0] == 0 ) { // Write output to stdout
  613.     use_console = 1;
  614.     if(decimal_mode == 1)
  615.       DecFileDump(infile, cout);
  616.     else
  617.       HexFileDump(infile, cout);
  618.   }
  619.   else { // Write the output to a file
  620.     ofstream stream(out_file, ios::out); // Open file and truncate it
  621.     if(!stream) {
  622.       cerr << endl;
  623.       cerr << "Cannot create " << out_file << endl;
  624.       cerr << endl;
  625.       return 1;
  626.     }
  627.     use_console = 0;
  628.     cerr << "Processing file..." << endl;
  629.     if(decimal_mode == 1) {
  630.       DecFileDump(infile, stream);
  631.       stream.close();
  632.     }
  633.     else {
  634.       HexFileDump(infile, stream);
  635.       stream.close();
  636.     }
  637.     cerr << "Finished." << endl;
  638.   }
  639.  
  640.   return 0;
  641. }
  642. // ----------------------------------------------------------- // 
  643. // ------------------------------- //
  644. // --------- End of File --------- //
  645. // ------------------------------- //
  646.