Why do we still need a .lib stub file when we've got the actual .dll implementation? - dll

i'm wondering why linkers can not do their job simply by consulting the information in the actual .dll files that got the actual implementation code ? i mean why linkers still need .lib files to do implicit linking ?
are not the export and relative address tables enough for such linking ?
is there anyway by which one can do implicit linking using only the .dll without the .lib stub/proxy files ?
i thought the windows executable loader would simply do LoadLibrary/LoadLibraryEx calls on behalf of the program (hence the name implicit linking) which is the main difference to explicit linking. if that is true then doing it explicitly without .lib should indicate that it is doable without it implicitly, right ? or i'm just saying non sense?

I can think of a a few reasons.
Using .lib files mean you can build for a different version of a DLL than you have on your system, provided you just have the correct SDK installed.
Compilers & linkers need to support cross-platform compilations - You might be building for a 64-bit target on a 32-bit platform and vice-versa and not have the correct architecture DLL present.
.lib files enable you to "hide" certain parts of your implementation - you could have private exports that do not show up in the .lib but are discoverable via GetProcAddress. You can also do ordinal exports in which case they don't have a friendly name exported, but would have a friendly name in the .lib.
Native DLL's do not have strong names, so it may be possible to pick up the wrong version of the DLL.
And most importantly, this technology was designed in the 1980's. If it were designed today, it'd probably be closer to what you describe - for instance, .NET you just need to reference the target assembly and you have everything you need to use it.
I don't know of any way to do implicit linking solely with the DLL - A quick search revealed several tools, but I haven't used any of them.
In this case, I would create a separate source file with the functions you need to use, and dynamically load the DLL and bind them as needed. For example:
// using global variables and no-error handling for brevity.
HINSTANCE theDll = NULL;
typedef void (__stdcall * FooPtr)();
FooPtr pfnFoo = NULL;
INIT_ONCE initOnce;
BOOL CALLBACK BindDLL(PINIT_ONCE initOnce, PVOID parameter, PVOID context)
{
theDll = LoadLibrary();
pfnfoo = GetProcAddress(dll, "Foo");
return TRUE;
}
// Export for foo
void Foo()
{
// Use one-time init for thread-safe lazy initialization
InitOnceExecuteOnce(initOnce, BinDll, NULL, NULL)
pfnFoo();
}

Related

dllexport in headers confusion

