Make ArrayPortalWrapper more tolerant of host objects

The ArrayPortalWrapper is used for both execution and control portals.
When it was wrapped around a control portal that does not work on CUDA
devices, we were getting ugly warnings even though the intention was
only to use it in the control environment.
This commit is contained in:
Kenneth Moreland 2020-02-25 11:38:29 -07:00
parent 8569359e14
commit e5a6f2d4b6
7 changed files with 170 additions and 9 deletions

@ -40,6 +40,7 @@ public:
{
}
VTKM_SUPPRESS_EXEC_WARNINGS
VTKM_EXEC_CONT
ArrayPortalConcatenate(const PortalType1& p1, const PortalType2& p2)
: portal1(p1)
@ -48,6 +49,7 @@ public:
}
// Copy constructor
VTKM_SUPPRESS_EXEC_WARNINGS
template <typename OtherP1, typename OtherP2>
VTKM_EXEC_CONT ArrayPortalConcatenate(const ArrayPortalConcatenate<OtherP1, OtherP2>& src)
: portal1(src.GetPortal1())

@ -29,6 +29,7 @@ public:
using PortalType = P;
using ValueType = typename PortalType::ValueType;
VTKM_SUPPRESS_EXEC_WARNINGS
VTKM_EXEC_CONT
ArrayPortalStreaming()
: InputPortal()
@ -38,6 +39,7 @@ public:
{
}
VTKM_SUPPRESS_EXEC_WARNINGS
VTKM_EXEC_CONT
ArrayPortalStreaming(const PortalType& inputPortal,
vtkm::Id blockIndex,
@ -50,6 +52,7 @@ public:
{
}
VTKM_SUPPRESS_EXEC_WARNINGS
template <typename OtherP>
VTKM_EXEC_CONT ArrayPortalStreaming(const ArrayPortalStreaming<OtherP>& src)
: InputPortal(src.GetPortal())
@ -59,6 +62,52 @@ public:
{
}
VTKM_SUPPRESS_EXEC_WARNINGS
VTKM_EXEC_CONT
ArrayPortalStreaming(const ArrayPortalStreaming& src)
: InputPortal(src.InputPortal)
, BlockIndex(src.BlockIndex)
, BlockSize(src.BlockSize)
, CurBlockSize(src.CurBlockSize)
{
}
VTKM_SUPPRESS_EXEC_WARNINGS
VTKM_EXEC_CONT
ArrayPortalStreaming(const ArrayPortalStreaming&& rhs)
: InputPortal(std::move(rhs.InputPortal))
, BlockIndex(std::move(rhs.BlockIndex))
, BlockSize(std::move(rhs.BlockSize))
, CurBlockSize(std::move(rhs.CurBlockSize))
{
}
VTKM_SUPPRESS_EXEC_WARNINGS
VTKM_EXEC_CONT
~ArrayPortalStreaming() {}
VTKM_SUPPRESS_EXEC_WARNINGS
VTKM_EXEC_CONT
ArrayPortalStreaming& operator=(const ArrayPortalStreaming& src)
{
this->InputPortal = src.InputPortal;
this->BlockIndex = src.BlockIndex;
this->BlockSize = src.BlockSize;
this->CurBlockSize = src.CurBlockSize;
return *this;
}
VTKM_SUPPRESS_EXEC_WARNINGS
VTKM_EXEC_CONT
ArrayPortalStreaming& operator=(const ArrayPortalStreaming&& rhs)
{
this->InputPortal = std::move(rhs.InputPortal);
this->BlockIndex = std::move(rhs.BlockIndex);
this->BlockSize = std::move(rhs.BlockSize);
this->CurBlockSize = std::move(rhs.CurBlockSize);
return *this;
}
VTKM_EXEC_CONT
vtkm::Id GetNumberOfValues() const { return this->CurBlockSize; }
@ -119,10 +168,13 @@ class Storage<typename ArrayHandleInputType::ValueType, StorageTagStreaming<Arra
public:
using ValueType = typename ArrayHandleInputType::ValueType;
using PortalType =
vtkm::cont::internal::ArrayPortalStreaming<typename ArrayHandleInputType::WritePortalType>;
using PortalType = vtkm::cont::internal::ArrayPortalStreaming<
typename vtkm::cont::internal::Storage<typename ArrayHandleInputType::ValueType,
typename ArrayHandleInputType::StorageTag>::PortalType>;
using PortalConstType =
vtkm::cont::internal::ArrayPortalStreaming<typename ArrayHandleInputType::ReadPortalType>;
vtkm::cont::internal::ArrayPortalStreaming<typename vtkm::cont::internal::Storage<
typename ArrayHandleInputType::ValueType,
typename ArrayHandleInputType::StorageTag>::PortalConstType>;
VTKM_CONT
Storage()

@ -75,6 +75,39 @@ public:
{
}
// These are the same as the default implementation, but explicitly created to prevent warnings
// from the CUDA compiler where it tries to compile for the device when the underlying portal
// only works for the host.
VTKM_SUPPRESS_EXEC_WARNINGS
VTKM_EXEC_CONT
ArrayPortalToIterators(const ArrayPortalToIterators& src)
: Portal(src.Portal)
{
}
VTKM_SUPPRESS_EXEC_WARNINGS
VTKM_EXEC_CONT
ArrayPortalToIterators(ArrayPortalToIterators&& rhs)
: Portal(std::move(rhs.Portal))
{
}
VTKM_SUPPRESS_EXEC_WARNINGS
VTKM_EXEC_CONT
~ArrayPortalToIterators() {}
VTKM_SUPPRESS_EXEC_WARNINGS
VTKM_EXEC_CONT
ArrayPortalToIterators& operator=(const ArrayPortalToIterators& src)
{
this->Portal = src.Portal;
return *this;
}
VTKM_SUPPRESS_EXEC_WARNINGS
VTKM_EXEC_CONT
ArrayPortalToIterators& operator=(ArrayPortalToIterators&& rhs)
{
this->Portal = std::move(rhs.Portal);
return *this;
}
/// The type of the iterator.
///
using IteratorType = vtkm::cont::internal::IteratorFromArrayPortal<PortalType>;
@ -118,6 +151,43 @@ public:
VTKM_EXEC_CONT
IteratorType GetEnd() const { return this->End; }
// These are the same as the default implementation, but explicitly created to prevent warnings
// from the CUDA compiler where it tries to compile for the device when the underlying portal
// only works for the host.
VTKM_SUPPRESS_EXEC_WARNINGS
VTKM_EXEC_CONT
ArrayPortalToIterators(const ArrayPortalToIterators& src)
: Begin(src.Begin)
, End(src.End)
{
}
VTKM_SUPPRESS_EXEC_WARNINGS
VTKM_EXEC_CONT
ArrayPortalToIterators(ArrayPortalToIterators&& rhs)
: Begin(std::move(rhs.Begin))
, End(std::move(rhs.End))
{
}
VTKM_SUPPRESS_EXEC_WARNINGS
VTKM_EXEC_CONT
~ArrayPortalToIterators() {}
VTKM_SUPPRESS_EXEC_WARNINGS
VTKM_EXEC_CONT
ArrayPortalToIterators& operator=(const ArrayPortalToIterators& src)
{
this->Begin = src.Begin;
this->End = src.End;
return *this;
}
VTKM_SUPPRESS_EXEC_WARNINGS
VTKM_EXEC_CONT
ArrayPortalToIterators& operator=(ArrayPortalToIterators&& rhs)
{
this->Begin = std::move(rhs.Begin);
this->End = std::move(rhs.End);
return *this;
}
private:
IteratorType Begin;
IteratorType End;

@ -60,6 +60,33 @@ public:
{
}
// Even though these do not do anything the default implementation does not, they are defined so
// that the CUDA compiler does not try to compile it for devices and then fail because the
// std::shared_ptr does not work on CUDA devices.
VTKM_CONT ArrayPortalToken(const ArrayPortalToken& src)
: Superclass(src)
, Token(src.Token)
{
}
VTKM_CONT ArrayPortalToken(ArrayPortalToken&& rhs)
: Superclass(std::move(static_cast<Superclass&&>(rhs)))
, Token(std::move(rhs.Token))
{
}
VTKM_CONT ArrayPortalToken& operator=(const ArrayPortalToken& src)
{
this->Superclass::operator=(src);
this->Token = src.Token;
return *this;
}
VTKM_CONT ArrayPortalToken& operator=(ArrayPortalToken&& rhs)
{
this->Superclass::operator=(std::move(static_cast<Superclass&&>(rhs)));
this->Token = std::move(rhs.Token);
return *this;
}
VTKM_CONT ~ArrayPortalToken() {}
/// \brief Detach this portal from the `ArrayHandle`.
///
/// This will open up the `ArrayHandle` for reading and/or writing.

@ -35,6 +35,7 @@ public:
using iter = IteratorFromArrayPortal<ArrayPortalType>;
VTKM_SUPPRESS_EXEC_WARNINGS
VTKM_EXEC_CONT
IteratorFromArrayPortal()
: Portal()
@ -42,6 +43,7 @@ public:
{
}
VTKM_SUPPRESS_EXEC_WARNINGS
VTKM_EXEC_CONT
explicit IteratorFromArrayPortal(const ArrayPortalType& portal, vtkm::Id index = 0)
: Portal(portal)

@ -61,14 +61,18 @@ class VTKM_ALWAYS_EXPORT ArrayPortalWrapper final
public:
ArrayPortalWrapper(const PortalT& p) noexcept : ArrayPortalVirtual<T>(), Portal(p) {}
VTKM_EXEC
VTKM_SUPPRESS_EXEC_WARNINGS
VTKM_EXEC_CONT
~ArrayPortalWrapper() {}
VTKM_EXEC_CONT
T Get(vtkm::Id index) const noexcept
{
using call_supported_t = typename internal::PortalSupportsGets<PortalT>::type;
return this->Get(call_supported_t(), index);
}
VTKM_EXEC
VTKM_EXEC_CONT
void Set(vtkm::Id index, const T& value) const noexcept
{
using call_supported_t = typename internal::PortalSupportsSets<PortalT>::type;
@ -77,10 +81,10 @@ public:
private:
// clang-format off
VTKM_EXEC inline T Get(std::true_type, vtkm::Id index) const noexcept { return this->Portal.Get(index); }
VTKM_EXEC inline T Get(std::false_type, vtkm::Id) const noexcept { return T{}; }
VTKM_EXEC inline void Set(std::true_type, vtkm::Id index, const T& value) const noexcept { this->Portal.Set(index, value); }
VTKM_EXEC inline void Set(std::false_type, vtkm::Id, const T&) const noexcept {}
VTKM_EXEC_CONT inline T Get(std::true_type, vtkm::Id index) const noexcept { return this->Portal.Get(index); }
VTKM_EXEC_CONT inline T Get(std::false_type, vtkm::Id) const noexcept { return T{}; }
VTKM_EXEC_CONT inline void Set(std::true_type, vtkm::Id index, const T& value) const noexcept { this->Portal.Set(index, value); }
VTKM_EXEC_CONT inline void Set(std::false_type, vtkm::Id, const T&) const noexcept {}
// clang-format on

@ -333,6 +333,7 @@ public:
Variant& operator=(const Variant&) = default;
Variant& operator=(Variant&&) = default;
VTKM_SUPPRESS_EXEC_WARNINGS
template <typename T>
VTKM_EXEC_CONT Variant(const T& src) noexcept
{
@ -344,6 +345,7 @@ public:
this->Index = index;
}
VTKM_SUPPRESS_EXEC_WARNINGS
template <typename T>
VTKM_EXEC_CONT Variant(const T&& src) noexcept
{
@ -388,6 +390,7 @@ public:
}
private:
VTKM_SUPPRESS_EXEC_WARNINGS
template <typename T, vtkm::IdComponent I, typename... Args>
VTKM_EXEC_CONT T& EmplaceImpl(Args&&... args)
{
@ -397,6 +400,7 @@ private:
return *value;
}
VTKM_SUPPRESS_EXEC_WARNINGS
template <typename T, vtkm::IdComponent I, typename U, typename... Args>
VTKM_EXEC_CONT T& EmplaceImpl(std::initializer_list<U> il, Args&&... args)
{