So, I wrote some numerical code in C, but wanted to call it from F #. However, it works incredibly slowly.
Time:
- gcc -O3: 4 seconds
- gcc -O0: 30 seconds
- The fsharp code that invokes the optimized gcc code: 2 minutes 30 seconds.
For reference, code c
int main(int argc, char** argv) { setvals(100,100,15,20.0,0.0504); float* dmats = malloc(sizeof(float) * factor*factor); MakeDmat(1.4,-1.92,dmats); //dmat appears to be correct float* arr1 = malloc(sizeof(float)*xsize*ysize); float* arr2 = malloc(sizeof(float)*xsize*ysize); randinit(arr1); for (int i = 0;i < 10000;i++) { evolve(arr1,arr2,dmats); evolve(arr2,arr1,dmats); if (i==9999) {print(arr1,xsize,ysize);}; } return 0; }
I did not consider the implementation of functions. The F # code I'm using is
open System.Runtime.InteropServices open Microsoft.FSharp.NativeInterop [<DllImport("a.dll")>] extern void main (int argc, char* argv) [<DllImport("a.dll")>] extern void setvals (int _xsize, int _ysize, int _distlimit,float _tau,float _Iex) [<DllImport("a.dll")>] extern void MakeDmat(float We,float Wi, float*arr) [<DllImport("a.dll")>] extern void randinit(float* arr) [<DllImport("a.dll")>] extern void print(float* arr) [<DllImport("a.dll")>] extern void evolve (float* input, float* output,float* connections) let dlimit,xsize,ysize = 15,100,100 let factor = (2*dlimit)+1 setvals(xsize,ysize,dlimit,20.0,0.0504) let dmat = Array.zeroCreate (factor*factor) MakeDmat(1.4,-1.92,&&dmat.[0]) let arr1 = Array.zeroCreate (xsize*ysize) let arr2 = Array.zeroCreate (xsize*ysize) let addr1 = &&arr1.[0] let addr2 = &&arr2.[0] let dmataddr = &&dmat.[0] randinit(&&dmat.[0]) [0..10000] |> List.iter (fun _ -> evolve(addr1,addr2,dmataddr) evolve(addr2,addr1,dmataddr) ) print(&&arr1.[0])
F # code compiled with optimization.
Is the mono interface for calling C code really slow (almost 8 ms of overhead for calling a function), or am I just doing something stupid?