I'm confused as to why __declspec(dllexport) or equivalent needs to go in the header file. Say I'm writing a library. Surely the users don't need to know or worry about whether symbols are exported or not, all they care about is that the function declarations are there and will presumably be linked against the shared or static library itself. So why can't all this boilerplate go into source files, for use only at build time?
The only use case I think of is a situation where someone is writing a wrapper of my library and needs to export all of my functions as well, but in general that is not the case - is it really worth the hassle of having all the export stuff inside public headers? Is there something I'm missing, is this a technical limitation of linkers..?
I'm asking because I like my headers and build system to be clean, and as dllexport stuff is generally set/not set based on whether we are building the library as a shared or static library, I find it strange that it should end up inside public headers since it's (to my understanding) fundamentally a build time concept. So can someone please enlighten me on what I am missing?
I'm not really sure I can provide a great answer. My impression is that it serves several purposes:
It speeds the loading of DLLs, particularly when lots of DLLs are used (because there are fewer exported symbols to search through)
It reduces the possibility of symbols colliding at run-time (because there are fewer exported symbols)
It allows the linker to complain about undefined symbols (instead of just assuming it might find them at run time.
I'm sure there are other reasons. I generally wrap my APIs in something like this:
#if defined(MY_LIB_CREATION)
#define MY_LIB_API __declspec(dllexport)
#else
#define MY_LIB_API __declspec(dllimport)
#endif
And then all of my API functions & classes are defined as MY_LIB_API:
class MY_LIB_API Foo {};
MY_LIB_API void bar();
And then in the project file defined MY_LIB_CREATION for the project implementing your library.

Xcode: define preprocessor macro in one project used by another project

I have multiple app projects which all link to the same static library project. Each app project needs to compile the static library project using different settings.
At the moment I have a conditional compilation header in the static library project, let's call it ViewType.h which adds more types, typedefs, macros, etc specific to each view.
#define VIEW_A 1
#define VIEW_B 2
#define VIEW_C 3
#ifndef VIEWTYPE
#define VIEWTYPE VIEW_A
#endif
#if VIEWTYPE == VIEW_A
// further typedefs and defines tailored to VIEW_A
#elif VIEWTYPE == VIEW_B
// further typedefs and defines tailored to VIEW_B
#elif VIEWTYPE == VIEW_C
// further typedefs and defines tailored to VIEW_C
#endif
The problem here is that each app project needs to change the VIEWTYPE in the static library project, and every time I switch app projects I have to change the VIEWTYPE again.
Unfortunately it seems I can not define VIEWTYPE=2 (for example) as preprocessor macro in the app target. And I can't define this in the static library project either because all 3 projects include the same static library project, because the .xcodeproj is shared between the 3 apps (ie the .xcodeproj is dragged & dropped onto the app project; I'm not using a workspace).
I understand one issue is that the static library being a dependent target it is built first before the app target is even considered. So perhaps there's some way to make that decision which app the library is built for based on other conditionals (ie checking for a file, or including an optional app-specific header).
Question: How I can create a macro or otherwise perform conditional compilation based on macros/settings defined by the app target which are then adhered to by the static library project?
The first, simplest approach, is to get rid of the static library, and just include the source files directly into the dependent projects. I often find that intermediate static libraries are much more trouble than they're worth. Their one big benefit comes when they provide a significant build-performance improvement, but they can't here since you're rebuilding the static library for every final target anyway.
I will say that the use of a type #defines almost always makes me cry, and may suggest a design flaw that could be better handled. For instance, you may want to implement methods that return the class required (the way UIView layerClass does). Pre-processor trickery that changes type definitions can lead to extremely subtle bugs. (I just chased down a case of this last year… it was a horrible, horrible crash to figure out.)
That said, another approach for certain versions of this problem can be solved with xcconfig files. For example, if there are actually multiple copies of the static library (i.e. this is a library that is commonly copied into other projects), then you can use an xcconfig file that has an #include "../SpecialTypeDefs.xcconfig". That file would be provided by each project to set special declarations. Failure to define that file would lead to a complier error, so it's easy to not have an error.
But personally, I'd just include the files into the actual project directly and skip the library unless they're really enormous.

Including headers from an unmanaged C++ code inside C++/CLI code

I'm writing a CLR wrapper for an unmanaged C++ library.
There are two files I'm including from the unmanaged lib:
//MyCLIWrapper.h
#include "C:\PATH\TO\UNMANAGED\Header.h"
#include "C:\PATH\TO\UNMANAGED\Body.cpp"
Then I'm writing CLI implementations for the unmanaged library functions:
//MyCLIWrapper.h
// includes ...
void MyCLIWrapper::ManagedFunction()
{
UnmanagedFunction(); // this function is called successfuly
}
However, if my Unmanaged function contains calls to other functions that are defined in other unmanaged header files. This causes a compiler linkage error.
If I add includes to the unmanaged headers that define these functions, my errors get resolved. However, there is a lot of functions, and a lot of includes required.
Is there a different way to approach this?
EDIT:
P.S.
My managed code is in a separate Visual Studio project (output - DLL), and the compile settings are set to /CLR. Unmanaged code is in a separate Win32 project (output - DLL).
Also, after more research I concluded that theoretically I could set my Win32 unmanaged project to CLR and just add my managed classes and headers in there as an entry point, and then it would all compile into a single DLL file. That would probably solve (?) the linkage errors. However, I would prefer to preserve the loose coupling as well as the additional series of problems that can raise from setting my unmanaged project to CLR.
EDIT #2:
The unmanaged class that I'm referencing (body.cpp, header.h) contains includes to the required files that define the functions that are causing the problems. However, my managed code doesn't pick up on the includes that are in the unmanaged body.cpp and header.h.
Linker errors are a different kettle of fish from compiler errors. You forgot to document the exact linker errors you see, but a very common mishap when you compile code with /clr in effect is that the default calling convention for non-C++ member function changes. The default is __clrcall, a convention that's optimized for managed code. While functions compiled without /clr defaults to __cdecl. Which changes the way the function name is mangled. You see this back in the linker error message, is shows that it is looking for a __clrcall function and can't find it.
You'll need to either explicitly declare your functions in the .h file with __cdecl. Or tell the compiler that these functions are not managed code. Which is the best way to tackle it:
#pragma managed(push, off)
#include "unmanagedHeader.h"
#pragma managed(pop)
Solution was fairly simple:
I added both unmanaged and managed projects to a single solution in Visual Studio.
Set the unmanaged project's "Configuration Type" to "Static Library" (.lib).
Right click on the managed project -> References -> Add Reference -> Projects -> -> Add Reference.
Then in my managed class, I include the header.h (only) just like I did in my question.
Compiled successfully!
Thank you

Discovering registered COM components

Is there a way to determine if a registered COM component is creatable as a stand-alone component simply by parsing the information available in the registry? In particular, by the information found in HKCR/ClsId?
My system has over 12,000 entries in this key, and I am already excluding any items that do not have an InProcServer32 or LocalServer32 key, but this only eliminates about half of the items. I believe there are still another couple thousand that are not creatable objects. I really don't want to have to attempt to do a CreateObject() on every one of them to distinguish the ones that can be created from the ones that cannot. Is there a more efficient way?
Oleview
I used Oleview
for this purpose (back in the day :))
Manual/programmatic
If I remember correctly (no Windows PC nearby):
the class should link to a typelibrary
the typelib will point to a binary (dll, ocx, exe)
this binary contains the physical typelibrary, which you should parse
the midl compiler can do that (generate stubs/C headers)
oleview can do that (extract IDL)
tlbimp can do that
you can do it with Win32 API
any creatable objects should be marked coclass (not interface or source; there were also global modules which I suppose are creatable too: I'm just not sure whether they are defined as coclasses
Show me the code
It is possible to read the information within a type library with the ITypeLib and ITypeInfo interfaces. They can be created with the ICreateTypeLib and ICreateTypeInfo interfaces. However, the Microsoft IDL compiler (MIDL) is probably the only application to ever use ICreateType and ICreateTypeInfo.
A quick google turned up this useful page: Reading Type Libraries with C++.
It contains just the code to get started. Just to see whether it was worth anything, I fired up a cloud Windows instance, grabbed all the sources and compiled it.
In contrast with the options mentioned on the site, I simply compiled on windows with
cl.exe *.cpp /EHs ole32.lib oleaut32.lib
Just for fun, I compiled the stuff on Linux (64 bit) using MingW:
i586-mingw32msvc-g++ *.cpp -loleaut32 -lole32 -o Typelib.exe
To save you the work I have put a zip-file up for download containing:
win32_Unicode.cpp - sources by René Nyffenegger
win32_Unicode.h
TestTypelib.cpp
Typelib.cpp
Typelib.h
VariantHelper.cpp
VariantHelper.h
TestTypelib.exe - binary compiled on windows
A test run:
# linux: ./a.exe ~/.wine/drive_c/windows/system32/msxml6.dll
C:\Games\Stacko>TestTypelib.exe c:\Windows\System32\msxml6.dll
MSXML2: Microsoft XML, v6.0
Nof Type Infos: 149
IXMLDOMImplementation
----------------------------
Interface: Dispatch
functions: 8
variables: 0
Function : QueryInterface
returns : VT_VOID
flags :
invoke kind: function
params : 2
params opt : 0
Parameter : riid type = VT_PTR (VT_USERDEFINED (GUID)) in
Parameter : ppvObj type = VT_PTR (VT_PTR) out
Function : AddRef
returns : VT_UI4
flags :
invoke kind: function
params : 0
params opt : 0
(snip) and 15499 lines more
Concluding
I hope this gives you a good starting point in scanning your system for installed, creatable, COM components
Depends what you mean by "createable". If it has a LocalServer32 or InprocServer32 key it should be locally creatable. It may also be creatable remotely if it has an AppID and the AppID has either LocalService or RemoteServer keys.
However consulting the registry will only answer the question "does it look like it ought to be creatable".
You might still not be able to create it:
The registration might be broken, or "fossil" registry entries from uninstalled components.
The component might be an internal Windows component of some sort that you have no idea how to use since it is intentionally not documented.
The component might be an internal component of an installed application which has additional requirements not documented.
You might not have permission.
There may be other components you could create:
There might be registration-free COM components, such as WSC scriptlets.
there might be registration-free COM DLLs. There is no law saying you have to be registered to be a COM component. Registration is an optional service that most people opt into.
So I guess the answer is you should be able to get a mostly complete list using the registry, but what is the list for?
Without knowing what you want the list for, it is impossible to know if the list is good enough.

Converting static link library to dynamic dll

I have .lib file with its header (.h) file. This file have a few functions that need to be used in C# application.
After googling I found that I need to create a dynamic DLL from this static library and call this dynamic DLL from C# code using interop.
I have created a win32 project and selected type DLL.
Included header file and added .lib to additional dependencies.
I am able to see the functions defined in the static library (when I press ctrl + space).
As a total newbie I do not know how I can export the function, which is, in .lib with following signature:
void testfun( char* inp_buff, unsigned short* inp_len, char* buffer_decomp,unsigned *output_len,unsigned short *errorCode)
I want same signature in my dynamic DLL with a different name.
What to write in header file and .cpp file?
If you can recompile your lib, just add __declspec(dllexport) to the signatures of all of the functions you want to be exported.
void __declspec(dllexport) testfun( char* inp_buff, unsigned short* inp_len, char* buffer_decomp,unsigned *output_len,unsigned short *errorCode)
If you can't do that, then you can export them by writing a .def file instead. Using def files you can even change the name of a function as it is exported.
http://msdn.microsoft.com/en-us/library/28d6s79h.aspx
---- contents of mylib.def ----
LIBRARY
EXPORTS
testfun
newname=testfun2
Then when you link the dll, include mylib.def
link /dll /machine:x86 /def:mylib.def mylib.lib
Edit2:
note that pinvoke assumes that the functions you import will have _stdcall calling convention unless you say otherwise. So you might need to do this as well, in your C# code.
[DllImport("mylib.dll", CallingConvention=CallingConvention.Cdecl)]
Or, you could change your C++ code to be __stdcall
void __declspec(dllexport) __stdcall testfun( char* inp_buff, ...
This is what you can do
Add the following code to you .H file. rename "MYPROJECT" to your project name
#ifdef MYPROJECT_EXPORTS
#define MYPROJECT_API __declspec(dllexport)
#else
#define MYPROJECT_API _declspec(dllimport)
#endif
Go to Properties->C++->Preprocessor and Add the defenition - MYPROJECT_EXPORTS
Add MYPROJECT_API to all the functions you want the dll to expose eg:
MYPROJECT_API void Test();
Go to Project properties General -> Configuration Type change it to Dynamic Dll
You are done
Create new Dll project using Visual Studio Application Wizard, and check "Exports Symbols" in one of the Wizard steps. It creates sample Dll which exports class, function and variable. You can learn from this sample, how to do this.
Generally, every exported function is declared as __declspec(dllexport). In a client project it is declared as __declspec(dllimport). Dll code uses the constant which is defiled as __declspec(dllexport) inside of Dll project, and __declspec(dllimport) in any other place.
there are two versions of LIB can be generated,
the fist is the dynamic lib, (source file + header+ dynamic lib) --> to access the DLL
or static lib=(dynamic lib+DLL) --> (Source file+header) --> to access the DLL.
if you have the Dynamic Lib > there is no way to create the DLL (you cannot get something from nothing), dynamic lib is just an interface,
but if you have the Static Lib then there is no need to DLL to access it is functions.
Take a look at my answer to this question for a possible solution. Almost positive this will work for you...
In short: Enable the "Use Library Dependency Inputs" option in your Linker settings. If set to "true", it will force linking ALL symbols & code declared in every LIB specified as input to the project.
The issue here is not how the code is decorated, it's the extra step of creating a static library that contains all of the entry points, and trying to build the dll out of that.
If you go with the __delcspec approach and build the static library first, then try to link to it when building a DLL, you'll have to solve the dead-code stripping problem.
When you link, the obj srcs are used to find all of the decorated exports and dependencies are resolved, everything else is stripped. If you have no DLL src, so no obj files (except maybe a dll main), all of the code in the lib you want to export will be stripped (regardless of the attributes).
So, you either have to:
Tell the linker not to strip unused code, which is probably going to give you a lot of stuff you don't want.
Use a def file to expose the exports manually
Link the dll against the obj files used to create the lib instead of linking to the lib directly.
Or maybe create dummy code that references the functions you want to export from something you are exporting.