user846400
user846400

Reputation: 1101

synchronized write operation in C

I am working on a smart camera that runs linux. I capture images from the camera streaming software and writes the images on a SD card (attached with the camera). For writing the individual JPEG images, I used fopen and fwrite C functions. For synchronizing the disk write operation, I use fflulsh(pointer) to flush the buffers and write the data on the SD card. But it seems it has no effect as the write operation uses system memory and the memory gets decreased after every write operation. I also used low-level open and write functions in conjunction with fsync (filedesc), but it also has no effect.

The flushing of buffers take place only when I dismount the SD card and then the memory is freed. How can I disable this cache write instead of SD card write? or how can I force the data to be written on the SD card at the same time instead of using the system memory?

Upvotes: 2

Views: 5123

Answers (5)

caf
caf

Reputation: 239041

Just because it's still taking up memory doesn't mean it hasn't also been written out to storage - a clean (identical to the copy on physical storage) copy of the data will stay in the page cache until that memory is needed for something else, in case an application later reads that data back.

Note that fflush() doesn't ensure the data has been written to storage - if you are using stdio, you must first use fflush(f), then fsync(fileno(f)).

If you know that you will not need to read that data again in the forseeable future (as seems likely for this case), you can use posix_fadvise() with the POSIX_FADV_DONTNEED flag before closing the file.

Upvotes: 1

doron
doron

Reputation: 28892

There may be nothing that you can really do. Many file systems are heavily cached in memory so a write to a file may not immediately be written to disk. The only way to guarantee a write in this scenario is to actually unmount the drive.

When mounting the disk, you might want to specify the sync option (either using the -oflag in mount or on your fstab line. This will ensure that at least your writes are written synchronously. This is what you should always use for removable media.

Upvotes: 1

NPE
NPE

Reputation: 500357

sync(2) is probably your best bet:

SYNC(2)                    Linux Programmer's Manual                   SYNC(2)

NAME
       sync - commit buffer cache to disk

SYNOPSIS
       #include <unistd.h>

       void sync(void);

DESCRIPTION
       sync() first commits inodes to buffers, and then buffers to disk.

BUGS
       According  to  the  standard specification (e.g., POSIX.1-2001), sync()
       schedules the writes, but may return before the actual writing is done.
       However,  since  version  1.3.20 Linux does actually wait.  (This still
       does not guarantee data integrity: modern disks have large caches.)

Upvotes: 3

jbruni
jbruni

Reputation: 1247

Check out fsync(2) when working with specific files.

Upvotes: 1

Brian McFarland
Brian McFarland

Reputation: 9422

You can set the O_SYNC if you open the file using open(), or use sync() as suggested above.

With fopen(), you can use fsync(), or use a combination of fileno() and ioctl() to set options on the descriptor.

For more details see this very similar post: How can you flush a write using a file descriptor?

Upvotes: 2

Related Questions