18913, "LouisJenkinsCS", "Chapel I/O Significantly Slower than GLIBC fread/fwrite (10x)", "2022-01-05T16:48:28Z"
use SysBasic;
use IO;
use CPtr;
use Time;
extern proc fopen(name: c_string, mode: c_string): c_void_ptr;
extern proc fread(data:c_void_ptr, size: int, n: int, f: c_void_ptr): int;
extern proc fwrite(data:c_void_ptr, size: int, n: int, f: c_void_ptr): int;
extern proc fclose(f: c_void_ptr) : int;
proc chpl_write() {
type byte = uint(8);
var memAvail : int(64) = (here.physicalMemory(retType=int(64)) * 0.75):int(64);
var buf : [0..#memAvail] byte;
var fname = "dummy.bin";
var style : iostyle;
style.binary = 1;
var f = open(fname, iomode.cw, hints=IOHINT_SEQUENTIAL, style=style);
var c = f.writer();
var t : Timer;
t.start();
c.write(buf, memAvail);
writeln("Elapsed: ", t.elapsed());
c.close();
f.close();
writeln("Wrote ", memAvail, " bytes to ", fname);
}
proc c_write() {
type byte = uint(8);
var memAvail : int(64) = (here.physicalMemory(retType=int(64)) * 0.75):int(64);
var buf = c_malloc(byte, memAvail);
forall i in 0..#memAvail do buf[i] = i:uint(8);
var fname = "dummy.bin";
var fp = fopen(fname.c_str(), "w");
var t : Timer;
t.start();
var bytesWritten = 0;
while (bytesWritten < memAvail) {
var tmp = c_ptrTo(buf[bytesWritten]);
bytesWritten += fwrite(tmp, 1, memAvail - bytesWritten, fp);
}
writeln("Elapsed: ", t.elapsed());
fclose(fp);
c_free(buf);
writeln("Wrote " + memAvail:int(64):string + " bytes to " + fname);
}
proc main() {
chpl_write();
c_write();
}
Example Output
Elapsed: 246.306
Wrote 24940502016 bytes to dummy.bin
Elapsed: 20.4269
Wrote 24940502016 bytes to dummy.bin
Note this is to an NVMe SSD not over Lustre, so very low latency and high bandwidth.
Let me know if I was doing something wrong here.