Skip to main content
1-Visitor
April 5, 2016
Question

Eliminating Linker Warnings with OTK C++

  • April 5, 2016
  • 2 replies
  • 4261 views

I revisited the sample OTK C++ program named otk_install, which I hadn't looked at in about 2 years. I discovered, once again, that I couldn't build a DLL without provoking linker warnings 4049 and 4217. It's not just one or two of these warnings, either; I received 104 warnings for the tiny amount of code in otk_install.

PTC seems to be aware of this problem, because their OTK C++ make files include these linker options:

/ignore:4049 /ignore:4219 /ignore:4217

I haven't been able to do better. All of my current code that uses OTK C++ also includes these options.

I don't like suppressing warnings. When you do that, you don't know whether the warning is happening only once or a thousand times. I nearly always believe that there will be consequences one day for hiding the warnings instead of addressing them.

Microsoft states that these warnings carry only a (presumably minor) performance impact:

Although the final generated code will behave correctly, the code generated to call the imported function is less efficient than calling the function directly.

...but given that I received 104 instances of these warnings, I have to assume that there could be as many (or more) invocations of the affected functions.

I have noticed these warnings when building DLL's, but not EXE's. Of course, I use DLLs for my synchronous applications.

Has anyone successfully built a DLL in OTK C++ without provoking these warnings?

|+|  M a r k  |+|


This thread is inactive and closed by the PTC Community Management Team. If you would like to provide a reply and re-open this thread, please notify the moderator and reference the thread. You may also use "Start a topic" button to ask a new question. Please be sure to include what version of the PTC product you are using so another community member knowledgeable about your version may be able to assist.

2 replies

FV_01
April 6, 2016

Hi all,

Mark, to my knowledge, OTK classes quite often are wrappers for Pro/Toolkit C style functions. C and C++ approach to import/export of symbols is not the same, hence the warnings.  In ideal world OTK would be a nice and shinny, pure C++, C14 compatible set of libraries with no warnings whatsoever...

Feliks.

1-Visitor
April 6, 2016

Feliks -

This, by itself, should not be a problem:

Feliks Veysman wrote:

Mark, to my knowledge, OTK classes quite often are wrappers for Pro/Toolkit C style functions. C and C++ approach to import/export of symbols is not the same, hence the warnings.

I have also written C++ wrapper methods to call Pro/Toolkit functions, but I never got these warnings.

I dug a little further into these warnings and found that, for the otk_install example, all the LNK4049 and LNK4217 warnings were caused by the OTK C++ xstring class. I attached the otk_install warnings to this post. Importing these 25 methods caused the 109 warnings in that file:

private: char const * __cdecl xstring::CastToCString(void)const

private: wchar_t const * __cdecl xstring::CastToCWString(void)const

public: __cdecl xstring::~xstring(void)

public: __cdecl xstring::operator char const *(void)const

public: __cdecl xstring::xstring(char const *)

public: __cdecl xstring::xstring(char const *,char const *)

public: __cdecl xstring::xstring(char const *,int)

public: __cdecl xstring::xstring(class xstring const &)

public: __cdecl xstring::xstring(void)

public: __cdecl xstring::xstring(wchar_t const *)

public: bool __cdecl xstring::IsEmpty(void)const

public: bool __cdecl xstring::Match(char const *)const

public: bool __cdecl xstring::Match(class xstring const &)const

public: bool __cdecl xstring::ToInt(int *)const

public: class xstring & __cdecl xstring::operator+=(char const *)

public: class xstring & __cdecl xstring::operator+=(char)

public: class xstring & __cdecl xstring::operator+=(class xstring const &)

public: class xstring & __cdecl xstring::operator=(char const *)

public: class xstring & __cdecl xstring::operator=(class xstring const &)

public: class xstring __cdecl xstring::Substring(int,int)const

public: class xstring __cdecl xstring::ToLower(void)const

public: int __cdecl xstring::GetLength(void)const

