Пример #1
0
/* 
 * ===  FUNCTION  ==============================================================
 *         Name:  get_device_id
 *
 *  Description:  Calls `djtgcfg enum` and looks for device username. Prompts
 *                for user input if more than one device. Exits with error if
 *                no devices found or djtgcfg is not installed.
 * 
 *      Version:  0.0.1
 *       Params:  Device *device
 *      Returns:  void
 *        Usage:  get_device_id(Device *device)
 *      Outputs:  N/A
 *
 *        Notes:  
 * =============================================================================
 */
void get_device_id(Device *device) {
    char *tmp;
    char* args[3];
    char output[80];
    char* combined;
    int pipe_id, exit_status, device_id_len;
    FILE *input;

    pipe_id = pipe_and_fork();

    if (childPid == 0) {
        // Child process
        args[0] = "djtgcfg";
        args[1] = "enum";
        args[2] = (char*) 0;
        execvp("djtgcfg", args);

        // Should never happen normally
        exit(999);
    } else {
        // Parent process
        input = fdopen(pipe_id, "r");
        combined = (char*) malloc(80);

        while (fgets(output, 80, input) != NULL) {
            combined = (char *) realloc(combined, strlen(combined) + 1 +
                    strlen(output));
            combined = strcat(combined, output);
        }

        wait(&exit_status);
        childPid = 0;
    }

    // No devices
    if (strstr(combined, "No devices found") != NULL) {
        printf("%s\n", "Failed to find device");
    } else {
        // Extract the device user name
        tmp = strstr(combined, "Device: ");
        device_id_len = strchr(tmp, '\n') - tmp - 8;
        device->id = (char *) malloc(device_id_len);
        strncpy(device->id, tmp + 8, device_id_len);
    }

    free(combined);
    close(pipe_id);
}
Пример #2
0
/* 
 * ===  FUNCTION  ==============================================================
 *         Name:  get_device_index
 *
 *  Description:  Calls `djtgcfg init` and looks for device indexes. Prompts
 *                for user input if more than one index. Exits with error if
 *                no devices found or djtgcfg is not installed.
 * 
 *      Version:  0.0.1
 *       Params:  Device *device
 *      Returns:  Device index from djtgcfg init
 *        Usage:  get_device_index(Device *device)
 *      Outputs:  N/A
 *
 *        Notes:  
 * =============================================================================
 */
void get_device_index(Device *device) {
    char* tmp, *cmp;
    char* args[5];
    char output[80];
    char* combined;
    int pipe_id, exit_status, i, response;
    FILE *input;

    pipe_id = pipe_and_fork();

    if (childPid == 0) {
        // Child process
        args[0] = "djtgcfg";
        args[1] = "init";
        args[2] = "-d";
        args[3] = device->id;
        args[4] = (char*) 0;
        execvp("djtgcfg", args);

        // Should never happen normally
        exit(999);
    } else {
        // Parent process
        input = fdopen(pipe_id, "r");
        combined = (char*) malloc(80);

        while (fgets(output, 80, input) != NULL) {
            combined = (char *) realloc(combined, strlen(combined) + 1 +
                    strlen(output));
            combined = strcat(combined, output);
        }

        wait(&exit_status);
        childPid = 0;
    }

    cmp = malloc(22);
    for (i = 1; i < 1000; i++) {
        sprintf(cmp, "Found %d device(s):", i);
        tmp = strstr(combined, cmp);
        if (tmp != NULL)
            break;
    }
    free(cmp);
    free(combined);
    close(pipe_id);

    if (tmp == NULL) {
        printf("%s\n", "No indexes found. Is device switched on?");
        exit(5);
    }

    printf("%s", tmp);

    response = -1;
    while (response < 0 || response > i - 1) {
        printf("Which device would you like to program?: [0] ");
        tmp = fgets(output, 80, stdin);
        response = atoi(output);
    }

    device->index = (char *) malloc(strlen(output) + 1);
    strcpy(device->index, output);

    // Remove \n char
    for (int i = 0; i <= strlen(device->index); i++) {
        if (device->index[i] == '\n')
            device->index[i] = '\0';
    }

    if (device->index[0] == 0)
        device->index[0] = '0';
}
Пример #3
0
/**
 * DESCRIPTION: 
 *
 * Prints a promt to the screen. Reads a command line of the following format from the  the user:
 * 
 *	cmd0 -a00 -b01 ... -z0n | cmd1 | cmd2 | ... | cmdN -an0 ... -znn
 *
 * For each command, the fork_and_pipe() function is called with the
 * appropiate argv and relative position of the command.
 * 
 * NOTE: 
 * 
 * You only have to add code at the end of main, see TODO comment. 
 */
