Thread: How exactly do i "create" a binary file to check if my program works?

  1. #1
    Registered User
    Join Date
    Oct 2020
    Posts
    18

    How exactly do i "create" a binary file to check if my program works?

    Hi all, I am currently doing an exercise in KNKING C program a modern approach. THis exerise

    ----------------------
    Of the many techniques for compressing the contents of a file, one of the simplest and fastest is known as run-length encoding. This technique compresses a file by replacing sequences of identical bytes by a pair of bytes: a repetition count followed by a byte to be repeated. For example, suppose that the file to be compressed begins with the following sequence of bytes (shown in hexadecimal):


    46 6F 6F 20 62 61 72 21 21 21 20 20 20 20 20


    The compressed file will contain the following bytes:


    01 46 02 6F 01 20 01 62 01 61 01 72 03 21 05 20


    Run-length encoding works well if the original file contains many long sequences of identical bytes. In the worst case (a file with no repeated bytes), run-length encoding can actually double the length of the file.
    ----------------------------------

    I have made the program, and it should be functioning (cross checked with online answer sources).

    But I am now facing this obstacle. How do i create/make a binary file to test my program? Normally when tresting programs that worked on text files I would just create one in notepad and run it, but I am unsure how to do this with binary files.

    Would appreciate any kind advice. Thank you everyone

  2. #2
    Registered User
    Join Date
    Sep 2020
    Posts
    164
    You could write a program to write your data!

    Code:
    #include <stdio.h>
    
    
    static unsigned char data[] = {
      0x46, 0x6F, 0x6F, 0x20, 0x62, 0x61, 0x72, 0x21, 0x21, 0x21, 0x20, 0x20, 0x20, 0x20, 0x20
    };
    
    
    int main(int argc, char *argv[]) {
       FILE *f = fopen("out.data","wb");
       if(f == NULL) {
          fprintf(stderr,"Unable to open file\n");
          return 0;
       }
       if(fwrite(data, sizeof(data), 1, f) == 1) {
         fprintf(stderr, "Written data successfully\n");
       } else {
         fprintf(stderr, "Write wrror\n");
       }
       fclose(f);
       return 0;
    }
    Here's the output and a dump of the resulting data file:

    Code:
    $ gcc -o writedata writedata.c -Wall -pedantic -O4
    
    $ ./writedata
    Written data successfully
    
    $ od -t x1 out.data
    0000000 46 6f 6f 20 62 61 72 21 21 21 20 20 20 20 20
    0000017
    Just remember when you put in hex numbers, you need to put "0x" in front of the them, to let the compiler know that it is hex.

  3. #3
    Registered User
    Join Date
    Oct 2020
    Posts
    18
    Quote Originally Posted by hamster_nz View Post
    You could write a program to write your data!

    Code:
    #include <stdio.h>
    
    
    static unsigned char data[] = {
      0x46, 0x6F, 0x6F, 0x20, 0x62, 0x61, 0x72, 0x21, 0x21, 0x21, 0x20, 0x20, 0x20, 0x20, 0x20
    };
    
    
    int main(int argc, char *argv[]) {
       FILE *f = fopen("out.data","wb");
       if(f == NULL) {
          fprintf(stderr,"Unable to open file\n");
          return 0;
       }
       if(fwrite(data, sizeof(data), 1, f) == 1) {
         fprintf(stderr, "Written data successfully\n");
       } else {
         fprintf(stderr, "Write wrror\n");
       }
       fclose(f);
       return 0;
    }
    Here's the output and a dump of the resulting data file:

    Code:
    $ gcc -o writedata writedata.c -Wall -pedantic -O4
    
    $ ./writedata
    Written data successfully
    
    $ od -t x1 out.data
    0000000 46 6f 6f 20 62 61 72 21 21 21 20 20 20 20 20
    0000017
    Just remember when you put in hex numbers, you need to put "0x" in front of the them, to let the compiler know that it is hex.

    Thank you sir! That seems to work May i ask how do you do this in cmd?

    $ od -t x1 out.data
    0000000 46 6f 6f 20 62 61 72 21 21 21 20 20 20 20 20
    0000017





    What I am doing now is I followed ur program to build a binary file, run my program on it, and then I use a binary viewer that i downloaded online to view the end product haha. Is there any faster/easier method

    Thank you so much for the reply!

  4. #4
    Registered User
    Join Date
    Sep 2020
    Posts
    45
    If you want to do some automated testing - and at some point you need to learn it - you follow this pattern:
    1. define your input
    2. define the expected output
    3. get the actual output
    4. check that expected output == actual output

  5. #5
    Registered User
    Join Date
    Sep 2020
    Posts
    164
    "od" is a standard Unix/Linux tool to inspect the contents of binary files - it's short for "octal dump"

    The -t is the type parameter in this case one-byte hex values - It defaults to 16-bit octal values IIRC.

  6. #6
    Registered User
    Join Date
    Oct 2020
    Posts
    18

    Help with code

    I see, thank you everyone for the input. I have a question regarding my code related to the exercise, this part of the code (and a particular line in question)
    Code:
        while ( fread(&value,sizeof(unsigned char),1,fp) > 0)
        {
            count = 1;
            position = ftell(fp);
            while ( fread(&next,sizeof(unsigned char),1,fp) > 0 && next == value)
            {
                    count ++;
            }
    
    
            fwrite(&count,sizeof(unsigned char),1,fpout);
            fwrite(&value,sizeof(unsigned char),1,fpout);
            fseek(fp,-1L,SEEK_CUR);  (THIS LINE IN PARTICULAR)
        }
    with regards to "fseek(fp,-1L,SEEK_CUR);" , my rationale behind it was the program will keep reading the bytes until it has read the first byte that is different. It then moves back by one byte position hence the "-1L", so that on the next loop it will read back the byte. E.g.

    01 01 01 01 02 02

    It reads all the 01 until it reads the first 02, then fseek moves the file positon back by 1 byte so on the next iteration of the loop it will read the first 02 again. However, if I implement the code this way it doesnt work.

    fseek(fpin, position + (amount - 1), SEEK_SET);
    ^ This works however. Positon is the position of the file after reading the first byte, and amount is the number of bytes already read. I understand how this particular line of code works, but I do not understand why my SEEK_CUR method doesnt work. Thank you all for the help really

  7. #7
    Registered User
    Join Date
    May 2012
    Posts
    470
    Quote Originally Posted by kuasimikua View Post
    But I am now facing this obstacle. How do i create/make a binary file to test my program? Normally when tresting programs that worked on text files I would just create one in notepad and run it, but I am unsure how to do this with binary files.

    Would appreciate any kind advice. Thank you everyone
    You want to open the text file, as binary. Call fopen "rb".

    When you compress it, you're not treating it as a text file any more. You're treating it as a sequence of bytes. Similarly, the decompress should be in binary mode. But the underlying file is still a text file, you're just treating it as a binary object to make the compression / decompression logic easier.
    I'm the author of MiniBasic: How to write a script interpreter and Basic Algorithms
    Visit my website for lots of associated C programming resources.
    https://github.com/MalcolmMcLean


Popular pages Recent additions subscribe to a feed

Similar Threads

  1. Replies: 5
    Last Post: 10-12-2012, 06:17 AM
  2. "Invalid chars", when I try to create a text file
    By frank1 in forum C Programming
    Replies: 7
    Last Post: 10-02-2012, 09:31 PM
  3. how to check if the content of a file is "1"?
    By fbs777 in forum C Programming
    Replies: 5
    Last Post: 02-07-2010, 07:49 PM
  4. Replies: 1
    Last Post: 08-06-2007, 10:09 PM
  5. Replies: 4
    Last Post: 04-02-2006, 09:31 AM

Tags for this Thread