When using fstream in a library I get linker errors in the executable

前端 未结 2 1024
轮回少年
轮回少年 2021-01-25 09:24

When I add

#include 

and try to use

std::ifstream (i.e. std::ifstream ifile(pDest))

in my lib

相关标签:
2条回答
  • 2021-01-25 09:40

    for anyone like me that this answer did not ring helpful, a second option is to go to: Project Properties->Configuration Properties->General->Project Defaults->.NET Target Framework Version and set it to v4.0

    https://connect.microsoft.com/VisualStudio/feedbackdetail/view/806238/unwarranted-linker-errors-using-stl-filestream-class-in-managed-classes-in-c-11-cli has an obscure answer from Microsoft team that fixed my issue.

    I also added this answer to another version of the same problem.

    0 讨论(0)
  • 2021-01-25 09:41

    5+ years later... the problem (and maybe many others) is already solved (and forgotten :) )

    You have 1 lib project that contains the code above: I assume it's in a .c(xx) file and not in a .h file (included in both projects), and an app project that makes use of the previous one.
    I've thought about what could the configuration that would yield this behavior be (the lib project building fine and the app project having these unresolved externals) and the only configuration that stands up is: the lib project is not correct. Let me detail:

    • One missing symbol is CrtDbgReport, that tells me that the lib is built in Debug mode.
    • The fact that the lib is building OK, tells me that either:
      1. The lib project is fine, and the error is in the app project
      2. The lib project is not fine (and the app project may or may not be fine) but it's a static library - and in this case the .obj files are simply "merged" together in the resulting .lib file - it is not linked so the linker does not search for unresolved externals at this point and it will only search when this library will be linked in an executable (.exe or .dll). This is backed out by the fact that I saw libcpmtd.lib(1) in the error log: using the static runtime library ((U)CRT) version (especially in a project that contains libraries) only makes sense when building a static app (usually designed to run in a stripped out environment - e.g. on a "Windows minimalistic core" distribution where it could only need core libraries like: ntdll.dll, kernel32.dll, ...).
    • The fact that there were no duplicate symbols at link time (app project) rules out the 1st option.

    This is better that we can simplify the environment required for reproducing the behavior. You can switch Project Properties -> Configuration Properties -> General -> Configuration Type and change from Static Library (.lib) to Dynamic Library (.dll). Now, at the end it will link and will fail spitting the errors when building the lib project.

    1 Check [SO]: Errors when linking to protobuf 3 on MSVC 2013 for details about the CRT linking types (check the links as well). Also check [SO]: LNK2005 Error in CLR Windows Form for more details about what happens when building C and C++ code.

    A few words about [MSDN.Blogs]: Debug vs Release builds: when building in Debug mode, some instrumentation code is silently added in your code to facilitate debugging. That's why Debug build artifacts (vs their Release counterparts):

    • Have significantly larger size
    • Run slower

    The code addition is typically achieved by differences between build steps (simplified version):

    • Preprocess: the _DEBUG macro is defined (as opposed to Release where NDEBUG is defined). You can browse standard include files and you'll see lots of preprocessor directives (#ifdefs mostly) on these macros. This phase has a direct impact on compile phase
    • Link: the right libraries (that actually contain that instrumentation code) are chosen

    The most important thing is that the compile (and indirectly, preprocess) and link phases must be in sync. This is not the case for your lib project, so you have an UCRT mismatch (as the 3rd comment states). To fix this, either:

    • Change the _DEBUG / NDEBUG macro definition from: Project Properties -> C/C++ -> Preprocessor -> Preprocessor Definitions
    • Change UCRT type from: Project Properties -> C/C++ -> Code Generation -> Runtime Library

    I listed them both, since I don't know which one is incorrect (as you would want the configuration settings to match the configuration name (Debug / Release)), but I have a feeling that it's the latter.

    Also, make sure to have consistent settings across projects that are supposed to work together.

    0 讨论(0)
提交回复
热议问题