5 minute read

Exercise 3 Recover - Make a program that takes a raw file of lost jpgs as input and sorts through the bytes to regenerate the individual images.

#include <stdio.h>
#include <stdlib.h>
#include <stdint.h>

int main(int argc, char *argv[])
{
    //Your program should accept exactly one command-line argument, the name of a forensic image from which to recover JPEGs.
    //If your program is not executed with exactly one command-line argument, it should remind the user of correct usage,
    //and main should return 1.
    if(argc != 2)
    {
        printf("Correct usage ./recover FILE\n");
        return 1;
    }
    //If the forensic image cannot be opened for reading, your program should inform the user as much, and main should return 1.

    FILE *card = fopen(argv[1], "r");

    //buffer for block of data
    uint8_t buffer[512];

    FILE *img = NULL;
    int count = 0;
    //while ther is still data being read out
    while(fread(buffer, 1, 512, card) == 512)
    {
        //create jpegs from the data
        if(buffer[0] == 0xff && buffer[1] == 0xd8 && buffer[2] == 0xff)
        {
            if(img != NULL)
            {
                fclose(img);
            }

            char filename[8];
            sprintf(filename, "%03i.jpg", count);
            img = fopen(filename, "w");
            count ++;
        }

        if(img != NULL)
        {
            fwrite(buffer, 1, 512, img);
        }
    }
    if(img != NULL)
    {
        fclose(img);
    }
    fclose(card);
}

Exercise 2 Filters - Complete the helper functions to implement greyscale, reflection, sepia, and blurred filters to an image.

#include "helpers.h"
#include <math.h>

// Convert image to grayscale
void grayscale(int height, int width, RGBTRIPLE image[height][width])
{
    for(int i = 0; i < height; i++)
    {
        for(int j = 0; j < width; j++)
        {
            //new value that will be given to each of these individual components
            float grey = (image[i][j].rgbtRed + image[i][j].rgbtBlue + image[i][j].rgbtGreen ) / 3;
            int gray = round(grey);
            //update values
            image[i][j].rgbtRed = image[i][j].rgbtBlue = image[i][j].rgbtGreen = gray;
        }
    }
    return;
}

// Convert image to sepia
void sepia(int height, int width, RGBTRIPLE image[height][width])
{
    for(int i = 0; i < height; i++)
    {
        for(int j = 0; j < width; j++)
        {
            //algorithm for sepia given:
            // sepiaRed = .393 * originalRed + .769 * originalGreen + .189 * originalBlue
            // sepiaGreen = .349 * originalRed + .686 * originalGreen + .168 * originalBlue
            // sepiaBlue = .272 * originalRed + .534 * originalGreen + .131 * originalBlue
            float sepiaRed = .393 * image[i][j].rgbtRed + .769 * image[i][j].rgbtGreen + .189 * image[i][j].rgbtBlue;
            float sepiaGreen = .349 * image[i][j].rgbtRed + .686 * image[i][j].rgbtGreen + .168 * image[i][j].rgbtBlue;
            float sepiaBlue = .272 * image[i][j].rgbtRed + .534 * image[i][j].rgbtGreen + .131 * image[i][j].rgbtBlue;
            //round output
            int sepiared = round(sepiaRed);
            int sepiablue = round(sepiaBlue);
            int sepiagreen = round(sepiaGreen);
            //check if more than 255 make 255
            if(sepiared > 255)
            {
                sepiared = 255;
            }
            if(sepiablue > 255)
            {
                sepiablue = 255;
            }
            if(sepiagreen > 255)
            {
                sepiagreen = 255;
            }
            image[i][j].rgbtBlue = sepiablue;
            image[i][j].rgbtGreen = sepiagreen;
            image[i][j].rgbtRed = sepiared;
        }
    }
    return;
}

