[llvm] r174357 - [Support][ErrorOr] Add support for convertable types.

Andrew Trick atrick at apple.com
Tue Feb 5 23:11:39 PST 2013


Michael,

-  ErrorOr(const ErrorOr &Other) : IsValid(false) {
+  template <class OtherT>
+  ErrorOr(ErrorOr<OtherT> &Other) : IsValid(false) {

I'm not a language guy, but this change prevents clang from using the method as a copy ctor. Hence we fail to acquire the ErrorHolderBase and free it early.

Actually, this change alone hides the copy ctor.

+  template <class OtherT>
ErrorOr(const ErrorOr &Other) : IsValid(false) {

I'm not sure how to do this the right way, but there should be plenty of other people on the list who can advise.

Note, this is a problem with the non-cxx11 build.

-Andy

On Feb 5, 2013, at 2:53 PM, Andrew Trick <atrick at apple.com> wrote:

> On Feb 5, 2013, at 12:22 AM, Michael J. Spencer <bigcheesegs at gmail.com> wrote:
> 
>> Author: mspencer
>> Date: Tue Feb  5 02:22:27 2013
>> New Revision: 174357
>> 
>> URL: http://llvm.org/viewvc/llvm-project?rev=174357&view=rev
>> Log:
>> [Support][ErrorOr] Add support for convertable types.
>> 
>> Modified:
>>   llvm/trunk/include/llvm/Support/ErrorOr.h
>>   llvm/trunk/unittests/Support/ErrorOrTest.cpp
> 
> I temporarily reverted this because it's crashing a unit test and blocking the buildbots. I'm not sure yet what the proper workaround should be.
> 
> -Andy
> 
> ErrorOr.SimpleValue
> [       OK ] ErrorOr.SimpleValueSupportTests(65303) malloc: *** error for object 0x100416988: incorrect checksum for freed object - object was probably modified after being freed.
> *** set a breakpoint in malloc_error_break to debug
> 0  SupportTests      0x0000000100253195 llvm::sys::PrintStackTrace(__sFILE*) + 37
> 1  SupportTests      0x0000000100253754 SignalHandler(int) + 676
> 2  libSystem.B.dylib 0x00007fff870631ba _sigtramp + 26
> 3  libSystem.B.dylib 0x0000000000004000 _sigtramp + 2029653600
> 4  libSystem.B.dylib 0x00007fff870e062d szone_error + 519
> 5  libSystem.B.dylib 0x00007fff87007a46 tiny_malloc_from_free_list + 715
> 6  libSystem.B.dylib 0x00007fff87006abd szone_malloc_should_clear + 242
> 7  libSystem.B.dylib 0x00007fff8700698a malloc_zone_malloc + 82
> 8  libSystem.B.dylib 0x00007fff87004c88 malloc + 44
> 9  libstdc++.6.dylib 0x00007fff84046f05 operator new(unsigned long) + 97
> 10 libstdc++.6.dylib 0x00007fff8402c4d1 std::string::_Rep::_S_create(unsigned long, unsigned long, std::allocator<char> const&) + 121
> 11 libstdc++.6.dylib 0x00007fff8402d052 std::string::_Rep::_M_clone(std::allocator<char> const&, unsigned long) + 44
> 12 libstdc++.6.dylib 0x00007fff8402d1d5 std::string::reserve(unsigned long) + 71
> 13 libstdc++.6.dylib 0x00007fff8402ae56 std::basic_stringbuf<char, std::char_traits<char>, std::allocator<char> >::overflow(int) + 188
> 14 libstdc++.6.dylib 0x00007fff84025a19 std::ostream::put(char) + 97
> 15 SupportTests      0x0000000100132104 testing::internal::StringStreamToString(std::basic_stringstream<char, std::char_traits<char>, std::allocator<char> >*) + 500
> 16 SupportTests      0x0000000100145b9a testing::internal::String testing::internal::StreamableToString<long long>(long long const&) + 698
> 17 SupportTests      0x000000010013bf0f testing::internal::PrettyUnitTestResultPrinter::OnTestEnd(testing::TestInfo const&) + 383
> 18 SupportTests      0x000000010013d294 testing::internal::TestEventRepeater::OnTestEnd(testing::TestInfo const&) + 84
> 
> -Andy
> 
>> 
>> Modified: llvm/trunk/include/llvm/Support/ErrorOr.h
>> URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/include/llvm/Support/ErrorOr.h?rev=174357&r1=174356&r2=174357&view=diff
>> ==============================================================================
>> --- llvm/trunk/include/llvm/Support/ErrorOr.h (original)
>> +++ llvm/trunk/include/llvm/Support/ErrorOr.h Tue Feb  5 02:22:27 2013
>> @@ -162,6 +162,7 @@ public:
>> /// T cannot be a rvalue reference.
>> template<class T>
>> class ErrorOr {
>> +  template <class OtherT> friend class ErrorOr;
>>  static const bool isRef = is_reference<T>::value;
>>  typedef ReferenceStorage<typename remove_reference<T>::type> wrap;
>> 
>> @@ -198,7 +199,8 @@ public:
>>    new (get()) storage_type(moveIfMoveConstructible<storage_type>(Val));
>>  }
>> 
>> -  ErrorOr(const ErrorOr &Other) : IsValid(false) {
>> +  template <class OtherT>
>> +  ErrorOr(ErrorOr<OtherT> &Other) : IsValid(false) {
>>    // Construct an invalid ErrorOr if other is invalid.
>>    if (!Other.IsValid)
>>      return;
>> @@ -227,7 +229,8 @@ public:
>>  }
>> 
>> #if LLVM_HAS_RVALUE_REFERENCES
>> -  ErrorOr(ErrorOr &&Other) : IsValid(false) {
>> +  template <class OtherT>
>> +  ErrorOr(ErrorOr<OtherT> &&Other) : IsValid(false) {
>>    // Construct an invalid ErrorOr if other is invalid.
>>    if (!Other.IsValid)
>>      return;
>> @@ -311,7 +314,6 @@ private:
>>    return &Val->get();
>>  }
>> 
>> -protected:
>>  storage_type *get() {
>>    assert(IsValid && "Can't do anything on a default constructed ErrorOr!");
>>    assert(!HasError && "Cannot get value when an error exists!");
>> 
>> Modified: llvm/trunk/unittests/Support/ErrorOrTest.cpp
>> URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/unittests/Support/ErrorOrTest.cpp?rev=174357&r1=174356&r2=174357&view=diff
>> ==============================================================================
>> --- llvm/trunk/unittests/Support/ErrorOrTest.cpp (original)
>> +++ llvm/trunk/unittests/Support/ErrorOrTest.cpp Tue Feb  5 02:22:27 2013
>> @@ -53,6 +53,17 @@ TEST(ErrorOr, Types) {
>>  EXPECT_EQ(3, **t3());
>> #endif
>> }
>> +
>> +struct B {};
>> +struct D : B {};
>> +
>> +TEST(ErrorOr, Covariant) {
>> +  ErrorOr<B*> b(ErrorOr<D*>(0));
>> +
>> +#if LLVM_HAS_CXX11_STDLIB
>> +  ErrorOr<std::unique_ptr<B> > b1(ErrorOr<std::unique_ptr<D> >(0));
>> +#endif
>> +}
>> } // end anon namespace
>> 
>> struct InvalidArgError {
>> 
>> 
>> _______________________________________________
>> llvm-commits mailing list
>> llvm-commits at cs.uiuc.edu
>> http://lists.cs.uiuc.edu/mailman/listinfo/llvm-commits
> 




More information about the llvm-commits mailing list