Skip to content

Commit e0d7d95

Browse files
committed
Revert using __builtin_dump_struct as a fallback to print object description
This call is unsafe and cannot be made safe unfortunately.
1 parent e03b687 commit e0d7d95

File tree

4 files changed

+12
-25
lines changed

4 files changed

+12
-25
lines changed

CHANGELOG.md

-3
Original file line numberDiff line numberDiff line change
@@ -5,9 +5,6 @@ The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/),
55

66
## Unreleased
77

8-
### Changed
9-
- `XCTestUtil.h`: default output for printing C++ objects changed to use [`__builtin_dump_struct`](https://clang.llvm.org/docs/LanguageExtensions.html#builtin-dump-struct) clang intrinsic.
10-
118
## [3.0] - 2024-01-17
129

1310
### Changed

README.md

+1-1
Original file line numberDiff line numberDiff line change
@@ -349,7 +349,7 @@ That, in the case of failure, try to obtain description using the following meth
349349
- If there is an ADL call `testDescription(obj)` that produces `NSString *`, use that.
350350
- Otherwise, if there is an ADL call `to_string(obj)` in `using std::to_string` scope, use that
351351
- Otherwise, if it is possible to do `ostream << obj`, use that
352-
- Finally produce use the output of [`__builtin_dump_struct`](https://clang.llvm.org/docs/LanguageExtensions.html#builtin-dump-struct) clang intrinsic.
352+
- Finally produce `"<full name of the type> object"` string.
353353
354354
Thus if an object is printable using the typical means those will be automatically used. You can also make your own objects printable using either of the means above. The `testDescription` approach specifically exists to allow you to print something different for tests than in normal code.
355355

include/objc-helpers/XCTestUtil.h

+10-20
Original file line numberDiff line numberDiff line change
@@ -18,8 +18,7 @@
1818
#import <XCTest/XCTest.h>
1919

2020
#include <sstream>
21-
#include <string>
22-
#include <stdarg.h>
21+
#include <cxxabi.h>
2322

2423
namespace TestUtil {
2524
using std::to_string;
@@ -41,21 +40,14 @@ namespace TestUtil {
4140
{ str << obj };
4241
};
4342

44-
auto sprintf(std::string & res, const char * format, ...) -> int {
45-
va_list vl;
46-
va_start(vl, format);
47-
const int size = vsnprintf(0, 0, format, vl);
48-
va_end(vl);
49-
if (size <= 0)
50-
return size;
51-
size_t appendPos = res.size();
52-
size_t appendSize = size_t(size) + 1;
53-
res.resize(appendPos + appendSize);
54-
va_start(vl, format);
55-
const int ret = vsnprintf(&res[appendPos], appendSize, format, vl);
56-
va_end(vl);
57-
res.resize(appendPos + size_t(ret > 0 ? ret : 0));
58-
return ret;
43+
inline auto demangle(const char * name) -> std::string {
44+
45+
int status = 0;
46+
std::unique_ptr<char, void(*)(void*)> res {
47+
abi::__cxa_demangle(name, nullptr, nullptr, &status),
48+
std::free
49+
};
50+
return (status==0) ? res.get() : name ;
5951
}
6052

6153
template<class T>
@@ -72,9 +64,7 @@ namespace TestUtil {
7264
str << val;
7365
return @(str.str().c_str());
7466
} else {
75-
std::string res;
76-
__builtin_dump_struct(&val, sprintf, res);
77-
return @(res.c_str());
67+
return [NSString stringWithFormat:@"%s object", demangle(typeid(T).name()).c_str()];
7868
}
7969
}
8070
}

test/XCTestUtilTests.mm

+1-1
Original file line numberDiff line numberDiff line change
@@ -173,7 +173,7 @@ void _XCTFailureHandler(XCTestCase * _Nullable test, BOOL expected, const char *
173173
TEST_CASE( "Generic" ) {
174174
failures.clear();
175175
XCTAssertCppEqual(bar{1}, bar{2});
176-
CHECK_FAILURE(__LINE__ - 1, true, "((bar{1}) equal to (bar{2})) failed: (\"(anonymous namespace)::bar {\n int i = 1\n}\n\") is not equal to (\"(anonymous namespace)::bar {\n int i = 2\n}\n\")", "");
176+
CHECK_FAILURE(__LINE__ - 1, true, "((bar{1}) equal to (bar{2})) failed: (\"(anonymous namespace)::bar object\") is not equal to (\"(anonymous namespace)::bar object\")", "");
177177
}
178178

179179
namespace {

0 commit comments

Comments
 (0)