I have a legacy Windows project using the legacy 32 Bit C++ compiler. For various reasons I need to use the Windows 8+ function PathCchCanonicalizeEx. C++Builder seems to provide the header and some module definition file for that, but I can't find any library to link against:
[ilink32 Error] Error: Unresolved external 'PathCchCanonicalizeEx' referenced from C:\[...]\WIN32\DEBUG\TMP\FILE.OBJ
How am I supposed to fix this? Do I need to add a Windows 8.1 SDK? Is the necessary lib simply named differently and I can't find it? Something completely different?
According my tests, one has two options:
I'm developing/testing a some Windows 10 21H2, which provides an implementation for
PathCchCanonicalizeExin some DLL already. So if that source DLL is known, one can useIMPLIBorMKEXPto create an import library manually. I did that and after adding the created library fromIMPLIBto my project, the linker errors were instantly gone.Though, it's not that easy to know where
PathCchCanonicalizeExis placed in. One pretty easily finds theapi-ms-win-core-path-l1-1-0.dll, but that thing is NOT an actual file on the disk and therefore can't be used byIMPLIBorMKEXP. That name is only a virtual concept for the library loader to address the same named API set of modern Windows, the extension.dlldoesn't mean it's a file at all.https://learn.microsoft.com/en-us/windows/win32/apiindex/windows-apisets#api-set-contract-names
What you really need to work with is
KernelBase.dll, which is even documented by MS.The downside of manually creating LIB files is that one needs to maintain those with the project. Things depend on if the target is 32 or 64 Bit, DEBUG or RELEASE, so paths might become a bit complex, one might need to create relative paths for libraries in the project settings using placeholders for the target and stuff like that.
It seems that all of this can be avoided with Module Definition Files, which's purpose is to provide IMPORT and EXPORT statements to either consume exported functions by other DLLs or make that possible for others with own functions. I've successfully resolved my linker problems by simply creating a file named like my app using the extension
.defalongside my other project files. That file needs to be added to the project, though.The following content made the app use the correct function from the correct DLL. Though, what didn't work was using the API set name, which resulted in an error message by the linker.
The latter is after restarting C++Builder, so I guess the format of the file is simply wrong because of the API set name.