rtlds_imp.hpp 23 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639
  1. /*##############################################################################
  2. HPCC SYSTEMS software Copyright (C) 2012 HPCC Systems.
  3. Licensed under the Apache License, Version 2.0 (the "License");
  4. you may not use this file except in compliance with the License.
  5. You may obtain a copy of the License at
  6. http://www.apache.org/licenses/LICENSE-2.0
  7. Unless required by applicable law or agreed to in writing, software
  8. distributed under the License is distributed on an "AS IS" BASIS,
  9. WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
  10. See the License for the specific language governing permissions and
  11. limitations under the License.
  12. ############################################################################## */
  13. #ifndef rtlds_imp_hpp
  14. #define rtlds_imp_hpp
  15. #include "eclhelper.hpp"
  16. #include "eclrtl_imp.hpp"
  17. //These interfaces aren't always used (because of speed), although may be sensible to switch to them if they prove useful
  18. //either for hiding the implementations, or because I can then write general library functions.
  19. interface IRtlDatasetSimpleCursor
  20. {
  21. virtual const byte * first() = 0;
  22. virtual const byte * next() = 0;
  23. };
  24. interface IRtlDatasetCursor : public IRtlDatasetSimpleCursor
  25. {
  26. virtual const byte * get() = 0;
  27. virtual bool isValid() = 0;
  28. virtual const byte * select(unsigned idx) = 0;
  29. };
  30. //---------------------------------------------------------------------------
  31. interface IResourceContext;
  32. typedef size32_t (*DefaultRowCreator)(ARowBuilder & self, IResourceContext *ctx);
  33. //shouldn't really be derived from ARowBuilder - not a isA, but more efficient
  34. class ECLRTL_API RtlDatasetBuilder : protected ARowBuilder, public RtlCInterface
  35. {
  36. public:
  37. RtlDatasetBuilder();
  38. ~RtlDatasetBuilder();
  39. RTLIMPLEMENT_IINTERFACE
  40. void getData(size32_t & len, void * & data);
  41. size32_t getSize();
  42. byte * queryData();
  43. void queryData(size32_t & len, void * & data);
  44. byte * createRow() { return rowBuilder().getSelf(); }
  45. void finalizeRow(size32_t rowSize) { totalSize += rowSize; self = NULL; }
  46. inline ARowBuilder & rowBuilder() { return *this; }
  47. //IRowBuilder
  48. virtual byte * ensureCapacity(size32_t required, const char * fieldName);
  49. virtual void reportMissingRow() const;
  50. virtual byte * createSelf() = 0;
  51. protected:
  52. void ensure(size32_t required);
  53. protected:
  54. virtual void flushDataset();
  55. protected:
  56. size32_t maxSize;
  57. size32_t totalSize;
  58. byte * buffer;
  59. };
  60. class ECLRTL_API RtlFixedDatasetBuilder : public RtlDatasetBuilder
  61. {
  62. public:
  63. RtlFixedDatasetBuilder(unsigned _recordSize, unsigned _initRows);
  64. byte * createSelf();
  65. protected:
  66. unsigned recordSize;
  67. };
  68. class ECLRTL_API RtlLimitedFixedDatasetBuilder : public RtlFixedDatasetBuilder
  69. {
  70. public:
  71. RtlLimitedFixedDatasetBuilder(unsigned _recordSize, unsigned _maxRows, DefaultRowCreator _rowCreator, IResourceContext *_ctx);
  72. byte * createRow();
  73. protected:
  74. virtual void flushDataset();
  75. protected:
  76. unsigned maxRows;
  77. DefaultRowCreator rowCreator;
  78. IResourceContext *ctx;
  79. };
  80. class ECLRTL_API RtlVariableDatasetBuilder : public RtlDatasetBuilder
  81. {
  82. public:
  83. RtlVariableDatasetBuilder(IRecordSize & _recordSize);
  84. void deserializeRow(IOutputRowDeserializer & deserializer, IRowDeserializerSource & in);
  85. virtual byte * createSelf();
  86. protected:
  87. IRecordSize * recordSize;
  88. unsigned maxRowSize;
  89. };
  90. class ECLRTL_API RtlLimitedVariableDatasetBuilder : public RtlVariableDatasetBuilder
  91. {
  92. public:
  93. RtlLimitedVariableDatasetBuilder(IRecordSize & _recordSize, unsigned _maxRows, DefaultRowCreator _rowCreator, IResourceContext * _ctx);
  94. byte * createRow();
  95. protected:
  96. virtual void flushDataset();
  97. protected:
  98. unsigned numRows;
  99. unsigned maxRows;
  100. DefaultRowCreator rowCreator;
  101. IResourceContext *ctx;
  102. };
  103. //---------------------------------------------------------------------------
  104. class ECLRTL_API rtlRowAttr
  105. {
  106. public:
  107. inline rtlRowAttr() { row=NULL; };
  108. inline ~rtlRowAttr() { dispose(); }
  109. inline void clear() { dispose(); row = NULL; }
  110. inline byte * getClear() { byte * ret = row; row = NULL; return ret; }
  111. inline byte * getbytes() const { return row; }
  112. inline byte * link() const { return (byte *)rtlLinkRow(row); }
  113. inline void set(byte * _row) { rtlLinkRow(_row); dispose(); row = _row; }
  114. inline void setown(byte * _row) { dispose(); row = _row; }
  115. inline void set(const void * _row) { rtlLinkRow(_row); setown(_row); }
  116. inline void setown(const void * _row) { dispose(); row = static_cast<byte *>(const_cast<void *>(_row)); } // ugly - need to clean up const tracking in code generator
  117. protected:
  118. inline void dispose() { rtlReleaseRow(row); }
  119. private:
  120. //Force errors....
  121. inline rtlRowAttr(const rtlRowAttr &) {}
  122. inline rtlRowAttr & operator = (const rtlRowAttr & other) { row = NULL; return *this; }
  123. protected:
  124. byte * row;
  125. };
  126. class ECLRTL_API rtlRowsAttr
  127. {
  128. public:
  129. inline rtlRowsAttr() { count = 0; rows=NULL; };
  130. inline ~rtlRowsAttr() { dispose(); }
  131. inline void clear() { dispose(); rows = NULL; }
  132. inline byte * * * addrrows() { clear(); return &rows; }
  133. inline byte * * queryrows() const { return rows; }
  134. inline unsigned querycount() const { return count; }
  135. byte * * linkrows() const;
  136. inline byte * * & refrows() { clear(); return rows; }
  137. void set(size32_t _count, byte * * _rows);
  138. void setRow(IEngineRowAllocator * rowAllocator, const byte * row);
  139. void setown(size32_t _count, byte * * _rows);
  140. protected:
  141. void dispose();
  142. private:
  143. //Force errors....
  144. inline rtlRowsAttr(const rtlRowsAttr &) {}
  145. inline rtlRowsAttr & operator = (const rtlRowsAttr & other) { count = 0; rows = NULL; return *this; }
  146. public:
  147. unsigned count;
  148. protected:
  149. byte * * rows;
  150. };
  151. //---------------------------------------------------------------------------
  152. void ECLRTL_API rtlReportFieldOverflow(unsigned size, unsigned max, const RtlFieldInfo * field);
  153. class ECLRTL_API RtlRowBuilderBase : implements ARowBuilder, public RtlCInterface
  154. {
  155. public:
  156. RTLIMPLEMENT_IINTERFACE
  157. virtual void reportMissingRow() const;
  158. };
  159. class ECLRTL_API RtlDynamicRowBuilder : implements RtlRowBuilderBase
  160. {
  161. public:
  162. inline RtlDynamicRowBuilder(IEngineRowAllocator * _rowAllocator) : rowAllocator(_rowAllocator)
  163. {
  164. if (rowAllocator)
  165. create();
  166. else
  167. {
  168. self = NULL;
  169. maxLength = 0;
  170. }
  171. }
  172. inline RtlDynamicRowBuilder(IEngineRowAllocator * _rowAllocator, bool createInitial) : rowAllocator(_rowAllocator)
  173. {
  174. if (rowAllocator && createInitial)
  175. create();
  176. else
  177. {
  178. self = NULL;
  179. maxLength = 0;
  180. }
  181. }
  182. //This is here to allow group aggregates to perform resizing.
  183. inline RtlDynamicRowBuilder(IEngineRowAllocator * _rowAllocator, size32_t _maxLength, void * _self) : rowAllocator(_rowAllocator)
  184. {
  185. self = static_cast<byte *>(_self);
  186. maxLength = _maxLength;
  187. }
  188. inline ~RtlDynamicRowBuilder() { clear(); }
  189. virtual byte * ensureCapacity(size32_t required, const char * fieldName);
  190. inline RtlDynamicRowBuilder & ensureRow() { if (!self) create(); return *this; }
  191. inline bool exists() { return (self != NULL); }
  192. inline const void * finalizeRowClear(size32_t len)
  193. {
  194. const unsigned finalMaxLength = maxLength;
  195. maxLength = 0;
  196. return rowAllocator->finalizeRow(len, getUnfinalizedClear(), finalMaxLength);
  197. }
  198. inline size32_t getMaxLength() const { return maxLength; }
  199. inline void * getUnfinalizedClear() { void * ret = self; self = NULL; return ret; }
  200. inline void clear() { if (self) { rowAllocator->releaseRow(self); self = NULL; } }
  201. inline RtlDynamicRowBuilder & setAllocator(IEngineRowAllocator * _rowAllocator) { rowAllocator = _rowAllocator; return *this; }
  202. inline void setown(size32_t _maxLength, void * _self) { self = static_cast<byte *>(_self); maxLength = _maxLength; }
  203. void swapWith(RtlDynamicRowBuilder & other);
  204. protected:
  205. inline byte * create() { self = static_cast<byte *>(rowAllocator->createRow(maxLength)); return self; }
  206. virtual byte * createSelf() { return create(); }
  207. protected:
  208. IEngineRowAllocator * rowAllocator; // does this need to be linked???
  209. size32_t maxLength;
  210. };
  211. class ECLRTL_API RtlStaticRowBuilder : extends RtlRowBuilderBase
  212. {
  213. public:
  214. inline RtlStaticRowBuilder(void * _self, size32_t _maxLength)
  215. {
  216. self = static_cast<byte *>(_self);
  217. maxLength = _maxLength;
  218. }
  219. virtual byte * ensureCapacity(size32_t required, const char * fieldName);
  220. inline void clear() { self = NULL; maxLength = 0; }
  221. inline void set(size32_t _maxLength, void * _self) { self = static_cast<byte *>(_self); maxLength = _maxLength; }
  222. protected:
  223. virtual byte * createSelf();
  224. protected:
  225. size32_t maxLength;
  226. };
  227. class ECLRTL_API RtlNestedRowBuilder : extends RtlRowBuilderBase
  228. {
  229. public:
  230. inline RtlNestedRowBuilder(ARowBuilder & _container, size32_t _offset, size32_t _suffix)
  231. : container(_container), offset(_offset), suffix(_suffix)
  232. {
  233. self = container.row()+offset;
  234. }
  235. virtual byte * ensureCapacity(size32_t required, const char * fieldName)
  236. {
  237. self = container.ensureCapacity(offset+required+suffix, fieldName) + offset;
  238. return self;
  239. }
  240. protected:
  241. virtual byte * createSelf()
  242. {
  243. self = container.getSelf()+offset;
  244. return self;
  245. }
  246. protected:
  247. ARowBuilder & container;
  248. size32_t offset;
  249. size32_t suffix;
  250. };
  251. extern ECLRTL_API const void * rtlCloneRow(IEngineRowAllocator * rowAllocator, size32_t len, const void * row);
  252. //---------------------------------------------------------------------------
  253. class ECLRTL_API CSimpleSourceRowPrefetcher : public ISourceRowPrefetcher, public RtlCInterface
  254. {
  255. public:
  256. CSimpleSourceRowPrefetcher(IOutputMetaData & _meta, ICodeContext * _ctx, unsigned _activityId)
  257. {
  258. deserializer.setown(_meta.querySerializedDiskMeta()->createDiskDeserializer(_ctx, _activityId));
  259. rowAllocator.setown(_ctx->getRowAllocator(&_meta, _activityId));
  260. }
  261. RTLIMPLEMENT_IINTERFACE
  262. virtual void readAhead(IRowDeserializerSource & in)
  263. {
  264. RtlDynamicRowBuilder rowBuilder(rowAllocator);
  265. size32_t len = deserializer->deserialize(rowBuilder, in);
  266. rtlReleaseRow(rowBuilder.finalizeRowClear(len));
  267. }
  268. protected:
  269. Owned<IOutputRowDeserializer> deserializer;
  270. Owned<IEngineRowAllocator> rowAllocator;
  271. };
  272. //---------------------------------------------------------------------------
  273. class ECLRTL_API RtlLinkedDatasetBuilder
  274. {
  275. public:
  276. RtlLinkedDatasetBuilder(IEngineRowAllocator * _rowAllocator, int _choosenLimit=-1);
  277. ~RtlLinkedDatasetBuilder();
  278. void append(const void * source);
  279. void appendRows(size32_t num, byte * * rows);
  280. inline void appendEOG() { appendOwn(NULL); }
  281. byte * createRow();
  282. void cloneRow(size32_t len, const void * ptr);
  283. void deserializeRow(IOutputRowDeserializer & deserializer, IRowDeserializerSource & in);
  284. void expand(size32_t required);
  285. void resize(size32_t required);
  286. void finalizeRows();
  287. void finalizeRow(size32_t len);
  288. void clear();
  289. inline RtlDynamicRowBuilder & rowBuilder() { return builder; }
  290. inline void ensure(size32_t required) { if (required > max) expand(required); }
  291. inline size32_t getcount() { finalizeRows(); return count; }
  292. byte * * linkrows();
  293. inline byte * * queryrows() { finalizeRows(); return rowset; }
  294. void appendOwn(const void * row);
  295. inline byte * row() const { return builder.row(); }
  296. protected:
  297. IEngineRowAllocator * rowAllocator;
  298. RtlDynamicRowBuilder builder;
  299. byte * * rowset;
  300. size32_t count;
  301. size32_t max;
  302. size32_t choosenLimit;
  303. };
  304. class ECLRTL_API RtlLinkedDictionaryBuilder
  305. {
  306. public:
  307. RtlLinkedDictionaryBuilder(IEngineRowAllocator * _rowAllocator, IHThorHashLookupInfo *_hashInfo, unsigned _initialTableSize);
  308. RtlLinkedDictionaryBuilder(IEngineRowAllocator * _rowAllocator, IHThorHashLookupInfo *_hashInfo);
  309. ~RtlLinkedDictionaryBuilder();
  310. void append(const void * source);
  311. void appendOwn(const void * source);
  312. void appendRows(size32_t num, byte * * rows);
  313. inline size32_t getcount() { return tableSize; }
  314. inline byte * * linkrows() { return rtlLinkRowset(table); }
  315. byte * createRow() { return builder.getSelf(); }
  316. void finalizeRow(size32_t len);
  317. inline RtlDynamicRowBuilder & rowBuilder() { return builder; }
  318. void cloneRow(size32_t len, const void * ptr);
  319. void deserializeRow(IOutputRowDeserializer & deserializer, IRowDeserializerSource & in);
  320. /*
  321. Not clear which if any of these we will want...
  322. void expand(size32_t required);
  323. void resize(size32_t required);
  324. void finalizeRows();
  325. inline void ensure(size32_t required) { if (required > max) expand(required); }
  326. */
  327. inline byte * * queryrows() { return table; }
  328. inline byte * row() const { return builder.row(); }
  329. protected:
  330. void checkSpace();
  331. void init(IEngineRowAllocator * _rowAllocator, IHThorHashLookupInfo *_hashInfo, unsigned _initialTableSize);
  332. protected:
  333. IEngineRowAllocator *rowAllocator;
  334. IHash *hash;
  335. ICompare *compare;
  336. RtlDynamicRowBuilder builder;
  337. byte * * table;
  338. size32_t usedCount;
  339. size32_t usedLimit;
  340. size32_t initialSize;
  341. size32_t tableSize;
  342. };
  343. extern ECLRTL_API unsigned __int64 rtlDictionaryCount(size32_t tableSize, byte **table);
  344. extern ECLRTL_API bool rtlDictionaryExists(size32_t tableSize, byte **table);
  345. extern ECLRTL_API byte *rtlDictionaryLookup(IHThorHashLookupInfo &hashInfo, size32_t tableSize, byte **table, const byte *source, byte *defaultRow);
  346. extern ECLRTL_API byte *rtlDictionaryLookupString(size32_t tableSize, byte **table, size32_t len, const char *source, byte *defaultRow);
  347. extern ECLRTL_API byte *rtlDictionaryLookupStringN(size32_t tableSize, byte **table, size32_t N, size32_t len, const char *source, byte *defaultRow);
  348. extern ECLRTL_API byte *rtlDictionaryLookupSigned(size32_t tableSize, byte **table, __int64 source, byte *defaultRow);
  349. extern ECLRTL_API byte *rtlDictionaryLookupUnsigned(size32_t tableSize, byte **table, __uint64 source, byte *defaultRow);
  350. extern ECLRTL_API byte *rtlDictionaryLookupSignedN(size32_t tableSize, byte **table, size32_t size, __int64 source, byte *defaultRow);
  351. extern ECLRTL_API byte *rtlDictionaryLookupUnsignedN(size32_t tableSize, byte **table, size32_t size, __uint64 source, byte *defaultRow);
  352. extern ECLRTL_API bool rtlDictionaryLookupExists(IHThorHashLookupInfo &hashInfo, size32_t tableSize, byte **table, const byte *source);
  353. extern ECLRTL_API bool rtlDictionaryLookupExistsString(size32_t tableSize, byte **table, size32_t len, const char *source);
  354. extern ECLRTL_API bool rtlDictionaryLookupExistsStringN(size32_t tableSize, byte **table, size32_t N, size32_t len, const char *source);
  355. extern ECLRTL_API bool rtlDictionaryLookupExistsSigned(size32_t tableSize, byte **table, __int64 source);
  356. extern ECLRTL_API bool rtlDictionaryLookupExistsUnsigned(size32_t tableSize, byte **table, __uint64 source);
  357. extern ECLRTL_API bool rtlDictionaryLookupExistsSignedN(size32_t tableSize, byte **table, size32_t size, __uint64 source);
  358. extern ECLRTL_API bool rtlDictionaryLookupExistsUnsignedN(size32_t tableSize, byte **table, size32_t size, __uint64 source);
  359. extern ECLRTL_API void appendRowsToRowset(size32_t & targetCount, byte * * & targetRowset, IEngineRowAllocator * rowAllocator, size32_t count, byte * * rows);
  360. //Functions that are used to convert between the serialized and internal memory format
  361. //functions containing child also serialize the length of the dataset, functions without it pass it independently
  362. extern ECLRTL_API void rtlDeserializeChildRowset(size32_t & count, byte * * & rowset, IEngineRowAllocator * _rowAllocator, IOutputRowDeserializer * deserializer, IRowDeserializerSource & in);
  363. extern ECLRTL_API void rtlDeserializeChildGroupRowset(size32_t & count, byte * * & rowset, IEngineRowAllocator * _rowAllocator, IOutputRowDeserializer * deserializer, IRowDeserializerSource & in);
  364. extern ECLRTL_API void rtlSerializeChildRowset(IRowSerializerTarget & out, IOutputRowSerializer * serializer, size32_t count, byte * * rows);
  365. extern ECLRTL_API void rtlSerializeChildGroupRowset(IRowSerializerTarget & out, IOutputRowSerializer * serializer, size32_t count, byte * * rows);
  366. //Functions for converting between rowsets and complete datasets (where length is known)
  367. extern ECLRTL_API void rtlDataset2RowsetX(size32_t & count, byte * * & rowset, IEngineRowAllocator * _rowAllocator, IOutputRowDeserializer * deserializer, size32_t lenSrc, const void * src, bool isGrouped);
  368. extern ECLRTL_API void rtlRowset2DatasetX(unsigned & tlen, void * & tgt, IOutputRowSerializer * serializer, size32_t count, byte * * rows, bool isGrouped);
  369. extern ECLRTL_API void rtlDataset2RowsetX(size32_t & count, byte * * & rowset, IEngineRowAllocator * _rowAllocator, IOutputRowDeserializer * deserializer, size32_t lenSrc, const void * src);
  370. extern ECLRTL_API void rtlGroupedDataset2RowsetX(size32_t & count, byte * * & rowset, IEngineRowAllocator * _rowAllocator, IOutputRowDeserializer * deserializer, size32_t lenSrc, const void * src);
  371. extern ECLRTL_API void rtlRowset2DatasetX(unsigned & tlen, void * & tgt, IOutputRowSerializer * serializer, size32_t count, byte * * rows);
  372. extern ECLRTL_API void rtlGroupedRowset2DatasetX(unsigned & tlen, void * & tgt, IOutputRowSerializer * serializer, size32_t count, byte * * rows);
  373. extern ECLRTL_API size32_t rtlDeserializeToBuilder(ARowBuilder & builder, IOutputRowDeserializer * deserializer, const void * src);
  374. extern ECLRTL_API size32_t rtlSerializeToBuilder(ARowBuilder & builder, IOutputRowSerializer * serializer, const void * src);
  375. //Dictionary serialization/deserialization
  376. extern ECLRTL_API void rtlDeserializeDictionary(size32_t & count, byte * * & rowset, IEngineRowAllocator * rowAllocator, IOutputRowDeserializer * deserializer, size32_t lenSrc, const void * src);
  377. extern ECLRTL_API void rtlDeserializeDictionaryFromDataset(size32_t & count, byte * * & rowset, IEngineRowAllocator * rowAllocator, IOutputRowDeserializer * deserializer, IHThorHashLookupInfo & hashInfo, size32_t lenSrc, const void * src);
  378. extern ECLRTL_API void rtlSerializeDictionary(unsigned & tlen, void * & tgt, IOutputRowSerializer * serializer, size32_t count, byte * * rows);
  379. extern ECLRTL_API void rtlSerializeDictionaryToDataset(unsigned & tlen, void * & tgt, IOutputRowSerializer * serializer, size32_t count, byte * * rows);
  380. extern ECLRTL_API void rtlSerializeDictionary(IRowSerializerTarget & out, IOutputRowSerializer * serializer, size32_t count, byte * * rows);
  381. extern ECLRTL_API void rtlSerializeDictionaryToDataset(IRowSerializerTarget & out, IOutputRowSerializer * serializer, size32_t count, byte * * rows);
  382. //Dictionary serialization/deserialization to a stream - includes length prefix
  383. extern ECLRTL_API void rtlDeserializeChildDictionary(size32_t & count, byte * * & rowset, IEngineRowAllocator * _rowAllocator, IOutputRowDeserializer * deserializer, IRowDeserializerSource & in);
  384. extern ECLRTL_API void rtlDeserializeChildDictionaryFromDataset(size32_t & count, byte * * & rowset, IEngineRowAllocator * rowAllocator, IOutputRowDeserializer * deserializer, IHThorHashLookupInfo & hashInfo, IRowDeserializerSource & in);
  385. extern ECLRTL_API void rtlSerializeChildDictionary(IRowSerializerTarget & out, IOutputRowSerializer * serializer, size32_t count, byte * * rows);
  386. extern ECLRTL_API void rtlSerializeChildDictionaryToDataset(IRowSerializerTarget & out, IOutputRowSerializer * serializer, size32_t count, byte * * rows);
  387. //---------------------------------------------------------------------------
  388. class ECLRTL_API ARtlDatasetCursor
  389. {
  390. //if we ever made the functions virtual, then they would go in here
  391. };
  392. class ECLRTL_API RtlDatasetCursor : public ARtlDatasetCursor
  393. {
  394. public:
  395. RtlDatasetCursor(size32_t _len, const void * _data);
  396. bool exists();
  397. const byte * first();
  398. const byte * get();
  399. void setDataset(size32_t len, const void * data);
  400. bool isValid();
  401. //const byte * next();
  402. protected:
  403. const byte * buffer;
  404. const byte * end;
  405. const byte * cur;
  406. };
  407. class ECLRTL_API RtlFixedDatasetCursor : public RtlDatasetCursor
  408. {
  409. public:
  410. RtlFixedDatasetCursor(size32_t _len, const void * _data, unsigned _recordSize);
  411. RtlFixedDatasetCursor();
  412. void init(size32_t _len, const void * _data, unsigned _recordSize);
  413. size32_t count();
  414. size32_t getSize();
  415. const byte * next();
  416. const byte * select(unsigned idx);
  417. protected:
  418. unsigned recordSize;
  419. };
  420. class ECLRTL_API RtlVariableDatasetCursor : public RtlDatasetCursor
  421. {
  422. public:
  423. RtlVariableDatasetCursor(size32_t _len, const void * _data, IRecordSize & _recordSize);
  424. RtlVariableDatasetCursor();
  425. void init(size32_t _len, const void * _data, IRecordSize & _recordSize);
  426. size32_t count();
  427. size32_t getSize();
  428. const byte * next();
  429. const byte * select(unsigned idx);
  430. protected:
  431. IRecordSize * recordSize;
  432. };
  433. class ECLRTL_API RtlLinkedDatasetCursor : public ARtlDatasetCursor
  434. {
  435. public:
  436. RtlLinkedDatasetCursor(unsigned _numRows, byte * * _rows);
  437. RtlLinkedDatasetCursor();
  438. void setDataset(unsigned _numRows, byte * * _rows) { init(_numRows, _rows); }
  439. void init(unsigned _numRows, byte * * _rows);
  440. inline size32_t count() { return numRows; }
  441. inline bool exists() { return numRows != 0; }
  442. // size32_t getSize() // no sensible implementation
  443. const byte * next();
  444. const byte * select(unsigned idx);
  445. const byte * first();
  446. const byte * get();
  447. bool isValid();
  448. protected:
  449. byte * * rows;
  450. unsigned numRows;
  451. unsigned cur;
  452. };
  453. //Some sample helper functions/classes:
  454. interface ICompare;
  455. extern bool ECLRTL_API rtlCheckInList(const void * lhs, IRtlDatasetCursor * cursor, ICompare * compare);
  456. class ECLRTL_API RtlHashInlistChecker
  457. {
  458. public:
  459. RtlHashInlistChecker(IHash * hashLeft, IHash * hashList, IRtlDatasetCursor * cursor);
  460. bool inList(const void * lhs);
  461. };
  462. class ECLRTL_API RtlCompoundIterator
  463. {
  464. public:
  465. RtlCompoundIterator();
  466. ~RtlCompoundIterator();
  467. void init(unsigned numLevels);
  468. void addIter(unsigned idx, IRtlDatasetSimpleCursor * iter, byte * * cursor);
  469. bool first(unsigned level);
  470. bool next(unsigned level);
  471. inline bool first() { ok = first(numLevels-1); return ok; }
  472. inline bool next() { ok = next(numLevels-1); return ok; }
  473. inline bool isValid() { return ok; }
  474. protected:
  475. inline void setCursor(unsigned level, const void * value)
  476. {
  477. *cursors[level] = (byte *)value;
  478. }
  479. protected:
  480. IRtlDatasetSimpleCursor * * iters;
  481. byte * * * cursors;
  482. unsigned numLevels;
  483. bool ok;
  484. };
  485. //Probably generate inline , rather than use this class, since very simple code...
  486. class ECLRTL_API RtlSimpleIterator
  487. {
  488. public:
  489. void addIter(unsigned idx, IRtlDatasetSimpleCursor * iter, byte * * cursor);
  490. bool first();
  491. bool next();
  492. inline bool isValid() { return (*cursor != NULL); }
  493. protected:
  494. IRtlDatasetSimpleCursor * iter;
  495. byte * * cursor;
  496. };
  497. #endif