diff --git a/vtkm/cont/arg/TransportTagAtomicArray.h b/vtkm/cont/arg/TransportTagAtomicArray.h index 0480aa630..b8e6aa709 100644 --- a/vtkm/cont/arg/TransportTagAtomicArray.h +++ b/vtkm/cont/arg/TransportTagAtomicArray.h @@ -23,7 +23,10 @@ #include #include +#include #include +#include + #include @@ -70,6 +73,50 @@ struct Transport +struct Transport, + Device> +{ + using ExecObjectType = vtkm::exec::AtomicArrayExecutionObject; + using ExecType = vtkm::cont::AtomicArray; + + template + VTKM_CONT ExecObjectType + operator()(vtkm::cont::ArrayHandle& array, + const InputDomainType&, + vtkm::Id, + vtkm::Id) const + { + using S = vtkm::cont::StorageTagBasic; + + const vtkm::cont::StorageVirtual* storage = array.GetStorage(); + if (!storage) + { + throw vtkm::cont::ErrorBadValue("ArrayHandleVirtual must not have a nullptr for storage."); + } + + if (!storage->IsType(typeid(vtkm::cont::internal::Storage))) + { +#if defined(VTKM_ENABLE_LOGGING) + using AH = vtkm::cont::ArrayHandle; + VTKM_LOG_CAST_FAIL(array, AH); +#endif + throw vtkm::cont::ErrorBadValue("Arrays being used as atomic's must always have storage that " + "is of the type StorageTagBasic."); + } + + const auto* any = static_cast*>(storage); + VTKM_LOG_CAST_SUCC(array, *any); + + // Note: we ignore the size of the domain because the randomly accessed + // array might not have the same size depending on how the user is using + // the array. + ExecType obj(any->GetHandle()); + return obj.PrepareForExecution(Device()); + } +}; } } } // namespace vtkm::cont::arg diff --git a/vtkm/cont/arg/TypeCheckTagAtomicArray.h b/vtkm/cont/arg/TypeCheckTagAtomicArray.h index 9eb653d21..7997bc340 100644 --- a/vtkm/cont/arg/TypeCheckTagAtomicArray.h +++ b/vtkm/cont/arg/TypeCheckTagAtomicArray.h @@ -26,6 +26,7 @@ #include #include +#include #include @@ -59,6 +60,14 @@ struct TypeCheck, static constexpr bool value = (vtkm::ListContains::value && vtkm::ListContains::value); }; + +template +struct TypeCheck, + vtkm::cont::ArrayHandle> +{ + static constexpr bool value = (vtkm::ListContains::value && + vtkm::ListContains::value); +}; } } } // namespace vtkm::cont::arg