1 /** 2 Microsoft Excel Developer's Toolkit 3 Version 14.0 4 5 File: SRC\XLCALL.CPP 6 Description: Code file for Excel callbacks 7 Platform: Microsoft Windows 8 9 This file defines the entry points 10 which are used in the Microsoft Excel C API. 11 12 */ 13 module xlld.sdk.xlcallcpp; 14 15 import xlld.sdk.xlcall: LPXLOPER12; 16 17 /** 18 Excel 12 entry points backwards compatible with Excel 11 19 20 Excel12 and Excel12v ensure backwards compatibility with Excel 11 21 and earlier versions. These functions will return xlretFailed when 22 used to callback into Excel 11 and earlier versions 23 */ 24 25 26 // PASCAL 27 alias EXCEL12PROC = extern(Windows) int function (int xlfn, int coper, LPXLOPER12 *rgpxloper12, LPXLOPER12 xloper12Res) nothrow @nogc; 28 29 EXCEL12PROC gExcel12; 30 31 void FetchExcel12EntryPt() nothrow @nogc 32 { 33 version(Windows) { 34 import core.sys.windows.windows: GetModuleHandleW, GetProcAddress; 35 if (gExcel12 is null) 36 { 37 auto hmodule = GetModuleHandleW(null); 38 if (hmodule !is null) 39 { 40 enum EXCEL12ENTRYPT="MdCallBack12"; 41 gExcel12 = cast(EXCEL12PROC) GetProcAddress(hmodule, EXCEL12ENTRYPT); 42 } 43 assert(gExcel12 !is null, "No entry point fetched"); 44 } 45 } 46 } 47 48 /** 49 This function explicitly sets EXCEL12ENTRYPT. 50 51 If the XLL is loaded not by Excel.exe, but by a HPC cluster container DLL, 52 then GetModuleHandle(null) would return the process EXE module handle. 53 In that case GetProcAddress would fail, since the process EXE doesn't 54 export EXCEL12ENTRYPT ( since it's not Excel.exe). 55 56 First try to fetch the known good entry point, 57 then set the passed in address. 58 */ 59 extern(Windows) void SetExcel12EntryPt(EXCEL12PROC gExcel12New) @nogc nothrow 60 { 61 if (gExcel12 is null) 62 { 63 gExcel12 = gExcel12New; 64 } 65 } 66 67 //_cdecl 68 int Excel12(int xlfn, LPXLOPER12 operRes, LPXLOPER12[] args ...) 69 { 70 import core.vararg: va_list; 71 import xlld.sdk.xlcall: xlretFailed, xlretInvCount; 72 73 enum cxloper12Max=255; 74 LPXLOPER12[cxloper12Max] rgxloper12; 75 va_list ap; 76 int ioper; 77 int mdRet; 78 79 FetchExcel12EntryPt(); 80 if (gExcel12 is null) 81 { 82 mdRet = xlretFailed; 83 } 84 else 85 { 86 mdRet = xlretInvCount; 87 if ((args.length >= 0) && (args.length<= cxloper12Max)) 88 { 89 foreach(i,arg;args) 90 rgxloper12[ioper] = arg; 91 // original line was mdRet = (gExcel12)(xlfn, count, &rgxloper12[0], operRes); 92 mdRet = (*gExcel12)(xlfn, cast(int)args.length, rgxloper12.ptr, operRes); 93 } 94 } 95 return(mdRet); 96 97 } 98 99 extern(Windows) int Excel12v(int xlfn, LPXLOPER12 operRes, int count, LPXLOPER12* opers) 100 nothrow @nogc 101 { 102 import xlld.sdk.xlcall: xlretFailed; 103 104 int mdRet; 105 FetchExcel12EntryPt(); 106 if (gExcel12 is null) 107 { 108 mdRet = xlretFailed; 109 } 110 else 111 { 112 // original line was mdRet = (gExcel12)(xlfn, count, &rgxloper12[0], operRes); 113 mdRet = (*gExcel12)(xlfn, count, opers, operRes); 114 } 115 return(mdRet); 116 117 }