int main() {
  
  // Allocate a buffer for the command line read from the user. 

  char line_buffer[COMMAND_LINE_BUFFER_SIZE];
  
  
  // We parse the command line using the next_command() parser. The
  // parser will populate the following array with the result of each call
  // to the parse.
  
  char* argv[MAX_ARGV_SIZE];  
    
  // Count the number of non empty command lines.
  
  int line_nr = 0;
 
  
  // Position of each command in a command line.
  
  enum cmd_pos pos;  // {single, first, middle, last}
  
  
  // Pipe read descriptor to the pipe to the "left".
  
  int left_pipe_read_fd = -1;

  // Count the number of children forked for each command line. 

  int children = 0; 
  

  while(1) {

    do {
      
      // Print the command prompt including the command line counter. 
      printf(" %d> ", line_nr);
      fflush(NULL);
      
      
      // Read input from the user. 
      if ( fgets(line_buffer, COMMAND_LINE_BUFFER_SIZE, stdin) == NULL) {
	perror("====== ERROR ====> READING COMMAND LINE FAILED :(");
	exit(EXIT_FAILURE);
      }

      // Exit if the user types "exit" and presses enter. 
      if (strcmp(line_buffer, "exit\n") == 0) {
	printf("     Goodbye!\n");
	exit(EXIT_SUCCESS);
      }
      
      // If the user presses enter without typing anything else, don't
      // update the command line counter, just start over again.
      
    } while (empty_line(line_buffer));
    
    // We got some input from the user.
    line_nr++;
    
    // Parse the command line
    do {
      pos = next_command(line_buffer, argv);
      
      // After the call to the next_command() parser function, the
      // command possition within the command line is now available in the pos
      // varialble.
      
      DBG("\n%6s command %s\n", pos2str(pos), argv[0]);
      
      // Loop through the argv and print the command data. 
          
      int i = 0;
      
      
      while (argv[i] != NULL) {
	DBG("         argv[%d] @ [0x%x] = \"%s\"\n", i, (unsigned int) argv[i], argv[i]);
	i++;
      }
      
      
      // Create a pipe fork a new process for the command. We also
      // must remember the read descriptor to the new pipe. This
      // descriptor will become the read descriptor to the pipe to the
      // "left" for the next command (if any).
      
      left_pipe_read_fd = pipe_and_fork(pos, argv, left_pipe_read_fd);
      
      children++;

      // When are we done?
    } while (pos != single && pos != last);
    
    
    DBG("\nAfter calling next_command(), line [0x%X]  ==>%s<==\n",  
	(unsigned int) &line_buffer, line_buffer);
    
    
    // The parent goes here after after all children have been 
    // created for the command. 
    
    // TODO: Make sure shell doesn't print a new prompt until 
    // all the command processes (children) have terminated.
    while(children>0){
      wait(NULL);   
      children--;
    }
    
  } // end while(1)
} // end of main()
Пример #4
0
/*
 * ===  FUNCTION  ==============================================================
 *         Name:  run_test
 *
 *  Description:  Flexible method for running tests on the ccsrch suite
 *
 *                LOG FILE TESTS - Format: SELF_LOG
 *                    Verifies that the modified ccsrch successfully detects
 *                    its own log file regardless of path
 *                    Directory scanned: ./tests
 *                    Log file outputs:
 *                        ./tests/log.log
 *                        tests/../tests/log.log
 *                        tests/log.log
 *                        log.log
 *
 *                    Tests absolute paths, relative with redundancy, relative,
 *                    symlinks and no log file output
 *                
 *                IMAGE FILE TESTS - Format: IMAGE
 *                    Verifies that the modified ccsrch successfully detects
 *                    and skips image files
 *                    Files scanned: tests/img.jpg
 *                                   tests/img.png
 *                                   tests/img.gif
 *                                   tests/img.not_an_image_extension
 *                                   tests/not_an_image.jpg
 *
 *                SEPARATOR TESTS - Format: SKIPCHARS
 *                    Verifies that the modified ccsrch successfully detects and
 *                    ignores the default ignore characters
 *                    Tests, in order:
 *                        space
 *                        \n
 *                        \r
 *                        -
 *                        combination of above
 *
 *                    There should be 3 credit card matches in the given file
 *                    out of 6 potential PANs
 *
 *                COMPRESSION TESTS - Format: ZIP
 *                    Verifies that the modified ccsrch successfully detects,
 *                    unpacks and parses compressed files.
 *                    Tests, in order:
 *                        tar.gzip
 *                        mac os zip file
 *                        zip file
 *                        zip file containing zip files
 *
 *                PDF TESTS - Format: PDF
 *                    Verifies that the modified ccsrch successfully detects,
 *                    unpacks and parses PDF Documents.
 *
 *                .xlsx TESTS - Format: MS_EXCELX
 *                    Verifies that the modified ccsrch successfully detects,
 *                    unpacks and parses xlsx documents.
 *
 *                .docx TESTS - Format: MS_WORDX
 *                    Verifies that the modified ccsrch successfully detects,
 *                    unpacks and parses docx documents.
 *
 *                ODS TESTS - Format: ODS
 *                    Verifies that the modified ccsrch successfully detects,
 *                    unpacks and parses ODS and OTS Open Document Spreadsheet
 *                    formatted documents.
 *                    Tests, in order:
 *                        ods.ods
 *                        ots.ots
 *
 *                ODT TESTS - Format: ODT
 *                    Verifies that the modified ccsrch successfully detects,
 *                    unpacks and parses ODT and OTT Open Document formatted
 *                    documents.
 *                    Tests, in order:
 *                        odt.odt
 *                        ott.ott
 *
 *                BINARY TESTS - FormatL BINARY
 *                    Verifies that AUDIO, VIDEO, EXECUTABLE and BINARY types
 *                    are skipped appropriately.
 *                    Tests, in order:
 *                        ogv.ogv
 *                        mp3.mp3
 *                        ccsrch.o
 *                        ccsrch
 *
 *      Version:  0.0.1
 *       Params:  FILE *output
 *                file_type type
 *      Returns:  void
 *        Usage:  run_test( FILE *output, file_type type )
 *      Outputs:  Test results for given format
 * =============================================================================
 */