// Reflect image horizontally
void reflect(int height, int width, RGBTRIPLE image[height][width])
{
    //for reflecting the pixes i can probably find the dimensions of the image by looping over i and j then use that to find the
    //dimensions of the image. based off that i can just loop to switch the first with the last and so on and i only need to do j
    for(int i = 0; i < height; i++)
    {
        for(int j = 0; j < width / 2; j++)
        {
            int blue = image[i][j].rgbtBlue;
            int green = image[i][j].rgbtGreen;
            int red = image[i][j].rgbtRed;
            image[i][j].rgbtBlue = image[i][width - j - 1].rgbtBlue;
            image[i][j].rgbtGreen = image[i][width - j - 1].rgbtGreen;
            image[i][j].rgbtRed = image[i][width - j - 1].rgbtRed;
            image[i][width - j - 1].rgbtBlue = blue;
            image[i][width - j - 1].rgbtGreen = green;
            image[i][width - j - 1].rgbtRed = red;
        }
    }
    return;
}

// Blur image
void blur(int height, int width, RGBTRIPLE image[height][width])
{
    //for this one maybe i can add up pixels [i][j] + [i + 1][j] + [i][j + 1] + [i + 1][j + 1] then set each of those to the average
    RGBTRIPLE copy[height][width];
    for(int i = 0; i < height; i++)
    {
        for(int j = 0; j < width; j++)
        {
            copy[i][j] = image[i][j];
        }
    }

    for(int i = 0; i < height; i++)
    {
        for(int j = 0; j < width; j++)
        {
            int red_sum = 0;
                green_sum = 0;
                blue_sum = 0;
                count = 0;
            //make a copy of image to calculate new pixel values and modify original without it factoring into next calc
            //check you are adding only terms that exist
            for(int di = -1; di <= 1; di++)
            {
                for (int dj = -1; dj <= 1; dj++)
                {
                    int ni = i + di;
                    int nj = j + dj;
                    if(ni >=0 && ni < height && nj >= 0 && nj < width)
                    {

                        red_sum += copy[ni][nj].rgbtRed;
                        blue_sum += copy[ni][nj].rgbtBlue;
                        green_sum += copy[ni][nj].rgbtGreen;
                        count ++;
                    }
                }
            }
            image[i][j].rgbtRed = round(red_sum/count);
            image[i][j].rgbtBlue = round(blue_sum / count);
            image[i][j].rgbtGreen = round(green_sum / count);
        }
    }
    return;
}

Exercise 1 Volume - Complete the two necessary functions to first copy the header of a wav music file and then to scale the volume of the file by multiplying each sample by the factor indicated by the user as input.

// Modifies the volume of an audio file

#include <stdint.h>
#include <stdio.h>
#include <stdlib.h>

// Number of bytes in .wav header
const int HEADER_SIZE = 44;

int main(int argc, char *argv[])
{
    // Check command-line arguments
    if (argc != 4)
    {
        printf("Usage: ./volume input.wav output.wav factor\n");
        return 1;
    }

    // Open files and determine scaling factor
    FILE *input = fopen(argv[1], "r");
    if (input == NULL)
    {
        printf("Could not open file.\n");
        return 1;
    }

    FILE *output = fopen(argv[2], "w");
    if (output == NULL)
    {
        printf("Could not open file.\n");
        return 1;
    }

    float factor = atof(argv[3]);

    // TODO: Copy header from input file to output file
    uint8_t header[HEADER_SIZE];
    fread(header, 1, HEADER_SIZE, input);
    fwrite(header, 1, HEADER_SIZE, output);


    // TODO: Read samples from input file and write updated data to output file
    int16_t buffer;
    while(fread(&buffer, sizeof(int16_t), 1, input) == 1)
    {
        buffer *= factor;
        fwrite(&buffer, sizeof(int16_t), 1, output);
    }



    // Close files
    fclose(input);
    fclose(output);
}

Section 4 PDF Check - Write program to check if a file is a pdf.

#include <stdio.h>
#include <stdlib.h>
#include <stdint.h>



int main(int argc, char *argv[])
{
    if(argc != 2)
    {
        printf("correct usage ./checkpdf FILE");
    }

    FILE *pdf = fopen(argv[1], "r");

    uint8_t buffer[512];

    while(fread(buffer, 1, 512, pdf) == 512)
    {
        if(buffer[0] == 0x25 && buffer[1] == 0x50 && buffer[2] == 0x44 && buffer[3] == 0x46)
        {
            printf("file is pdf\n");
        }
    }
    fclose(pdf);


}

Updated: