Intel® oneAPI DPC++/C++ Compiler
Talk to fellow users of Intel® oneAPI DPC++/C++ Compiler and companion tools like Intel® oneAPI DPC++ Library, Intel® DPC++ Compatibility Tool, and Intel® Distribution for GDB*

Error Passing Objects to PageRank

Alechiove
Beginner
992 Views

Hi!

I'm trying to write down a program with buffers to perform PageRank algorithm.

The code that works with stl reads a csv with edges of the graph. Returns a std::vector<std::vector<int>>. Then, i flat that vector to a std::vector<int>.

The problem is in the lambda function that starts down the code for the ranks calculation. But i can't figure out if it is the vectors or some hyperparameters...

Can someone help me?

Here's the Code:

#include <sycl/sycl.hpp>
#include <sycl/ext/intel/fpga_extensions.hpp>
// #include <oneapi/mkl/blas.hpp>
#include <cmath>
#include <chrono>
#include <iostream>
#include <vector>
#include <cmath>
#include "guideline.h"
#include "print_vector.h"
#include "print_time.h"
#include "read_graph.h"
#include "flatVector.h"


using namespace sycl;

int main(int argc, char* argv[]){
    // Check CL Parameters
    if(argc < 5){
        // FAILURE
        guideline();
        return 0;
    }
    else{
        // Parse CL Objects
        int device_selected = atoi(argv[1]);
        std::string csv_path = argv[2];
        float threshold = atof(argv[3]);
        float damping = atof(argv[3]);
        device d;
        // Select Accelerator
        if(device_selected == 1){
            d = device(cpu_selector()); //# cpu_selector returns a cpu device
        }
        if(device_selected == 2){
            try {
                d = device(gpu_selector());      //# gpu_selector returns a gpu device
            } catch (exception const& e) {
                std::cout << "Cannot select a GPU\n" << e.what() << "\n";
                std::cout << "Using a CPU device\n";
                d = device(cpu_selector());      //# cpu_selector returns a cpu device
            }
        }
        if(device_selected == 3){
            ext::intel::fpga_selector d;
        }
        // Queue
        queue q(d);
        std::cout << "Device : " << q.get_device().get_info<info::device::name>() << "\n"; // print del device
        // Time for setup
        auto start_setup = std::chrono::steady_clock::now();
        // Graph Expressed by edges
        std::vector<std::vector<int>> graph = Read_graph(csv_path);/*edges of graph (Sparse matrix rep.)*/
        std::vector<int> flatGraph = flatten<int>(graph);
        // Calculation of # nodes
        int numNodes  = countNodes(graph);
        // Degree of Each node
        std::vector<int> degreesNodes = getDegrees(graph, numNodes+1);
        auto end_setup = std::chrono::steady_clock::now();
        // prints for debug
        print_time(start_setup, end_setup);
        // prints for debug
        //printVector<int>(degreesNodes);
        //Init - Final Vectors for ratings [R(t); R(t+1)]
        std::vector<float> ranks_t(numNodes, (float)(1.0/ (float)(numNodes)));
        std::vector<float> ranks_t_plus_one(numNodes);

        // Pagerank Execution Time
        auto start = std::chrono::steady_clock::now();
        buffer<int> bufferEdges(flatGraph.data(),flatGraph.size());
        buffer<float> bufferRanks(ranks_t.data(),ranks_t.size());
        buffer<int> bufferDegrees(degreesNodes.data(),degreesNodes.size());
        buffer<float> bufferRanksNext(ranks_t_plus_one.data(),ranks_t_plus_one.size());
        float distance = threshold + 1;
        while (distance > threshold) {
            q.submit([&](handler &h){
                auto accessorsEdges = bufferEdges.get_access<access::mode::read>(h);
                auto accessorsRanks = bufferRanks.get_access<access::mode::read>(h);
                auto accessorsDegrees = bufferDegrees.get_access<access::mode::read>(h);
                auto accessorsRanksNext = bufferRanksNext.get_access<access::mode::read_write>(h);
                h.parallel_for(range<1>(numNodes),[=] (id<1> i){// Errors not  device copiable
                    accessorsRanksNext[i] = (1.0 - damping) / numNodes;
                    int index_node_i;
                    int index_node_j;
                    for (int j = 0; j<flatGraph.size() / 2;j++) {
                        index_node_i = 2 * j;
                        index_node_j = index_node_i + 1;
                        if (accessorsEdges[index_node_j] == i) {
                            accessorsRanksNext[i] += damping * accessorsRanks[accessorsEdges[index_node_i]] / accessorsDegrees[accessorsEdges[index_node_i]];
                        }
                    }
                });
                
            });
            distance = 0;
            for (int i = 0; i < numNodes; i++) {
                distance += (ranks_t[i] - ranks_t_plus_one[i]) * (ranks_t[i] - ranks_t_plus_one[i]);
            }
            distance = sqrt(distance);
            ranks_t_plus_one = ranks_t;
        }
        auto end = std::chrono::steady_clock::now();
        // Print
        printVector(ranks_t_plus_one);
        std::cout<<std::endl<<std::endl<<std::endl;
        std::cout<<"Final Norm:\t"<<distance<<std::endl;
        // Print time PageRank
        print_time(start, end);

        return 0;
    }
}

 Errors:

BUFFER_PageRank.cpp:34:24: warning: 'cpu_selector' is deprecated: Use the callable sycl::cpu_selector_v instead. [-Wdeprecated-declarations]
            d = device(cpu_selector()); //# cpu_selector returns a cpu device
                       ^
/glob/development-tools/versions/oneapi/2023.0/oneapi/compiler/2023.0.0/linux/bin-llvm/../include/sycl/device_selector.hpp:74:21: note: 'cpu_selector' has been explicitly marked deprecated here
class __SYCL_EXPORT __SYCL2020_DEPRECATED(
                    ^
/glob/development-tools/versions/oneapi/2023.0/oneapi/compiler/2023.0.0/linux/bin-llvm/../include/sycl/detail/defines_elementary.hpp:52:40: note: expanded from macro '__SYCL2020_DEPRECATED'
#define __SYCL2020_DEPRECATED(message) __SYCL_DEPRECATED(message)
                                       ^
/glob/development-tools/versions/oneapi/2023.0/oneapi/compiler/2023.0.0/linux/bin-llvm/../include/sycl/detail/defines_elementary.hpp:43:38: note: expanded from macro '__SYCL_DEPRECATED'
#define __SYCL_DEPRECATED(message) [[deprecated(message)]]
                                     ^
BUFFER_PageRank.cpp:38:28: warning: 'gpu_selector' is deprecated: Use the callable sycl::gpu_selector_v instead. [-Wdeprecated-declarations]
                d = device(gpu_selector());      //# gpu_selector returns a gpu device
                           ^
/glob/development-tools/versions/oneapi/2023.0/oneapi/compiler/2023.0.0/linux/bin-llvm/../include/sycl/device_selector.hpp:62:21: note: 'gpu_selector' has been explicitly marked deprecated here
class __SYCL_EXPORT __SYCL2020_DEPRECATED(
                    ^
/glob/development-tools/versions/oneapi/2023.0/oneapi/compiler/2023.0.0/linux/bin-llvm/../include/sycl/detail/defines_elementary.hpp:52:40: note: expanded from macro '__SYCL2020_DEPRECATED'
#define __SYCL2020_DEPRECATED(message) __SYCL_DEPRECATED(message)
                                       ^
/glob/development-tools/versions/oneapi/2023.0/oneapi/compiler/2023.0.0/linux/bin-llvm/../include/sycl/detail/defines_elementary.hpp:43:38: note: expanded from macro '__SYCL_DEPRECATED'
#define __SYCL_DEPRECATED(message) [[deprecated(message)]]
                                     ^
BUFFER_PageRank.cpp:42:28: warning: 'cpu_selector' is deprecated: Use the callable sycl::cpu_selector_v instead. [-Wdeprecated-declarations]
                d = device(cpu_selector());      //# cpu_selector returns a cpu device
                           ^
/glob/development-tools/versions/oneapi/2023.0/oneapi/compiler/2023.0.0/linux/bin-llvm/../include/sycl/device_selector.hpp:74:21: note: 'cpu_selector' has been explicitly marked deprecated here
class __SYCL_EXPORT __SYCL2020_DEPRECATED(
                    ^
/glob/development-tools/versions/oneapi/2023.0/oneapi/compiler/2023.0.0/linux/bin-llvm/../include/sycl/detail/defines_elementary.hpp:52:40: note: expanded from macro '__SYCL2020_DEPRECATED'
#define __SYCL2020_DEPRECATED(message) __SYCL_DEPRECATED(message)
                                       ^
/glob/development-tools/versions/oneapi/2023.0/oneapi/compiler/2023.0.0/linux/bin-llvm/../include/sycl/detail/defines_elementary.hpp:43:38: note: expanded from macro '__SYCL_DEPRECATED'
#define __SYCL_DEPRECATED(message) [[deprecated(message)]]
                                     ^
In file included from BUFFER_PageRank.cpp:1:
In file included from /glob/development-tools/versions/oneapi/2023.0/oneapi/compiler/2023.0.0/linux/bin-llvm/../include/sycl/sycl.hpp:11:
In file included from /glob/development-tools/versions/oneapi/2023.0/oneapi/compiler/2023.0.0/linux/bin-llvm/../include/sycl/accessor.hpp:25:
In file included from /glob/development-tools/versions/oneapi/2023.0/oneapi/compiler/2023.0.0/linux/bin-llvm/../include/sycl/image.hpp:18:
/glob/development-tools/versions/oneapi/2023.0/oneapi/compiler/2023.0.0/linux/bin-llvm/../include/sycl/types.hpp:2440:3: error: static assertion failed due to requirement 'is_device_copyable<std::vector<int, std::allocator<int>>, void>::value || detail::IsDeprecatedDeviceCopyable<std::vector<int, std::allocator<int>>, void>::value': The specified type is not device copyable
  static_assert(is_device_copyable<FieldT>::value ||
  ^             ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
/glob/development-tools/versions/oneapi/2023.0/oneapi/compiler/2023.0.0/linux/bin-llvm/../include/sycl/types.hpp:2438:7: note: in instantiation of template class 'sycl::detail::CheckFieldsAreDeviceCopyable<(lambda at BUFFER_PageRank.cpp:84:51), 4>' requested here
    : CheckFieldsAreDeviceCopyable<T, NumFieldsToCheck - 1> {
      ^
/glob/development-tools/versions/oneapi/2023.0/oneapi/compiler/2023.0.0/linux/bin-llvm/../include/sycl/types.hpp:2438:7: note: in instantiation of template class 'sycl::detail::CheckFieldsAreDeviceCopyable<(lambda at BUFFER_PageRank.cpp:84:51), 5>' requested here
/glob/development-tools/versions/oneapi/2023.0/oneapi/compiler/2023.0.0/linux/bin-llvm/../include/sycl/types.hpp:2438:7: note: in instantiation of template class 'sycl::detail::CheckFieldsAreDeviceCopyable<(lambda at BUFFER_PageRank.cpp:84:51), 6>' requested here
/glob/development-tools/versions/oneapi/2023.0/oneapi/compiler/2023.0.0/linux/bin-llvm/../include/sycl/types.hpp:2473:7: note: in instantiation of template class 'sycl::detail::CheckFieldsAreDeviceCopyable<(lambda at BUFFER_PageRank.cpp:84:51), 7>' requested here
    : CheckFieldsAreDeviceCopyable<FuncT, __builtin_num_fields(FuncT)>,
      ^
/glob/development-tools/versions/oneapi/2023.0/oneapi/compiler/2023.0.0/linux/bin-llvm/../include/sycl/types.hpp:2481:7: note: in instantiation of template class 'sycl::detail::CheckDeviceCopyable<(lambda at BUFFER_PageRank.cpp:84:51)>' requested here
    : CheckDeviceCopyable<KernelType> {};
      ^
/glob/development-tools/versions/oneapi/2023.0/oneapi/compiler/2023.0.0/linux/bin-llvm/../include/sycl/handler.hpp:1251:5: note: in instantiation of template class 'sycl::detail::CheckDeviceCopyable<sycl::detail::RoundedRangeKernel<sycl::item<1, true>, 1, (lambda at BUFFER_PageRank.cpp:84:51)>>' requested here
    detail::CheckDeviceCopyable<KernelType>();
    ^
/glob/development-tools/versions/oneapi/2023.0/oneapi/compiler/2023.0.0/linux/bin-llvm/../include/sycl/handler.hpp:1042:7: note: in instantiation of function template specialization 'sycl::handler::kernel_parallel_for_wrapper<sycl::detail::RoundedRangeKernel<sycl::item<1, true>, 1, (lambda at BUFFER_PageRank.cpp:84:51)>, sycl::item<1, true>, sycl::detail::RoundedRangeKernel<sycl::item<1, true>, 1, (lambda at BUFFER_PageRank.cpp:84:51)>>' requested here
      kernel_parallel_for_wrapper<KName, TransformedArgType>(Wrapper);
      ^
/glob/development-tools/versions/oneapi/2023.0/oneapi/compiler/2023.0.0/linux/bin-llvm/../include/sycl/handler.hpp:1471:5: note: in instantiation of function template specialization 'sycl::handler::parallel_for_lambda_impl<sycl::detail::auto_name, (lambda at BUFFER_PageRank.cpp:84:51), 1>' requested here
    parallel_for_lambda_impl<KernelName>(NumWorkItems, std::move(KernelFunc));
    ^
BUFFER_PageRank.cpp:84:19: note: in instantiation of function template specialization 'sycl::handler::parallel_for<sycl::detail::auto_name, (lambda at BUFFER_PageRank.cpp:84:51)>' requested here
                h.parallel_for(range<1>(numNodes),[=] (id<1> i){// i vettori di interi non sono device copiable
                  ^
/glob/development-tools/versions/oneapi/2023.0/oneapi/compiler/2023.0.0/linux/bin-llvm/../include/sycl/types.hpp:2440:51: note: expression evaluates to 'false || false'
  static_assert(is_device_copyable<FieldT>::value ||
                ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~^~
3 warnings and 1 error generated.

 Here's also the rest of the codes for debugging if it helps:

FlatVector.h

#include <iostream>
#include <vector>

template<typename T>
std::vector<T> flatten(const std::vector<std::vector<T>>& nestedVector) {
    std::vector<T> flatVector;
    for (const auto& subVector : nestedVector) {
        for (const auto& element : subVector) {
            flatVector.push_back(element);
        }
    }
    return flatVector;
}

read_graph.h

#include <iostream>
#include <fstream>
#include <sstream>
#include <vector>
// #include "print_vector.h"


std::vector<int> getDegrees(const std::vector<std::vector<int>> &graph, int numNodes) {
    std::vector<int> degrees(numNodes);
    for (auto &edge : graph) {
        ++degrees[edge[0]];
        ++degrees[edge[1]];
    }
    return degrees;
}

std::vector<std::vector<int>> Read_graph(std::string file_name){
    // Apertura del file
    std::ifstream file(file_name);
    if (!file.is_open()) {
        std::cerr << "Impossibile aprire il file" << std::endl;
        return {};
    }

    // Lettura del file riga per riga
    std::string line;
    std::vector<std::vector<int>> graph;
    while (getline(file, line)) {
        std::stringstream ss(line);
        std::string cell;
        std::vector<int> edge;
        while (getline(ss, cell, ',')) {
            edge.push_back(stoi(cell));
        }
        graph.push_back(edge);
    }
    file.close();
    return graph;
}

int countNodes(std::vector<std::vector<int>> graph){
    int numNodes = 0;
    for(auto &i : graph){
        for(auto &j : i){
            numNodes = std::max(numNodes, j);
        }
    }
    return numNodes;
}

guideline.h

#include <iostream>

void guideline(){
    std::cout<<"Not enough input parameters!\n\n";
    std::cout<<"Usage guide:\n\n";
    std::cout<<"First parameter:\tDevice code (as int number)\n";
    std::cout<<"\t\t1: CPU\n";
    std::cout<<"\t\t2: GPU\n";
    std::cout<<"\t\t3: FPGA\n";
    std::cout<<"Second parameter:\tCsv path of the dataset\n";
    std::cout<<"Available Ones:\n\n";
    std::cout<<"\t\t\"datasets/cit-Patents.csv\""<<std::endl;
    std::cout<<"\t\t\"datasets/soc-LiveJournal1.csv\""<<std::endl;
    std::cout<<"\t\t\"datasets/twitter-2010.csv\""<<std::endl;
    std::cout<<"\t\t\"datasets/web-uk-2005-all.csv\""<<std::endl;
    std::cout<<"Third parameter:\tThreshold (float value)\n";
    std::cout<<"Fourth parameter:\tDamping (float value)\n";
    }

 printTime.h

#include <iostream>
#include <chrono>

void print_time(std::chrono::time_point<std::chrono::steady_clock> start, std::chrono::time_point<std::chrono::steady_clock> end){
    std::cout << "Elapsed time in nanoseconds: " << std::chrono::duration_cast<std::chrono::nanoseconds>(end - start).count() << " ns" << std::endl;
    std::cout << "Elapsed time in microseconds: " << std::chrono::duration_cast<std::chrono::microseconds>(end - start).count() << " µs" << std::endl;
    std::cout << "Elapsed time in milliseconds: " << std::chrono::duration_cast<std::chrono::milliseconds>(end - start).count() << " ms" << std::endl;
    std::cout << "Elapsed time in seconds: " << std::chrono::duration_cast<std::chrono::seconds>(end - start).count() << " sec" << std::endl;    
}
0 Kudos
1 Solution
SeshaP_Intel
Moderator
908 Views

Hi,

 

Thank you for posting in Intel Communities.

 

Could you please try calculating the flatGraph size outside the while loop block using the below command?

auto fd=flatGraph.size();

Hope this resolves your issue. Please let us know if you still face any issues.

 

Thanks and Regards,

Pendyala Sesha Srinivas

View solution in original post

0 Kudos
3 Replies
SeshaP_Intel
Moderator
909 Views

Hi,

 

Thank you for posting in Intel Communities.

 

Could you please try calculating the flatGraph size outside the while loop block using the below command?

auto fd=flatGraph.size();

Hope this resolves your issue. Please let us know if you still face any issues.

 

Thanks and Regards,

Pendyala Sesha Srinivas

0 Kudos
Alechiove
Beginner
888 Views

Yes, it Worked! thank you so much 

0 Kudos
SeshaP_Intel
Moderator
880 Views

Hi,


Thanks for accepting our solution. If you need any additional information, please post a new question as this thread will no longer be monitored by Intel.


Thanks and Regards,

Pendyala Sesha Srinivas


0 Kudos
Reply