void run_test(FILE *output, file_type type) {
    int num_tests, loop_count;
    char buffer[80], **test_files, **expected_results;
    int i, pipe;
    pid_t pid;
    FILE *in_out;
    bool found;

    // Test counts
    switch (type) {
        case SELF_LOG:
        case ZIP:
        case BINARY:
            num_tests = 4;
            break;
        case IMAGE:
        case SKIPCHARS:
            num_tests = 5;
            break;
        case PDF:
        case MS_EXCELX:
        case MS_WORDX:
            num_tests = 1;
            break;
        case ODS:
        case ODT:
            num_tests = 2;
            break;
    }

    // Initialise as empty strings. 2D memset
    test_files = malloc(sizeof(char*) * num_tests);
    expected_results = malloc(sizeof(char*) * num_tests);
    for ( i = 0; i < num_tests; i++ ) {
        test_files[i] = malloc(MAXPATH);
        expected_results[i] = malloc(MAXPATH);
        memset(test_files[i], '\0', MAXPATH);
        memset(expected_results[i], '\0', MAXPATH);
    }

    // Files and expected outputs
    switch (type) {
        case SELF_LOG:
            strncpy(test_files[0], "./tests/log.log", MAXPATH); /* Absolute path (as best we can) */
            strncpy(test_files[1], "tests/../tests/log.log", MAXPATH); /* Weird path */
            strncpy(test_files[2], "tests/log.log", MAXPATH); /* Relative path */
            strncpy(test_files[3], "tests/log_symlink", MAXPATH); /* Symlink test */
            for ( i = 0; i < num_tests; i++ )
                strncpy(expected_results[i], "Skipping log file: ", MAXPATH);
            break;
        case IMAGE:
            strncpy(test_files[0], "tests/img.jpg", MAXPATH);
            strncpy(test_files[1], "tests/img.png", MAXPATH);
            strncpy(test_files[2], "tests/img.gif", MAXPATH);
            strncpy(test_files[3], "tests/img.not_an_image_extension", MAXPATH);
            strncpy(test_files[4], "tests/not_an_image.jpg", MAXPATH);
            for ( i = 0; i < num_tests - 1; i++ )
                strncpy(expected_results[i], "Binary types skipped ->\t\t1",
                        MAXPATH);
            strncpy(expected_results[4], "Binary types skipped ->\t\t0",
                    MAXPATH);
            break;
        case BINARY:
            strncpy(test_files[0], "tests/ogv.ogv", MAXPATH);
            strncpy(test_files[1], "tests/mp3.mp3", MAXPATH);
            strncpy(test_files[2], "tests/ccsrch.o", MAXPATH);
            strncpy(test_files[3], "tests/ccsrch", MAXPATH);
            for ( i = 0; i < num_tests - 1; i++ )
                strncpy(expected_results[i], "Binary types skipped ->\t\t1",
                        MAXPATH);
            break;
        case SKIPCHARS:
            strncpy(test_files[0], "tests/ignore_space.txt", MAXPATH);
            strncpy(test_files[1], "tests/ignore_unix_newline.txt", MAXPATH);
            strncpy(test_files[2], "tests/ignore_windows_newline.txt", MAXPATH);
            strncpy(test_files[3], "tests/ignore_dash.txt", MAXPATH);
            strncpy(test_files[4], "tests/ignore_combination.txt", MAXPATH);
            for ( i = 0; i < num_tests; i++ )
                strncpy(expected_results[i], "Credit card matches ->\t\t3",
                        MAXPATH);
            break;
        case ZIP:
            strncpy(test_files[0], "tests/tartest.tar.gz", MAXPATH);
            strncpy(test_files[1], "tests/test.mac.zip", MAXPATH);
            strncpy(test_files[2], "tests/test.zip", MAXPATH);
            strncpy(test_files[3], "tests/test2.zip", MAXPATH);
            strncpy(expected_results[0], "Credit card matches ->\t\t9", MAXPATH);
            strncpy(expected_results[1], "Credit card matches ->\t\t30", MAXPATH);
            strncpy(expected_results[2], "Credit card matches ->\t\t30", MAXPATH);
            strncpy(expected_results[3], "Credit card matches ->\t\t15", MAXPATH);
            break;
        case PDF:
            strncpy(test_files[0], "tests/pdf.pdf", MAXPATH);
            strncpy(expected_results[0], "Credit card matches ->\t\t15", MAXPATH);
            break;
        case MS_EXCELX:
            strncpy(test_files[0], "tests/xlsx.xlsx", MAXPATH);
            strncpy(expected_results[0], "Credit card matches ->\t\t3", MAXPATH);
            break;
        case MS_WORDX:
            strncpy(test_files[0], "tests/docx.docx", MAXPATH);
            strncpy(expected_results[0], "Credit card matches ->\t\t3", MAXPATH);
            break;
        case ODS:
            strncpy(test_files[0], "tests/ods.ods", MAXPATH);
            strncpy(test_files[1], "tests/ots.ots", MAXPATH);
            for ( i = 0; i < num_tests; i++ )
                strncpy(expected_results[i], "Credit card matches ->\t\t3",
                        MAXPATH);
            break;
        case ODT:
            strncpy(test_files[0], "tests/odt.odt", MAXPATH);
            strncpy(test_files[1], "tests/ott.ott", MAXPATH);
            for ( i = 0; i < num_tests; i++ )
                strncpy(expected_results[i], "Credit card matches ->\t\t3",
                        MAXPATH);
            break;
    }

    // Loop counts
    switch (type) {
        case SELF_LOG:
            loop_count = num_tests + 1;
            break;
        default:
            loop_count = num_tests;
    }

    for ( i = 0; i < loop_count; i++ ) {
        pid = pipe_and_fork(&pipe, true);
        if (pid == (pid_t) 0) {
            /* Child */
            dup2(pipe, STDOUT_FILENO);
            dup2(pipe, STDERR_FILENO);

            // Particulars of the invocation of ccsrch
            switch (type) {
                case SELF_LOG:
                    if (i < num_tests)
                        execl("./ccsrch", "ccsrch", "-o", test_files[i], "tests",
                                NULL);
                    else
                        execl("./ccsrch", "ccsrch", "tests", NULL);
                    break;
                default:
                    execl("./ccsrch", "ccsrch", test_files[i], NULL);
            }

        } else if (pid > (pid_t) 0) {
            /* Parent */
            in_out = fdopen(pipe, "r");
            found = false;
            while (!found && in_out != NULL && !feof(in_out)) {
                fgets(buffer, 80, in_out);

                // Result checking
                switch (type) {
                    case SELF_LOG:
                        if (strstr(buffer, expected_results[0]) != NULL)
                            found = true;
                        break;
                    default:
                        if (strstr(buffer, expected_results[i]) != NULL)
                            found = true;
                }
            }

            // Result printing
            switch (type) {
                case SELF_LOG:
                    if ((i < num_tests && found) || (i == num_tests && !found))
                        fprintf(output, "%s", ".");
                    else
                        fprintf(output, "%s", "F");
                    break;
                default:
                    if (found)
                        fprintf(output, "%s", ".");
                    else
                        fprintf(output, "%s", "F");
            }
            fflush(output);

            wait(NULL);
            close(pipe);
        } else {
            /* Fork failed */
            fprintf(stderr, "\n%s\n", "Failed to pipe and fork");
        }
    }

    // Clean up
    for ( i = 0; i < num_tests; i++ ) {
        free(test_files[i]);
        free(expected_results[i]);
    }
    free(test_files);
    free(expected_results);
}
Пример #5
0
/*
 * ===  FUNCTION  ==============================================================
 *         Name:  detect_file_type
 *
 *  Description:  Detects file type of given file and returns true if we should
 *                skip it and false otherwise.
 *                Forks and calls file from command line. Parses result to
 *                determine file type.
 *
 *      Version:  0.0.1
 *       Params:  char *filename
 *      Returns:  bool true if type to skip
 *                bool false otherwise
 *        Usage:  detect_file_type( char *filename )
 *      Outputs:  N/A
 *
 *        Notes:
 *                Open Office mime types from:
 *                  http://www.openoffice.org/framework/documentation/mimetypes/mimetypes.html
 *                Image mime types from:
 *                  http://www.iana.org/assignments/media-types/image/index.html
 * =============================================================================
 */
