63 lines · cpp
1//===----------------------------------------------------------------------===//2//3// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.4// See https://llvm.org/LICENSE.txt for license information.5// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception6//7//===----------------------------------------------------------------------===//8 9// <memory>10 11// weak_ptr12 13// template<class Y> weak_ptr(const weak_ptr<Y>& r);14// template<class Y> weak_ptr(weak_ptr<Y>&& r);15//16// Regression test for https://llvm.org/PR4111417// Verify that these constructors never attempt a derived-to-virtual-base18// conversion on a dangling weak_ptr.19 20#include <cassert>21#include <cstring>22#include <memory>23#include <new>24#include <utility>25 26#include "test_macros.h"27 28struct A {29 int i;30 virtual ~A() {}31};32struct B : public virtual A {33 int j;34};35struct Deleter {36 void operator()(void*) const {37 // do nothing38 }39};40 41int main(int, char**) {42#if TEST_STD_VER >= 1143 alignas(B) char buffer[sizeof(B)];44#else45 std::aligned_storage<sizeof(B), std::alignment_of<B>::value>::type buffer;46#endif47 B* pb = ::new ((void*)&buffer) B();48 std::shared_ptr<B> sp = std::shared_ptr<B>(pb, Deleter());49 std::weak_ptr<B> wp = sp;50 sp = nullptr;51 assert(wp.expired());52 53 // Overwrite the B object with junk.54 std::memset(&buffer, '*', sizeof(buffer));55 56 std::weak_ptr<A> wq = wp;57 assert(wq.expired());58 std::weak_ptr<A> wr = std::move(wp);59 assert(wr.expired());60 61 return 0;62}63