int check(std::vector<NumericT> const & std_dest, std::size_t start1, std::size_t inc1, std::size_t size1, std::size_t start2, std::size_t inc2, std::size_t size2, std::size_t internal_size2, MatrixT const & vcl_dest) { viennacl::backend::typesafe_host_array<NumericT> tempmat(vcl_dest.handle(), vcl_dest.internal_size()); viennacl::backend::memory_read(vcl_dest.handle(), 0, tempmat.raw_size(), reinterpret_cast<NumericT*>(tempmat.get())); for (std::size_t i=0; i < size1; ++i) { for (std::size_t j=0; j < size2; ++j) { NumericT value_std = std_dest[(i*inc1 + start1) * internal_size2 + (j*inc2 + start2)]; NumericT value_dest = vcl_dest.row_major() ? tempmat[(i * vcl_dest.stride1() + vcl_dest.start1()) * vcl_dest.internal_size2() + (j * vcl_dest.stride2() + vcl_dest.start2())] : tempmat[(i * vcl_dest.stride1() + vcl_dest.start1()) + (j * vcl_dest.stride2() + vcl_dest.start2()) * vcl_dest.internal_size1()]; if (value_std < value_dest || value_std > value_dest) { std::cerr << "Failure at row " << i << ", col " << j << ": STL value " << value_std << ", ViennaCL value " << value_dest << std::endl; return EXIT_FAILURE; } } } return EXIT_SUCCESS; }
NumericT diff(std::vector<std::map<IndexT, NumericT> > const & stl_A, MatrixT & vcl_A) { viennacl::switch_memory_context(vcl_A, viennacl::context(viennacl::MAIN_MEMORY)); NumericT error = NumericT(-1.0); NumericT const * vcl_A_elements = viennacl::linalg::host_based::detail::extract_raw_pointer<NumericT>(vcl_A.handle()); unsigned int const * vcl_A_row_buffer = viennacl::linalg::host_based::detail::extract_raw_pointer<unsigned int>(vcl_A.handle1()); unsigned int const * vcl_A_col_buffer = viennacl::linalg::host_based::detail::extract_raw_pointer<unsigned int>(vcl_A.handle2()); /* Simultaneously compare the sparsity patterns of both matrices against each other. */ unsigned int const * vcl_A_current_col_ptr = vcl_A_col_buffer; NumericT const * vcl_A_current_val_ptr = vcl_A_elements; for (std::size_t row = 0; row < stl_A.size(); ++row) { if (vcl_A_current_col_ptr != vcl_A_col_buffer + vcl_A_row_buffer[row]) { std::cerr << "Sparsity pattern mismatch detected: Start of row out of sync!" << std::endl; std::cerr << " STL row: " << row << std::endl; std::cerr << " ViennaCL col ptr is: " << vcl_A_current_col_ptr << std::endl; std::cerr << " ViennaCL col ptr should: " << vcl_A_col_buffer + vcl_A_row_buffer[row] << std::endl; std::cerr << " ViennaCL col ptr value: " << *vcl_A_current_col_ptr << std::endl; return NumericT(1.0); } //std::cout << "Row " << row_it.index1() << ": " << std::endl; for (typename std::map<IndexT, NumericT>::const_iterator col_it = stl_A[row].begin(); col_it != stl_A[row].end(); ++col_it, ++vcl_A_current_col_ptr, ++vcl_A_current_val_ptr) { if (col_it->first != std::size_t(*vcl_A_current_col_ptr)) { std::cerr << "Sparsity pattern mismatch detected!" << std::endl; std::cerr << " STL row: " << row << std::endl; std::cerr << " STL col: " << col_it->first << std::endl; std::cerr << " ViennaCL row entries: " << vcl_A_row_buffer[row] << ", " << vcl_A_row_buffer[row + 1] << std::endl; std::cerr << " ViennaCL entry in row: " << vcl_A_current_col_ptr - (vcl_A_col_buffer + vcl_A_row_buffer[row]) << std::endl; std::cerr << " ViennaCL col: " << *vcl_A_current_col_ptr << std::endl; return NumericT(1.0); } // compute relative error (we know for sure that the uBLAS matrix only carries nonzero entries: NumericT current_error = std::fabs(col_it->second - *vcl_A_current_val_ptr) / std::max(std::fabs(col_it->second), std::fabs(*vcl_A_current_val_ptr)); if (current_error > 0.1) { std::cerr << "Value mismatch detected!" << std::endl; std::cerr << " STL row: " << row << std::endl; std::cerr << " STL col: " << col_it->first << std::endl; std::cerr << " STL value: " << col_it->second << std::endl; std::cerr << " ViennaCL value: " << *vcl_A_current_val_ptr << std::endl; return NumericT(1.0); } if (current_error > error) error = current_error; } } return error; }