Today I experienced what every Windows programmer experiences when interacting with DLLs - only on a much grander scale. What I am talking about is "DLL Hell." The results of these efforts caused me to have 23 programs open along with 50 unique files.
Over the past week I have been working on huge modifications to some core library code. This code is fairly proprietary, but basically what I was striving for is perhaps the most unique approach to interacting with DLLs. As many people know, I already live and thrive in macro hell. For instance, my most evil macro to date is basically unreadable and 335 characters long...and on one line. Anyway, as I said, I have come up with a really creative and unique way to load in a DLL. The way this works is to simulate delay-loading with the option of not running into the issue of crashing if it fails to load for whatever reason. This feature is actually useful where plug-ins are concerned. The other issue is that I needed application portability between platforms for various reasons only known to my twisted mind.
Anywho, I digress. Basically, I chugging along happily and working out the kinks until I ran into the most bizarre issue of all time. The __stdcall calling convention is how each function is called that I wanted to __declspec(dllexport). However, there was one function that was not exporting properly and was decorated with a leading underscore.
I searched Google high and low and high and low again and kept coming up empty-handed. It did not help me out much that only 20 results were coming back. Basically, I was scraping the bottom of the barrel only turning up with coffee sludge. I guess that happens when you start managing over a half-million lines of code every day.
After about 6 hours, I finally hit upon some keywords that got me the hint that I needed. The calling convention was being changed by the compiler. Why? The one function I was working with has variable arguments (...) and __stdcall doesn't support that, but __cdecl. You would think those brilliant compiler developers would think to notify me that they were changing an explicitly declared calling convention to tell me they weren't compatible. Good job guys. Way to go Borland/Inprise/whatever your name is today.
Well, I was not actually 100% certain about the whole conversion thing at first. Seemed kind of hokey. After about 8 hours, I finally hit upon the right order and keyword selection that gave me a pointer to a website I knew had articles on this sort of topic. (Yay me for losing my mind). It turns out that my guess as to what was going on seemed to be correct. The next step is what really boggles the mind. I had to create a ".def" file just for this one function and map the export with another name. The result was that both the decorated and undecorated functions show up in the DLL. (I only need one of them Borland people - the one I say to export in the first place).
My goal of a DLL with completely undecorated names that works beautifully across compilers works like a charm. The last step was to verify that everything still worked with a sample interface.
It didn't. Go figure.