public: int __cdecl xstring::Pos(char const *)const

public: static class xstring __cdecl xstring::Printf(char const *,...)

public: struct __xstring_c __cdecl xstring::getxstring_c(void)const

There may be other OTK C++ classes that cause these problems. It would help if PTC eliminated these warnings from fundamental classes like xstring.

In ideal world OTK would be a nice and shinny, pure C++, C14 compatible set of libraries with no warnings whatsoever...

Well, if OTK C++ used std::string and std::wstring in place of xstring, that would eliminate the warnings I just mentioned!

|+|  M a r k  |+|

14-Alexandrite
April 13, 2016

Just chiming in - I've seen the same warnings. I agree completely... I really don't like having to suppress warnings, especially because I personally like to use the "treat warnings as errors" option in Visual studio.

My temporary solution: I created a separate property sheet in visual studio to enable the OTK libraries, add the header directories, and remove the linker warnings.

Also, +1 for this:

In ideal world OTK would be a nice and shinny, pure C++, C14 compatible set of libraries with no warnings whatsoever...

FV_01
May 2, 2016

Hi all,

Back to the linker warnings.

Mark is correct - warnings had nothing to do with mixing C and C++ calls.

Microsoft has an explanation for LNK4049 :

Linker Tools Warning LNK4049

I had tried to follow Microsoft recommendations and this is what I'm guessing is happening.

I had dumped symbols out of otk_cpp.lib and sure thing for  xstring::xstring(...) there were a number of symbols with dllimport  and without dllimport, so when we are trying to link with otk_cpp.lib the linker is quite confused while parsing otk_cpp.lib. The answer the linker is trying to figure out if xstring::xstring defined locally in otk_cpp.lib why there was a number of dllimport(s) in the same library and this generates warnings.

Here is an example of dumpbin:

866 00000000 UNDEF  notype       External     | __imp_??0xstring@@QEAA@PEBD@Z (__declspec(dllimport) public: __cdecl xstring::xstring(char const *))

3372 00000000 UNDEF  notype       External     | __imp_??0xstring@@QEAA@XZ (__declspec(dllimport) public: __cdecl xstring::xstring(void))

3373 00000000 UNDEF  notype       External     | __imp_??0xstring@@QEAA@AEBV0@@Z (__declspec(dllimport) public: __cdecl xstring::xstring(class xstring const &))

3375 00000000 UNDEF  notype       External     | __imp_??0xstring@@QEAA@PEBD@Z (__declspec(dllimport) public: __cdecl xstring::xstring(char const *))

3376 00000000 UNDEF  notype       External     | __imp_??0xstring@@QEAA@PEB_W@Z (__declspec(dllimport) public: __cdecl xstring::xstring(wchar_t const *))

844 00000000 SECT146 notype ()    External    | ??0xstring@@QEAA@XZ (public: __cdecl xstring::xstring(void))

845 00000000 SECT130 notype ()    External    | ??0xstring@@QEAA@AEBV0@@Z (public: __cdecl xstring::xstring(class xstring const &))

846 00000000 SECT124 notype ()    External    | ??0xstring@@QEAA@$$QEAV0@@Z (public: __cdecl xstring::xstring(class xstring &&))

848 00000000 SECT12E notype ()    External    | ??0xstring@@QEAA@AEBU__xstring_c@@_N@Z (public: __cdecl xstring::xstring(struct __xstring_c const &,bool))

849 00000000 SECT138 notype ()    External    | ??0xstring@@QEAA@PEBD@Z (public: __cdecl xstring::xstring(char const *))

84A 00000000 SECT140 notype ()    External    | ??0xstring@@QEAA@PEB_W@Z (public: __cdecl xstring::xstring(wchar_t const *))

84B 00000000 SECT136 notype ()    External    | ??0xstring@@QEAA@PEBD0@Z (public: __cdecl xstring::xstring(char const *,char const *))

...