Make ArrayCopy not depend on a device compiler

Rather than require `ArrayCopy` to create special versions of copy for
all arrays, use a precompiled versions. This should speed up compiles,
reduce the amount of code being generated, and require the device
compiler on fewer source files.

There are some cases where you still need to copy arrays that are not
well supported by the precompiled versions in `ArrayCopy`. (It will
always work, but the fallback is very slow.) In this case, you will want
to switch over to `ArrayCopyDevice`, which has the old behavior.
This commit is contained in:
Kenneth Moreland 2022-01-05 14:46:37 -07:00
parent aefc753329
commit 00609b0af2
11 changed files with 312 additions and 146 deletions

@ -0,0 +1,11 @@
# Make ArrayCopy not depend on a device compiler
Rather than require `ArrayCopy` to create special versions of copy for
all arrays, use a precompiled versions. This should speed up compiles,
reduce the amount of code being generated, and require the device
compiler on fewer source files.
There are some cases where you still need to copy arrays that are not
well supported by the precompiled versions in `ArrayCopy`. (It will
always work, but the fallback is very slow.) In this case, you will want
to switch over to `ArrayCopyDevice`, which has the old behavior.

@ -10,19 +10,10 @@
#ifndef vtk_m_cont_ArrayCopy_h
#define vtk_m_cont_ArrayCopy_h
#include <vtkm/cont/Algorithm.h>
#include <vtkm/cont/ArrayHandle.h>
#include <vtkm/cont/DeviceAdapterTag.h>
#include <vtkm/cont/ErrorExecution.h>
#include <vtkm/cont/Logging.h>
#include <vtkm/cont/UnknownArrayHandle.h>
#include <vtkm/cont/internal/ArrayHandleDeprecated.h>
#include <vtkm/cont/vtkm_cont_export.h>
// TODO: When virtual arrays are available, compile the implementation in a .cxx/.cu file. Common
// arrays are copied directly but anything else would be copied through virtual methods.
#include <vtkm/StaticAssert.h>
#include <vtkm/VecTraits.h>
namespace vtkm
{
@ -32,72 +23,27 @@ namespace cont
namespace detail
{
// Element-wise copy.
template <typename InArrayType, typename OutArrayType>
void ArrayCopyWithAlgorithm(const InArrayType& source, OutArrayType& destination)
// Compile-time check to make sure that an `ArrayHandle` passed to `ArrayCopy`
// can be passed to a `UnknownArrayHandle`. This function does nothing
// except provide a compile error that is easier to understand than if you
// let it go and error in `UnknownArrayHandle`. (Huh? I'm not using that.)
template <typename T>
inline void ArrayCopyValueTypeCheck()
{
// Current implementation of Algorithm::Copy will first try to copy on devices where the
// data is already available.
vtkm::cont::Algorithm::Copy(source, destination);
VTKM_STATIC_ASSERT_MSG(vtkm::HasVecTraits<T>::value,
"An `ArrayHandle` that has a special value type that is not supported "
"by the precompiled version of `ArrayCopy` has been used. If this array "
"must be deep copied, consider using `ArrayCopyDevice`. Look at the "
"compile error for the type assigned to template parameter `T` to "
"see the offending type.");
}
// TODO: Remove last argument once ArryHandleNewStyle becomes ArrayHandle
template <typename InArrayType, typename OutArrayType>
void ArrayCopyOldImpl(const InArrayType& in, OutArrayType& out, std::false_type /* Copy storage */)
{
ArrayCopyWithAlgorithm(in, out);
}
// Copy storage for implicit arrays, must be of same type:
// TODO: This will go away once ArrayHandleNewStyle becomes ArrayHandle.
template <typename ArrayType>
void ArrayCopyOldImpl(const ArrayType& in, ArrayType& out, std::true_type /* Copy storage */)
{
// This is only called if in/out are the same type and the handle is not
// writable. This allows read-only implicit array handles to be copied.
auto newStorage = in.GetStorage();
out = ArrayType(newStorage);
}
// TODO: This will go away once ArrayHandleNewStyle becomes ArrayHandle.
template <typename InArrayType, typename OutArrayType>
VTKM_CONT void ArrayCopyImpl(const InArrayType& source,
OutArrayType& destination,
std::false_type /* New style */)
{
using SameTypes = std::is_same<InArrayType, OutArrayType>;
using IsWritable = vtkm::cont::internal::IsWritableArrayHandle<OutArrayType>;
using JustCopyStorage = std::integral_constant<bool, SameTypes::value && !IsWritable::value>;
ArrayCopyOldImpl(source, destination, JustCopyStorage{});
}
// TODO: ArrayHandleNewStyle will eventually become ArrayHandle, in which case this
// will become ArrayCopyWithAlgorithm
template <typename T1, typename S1, typename T2, typename S2>
VTKM_CONT void ArrayCopyImpl(const vtkm::cont::ArrayHandle<T1, S1>& source,
vtkm::cont::ArrayHandle<T2, S2>& destination,
std::true_type /* New style */)
{
VTKM_STATIC_ASSERT((!std::is_same<T1, T2>::value || !std::is_same<S1, S2>::value));
ArrayCopyWithAlgorithm(source, destination);
}
// TODO: ArrayHandleNewStyle will eventually become ArrayHandle, in which case this
// will become the only version with the same array types.
template <typename T, typename S>
VTKM_CONT void ArrayCopyImpl(const vtkm::cont::ArrayHandle<T, S>& source,
vtkm::cont::ArrayHandle<T, S>& destination,
std::true_type /* New style */)
{
destination.DeepCopyFrom(source);
}
} // namespace detail
/// \brief Does a deep copy from one array to another array.
///
/// Given a source \c ArrayHandle and a destination \c ArrayHandle, this
/// function allocates the destination \c ArrayHandle to the correct size and
/// Given a source `ArrayHandle` and a destination `ArrayHandle`, this
/// function allocates the destination `ArrayHandle` to the correct size and
/// deeply copies all the values from the source to the destination.
///
/// This method will attempt to copy the data using the device that the input
@ -108,63 +54,71 @@ VTKM_CONT void ArrayCopyImpl(const vtkm::cont::ArrayHandle<T, S>& source,
/// This should work on some non-writable array handles as well, as long as
/// both \a source and \a destination are the same type.
///
/// This version of array copy uses a precompiled version of copy that is
/// efficient for most standard memory layouts. However, there are some
/// types of fancy `ArrayHandle` that cannot be handled directly, and
/// the fallback for these arrays can be slow. If you see a warning in
/// the log about an inefficient memory copy when extracting a component,
/// pay heed and look for a different way to copy the data (perhaps
/// using `ArrayCopyDevice`).
///
/// @{
///
template <typename InValueType, typename InStorage, typename OutValueType, typename OutStorage>
VTKM_CONT void ArrayCopy(const vtkm::cont::ArrayHandle<InValueType, InStorage>& source,
vtkm::cont::ArrayHandle<OutValueType, OutStorage>& destination)
inline void ArrayCopy(const vtkm::cont::UnknownArrayHandle& source,
vtkm::cont::UnknownArrayHandle& destination)
{
using InArrayType = vtkm::cont::ArrayHandle<InValueType, InStorage>;
using OutArrayType = vtkm::cont::ArrayHandle<OutValueType, OutStorage>;
using SameTypes = std::is_same<InArrayType, OutArrayType>;
using IsWritable = vtkm::cont::internal::IsWritableArrayHandle<OutArrayType>;
// There are three cases handled here:
// 1. The arrays are the same type:
// -> Deep copy the buffers and the Storage object
// 2. The arrays are different and the output is writable:
// -> Do element-wise copy
// 3. The arrays are different and the output is not writable:
// -> fail (cannot copy)
// Give a nice error message for case 3:
VTKM_STATIC_ASSERT_MSG(IsWritable::value || SameTypes::value,
"Cannot copy to a read-only array with a different "
"type than the source.");
using IsOldStyle =
std::is_base_of<vtkm::cont::internal::ArrayHandleDeprecated<InValueType, InStorage>,
InArrayType>;
// Static dispatch cases 1 & 2
detail::ArrayCopyImpl(source, destination, std::integral_constant<bool, !IsOldStyle::value>{});
destination.DeepCopyFrom(source);
}
inline void ArrayCopy(const vtkm::cont::UnknownArrayHandle& source,
const vtkm::cont::UnknownArrayHandle& destination)
{
destination.DeepCopyFrom(source);
}
VTKM_CONT_EXPORT void ArrayCopy(const vtkm::cont::UnknownArrayHandle& source,
vtkm::cont::UnknownArrayHandle& destination);
VTKM_CONT_EXPORT void ArrayCopy(const vtkm::cont::UnknownArrayHandle& source,
const vtkm::cont::UnknownArrayHandle& destination);
template <typename T, typename S>
VTKM_CONT void ArrayCopy(const vtkm::cont::UnknownArrayHandle& source,
vtkm::cont::ArrayHandle<T, S>& destination)
void ArrayCopy(const vtkm::cont::UnknownArrayHandle& source,
vtkm::cont::ArrayHandle<T, S>& destination)
{
detail::ArrayCopyValueTypeCheck<T>();
using DestType = vtkm::cont::ArrayHandle<T, S>;
if (source.CanConvert<DestType>())
{
ArrayCopy(source.AsArrayHandle<DestType>(), destination);
destination.DeepCopyFrom(source.AsArrayHandle<DestType>());
}
else
{
vtkm::cont::UnknownArrayHandle destWrapper(destination);
ArrayCopy(source, destWrapper);
vtkm::cont::ArrayCopy(source, destWrapper);
// Destination array should not change, but just in case.
destWrapper.AsArrayHandle(destination);
}
}
template <typename T, typename S, typename DestArray>
void ArrayCopy(const vtkm::cont::ArrayHandle<T, S>& source, DestArray& destination)
{
detail::ArrayCopyValueTypeCheck<T>();
vtkm::cont::ArrayCopy(vtkm::cont::UnknownArrayHandle{ source }, destination);
}
// Special case of copying data when type is the same.
template <typename T, typename S>
void ArrayCopy(const vtkm::cont::ArrayHandle<T, S>& source,
vtkm::cont::ArrayHandle<T, S>& destination)
{
destination.DeepCopyFrom(source);
}
// Invalid const ArrayHandle in destination, which is not allowed because it will
// not work in all cases.
template <typename T, typename S>
void ArrayCopy(const vtkm::cont::UnknownArrayHandle&, const vtkm::cont::ArrayHandle<T, S>&)
{
VTKM_STATIC_ASSERT_MSG(sizeof(T) == 0, "Copying to a constant ArrayHandle is not allowed.");
}
/// @}
/// \brief Copies from an unknown to a known array type.
@ -190,13 +144,13 @@ VTKM_CONT void ArrayCopyShallowIfPossible(const vtkm::cont::UnknownArrayHandle s
else
{
vtkm::cont::UnknownArrayHandle destWrapper(destination);
ArrayCopy(source, destWrapper);
vtkm::cont::ArrayCopy(source, destWrapper);
// Destination array should not change, but just in case.
destWrapper.AsArrayHandle(destination);
}
}
}
} // namespace vtkm::cont
} // namespace cont
} // namespace vtkm
#endif //vtk_m_cont_ArrayCopy_h

