Hi, I am trying to wrap around OpenCL. But I am running into some problems when I try to return pointers to R. Later I want to be able to use these pointers in other c functions. As an example I have the following code:
#include "createContext.h" #include <CL/opencl.h> #include <Rcpp.h> // Stuff to expose the cl_platform_id to R static void cl_platform_idObjFinalizer(SEXP ref){ if(TYPEOF(ref) == EXTPTRSXP){ cl_platform_id *o = static_cast<cl_platform_id*> (R_ExternalPtrAddr(ref)); if (o) delete o; } } SEXP cl_platform_id2EXP(cl_platform_id *o){ SEXP xp = R_MakeExternalPtr(o, R_NilValue, R_NilValue); R_RegisterCFinalizerEx(xp, cl_platform_idObjFinalizer, TRUE); return xp; } cl_platform_id *SEXP2cl_platform_id(SEXP o){ if(TYPEOF(o) != EXTPTRSXP) Rf_error("invalid object"); return (cl_platform_id*) R_ExternalPtrAddr(o); } This bit I have found posted on this mailing list earlier. This is to expose a pointer to a cl_platform_id object in memory (and this should also take care of the clean up). Now I have the following method to get a list of platform_ids: SEXP getPlatformIDs(){ //returns a list of platform ids cl_uint num_platforms = 0; clGetPlatformIDs(0, 0, &num_platforms); std::vector<cl_platform_id> platforms(num_platforms); clGetPlatformIDs(num_platforms, platforms.empty() ? NULL : &platforms.front(), &num_platforms); //for each platform in platforms add its pointer to the return list Rcpp::List result(platforms.size()); for (int i=0; i<platforms.size(); i++){ cl_platform_id tempPlatformID = platforms[i]; result[i] = cl_platform_id2EXP(&tempPlatformID); } return result; } And I want to get the name of the platform as follows: SEXP getPlatformName(SEXP sPlatformID){ char cBuffer[1024]; cl_platform_id platformID = *SEXP2cl_platform_id(sPlatformID); clGetPlatformInfo (platformID, CL_PLATFORM_NAME, sizeof(cBuffer), cBuffer, NULL); Rcpp::CharacterVector ab(1); ab[0] = cBuffer; return ab; } The whole lot compiles, but gives a runtime error. When I try the following in R: library(ROpenCL) platformIDs <- getPlatformIDs() print(getPlatformName(platformIDs[[1]])) *** caught segfault *** address 0x51, cause 'memory not mapped' Now when I put all this together in one method which just returns the platform name, it works: SEXP getPlatformIDs2(){ //returns a list of platform ids cl_uint num_platforms = 0; clGetPlatformIDs(0, 0, &num_platforms); std::vector<cl_platform_id> platforms(num_platforms); clGetPlatformIDs(num_platforms, platforms.empty() ? NULL : &platforms.front(), &num_platforms); char cBuffer[1024]; clGetPlatformInfo (platforms[0], CL_PLATFORM_NAME, sizeof(cBuffer), cBuffer, NULL); Rcpp::CharacterVector ab(1); ab[0] = cBuffer; return ab; } This results in: getPlatformIDs2() [1] "NVIDIA CUDA" Could someone check if I am taking the pointer to and from R in the correct way? Thanks in advance, Willem Ligtenberg _______________________________________________ Rcpp-devel mailing list Rcpp-devel@lists.r-forge.r-project.org https://lists.r-forge.r-project.org/cgi-bin/mailman/listinfo/rcpp-devel