2017-11-02 6 views
1

私はこの問題のセットを提出しましたが、終了コードが "1ではなく0であると予想されるため、完全なマークグレードを取得できません"。しかし、コード(recover.cファイル)を見れば、終了コードは0です。何が間違っていますか?このプログラムは、破損したファイルのビットを読み込み、JPGファイルを構成するビットを見つけて別のファイルに書き込むことを目的としたすべての処理を実行します。唯一の問題は、前述の終了コードの問題です。助けてください!終了コード0(1ではない)が必要ですか?

recover.cファイル

#include <stdio.h> 
#include <cs50.h> 
#include <stdlib.h> 
#include "bmp.h" 


int main (void){ 



    FILE* card_ptr = fopen("card.raw","r"); 

    if (card_ptr == NULL){ 

     fprintf(stderr,"File Not Found!"); 
     return 1; 
    } 

    BYTE buffer[512]; 

    bool found_jpg = false; 

    FILE* new_jpg_ptr; 

    int file_counter = 0; 

    while(fread(buffer,1,512,card_ptr)!=0x00){ 

     if(buffer[0]== 0xff && buffer[1]== 0xd8 && buffer[2]==0xff && (buffer[3] & 0xf0)== 0xe0){ 

      if(!found_jpg){ 

       char filename[8]; 

       sprintf(filename, "%03i.jpg", file_counter++); 

       found_jpg = true; 

       new_jpg_ptr = fopen(filename,"w"); 

       if(new_jpg_ptr == NULL){ 
        return 2; 
       } 

       fwrite(buffer,1,512,new_jpg_ptr); 

      } 

      else { 

       fclose(new_jpg_ptr); 

       char filename[8]; 

       sprintf(filename, "%03i.jpg", file_counter++); 

       found_jpg = true; 

       new_jpg_ptr = fopen(filename,"w"); 

       if(new_jpg_ptr == NULL){ 
        return 3; 
       } 

       fwrite(buffer,1,512, new_jpg_ptr); 


      } 

     } 

     else { 

      if(found_jpg){ 

       fwrite(buffer,1,512, new_jpg_ptr); 

      } 


     } 




    } 

    fclose(new_jpg_ptr); 

    fclose(card_ptr); 

    return 0; 
} 

bmp.hファイル

/** 
* BMP-related data types based on Microsoft's own. 
*/ 

#include <stdint.h> 

/** 
* Common Data Types 
* 
* The data types in this section are essentially aliases for C/C++ 
* primitive data types. 
* 
* Adapted from https://msdn.microsoft.com/en-us/library/cc230309.aspx. 
* See http://en.wikipedia.org/wiki/Stdint.h for more on stdint.h. 
*/ 
typedef uint8_t BYTE; 
typedef uint32_t DWORD; 
typedef int32_t LONG; 
typedef uint16_t WORD; 

/** 
* BITMAPFILEHEADER 
* 
* The BITMAPFILEHEADER structure contains information about the type, size, 
* and layout of a file that contains a DIB [device-independent bitmap]. 
* 
* Adapted from https://msdn.microsoft.com/en-us/library/dd183374(v=vs.85).aspx. 
*/ 
typedef struct 
{ 
    WORD bfType; 
    DWORD bfSize; 
    WORD bfReserved1; 
    WORD bfReserved2; 
    DWORD bfOffBits; 
} __attribute__((__packed__)) 
BITMAPFILEHEADER; 

/** 
* BITMAPINFOHEADER 
* 
* The BITMAPINFOHEADER structure contains information about the 
* dimensions and color format of a DIB [device-independent bitmap]. 
* 
* Adapted from https://msdn.microsoft.com/en-us/library/dd183376(v=vs.85).aspx. 
*/ 
typedef struct 
{ 
    DWORD biSize; 
    LONG biWidth; 
    LONG biHeight; 
    WORD biPlanes; 
    WORD biBitCount; 
    DWORD biCompression; 
    DWORD biSizeImage; 
    LONG biXPelsPerMeter; 
    LONG biYPelsPerMeter; 
    DWORD biClrUsed; 
    DWORD biClrImportant; 
} __attribute__((__packed__)) 
BITMAPINFOHEADER; 

/** 
* RGBTRIPLE 
* 
* This structure describes a color consisting of relative intensities of 
* red, green, and blue. 
* 
* Adapted from https://msdn.microsoft.com/en-us/library/dd162939(v=vs.85).aspx. 
*/ 
typedef struct 
{ 
    BYTE rgbtBlue; 
    BYTE rgbtGreen; 
    BYTE rgbtRed; 
} __attribute__((__packed__)) 
RGBTRIPLE; 
+2

おそらくfopenが失敗し、終了コード1につながったでしょうか? –

+1

また、1000以上の入力ファイルがある場合、このプログラムはバッファをオーバーフローさせます。 –

+0

fclose(new_jpg_ptr);が常に呼び出されますが、new_jpg_ptrが未初期化されることがあります –

答えて

1

私は同じ問題を経験しました。私のプログラムは、戻りコード1の明らかな理由がなく、期待どおりに機能しました。ご存知のように、ヘッダーファイルにはいくつかの定義が含まれています。これらの定義をコアファイルに配置することで、私の問題が解決されました。おそらく、あなたのbmp.hファイルから必要な定義をrecover.cに移動すると、check50はコンパイルできます。

