Archived

This forum has been archived. Please start a new discussion on GitHub.

Patch for Ice 3.5.0: Allow proper C++11 detection for clang on non-Apple systems

Hi,

The detection of C++11 support for clang in cpp/include/IceUtil/Config.h is designed for Apple's version of clang. Unfortunately Apple decided role their own version numbering, forking the clang source. So e.g. Apple clang 4.2 was based on clang 3.2.

The attached patch allows proper detection of C++11 features on non-Apple platforms (FreeBSD, Linux etc.) while maintaining correct detection on Apple platforms as well.

To apply the source patch Attachment not found. to a fresh Ice 3.5.0 source distribution:
cd Ice-3.5.0
patch -p0 < ice350-detect-cpp11-clang.patch.txt

Additional thoughts/suggestion
The patch was designed so it will not change the behavior on platforms supported by ZeroC at all. What I would really like to see is though is some error condition in case __cplusplus >= 201103 - right now it's possible to build Ice with -std=c++11, but Ice won't detect it as such, leading to using wrong destructor exception specifications. One result of this is that Freeze operations might lead crashes due to unexpected exceptions thrown in destructors, e.g. in unit test Freeze/evictor.
[Ice-3.5.0/cpp/test/Freeze/evictor]$ ./run.py 
starting server... ok
starting client... ok
testing background-save Freeze Evictor... ok
testing transactional Freeze Evictor... -! 05/20/13 01:10:28.553 warning: connection exception:
   TcpTransceiver.cpp:212: Ice::ConnectionLostException:
   connection lost: recv() returned zero
   local address = 172.31.255.251:56910
   remote address = 172.31.255.251:12010
-! 05/20/13 01:10:28.558 warning: connection exception:
   TcpTransceiver.cpp:212: Ice::ConnectionLostException:
   connection lost: recv() returned zero
   local address = 172.31.255.251:22583
   remote address = 172.31.255.251:30228
Caught Ice::Exception: TcpTransceiver.cpp:212: Ice::ConnectionLostException:
connection lost: recv() returned zero
failed!
Client.cpp:424: assertion False' failed
Caught Ice::Exception: Tcunexpected exit status: expected: 0, got -6
Traceback (most recent call last):
  File "./run.py", line 28, in <module>
    TestUtil.clientServerTest(additionalServerOptions= testOptions, additionalClientOptions= testOptions)
  File "/var/ports/basejail/usr/ports/devel/ice/work/Ice-3.5.0/scripts/TestUtil.py", line 1331, in clientServerTest
    clientProc.waitTestSuccess()
  File "/var/ports/basejail/usr/ports/devel/ice/work/Ice-3.5.0/scripts/Expect.py", line 564, in waitTestSuccess
    test(self.exitstatus, exitstatus)
  File "/var/ports/basejail/usr/ports/devel/ice/work/Ice-3.5.0/scripts/Expect.py", line 549, in test
    assert False
AssertionError

To prevent this from happening - also on currently unreleased future compilers - I would suggest the detection algorithm to look like this (untested):
 // Check for C++ 11 support
 //
 #if (defined(__GNUC__) && (__GNUC__ > 4 || (__GNUC__ == 4 && __GNUC_MINOR__ >= 5)) && defined(__GXX_EXPERIMENTAL_CXX0X__)) || \
    (defined(__clang__) && ((defined(__APPLE__) && __clang_major__ >= 4) || (!defined(__APPLE__) && __clang_major__ >= 3)) && __cplusplus >= 201103) || \
     (defined(_MSC_VER) && (_MSC_VER >= 1600))
 #   define ICE_CPP11
 #elif __cplusplus >= 201103
 #   error Unknown C++11 compiler
 #endif