#c #image #jpeg #recovery #cs50
#c #изображение #jpeg #восстановление #cs50
Вопрос:
Итак, моя программа recover.c работает хорошо, за исключением того факта, что ей не удается восстановить ВСЕ 50 изображений из файла card.raw.
Я могу заставить ее восстановить только 49 из 50 изображений. Я почти уверен, что отсутствующее изображение — это самое первое изображение (девушка на фоне снега), потому что я видел это изображение на ранней стадии в процессе написания и тестирования, но финальная программа, похоже, больше не восстанавливает это изображение.
Любая помощь, ребята?
/**
* recover.c
*
* Computer Science 50
* Problem Set 4
*
* Recovers JPEGs from a forensic image.
*/
#include <stdio.h>
#include <stdlib.h>
#include <stdint.h>
typedef uint8_t BYTE;
typedef uint32_t DWORD;
typedef int32_t LONG;
typedef uint16_t WORD;
typedef struct
{
BYTE rgbtBlue;
BYTE rgbtGreen;
BYTE rgbtRed;
} __attribute__((__packed__))
RGBTRIPLE;
int main(void)
{
// OPEN CARD FILE
char* infile = "card.raw";
FILE* card = fopen(infile, "r");
if (card == NULL)
{
printf("Could not open %s.n", "card.raw");
return 2;
}
int f = 0, c = 0, imageno = 0;
// c signals that a jpg is being written
FILE* images;
char title[25];
BYTE buffer[512];
/*repeat until end of card*/
do
{
//read one block into buffer
fread(buffer, 512, 1, card);
if (buffer[0] == 0xff amp;amp; buffer[1] == 0xd8 amp;amp; buffer[2] == 0xff)
{
if (imageno < 10)
{
sprintf(title, "00%d.jpg", imageno); //change jpg title
}
else
{
sprintf(title, "0%d.jpg", imageno); //change jpg title
}
if (f == 1) //close previous jpg
{
fclose(images);
imageno ;
}
images = fopen(title, "w");
f = 1; //very first jpg has been opened
c = 1; //jpg open
}
//jpg already open?
if (c == 1) fwrite(buffer, 512, 1, images);
}
while (!feof(card));
return 0;
//close any remaining files
}
Комментарии:
1. Рассмотрите один
sprintf(title, "d.jpg", imageno)
вместо двухsprintf()
вызовов, которые вы используете сейчас.2. @JohnBollinger спасибо за это!
3. Проверьте возвращаемые значения ваших вызовов функций — например
fread()
, — на наличие кодов ошибок или неожиданных результатов.4.
} while (!feof(card));
плохо. Это означает, что вы уже обработали незаконное чтение. Заметным по его отсутствию является любая проверка (или использование) возвращаемого значения изfread
. В SO есть множество вопросов о восстановлении изображений с карты.5. измените
do...while()
цикл наwhile( fread(...) ) { ... }
цикл. НЕ управляйте никаким циклом с помощью функции:feof()
Ответ №1:
Вы создаете имя файла на основе значения переменной imageno
. Позже вы увеличиваете эту переменную, но только в том случае, если ваша программа ранее открыла другой файл. В частности, вы не увеличиваете его после открытия самого первого файла, поэтому для второго файла вычисляется то же имя, что и для первого, и первый извлеченный файл перезаписывается.
Вы должны безоговорочно увеличивать imageno
значение при каждом создании нового имени файла или, возможно, при каждом открытии файла.
Комментарии:
1. Вы, сэр, настоящий герой.