153
vtkm/cont/ArrayCopyDevice.h Normal file

@ -0,0 +1,153 @@
//============================================================================
// Copyright (c) Kitware, Inc.
// All rights reserved.
// See LICENSE.txt for details.
//
// This software is distributed WITHOUT ANY WARRANTY; without even
// the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR
// PURPOSE. See the above copyright notice for more information.
//============================================================================
#ifndef vtk_m_cont_ArrayCopyDevice_h
#define vtk_m_cont_ArrayCopyDevice_h
#include <vtkm/cont/Algorithm.h>
#include <vtkm/cont/ArrayHandle.h>
#include <vtkm/cont/DeviceAdapterTag.h>
#include <vtkm/cont/ErrorExecution.h>
#include <vtkm/cont/Logging.h>
#include <vtkm/cont/UnknownArrayHandle.h>
#include <vtkm/cont/internal/ArrayHandleDeprecated.h>
#include <vtkm/cont/vtkm_cont_export.h>
// TODO: When virtual arrays are available, compile the implementation in a .cxx/.cu file. Common
// arrays are copied directly but anything else would be copied through virtual methods.
namespace vtkm
{
namespace cont
{
namespace detail
{
// Element-wise copy.
template <typename InArrayType, typename OutArrayType>
void ArrayCopyWithAlgorithm(const InArrayType& source, OutArrayType& destination)
{
// Current implementation of Algorithm::Copy will first try to copy on devices where the
// data is already available.
vtkm::cont::Algorithm::Copy(source, destination);
}
// TODO: Remove last argument once ArryHandleNewStyle becomes ArrayHandle
template <typename InArrayType, typename OutArrayType>
void ArrayCopyOldImpl(const InArrayType& in, OutArrayType& out, std::false_type /* Copy storage */)
{
ArrayCopyWithAlgorithm(in, out);
}
// Copy storage for implicit arrays, must be of same type:
// TODO: This will go away once ArrayHandleNewStyle becomes ArrayHandle.
template <typename ArrayType>
void ArrayCopyOldImpl(const ArrayType& in, ArrayType& out, std::true_type /* Copy storage */)
{
// This is only called if in/out are the same type and the handle is not
// writable. This allows read-only implicit array handles to be copied.
auto newStorage = in.GetStorage();
out = ArrayType(newStorage);
}
// TODO: This will go away once ArrayHandleNewStyle becomes ArrayHandle.
template <typename InArrayType, typename OutArrayType>
VTKM_CONT void ArrayCopyImpl(const InArrayType& source,
OutArrayType& destination,
std::false_type /* New style */)
{
using SameTypes = std::is_same<InArrayType, OutArrayType>;
using IsWritable = vtkm::cont::internal::IsWritableArrayHandle<OutArrayType>;
using JustCopyStorage = std::integral_constant<bool, SameTypes::value && !IsWritable::value>;
ArrayCopyOldImpl(source, destination, JustCopyStorage{});
}
// TODO: ArrayHandleNewStyle will eventually become ArrayHandle, in which case this
// will become ArrayCopyWithAlgorithm
template <typename T1, typename S1, typename T2, typename S2>
VTKM_CONT void ArrayCopyImpl(const vtkm::cont::ArrayHandle<T1, S1>& source,
vtkm::cont::ArrayHandle<T2, S2>& destination,
std::true_type /* New style */)
{
VTKM_STATIC_ASSERT((!std::is_same<T1, T2>::value || !std::is_same<S1, S2>::value));
ArrayCopyWithAlgorithm(source, destination);
}
// TODO: ArrayHandleNewStyle will eventually become ArrayHandle, in which case this
// will become the only version with the same array types.
template <typename T, typename S>
VTKM_CONT void ArrayCopyImpl(const vtkm::cont::ArrayHandle<T, S>& source,
vtkm::cont::ArrayHandle<T, S>& destination,
std::true_type /* New style */)
{
destination.DeepCopyFrom(source);
}
} // namespace detail
/// \brief Does a deep copy from one array to another array.
///
/// Given a source `ArrayHandle` and a destination `ArrayHandle`, this
/// function allocates the destination `ArrayHandle` to the correct size and
/// deeply copies all the values from the source to the destination.
///
/// This method will attempt to copy the data using the device that the input
/// data is already valid on. If the input data is only valid in the control
/// environment, the runtime device tracker is used to try to find another
/// device.
///
/// This should work on some non-writable array handles as well, as long as
/// both \a source and \a destination are the same type.
///
/// This version of array copy is templated to create custom code for the
/// particular types of `ArrayHandle`s that you are copying. This will
/// ensure that you get the best possible copy, but requires a device
/// compiler and tends to bloat the code.
///
/// @{
///
template <typename InValueType, typename InStorage, typename OutValueType, typename OutStorage>
VTKM_CONT void ArrayCopyDevice(const vtkm::cont::ArrayHandle<InValueType, InStorage>& source,
vtkm::cont::ArrayHandle<OutValueType, OutStorage>& destination)
{
using InArrayType = vtkm::cont::ArrayHandle<InValueType, InStorage>;
using OutArrayType = vtkm::cont::ArrayHandle<OutValueType, OutStorage>;
using SameTypes = std::is_same<InArrayType, OutArrayType>;
using IsWritable = vtkm::cont::internal::IsWritableArrayHandle<OutArrayType>;
// There are three cases handled here:
// 1. The arrays are the same type:
// -> Deep copy the buffers and the Storage object
// 2. The arrays are different and the output is writable:
// -> Do element-wise copy
// 3. The arrays are different and the output is not writable:
// -> fail (cannot copy)
// Give a nice error message for case 3:
VTKM_STATIC_ASSERT_MSG(IsWritable::value || SameTypes::value,
"Cannot copy to a read-only array with a different "
"type than the source.");
using IsOldStyle =
std::is_base_of<vtkm::cont::internal::ArrayHandleDeprecated<InValueType, InStorage>,
InArrayType>;
// Static dispatch cases 1 & 2
detail::ArrayCopyImpl(source, destination, std::integral_constant<bool, !IsOldStyle::value>{});
}
/// @}
}
} // namespace vtkm::cont
#endif //vtk_m_cont_ArrayCopyDevice_h

