0

I wrote a very simple program in C to test the read/write speed of the storage device where the program is located. It could be a SSD, HDD or a usb stick. But I get very inconsistent results, which is weird because the program is very simple and straightforward.

When I run it on a usb 3.0 stick it gives values like 270 mb/s [write], and 2100 mb/s [read]. For a HDD it gives similar values. And for the SSD, it gives similar read speeds, and around 300 mb/s write speed.

This is weird, because there isn't anything complicated in the code, and I am not optimizing it either. The speeds reported don't match with the normal speeds of these devices. Though, it could be that I am not really understanding how this works.

#include <stdio.h>
#include <stdlib.h>
#include <omp.h>
#include <math.h>

const unsigned int N = 25000000;                         /// Number of floats to be written

int main(){
    double time0, time1, time2;
    unsigned int i, size = N*sizeof(float);              /// Size of the file to be written/read in bytes
    FILE *pfin, *pfout;

    float *array_write, *array_read, sum, delta_write, delta_read;

    array_write = (float *) malloc(N*sizeof(float));    /// Array to be written to a file
    array_read  = (float *) malloc(N*sizeof(float));    /// Array to be read


    for(i = 0; i < N; i++)
        array_write[i] = i*1.f/N;                        /// Filling in array with some values

    time0 = omp_get_wtime();
    pfout = fopen("test.dat", "wb");
    fwrite(array_write, N*sizeof(float), 1, pfout);
    fclose(pfout);

    time1 = omp_get_wtime();
    pfin  = fopen("test.dat", "rb");
    fread(array_read, N*sizeof(float), 1, pfin);
    fclose(pfin);

    time2 = omp_get_wtime();

    sum = 0.f;
    for(i = 0; i < N; i++)
        sum += fabsf(array_read[i] - array_write[i]);  /// Simple test to check whether it read properly or not

    delta_write = time1 - time0;
    delta_read  = time2 - time1;


    printf("delta1 = %f, delta2 = %f, size = %f Gb, diff = %f\n", delta_write, delta_read, size/1000000000.f, sum);


    printf("Speed: \n Write: %f [Mb/s]\n Read: %f [Mb/s]\n", size/1000000.f/delta_write, size/1000000.f/delta_read);
    free(array_read);
    free(array_write);
}


//// compile with gcc program.c -lgomp -lm -O0 -o program.x

Be aware that it creates a 100 mb file.

Agustín
  • 23
  • 4
  • 3
    Operating systems cache data in memory. It skews results. – Sami Kuhmonen Sep 12 '20 at 17:46
  • see [here for possible caches](https://stackoverflow.com/a/20215753/9306292) and [this for enforcing flushing read and write cache](https://stackoverflow.com/a/20215603/9306292). – Jay-Pi Sep 12 '20 at 18:28
  • Also [fopen is buffered](https://stackoverflow.com/a/1658517/9306292), so you should consider use the less-portable (non-POSIX) open to minimize any delay of the buffer for optimal accuracy. – Jay-Pi Sep 12 '20 at 18:32
  • Since there is no `sync()` (or similar) operation after writing data, it's plausible that the program completes before any data is actually written to disk. All the data might be queued up for writing in the kernel's I/O buffers. As a minimum, try calling `sync()` after closing the output file. On Linux, `sync()` is a blocking operation, so the time it takes will be included in your figures. Even then, it's very hard to disable _all_ the points of caching in the system. – Kevin Boone Sep 13 '20 at 07:07

0 Answers0