Repository navigation
Open
Description
I have a need to copy a view along with its underlying container. Could someone show me the right way to do it?
My current code doesn't propagate the strides info to the view expression. The code crashed when I printed the new view out.
template <class T, class... S>
auto copy_view_to_new_container(const xt::xview<T, S...>& view) {
const auto& container = view.expression();
auto new_container = xt::eval(container);
auto slices = view.slices();
auto new_view = xt::view(new_container, std::get<S>(slices)...);
return std::make_pair(std::move(new_container), std::move(new_view));
}
TEST(gpu_proxy, dtype_float_view1) {
xt::xarray<double> array = xt::arange<double>(100).reshape({10, 10});
auto view = xt::view(array, xt::range(2, 8), xt::range(3, 7));
auto [new_container, new_view] = copy_view_to_new_container(view);
std::cout << new_container << "\n";
std::cout << new_view << "\n"; // core dump here.
}The above code crashed at xview.hpp at the function of compute_strides_impl(). When I printed out xview's m_e, I noticed that m_strides and m_backstrides are not properly initialized. It seems to be the case that the view does not have trivial_strides, so the initialization of m_strides are skipped in xview constructor.
static static_layout = xt::layout_type::row_major}, <xt::xaccessible<xt::xarray_container<xt::uvector<double, std::allocator<double> >, (xt::layout_type)1, xt::svector<unsigned long, 4ul, std::allocator<unsigned long>, true>, xt::xtensor_expression_tag> >> = {<xt::xconst_accessible<xt::xarray_container<xt::uvector<double, std::allocator<double> >, (xt::layout_type)1, xt::svector<unsigned long, 4ul, std::allocator<unsigned long>, true>, xt::xtensor_expression_tag> >> = {<No data fields>}, <No data fields>},
static static_layout = xt::layout_type::row_major, static contiguous_layout = true},
m_shape = {
static alignment = 8,
m_allocator = {<__gnu_cxx::new_allocator<unsigned long>> = {<No data fields>}, <No data fields>},
m_begin = 0xffffffff000003e8, m_end = 0x4b00000003, m_capacity = 0x0, m_data = {0, 0,
140737337425920, 9}},
m_strides = {static alignment = 8,
m_allocator = {<__gnu_cxx::new_allocator<long>> = {<No data fields>}, <No data fields>},
m_begin = 0x0, m_end = 0x0, m_capacity = 0x0, m_data = {0, 0, 0, 6}},
m_backstrides = {
static alignment = 8,
m_allocator = {<__gnu_cxx::new_allocator<long>> = {<No data fields>}, <No data fields>},
m_begin = 0x1, m_end = 0x0, m_capacity = 0x4b00000003, m_data = {-4294966296, 36, 0,
140737488342728}}, Metadata
Metadata
Assignees
Labels
No labels
Activity
spectre-ns commentedon Dec 22, 2024
You code does not compile. I had to update it to the following:
The issue you're encountering here is
new_containeris captured by reference. It's life time is bound to the code ofcopy_view_to_new_containeryou then movenew_containerthis means thatnew_viewnow has a dangling reference which when called results in a segmentation fault.I'm not really sure what you're trying to accomplish to be honest.