@ -510,13 +510,13 @@ struct ExtractComponentCompositeVecFunctor
template <typename... StorageTags>
struct ArrayExtractComponentImpl<StorageTagCompositeVec<StorageTags...>>
{
template <typename T, vtkm::IdComponent NUM_COMPONENTS>
typename detail::ExtractComponentCompositeVecFunctor<T>::ResultArray operator()(
const vtkm::cont::ArrayHandle<vtkm::Vec<T, NUM_COMPONENTS>,
vtkm::cont::StorageTagCompositeVec<StorageTags...>>& src,
template <typename VecT>
auto operator()(
const vtkm::cont::ArrayHandle<VecT, vtkm::cont::StorageTagCompositeVec<StorageTags...>>& src,
vtkm::IdComponent componentIndex,
vtkm::CopyFlag allowCopy) const
{
using T = typename vtkm::VecTraits<VecT>::ComponentType;
vtkm::cont::ArrayHandleCompositeVector<vtkm::cont::ArrayHandle<T, StorageTags>...> array(src);
constexpr vtkm::IdComponent NUM_SUB_COMPONENTS = vtkm::VecFlat<T>::NUM_COMPONENTS;

@ -11,6 +11,7 @@
set(headers
Algorithm.h
ArrayCopy.h
ArrayCopyDevice.h
ArrayExtractComponent.h
ArrayGetValues.h
ArrayHandle.h
@ -182,7 +183,6 @@ set(sources
# This list of sources has code that uses devices and so might need to be
# compiled with a device-specific compiler (like CUDA).
set(device_sources
ArrayCopy.cxx
ArrayGetValues.cxx
ArrayRangeCompute.cxx
CellLocatorBoundingIntervalHierarchy.cxx
@ -192,6 +192,7 @@ set(device_sources
ColorTable.cxx
ConvertNumComponentsToOffsets.cxx
Field.cxx
internal/ArrayCopyUnknown.cxx
internal/Buffer.cxx
internal/MapArrayPermutation.cxx
MergePartitionedDataSet.cxx

@ -9,6 +9,7 @@
//============================================================================
#include <vtkm/cont/MergePartitionedDataSet.h>
#include <vtkm/cont/Algorithm.h>
#include <vtkm/cont/ArrayCopy.h>
#include <vtkm/cont/ArrayHandleGroupVecVariable.h>
#include <vtkm/cont/ArrayHandleView.h>

@ -275,12 +275,32 @@ VTKM_CONT void UnknownArrayHandle::Allocate(vtkm::Id numValues, vtkm::CopyFlag p
VTKM_CONT void UnknownArrayHandle::DeepCopyFrom(const vtkm::cont::UnknownArrayHandle& source)
{
vtkm::cont::internal::ArrayCopyUnknown(source, *this);
if (!this->IsValid())
{
*this = source.NewInstance();
}
const_cast<const UnknownArrayHandle*>(this)->DeepCopyFrom(source);
}
VTKM_CONT void UnknownArrayHandle::DeepCopyFrom(const vtkm::cont::UnknownArrayHandle& source) const
{
vtkm::cont::internal::ArrayCopyUnknown(source, *this);
if (!this->IsValid())
{
throw vtkm::cont::ErrorBadValue(
"Attempty to copy to a constant UnknownArrayHandle with no valid array.");
}
if (source.IsValueTypeImpl(this->Container->ValueType) &&
source.IsStorageTypeImpl(this->Container->StorageType))
{
this->Container->DeepCopy(source.Container->ArrayHandlePointer,
this->Container->ArrayHandlePointer);
}
else
{
vtkm::cont::internal::ArrayCopyUnknown(source, *this);
}
}
VTKM_CONT
@ -290,8 +310,10 @@ void UnknownArrayHandle::CopyShallowIfPossible(const vtkm::cont::UnknownArrayHan
{
*this = source;
}
const_cast<const UnknownArrayHandle*>(this)->CopyShallowIfPossible(source);
else
{
const_cast<const UnknownArrayHandle*>(this)->CopyShallowIfPossible(source);
}
}
VTKM_CONT
@ -311,7 +333,7 @@ void UnknownArrayHandle::CopyShallowIfPossible(const vtkm::cont::UnknownArrayHan
}
else
{
this->DeepCopyFrom(source);
vtkm::cont::internal::ArrayCopyUnknown(source, *this);
}
}

@ -113,6 +113,15 @@ void UnknownAHShallowCopy(const void* sourceMem, void* destinationMem)
*destination = *source;
}
template <typename T, typename S>
void UnknownAHDeepCopy(const void* sourceMem, void* destinationMem)
{
using AH = vtkm::cont::ArrayHandle<T, S>;
const AH* source = reinterpret_cast<const AH*>(sourceMem);
AH* destination = reinterpret_cast<AH*>(destinationMem);
destination->DeepCopyFrom(*source);
}
template <typename T, typename S>
std::vector<vtkm::cont::internal::Buffer>
UnknownAHExtractComponent(void* mem, vtkm::IdComponent componentIndex, vtkm::CopyFlag allowCopy)
@ -224,6 +233,9 @@ struct VTKM_CONT_EXPORT UnknownAHContainer
using ShallowCopyType = void(const void*, void*);
ShallowCopyType* ShallowCopy;
using DeepCopyType = void(const void*, void*);
DeepCopyType* DeepCopy;
using ExtractComponentType = std::vector<vtkm::cont::internal::Buffer>(void*,
vtkm::IdComponent,
vtkm::CopyFlag);
@ -331,6 +343,7 @@ inline UnknownAHContainer::UnknownAHContainer(const vtkm::cont::ArrayHandle<T, S
, NumberOfComponentsFlat(detail::UnknownAHNumberOfComponentsFlat<T>)
, Allocate(detail::UnknownAHAllocate<T, S>)
, ShallowCopy(detail::UnknownAHShallowCopy<T, S>)
, DeepCopy(detail::UnknownAHDeepCopy<T, S>)
, ExtractComponent(detail::UnknownAHExtractComponent<T, S>)
, ReleaseResources(detail::UnknownAHReleaseResources<T, S>)
, ReleaseResourcesExecution(detail::UnknownAHReleaseResourcesExecution<T, S>)

@ -95,12 +95,35 @@ struct UnknownCopyFunctor1
if (out.IsBaseComponentType<InType>())
{
// Arrays have the same base component type. Copy directly.
UnknownCopyFunctor2{}(out.ExtractArrayFromComponents<InType>(), in);
try
{
UnknownCopyFunctor2{}(out.ExtractArrayFromComponents<InType>(vtkm::CopyFlag::Off), in);
}
catch (vtkm::cont::Error& error)
{
throw vtkm::cont::ErrorBadType(
"Unable to copy to an array of type " + out.GetArrayTypeName() +
" using anonymous methods. Try using vtkm::cont::ArrayCopyDevice. "
"(Original error: `" +
error.GetMessage() + "')");
}
}
else if (out.IsBaseComponentType<vtkm::FloatDefault>())
{
// Can copy anything to default float.
UnknownCopyFunctor2{}(out.ExtractArrayFromComponents<vtkm::FloatDefault>(), in);
try
{
UnknownCopyFunctor2{}(
out.ExtractArrayFromComponents<vtkm::FloatDefault>(vtkm::CopyFlag::Off), in);
}
catch (vtkm::cont::Error& error)
{
throw vtkm::cont::ErrorBadType(
"Unable to copy to an array of type " + out.GetArrayTypeName() +
" using anonymous methods. Try using vtkm::cont::ArrayCopyDevice. "
"(Original error: `" +
error.GetMessage() + "')");
}
}
else
{
@ -141,9 +164,11 @@ namespace vtkm
{
namespace cont
{
namespace internal
{
void ArrayCopy(const vtkm::cont::UnknownArrayHandle& source,
vtkm::cont::UnknownArrayHandle& destination)
void ArrayCopyUnknown(const vtkm::cont::UnknownArrayHandle& source,
vtkm::cont::UnknownArrayHandle& destination)
{
if (!destination.IsValid())
{
@ -153,8 +178,8 @@ void ArrayCopy(const vtkm::cont::UnknownArrayHandle& source,
DoUnknownArrayCopy(source, destination);
}
void ArrayCopy(const vtkm::cont::UnknownArrayHandle& source,
const vtkm::cont::UnknownArrayHandle& destination)
void ArrayCopyUnknown(const vtkm::cont::UnknownArrayHandle& source,
const vtkm::cont::UnknownArrayHandle& destination)
{
if (!destination.IsValid())
{
@ -165,22 +190,6 @@ void ArrayCopy(const vtkm::cont::UnknownArrayHandle& source,
DoUnknownArrayCopy(source, destination);
}
namespace internal
{
void ArrayCopyUnknown(const vtkm::cont::UnknownArrayHandle& source,
vtkm::cont::UnknownArrayHandle& destination)
{
vtkm::cont::ArrayCopy(source, destination);
}
void ArrayCopyUnknown(const vtkm::cont::UnknownArrayHandle& source,
const vtkm::cont::UnknownArrayHandle& destination)
{
vtkm::cont::ArrayCopy(source, destination);
}
} // namespace vtkm::cont::internal
} // namespace vtkm::cont
} // namespace vtkm

@ -12,6 +12,7 @@
#include <vtkm/cont/Algorithm.h>
#include <vtkm/cont/ArrayCopy.h>
#include <vtkm/cont/ArrayCopyDevice.h>
#include <vtkm/cont/ArrayHandle.h>
#include <vtkm/cont/ArrayHandleConstant.h>
#include <vtkm/cont/ArrayHandleCounting.h>
@ -331,8 +332,8 @@ struct DecoratorTests
}
// Copy a constant array into the decorator. This should modify ah3Copy.
vtkm::cont::ArrayCopy(vtkm::cont::make_ArrayHandleConstant(ValueType{ 25 }, ARRAY_SIZE),
ahDecor);
vtkm::cont::ArrayCopyDevice(vtkm::cont::make_ArrayHandleConstant(ValueType{ 25 }, ARRAY_SIZE),
ahDecor);
{ // Accessing portal should give all 25s:
auto portalDecor = ahDecor.ReadPortal();
@ -390,7 +391,7 @@ struct DecoratorTests
}
vtkm::cont::ArrayHandle<ValueType> copiedInExec;
vtkm::cont::ArrayCopy(decorArray, copiedInExec);
vtkm::cont::ArrayCopyDevice(decorArray, copiedInExec);
{
auto copiedPortal = copiedInExec.ReadPortal();
auto countPortal = ahCount.ReadPortal();

@ -11,6 +11,7 @@
#ifndef vtk_m_worklet_connectivity_InnerJoin_h
#define vtk_m_worklet_connectivity_InnerJoin_h
#include <vtkm/cont/Algorithm.h>
#include <vtkm/cont/ArrayHandleIndex.h>
#include <vtkm/worklet/DispatcherMapField.h>
#include <vtkm/worklet/ScatterCounting.h>