1 /* 2 * Scilab ( http://www.scilab.org/ ) - This file is part of Scilab 3 * Copyright (C) 2012 - Scilab Enterprises - Calixte DENIZET 4 * 5 * Copyright (C) 2012 - 2016 - Scilab Enterprises 6 * 7 * This file is hereby licensed under the terms of the GNU GPL v2.0, 8 * pursuant to article 5.3.4 of the CeCILL v.2.1. 9 * This file was originally licensed under the terms of the CeCILL v2.1, 10 * and continues to be available under such terms. 11 * For more information, see the COPYING file which you should have received 12 * along with this program. 13 * 14 */ 15 16 #ifndef __H5BASICDATA_HXX__ 17 #define __H5BASICDATA_HXX__ 18 19 #include <string.h> 20 #include "H5Data.hxx" 21 #include "H5Object.hxx" 22 #include "H5DataConverter.hxx" 23 24 #define __SCILAB_STACK_CREATOR__(U,NAME) static void create(void * pvApiCtx, const int position, const int rows, const int cols, U const* ptr, int * list, const int listPosition) \ 25 { \ 26 SciErr err; \ 27 if (list) \ 28 { \ 29 if (rows == 0 || cols == 0) \ 30 { \ 31 createMatrixOfDoubleInList(pvApiCtx, position, list, listPosition, 0, 0, 0); \ 32 return; \ 33 } \ 34 err = createMatrixOf##NAME##InList(pvApiCtx, position, list, listPosition, rows, cols, ptr); \ 35 } \ 36 else \ 37 { \ 38 if (rows == 0 || cols == 0) \ 39 { \ 40 createEmptyMatrix(pvApiCtx, position); \ 41 return; \ 42 } \ 43 err = createMatrixOf##NAME(pvApiCtx, position, rows, cols, ptr); \ 44 } \ 45 if (err.iErr) \ 46 { \ 47 throw H5Exception(__LINE__, __FILE__, "Cannot allocate memory"); \ 48 } \ 49 } 50 51 #define __SCILAB_STACK_ALLOCATOR__(U,NAME) static void alloc(void * pvApiCtx, const int position, const int rows, const int cols, int * list, const int listPosition, U ** ptr) \ 52 { \ 53 SciErr err; \ 54 if (list) \ 55 { \ 56 err = allocMatrixOf##NAME##InList(pvApiCtx, position, list, listPosition, rows, cols, ptr); \ 57 } \ 58 else \ 59 { \ 60 err = allocMatrixOf##NAME(pvApiCtx, position, rows, cols, ptr); \ 61 } \ 62 if (err.iErr) \ 63 { \ 64 throw H5Exception(__LINE__, __FILE__, "Cannot allocate memory"); \ 65 } \ 66 } 67 68 #define __SCILAB_ALLOCATORS_CREATORS__(U,NAME) __SCILAB_STACK_CREATOR__(U,NAME) \ 69 __SCILAB_STACK_ALLOCATOR__(U,NAME) 70 71 72 namespace org_modules_hdf5 73 { 74 template<typename T> 75 class H5BasicData : public H5Data 76 { 77 78 protected: 79 80 T * transformedData; 81 82 public: 83 H5BasicData(H5Object & _parent,const hsize_t _totalSize,const hsize_t _dataSize,const hsize_t _ndims,const hsize_t * _dims,T * _data,const hsize_t _stride,const size_t _offset,const bool _dataOwner)84 H5BasicData(H5Object & _parent, const hsize_t _totalSize, const hsize_t _dataSize, const hsize_t _ndims, const hsize_t * _dims, T * _data, const hsize_t _stride, const size_t _offset, const bool _dataOwner) : H5Data(_parent, _totalSize, _dataSize, _ndims, _dims, static_cast<void *>(_data), _stride, _offset, _dataOwner), transformedData(0) 85 { 86 //std::cout << totalSize << ", " << stride << ", " << offset << std::endl; 87 } 88 ~H5BasicData()89 virtual ~H5BasicData() 90 { 91 if (transformedData) 92 { 93 delete[] transformedData; 94 } 95 } 96 printData(std::ostream & os,const unsigned int pos,const unsigned int indentLevel) const97 virtual void printData(std::ostream & os, const unsigned int pos, const unsigned int indentLevel) const 98 { 99 os << static_cast<T *>(getData())[pos]; 100 } 101 copyData(T * dest) const102 virtual void copyData(T * dest) const 103 { 104 if (dest) 105 { 106 if (stride == 0) 107 { 108 memcpy(static_cast<void *>(dest), data, totalSize * dataSize); 109 } 110 else if (transformedData) 111 { 112 memcpy(static_cast<void *>(dest), static_cast<void *>(transformedData), totalSize * dataSize); 113 } 114 else 115 { 116 char * cdata = static_cast<char *>(data) + offset; 117 if (sizeof(T) == dataSize) 118 { 119 for (int i = 0; i < totalSize; i++) 120 { 121 dest[i] = *((T *)cdata); 122 cdata += stride; 123 } 124 } 125 else 126 { 127 char * _dest = reinterpret_cast<char *>(dest); 128 for (int i = 0; i < totalSize; i++) 129 { 130 memcpy(_dest, cdata, dataSize); 131 cdata += stride; 132 _dest += dataSize; 133 } 134 } 135 } 136 } 137 else 138 { 139 throw H5Exception(__LINE__, __FILE__, _("Cannot copy data to an empty pointer")); 140 } 141 } 142 getData() const143 inline virtual void * getData() const 144 { 145 if (stride == 0) 146 { 147 return data; 148 } 149 else 150 { 151 if (!transformedData) 152 { 153 char * dest = new char[totalSize * dataSize]; 154 copyData(reinterpret_cast<T *>(dest)); 155 const_cast<H5BasicData *>(this)->transformedData = reinterpret_cast<T *>(dest); 156 } 157 158 return static_cast<void *>(transformedData); 159 } 160 } 161 toScilab(void * pvApiCtx,const int lhsPosition,int * parentList=0,const int listPosition=0,const bool flip=true) const162 virtual void toScilab(void * pvApiCtx, const int lhsPosition, int * parentList = 0, const int listPosition = 0, const bool flip = true) const 163 { 164 T * newData = 0; 165 hsize_t _ndims = ndims; 166 hsize_t _totalSize = totalSize; 167 hsize_t * _dims = const_cast<hsize_t *>(dims); 168 169 if (_ndims == 0) 170 { 171 create(pvApiCtx, lhsPosition, 1, 1, static_cast<T *>(getData()), parentList, listPosition); 172 } 173 else if (_ndims == 1) 174 { 175 alloc(pvApiCtx, lhsPosition, 1, (int)*_dims, parentList, listPosition, &newData); 176 copyData(newData); 177 } 178 else 179 { 180 if (_ndims == 2) 181 { 182 if (flip) 183 { 184 alloc(pvApiCtx, lhsPosition, (int)_dims[1], (int)_dims[0], parentList, listPosition, &newData); 185 } 186 else 187 { 188 alloc(pvApiCtx, lhsPosition, (int)_dims[0], (int)_dims[1], parentList, listPosition, &newData); 189 } 190 191 H5DataConverter::C2FHypermatrix(2, _dims, 0, static_cast<T *>(getData()), newData, flip); 192 } 193 else 194 { 195 int* pNewDataVar = NULL; 196 int i = 0; 197 int indims = (int)_ndims; 198 int* piDimsArray = new int[indims]; 199 200 alloc(pvApiCtx, lhsPosition, (int)_totalSize, 1, parentList, listPosition, &newData); 201 if (parentList) 202 { 203 getListItemAddress(pvApiCtx, parentList, listPosition, &pNewDataVar); 204 } 205 else 206 { 207 getVarAddressFromPosition(pvApiCtx, lhsPosition, &pNewDataVar); 208 } 209 210 if (flip) 211 { 212 for (i = 0; i < indims; i++) 213 { 214 piDimsArray[indims - 1 - i] = (int)_dims[i]; 215 } 216 } 217 else 218 { 219 for (i = 0; i < indims; i++) 220 { 221 piDimsArray[i] = (int)_dims[i]; 222 } 223 } 224 reshapeArray(pvApiCtx, pNewDataVar, piDimsArray, indims); 225 delete[] piDimsArray; 226 227 H5DataConverter::C2FHypermatrix(indims, _dims, _totalSize, static_cast<T *>(getData()), newData, flip); 228 } 229 } 230 } 231 dump(std::map<haddr_t,std::string> & alreadyVisited,const unsigned int indentLevel) const232 virtual std::string dump(std::map<haddr_t, std::string> & alreadyVisited, const unsigned int indentLevel) const 233 { 234 return H5DataConverter::dump(alreadyVisited, indentLevel, (int)ndims, dims, *this); 235 } 236 putStringVectorOnStack(std::vector<std::string> & strs,const int rows,const int cols,const int pos,void * pvApiCtx)237 static void putStringVectorOnStack(std::vector<std::string> & strs, const int rows, const int cols, const int pos, void * pvApiCtx) 238 { 239 if (rows * cols != strs.size()) 240 { 241 throw H5Exception(__LINE__, __FILE__, _("Wrong dimensions.")); 242 } 243 244 if (strs.size() == 0) 245 { 246 create(pvApiCtx, pos, 0, 0, "", 0, 0); 247 } 248 else 249 { 250 std::vector<const char *> _strs; 251 _strs.reserve(strs.size()); 252 for (unsigned int i = 0; i < strs.size(); i++) 253 { 254 _strs.push_back(strs[i].c_str()); 255 } 256 create(pvApiCtx, pos, rows, cols, const_cast<char **>(&(_strs[0])), 0, 0); 257 } 258 } 259 __SCILAB_ALLOCATORS_CREATORS__(double,Double)260 __SCILAB_ALLOCATORS_CREATORS__(double, Double) 261 __SCILAB_ALLOCATORS_CREATORS__(char, Integer8) 262 __SCILAB_ALLOCATORS_CREATORS__(unsigned char, UnsignedInteger8) 263 __SCILAB_ALLOCATORS_CREATORS__(short, Integer16) 264 __SCILAB_ALLOCATORS_CREATORS__(unsigned short, UnsignedInteger16) 265 __SCILAB_ALLOCATORS_CREATORS__(int, Integer32) 266 __SCILAB_ALLOCATORS_CREATORS__(unsigned int, UnsignedInteger32) 267 268 #ifdef __SCILAB_INT64__ 269 __SCILAB_ALLOCATORS_CREATORS__(long long, Integer64) 270 __SCILAB_ALLOCATORS_CREATORS__(unsigned long long, UnsignedInteger64) 271 #endif 272 273 __SCILAB_STACK_CREATOR__(char *, String) 274 static void alloc(void * pvApiCtx, const int position, const int rows, const int cols, int * list, const int listPosition, char*** ptr) {} 275 }; 276 } 277 278 279 #undef __SCILAB_STACK_CREATOR__ 280 #undef __SCILAB_STACK_ALLOCATOR__ 281 #undef __SCILAB_LIST_CREATOR__ 282 #undef __SCILAB_LIST_ALLOCATOR__ 283 #undef __SCILAB_ALLOCATORS_CREATORS__ 284 285 #endif // __H5BASICDATA_HXX__ 286