file_type detect_file_type(char *filename) {
    char buffer[80], *pipe_output, full_filename[MAXPATH], *file_cmd_output;
    int pipe, read_count, fork_count = 0;
    pid_t pid;
    file_type type;
    FILE *in_out;

    // Default
    type = UNKNOWN;
    while (fork_count++ < 2) {
        pid = pipe_and_fork(&pipe, true);
        if (pid == (pid_t) 0) {
            /* Child */
            dup2(pipe, STDOUT_FILENO);
            //dup2(pipe, STDERR_FILENO); /* Remove comment if you need to debug */

            full_filename[0] = '\0';
            if (filename[0] != '/')
                strncat(full_filename, pwd, MAXPATH - strlen(full_filename));
            strncat(full_filename, filename, MAXPATH - strlen(full_filename));

            if (fork_count == 1)
                execlp("file", "file", "--mime", "-b", full_filename, NULL);
            else
                execlp("file", "file", "-b", full_filename, NULL);

            // Exec failed
#ifdef DEBUG
            perror("detect_file_type: failed to execlp \"file\"");
#endif
            close(pipe);
            exit(errno);

        } else if (pid > (pid_t) 0) {
            /* Parent */
            in_out = fdopen(pipe, "r");
            file_cmd_output = malloc(80);
            file_cmd_output[0] = '\0';
            read_count = 1;
            while (in_out != NULL && !feof(in_out)) {
                pipe_output = fgets(buffer, 80, in_out);
                if (pipe_output != NULL) {
                    file_cmd_output = realloc(file_cmd_output,
                            strlen(file_cmd_output) + strlen(pipe_output) + 1);
                    strncat(file_cmd_output, pipe_output, 80);
                }
            }

            // Work out what it is
            if (file_cmd_output != NULL) {
                if (strstr(file_cmd_output, "text/plain") != NULL)
                    type = ASCII;
                else if (strstr(file_cmd_output, "application/x-executable") !=
                        NULL || strstr(file_cmd_output, "executable") != NULL ||
                        strstr(file_cmd_output, "relocatable") != NULL)
                    type = EXECUTABLE;
                else if (strstr(file_cmd_output, "image/") != NULL ||
                        strstr(file_cmd_output, "image data") != NULL)
                    type = IMAGE;
                else if (strstr(file_cmd_output, "video/") != NULL || 
                        strstr(file_cmd_output, "video") != NULL ||
                        strstr(file_cmd_output, "AVI") != NULL ||
                        strstr(file_cmd_output, "MPEG") != NULL)
                    type = VIDEO;
                else if (strstr(file_cmd_output, "audio/") != NULL || 
                        strstr(file_cmd_output, "application/octet-stream") !=
                        NULL || strstr(file_cmd_output, "Audio file") != NULL)
                    type = AUDIO;
                else if (strstr(file_cmd_output, "application/x-tar") != NULL)
                    type = TAR;
                else if (strstr(file_cmd_output, "application/zip") != NULL) {
                    // Due to poor msword filetype detection, we need to rely on
                    // file extensions here
                    if (strncmp(last_strstr(filename, "."), ".docx", 7) == 0)
                        type = MS_WORDX;
                    else if (strncmp(last_strstr(filename, "."), ".xlsx", 7) == 0)
                        type = MS_EXCELX;
                    else
                        // Make ZIP the default here
                        type = ZIP;
                }
                else if (strstr(file_cmd_output, "application/x-gzip") != NULL)
                    type = GZIP;
                else if (strstr(file_cmd_output, "application/xml") != NULL)
                    type = XML;
                else if (strstr(file_cmd_output, "application/pdf") != NULL)
                    type = PDF;
                else if (strstr(file_cmd_output, "opendocument.text-template") != NULL)
                    type = OTT;
                else if (strstr(file_cmd_output, "opendocument.text") != NULL)
                    type = ODT;
                else if (strstr(file_cmd_output, "opendocument.spreadsheet.template") != NULL)
                    type = OTS;
                else if (strstr(file_cmd_output, "opendocument.spreadsheet") != NULL)
                    type = ODS;
                else if (strstr(file_cmd_output, "application/vnd.ms-excel") != NULL)
                    type = MS_EXCEL;
                else if (strstr(file_cmd_output, "application/vnd.ms-word") != NULL)
                    type = MS_WORD;
                else if (strstr(file_cmd_output, "application/msword") != NULL ||
                        strstr(file_cmd_output, "application/vnd.ms-office") != NULL) {
                    // Due to poor msword filetype detection, we need to rely on
                    // file extensions here
                    if (strncmp(last_strstr(filename, "."), ".doc", 6) == 0)
                        type = MS_WORD;
                    else if (strncmp(last_strstr(filename, "."), ".xls", 6) == 0)
                        type = MS_EXCEL;
                    else
                        // Make MS_WORD the default here
                        type = MS_WORD;
                }
                // This should stay last. Other legitimate mime types often use this charset
                else if (fork_count == 2 && strstr(file_cmd_output, "binary") !=
                         NULL)
                    type = BINARY;
                else
                    type = UNKNOWN;
            }

            // Clean up
            wait(NULL);
            close(pipe);
            free(file_cmd_output);

#ifdef DEBUG
        } else {
            /* Fork failed */
            fprintf(stderr, "\n%s\n", "Failed to pipe and fork");
#endif
        }

        // Only check again if we didn't know what it was
        if (type != UNKNOWN)
            break;

    }

    return type;
}