2

I'm using fwrite to write a file (it's an image).

First, I'm writing a header that has a fixed size

int num_meta_write_bytes = fwrite(headerBuffer, 1, headerSize, file);

This works OK

Then I have to write the pixels:

num_write_bytes = fwrite(data_pointer, 1, image_size, file);

This works OK

For my case, I have to write a variable number of zeros between the header and the pixels, the (ugly?) solution I found is:

for (size_t i = 0; i < padding_zeros; i++) //padding_zeros is calculated in runtime
{
    uint8_t zero = 0;
    num_meta_write_bytes += fwrite(&zero, 1, sizeof(uint8_t), fp);
}

(This code is placed before writing the pixels)

My question is: is there a way to directly tell fwrite to continously write the same value padding_zeros times? instead of using this for loop?

8
  • 4
    Remember that in C (since the C99 standard) you can define variable-length arrays. You could define such an array of the exact size, memset it to zero, and write it in a single call to fwrite. Commented Mar 16, 2022 at 11:00
  • What does the padding depend on? Why does it have to be calculated in runtime? Sounds a bit strange to me. Commented Mar 16, 2022 at 11:02
  • @Aconcagua our app works with several different cameras, the padding depends on the camera resolution and it's pixel depth Commented Mar 16, 2022 at 11:03
  • 1
    Also, some filesystems support holes in files. So you could try to just seek over the padding area and start writing the data. When read, the hole should be read as zeros. Commented Mar 16, 2022 at 11:05
  • 1
    @Ivan 'out of scope' is a relative – you might have presented an XY-problem and for the true problem there might be a better solution, but we can only hint to if we know what you actually intend to do – which is why I've been asking. Still wondering how you or this software handles different image sizes and color depths (maybe scaling all images to the same format...), but that might finally really go out of scope here... Commented Mar 16, 2022 at 15:56

2 Answers 2

6

You can create a zero-filled block of data with calloc(), then write that data to the file in one call (and remember to free the data afterwards):

uint8_t* zeros = calloc(padding_zeros, sizeof(uint8_t));
if (zeros) {
    num_meta_write_bytes += fwrite(zeros, sizeof(uint8_t), padding_zeros, fp);
    free(zeros);
}
else {
    // Error handling, or use your 'loop' method if calloc fails
}

As mentioned in the comments, you could also use a variable length array; however, VLAs are an 'optional' feature in C (since the C11 Standard), and you would anyway have to explicitly set the data to zeros (with a call to memset), as VLAs cannot be initialized like ordinary (fixed-size) arrays.

Sign up to request clarification or add additional context in comments.

Comments

1

I found another solution, althouht I think is OS dependent:

fseek(fp, padding_zeros, SEEK_CUR);

This is quite fast as there is no allocation. Just when copying the resulting file, the OS will generate the actual zeros.

This worked fine in my linux target.

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.