#include "postgres.h" #include "fmgr.h" #define NARGS 2 /* Unrolled code can handle up to 10 */ /* * Initialize minimum fields of FunctionCallInfoData that must be * initialized. */ #define InitFunctionCallInfoData(Fcinfo, Flinfo, Nargs) \ do { \ int i_; \ (Fcinfo)->flinfo = Flinfo; \ (Fcinfo)->context = NULL; \ (Fcinfo)->resultinfo = NULL; \ (Fcinfo)->isnull = false; \ (Fcinfo)->nargs = Nargs; \ for(i_ = 0; i_ < Nargs; i_++) (Fcinfo)->argnull[i_] = false; \ } while(0) /* * dummyFunc is to control excessive optimization. * When this function is not called from loop, the initialization of * FunctionCallInfoData might move outside of the loop by gcc. */ void dummyFunc(FunctionCallInfoData *fcinfo, int cnt) { fcinfo->arg[0] = Int32GetDatum(cnt); } void TestMemSet(int cnt) { FunctionCallInfoData fcinfo; printf("test MemSetLoop(%d): %d\n", NARGS, cnt); for(; cnt; cnt--) { MemSetLoop(&fcinfo, 0, sizeof(fcinfo)); dummyFunc(&fcinfo, cnt); } } void TestOrigMacro(int cnt) { FunctionCallInfoData fcinfo; printf("test OrigMacro(%d): %d\n", NARGS, cnt); for(; cnt; cnt--) { InitFunctionCallInfoData(&fcinfo, NULL, NARGS); dummyFunc(&fcinfo, cnt); } } #undef InitFunctionCallInfoData #define InitFunctionCallInfoData(Fcinfo, Flinfo, Nargs) \ do { \ (Fcinfo)->flinfo = Flinfo; \ (Fcinfo)->context = NULL; \ (Fcinfo)->resultinfo = NULL; \ (Fcinfo)->isnull = false; \ (Fcinfo)->nargs = Nargs; \ MemSetLoop((Fcinfo)->argnull, 0, \ sizeof(int32) * ((Nargs + sizeof(int32)-1) / sizeof(int32))); \ } while(0) void TestSetMacro(int cnt) { FunctionCallInfoData fcinfo; printf("test SetMacro(%d): %d\n", NARGS, cnt); for(; cnt; cnt--) { InitFunctionCallInfoData(&fcinfo, NULL, NARGS); dummyFunc(&fcinfo, cnt); } } #undef InitFunctionCallInfoData #define InitFunctionCallInfoData(Fcinfo, Flinfo, Nargs) \ do { \ (Fcinfo)->flinfo = Flinfo; \ (Fcinfo)->context = NULL; \ (Fcinfo)->resultinfo = NULL; \ (Fcinfo)->isnull = false; \ (Fcinfo)->nargs = Nargs; \ } while(0) void TestUnrolled(int cnt) { FunctionCallInfoData fcinfo; printf("test Unrolled(%d): %d\n", NARGS, cnt); for(; cnt; cnt--) { InitFunctionCallInfoData(&fcinfo, NULL, NARGS); #if NARGS > 0 fcinfo.argnull[0] = false; #endif #if NARGS > 1 fcinfo.argnull[1] = false; #endif #if NARGS > 2 fcinfo.argnull[2] = false; #endif #if NARGS > 3 fcinfo.argnull[3] = false; #endif #if NARGS > 4 fcinfo.argnull[4] = false; #endif #if NARGS > 5 fcinfo.argnull[5] = false; #endif #if NARGS > 6 fcinfo.argnull[6] = false; #endif #if NARGS > 7 fcinfo.argnull[7] = false; #endif #if NARGS > 8 fcinfo.argnull[8] = false; #endif #if NARGS > 9 fcinfo.argnull[9] = false; #endif dummyFunc(&fcinfo, cnt); } } int main(int argc, char **argv) { int test_cnt; if(argc != 3) { printf("usage: fmgrtest -memset|-origmacro|-setmacro|-unrolled test_cnt\n"); return 1; } test_cnt = atoi(argv[2]); if(strcmp(argv[1], "-memset") == 0) TestMemSet(test_cnt); if(strcmp(argv[1], "-origmacro") == 0) TestOrigMacro(test_cnt); if(strcmp(argv[1], "-setmacro") == 0) TestSetMacro(test_cnt); if(strcmp(argv[1], "-unrolled") == 0) TestUnrolled(test_cnt); return 0; }