興味があれば私のソリューションです。

// Recover any forgotten JPEGS from a given forensic image 

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

typedef uint8_t BYTE; 

typedef struct 
{ 
    BYTE byte_1; 
    BYTE byte_2; 
    BYTE byte_3; 
    BYTE byte_4_min; 
    BYTE byte_4_max; 
} __attribute__((__packed__)) 
SIG; 

// declare helper function prototypes 
int check_args(int argc, char *argv[]); 
bool signature_is_present(BYTE potential_sig[4], SIG jpeg_sig); 

SIG set_jpeg_signature(void); 

// main program 
int main (int argc, char *argv[]) 
{ 
    // check input for validity 
    int check_args_value = check_args(argc, argv); 
    if (check_args_value != 0) 
    { 
     return check_args_value; 
    } 

    // call function to set default jpeg signature 
    SIG jpeg_sig = set_jpeg_signature(); 

    // open buffers and declare other necessary variables for later use 
    BYTE FAT_block[512]; 
    BYTE first_byte[1]; 
    int signature_offset = -4; 
    int counter = 0; 

    // open forensic image 
    FILE * inptr = fopen(argv[1], "r"); 
    FILE * outptr = NULL; 

    // loop through file searching for first '255' 
    while (fread(first_byte, sizeof(BYTE), 1, inptr) == 1) 
    { 
     // check if byte is 255, the first byte of a jpeg signature 
     if (*first_byte == jpeg_sig.byte_1) 
     { 
      // check for signature 
      BYTE possible_sig[4]; 

      // back pointer up one byte to compensate for already discovered 255 
      fseek(inptr, -1, SEEK_CUR); 

      // read four bytes from file that could potentially be a signature. 
      fread(possible_sig, sizeof(possible_sig), 1, inptr); 

      if (signature_is_present(possible_sig, jpeg_sig)) 
      { 
       // close previously open write file, if any. 
       if (outptr != NULL) 
       { 
        fclose(outptr); 

        //Increment counter for image signatures found. 
        counter++; 
       } 

       // setup name for image file 
       char file_name[8] = {}; 
       snprintf(file_name, 8, "%.3i.jpg\n", counter); 

       // move pointer back 4 bytes after checking what they contain 
       fseek(inptr, signature_offset, SEEK_CUR); 

       //read FAT block from forensic image into buffer 
       fread(FAT_block, sizeof(FAT_block), 1, inptr); 

       // open new output file based on current signature 
       outptr = fopen(file_name, "w"); 

       // write FAT block buffer to file 
       fwrite(FAT_block, sizeof(FAT_block), 1, outptr); 
      } 
      else // byte is 255 but not part of a signature 
      { 
       if (outptr != NULL) 
       { 
        // move pointer back 4 bytes after checking what they contain 
        fseek(inptr, signature_offset, SEEK_CUR); 

        //read FAT block from forensic image into buffer 
        fread(FAT_block, sizeof(FAT_block), 1, inptr); 

        // write FAT block buffer to file 
        fwrite(FAT_block, sizeof(FAT_block), 1, outptr); 
       } 
      } 
     } 
     else // if byte is not 255 
     { 
      if (outptr != NULL) 
      { 
       //back up one byte 
       fseek(inptr, -1, SEEK_CUR); 

       //read FAT block from forensic image into buffer 
       fread(FAT_block, sizeof(FAT_block), 1, inptr); 

       // write FAT block buffer to file 
       fwrite(FAT_block, sizeof(FAT_block), 1, outptr); 
      } 
     } 
    } 

    // close files 
    fclose(inptr); 

    if (outptr != NULL) 
    { 
     fclose(outptr); 
    } 

    return 0; 
} 

// helper functions 
int check_args(int argc, char *argv[]) 
{ 
    if (argc != 2) 
    { 
     fprintf(stderr, "Invalid Input.\nForensic image file must be provided.\n"); 
     return 1; 
    } 

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

    if (inptr == NULL) 
    { 
     fprintf(stderr, "File does not exist.\n"); 
     return 2; 
    } 

    fclose(inptr); 

    return 0; 
} 

bool signature_is_present(BYTE potential_sig[4], SIG jpeg_sig) 
{ 
    if(potential_sig[0] == jpeg_sig.byte_1 && 
     potential_sig[1] == jpeg_sig.byte_2 && 
     potential_sig[2] == jpeg_sig.byte_3 && 
     potential_sig[3] >= jpeg_sig.byte_4_min && 
     potential_sig[3] <= jpeg_sig.byte_4_max) 
    { 
     return true; 
    } 

    return false; 
} 

SIG set_jpeg_signature(void) 
{ 
    SIG jpeg_sig; 

    jpeg_sig.byte_1 = 255; 
    jpeg_sig.byte_2 = 216; 
    jpeg_sig.byte_3 = 255; 
    jpeg_sig.byte_4_min = 224; 
    jpeg_sig.byte_4_max = 239; 

    return jpeg_sig; 
} 
関連する問題