Tny* Tny_copy(size_t *docSizePtr, const Tny *src) { Tny *dest = NULL; Tny *newObj = NULL; Tny *next = NULL; for (next = src->root; next != NULL; next = next->next) { if (next->type == TNY_BIN || next->type == TNY_OBJ) { newObj = Tny_add(dest, next->type, next->key, next->value.ptr, next->size); } else { newObj = Tny_add(dest, next->type, next->key, &next->value.num, next->size); } if (newObj != NULL) { if (dest == NULL) { newObj->docSizePtr = docSizePtr; *docSizePtr += newObj->docSize; } dest = newObj; } else { Tny_free(dest); return NULL; } } return dest->root; }
int main(int argc, char **argv) { struct timeval t0, t1; double creation = 0.0f; double serialization = 0.0f; double deserialization = 0.0f; Tny *array = NULL; Tny *dict = NULL; char *name = "John Doe"; char *street = "Some street name"; uint32_t streetnr = 10; int count = 100000; size_t size = 0; void *dump = NULL; gettimeofday(&t0, NULL); array = Tny_add(NULL, TNY_ARRAY, NULL, NULL, 0); for(int i = 0; i < count; i++) { dict = Tny_add(NULL, TNY_DICT, NULL, NULL, 0); dict = Tny_add(dict, TNY_BIN, "Name", name, sizeof(name)); dict = Tny_add(dict, TNY_BIN, "Street", street, sizeof(street)); dict = Tny_add(dict, TNY_INT32, "Nr", &streetnr, 0); array = Tny_add(array, TNY_OBJ, NULL, dict, 0); } gettimeofday(&t1, NULL); creation = t1.tv_sec - t0.tv_sec + 1E-6 * (t1.tv_usec - t0.tv_usec); gettimeofday(&t0, NULL); size = Tny_dumps(array, &dump); gettimeofday(&t1, NULL); serialization = t1.tv_sec - t0.tv_sec + 1E-6 * (t1.tv_usec - t0.tv_usec); gettimeofday(&t0, NULL); dict = Tny_loads(dump, size); Tny_free(dict); gettimeofday(&t1, NULL); deserialization = t1.tv_sec - t0.tv_sec + 1E-6 * (t1.tv_usec - t0.tv_usec); printf("Created an array with %d objects in %.2g seconds.\n", count, creation); printf("The serialization of this object took %g seconds.\n", serialization); printf("The deserialization: of this dump took %g seconds.\n", deserialization); printf("The serialized document would be %luB long.\n", size); free(dump); Tny_free(array); return EXIT_SUCCESS; }
Tny* SystemCore::serializeActiveSystems() { // Iterate through all active systems and serialize them out, in order, to // a TNY dictionary. Tny* root = Tny_add(NULL, TNY_DICT, NULL, NULL, 0); for (SystemItem& item : mSystems) { Tny* obj = Tny_add(NULL, TNY_DICT, NULL, NULL, 0); obj = Tny_add(obj, TNY_INT64, const_cast<char*>("interval"), static_cast<void*>(&item.interval), 0); obj = Tny_add(obj, TNY_INT64, const_cast<char*>("stagger"), static_cast<void*>(&item.stagger), 0); obj = Tny_add(obj, TNY_INT64, const_cast<char*>("nextExec"), static_cast<void*>(&item.nextExecutionTime), 0); root = Tny_add(root, TNY_OBJ, const_cast<char*>(item.systemName.c_str()), obj->root, 0); } return root; }
int main(void) { Tny *root = NULL; Tny *embedded = NULL; Tny *tmp = NULL; char *message = "Message"; uint32_t ui32 = 0xB16B00B5; uint64_t ui64 = 0xDEADBEEFABAD1DEAlu; char c = 'A'; double flt = 13.37f; char *typesStr[] = {"BINARY", "INT32", "INT64", "CHAR", "NULL", "DOUBLE"}; TnyType types[] = {TNY_BIN, TNY_INT32, TNY_INT64, TNY_CHAR, TNY_NULL, TNY_DOUBLE}; void *values[] = {message, &ui32, &ui64, &c, NULL, &flt}; size_t sizes[] = {strlen(message),0, 0, 0, 0, 0}; char *keys[] = {"Key1", "Key2", "Key3", "Key4", "Key5", "Key6"}; char corruptedObj[] = {0x01, 0x01, 0x00, 0x00, 0x00, 0x04, 0x08, 0x00, 0x00, 0x00, 0x4D, 0x65, 0x73, 0x73, 0x61, 0x67, 0x65}; int counter = 0; int errors = 0; // Checking every datatype in an array. for (int i = 0; i < 6; i++) { root = Tny_add(NULL, TNY_ARRAY, NULL, NULL, 0); root = Tny_add(root, types[i], NULL, values[i], sizes[i]); if(serialize_deserialize(root)) { printf("Test with type %s in an array failed.\n", typesStr[i]); errors++; } TnyElement_free(root); } // Checking every datatype in a dictionary. for (int i = 0; i < 6; i++) { root = Tny_add(NULL, TNY_DICT, NULL, NULL, 0); root = Tny_add(root, types[i], keys[i], values[i], sizes[i]); if(serialize_deserialize(root)) { printf("Test with type %s in a dictionary failed.\n", typesStr[i]); errors++; } TnyElement_free(root); } // Adding every datatype to an array. root = Tny_add(NULL, TNY_ARRAY, NULL, NULL, 0); for (int i = 0; i < 6; i++) { root = Tny_add(root, types[i], NULL, values[i], sizes[i]); } if (serialize_deserialize(root)) { printf("Test with all types in an array failed.\n"); errors++; } TnyElement_free(root); // Adding every datatype to a dictionary. root = Tny_add(NULL, TNY_DICT, NULL, NULL, 0); for (int i = 0; i < 6; i++) { root = Tny_add(root, types[i], keys[i], values[i], sizes[i]); } if (serialize_deserialize(root)) { printf("Test with all types in a dictionary failed.\n"); errors++; } TnyElement_free(root); // Adding a dictionary to an array. root = Tny_add(NULL, TNY_ARRAY, NULL, NULL, 0); for (int i = 0; i < 6; i++) { root = Tny_add(root, types[i], NULL, values[i], sizes[i]); } embedded = Tny_add(NULL, TNY_DICT, NULL, NULL, 0); for (int i = 0; i < 6; i++) { embedded = Tny_add(embedded, types[i], keys[i], values[i], sizes[i]); } Tny_add(root, TNY_OBJ, NULL, embedded, 0); if (serialize_deserialize(root)) { printf("Test with a sub document in an array failed.\n"); errors++; } if (root != NULL && embedded != NULL) { // Fetching a random element from an array tmp = Tny_at(root, 2); if (tmp == NULL || tmp->value.num != *(uint64_t*)values[2]) { printf("Fetching element at position 2 failed!\n"); errors++; } // Fetching a random element from a dictionary tmp = Tny_get(embedded, "Key3"); if (tmp == NULL || tmp->value.num != *(uint64_t*)values[2]) { printf("Fetching element with key 'Key3' failed!\n"); errors++; } // Remove an element. Tny_remove(Tny_at(root, 2)); tmp = Tny_at(root, 2); if (tmp == NULL || tmp->value.chr != *(char*)values[3]) { printf("Deleting element at position 2 failed!\n"); errors++; } // Adding element after position 2 ui32 = 0x12345678; tmp = Tny_at(root, 2); Tny_add(tmp, TNY_INT32, NULL, &ui32, 0); tmp = Tny_at(root, 3); if (tmp == NULL || tmp->value.num != ui32) { printf("Adding element after position 2 failed!\n"); errors++; } } TnyElement_free(root); // Testing the iterator functions. root = Tny_add(NULL, TNY_ARRAY, NULL, NULL, 0); for (uint32_t i = 0; i < 10; i++) { root = Tny_add(root, TNY_INT32, NULL, &i, 0); } counter = 0; root = root->root; while (Tny_hasNext(root)) { root = Tny_next(root); if (root->value.num != counter) { printf("Iterator Test (1) failed!\n"); errors++; break; } counter++; } if (counter != root->root->size) { printf("Iterator Test (2) failed!\n"); errors++; } TnyElement_free(root); // Loading a corrupted document containing a corrupted size field. root = Tny_loads(corruptedObj, sizeof(corruptedObj)); if (root == NULL || root->size != 0) { printf("Loading of a corrupted document failed!\n"); errors++; } TnyElement_free(root); printf("Tny tests completed with %u error(s).\n", errors); return EXIT_SUCCESS; }
Tny* _Tny_loads(char *data, size_t length, size_t *pos, size_t *docSizePtr) { Tny *tny = NULL; Tny *newObj = NULL; TnyType type = TNY_NULL; uint32_t size = 0; uint32_t i32 = 0; uint64_t i64 = 0; double flt = 0.0f; char *key = NULL; uint64_t counter = 0; uint64_t elements = 0; while ((*pos) < length && (counter == 0 || counter < elements)) { type = data[(*pos)++]; if (tny == NULL) { if (type == TNY_ARRAY || type == TNY_DICT) { HASNEXTDATA(sizeof(uint32_t)); Tny_swapBytes32(&size, (const char*)(data + (*pos))); *pos += sizeof(uint32_t); elements = size; tny = Tny_add(NULL, type, NULL, NULL, size); if (tny != NULL) { if (docSizePtr != NULL) { tny->docSizePtr = docSizePtr; *tny->docSizePtr += tny->docSize; } } else { break; } if (elements == 0) { break; } else { continue; } } else { break; } } if (tny->root->type == TNY_DICT) { HASNEXTDATA(sizeof(uint32_t)); Tny_swapBytes32(&size, (const char*)(data + (*pos))); *pos += sizeof(uint32_t); HASNEXTDATA(size); if (data[(*pos) + size - 1] == '\0') { key = data + (*pos); *pos += size; } else { break; } } else { key = NULL; } if (type == TNY_NULL) { tny = Tny_add(tny, type, key, NULL, 0); } else if (type == TNY_OBJ) { newObj = _Tny_loads(data, length, pos, tny->root->docSizePtr); if (newObj != NULL) { tny = Tny_add(tny, type, key, NULL, 0); if (tny != NULL) { tny->value.tny = newObj->root; } else { break; } } else { break; } } else if (type == TNY_BIN) { HASNEXTDATA(sizeof(uint32_t)); Tny_swapBytes32(&size, (const char*)(data + (*pos))); *pos += sizeof(uint32_t); HASNEXTDATA(size); tny = Tny_add(tny, type, key, (data + *pos), size); *pos += size; } else if (type == TNY_CHAR) { HASNEXTDATA(1); tny = Tny_add(tny, type, key, (data + *pos), 0); (*pos)++; } else if (type == TNY_INT32) { HASNEXTDATA(sizeof(uint32_t)); Tny_swapBytes32(&i32, (const char*)(data + (*pos))); *pos += sizeof(uint32_t); tny = Tny_add(tny, type, key, &i32, 0); } else if (type == TNY_INT64) { HASNEXTDATA(sizeof(uint64_t)); Tny_swapBytes64(&i64, (data + (*pos))); *pos += sizeof(uint64_t); tny = Tny_add(tny, type, key, &i64, 0); } else if (type == TNY_DOUBLE) { HASNEXTDATA(sizeof(double)); Tny_swapBytes64((uint64_t*)&flt, (data + (*pos))); *pos += sizeof(double); tny = Tny_add(tny, type, key, &flt, 0); } counter++; } if (tny != NULL) { tny = tny->root; } return tny; }
Tny* _Tny_loads(char *data, size_t length, size_t *pos) { Tny *tny = NULL; TnyType type = TNY_NULL; uint32_t size = 0; uint32_t i32 = 0; uint64_t i64 = 0; double flt = 0.0f; char *key = NULL; uint64_t counter = 0; uint64_t elements = 0; while ((*pos) < length) { type = data[(*pos)++]; if (tny == NULL) { if (type == TNY_ARRAY || type == TNY_DICT) { HASNEXTDATA(sizeof(uint32_t)); Tny_swapBytes32(&size, (uint32_t*)(data + (*pos))); *pos += sizeof(uint32_t); elements = size; tny = Tny_add(NULL, type, NULL, NULL, size); continue; } else { break; } } if (tny->root->type == TNY_DICT) { HASNEXTDATA(sizeof(uint32_t)); Tny_swapBytes32(&size, (uint32_t*)(data + (*pos))); *pos += sizeof(uint32_t); HASNEXTDATA(size); if (data[(*pos) + size - 1] == '\0') { key = data + (*pos); *pos += size; } else { break; } } else { key = NULL; } if (type == TNY_NULL) { tny = Tny_add(tny, type, key, NULL, 0); } else if (type == TNY_OBJ) { tny = Tny_add(tny, type, key, _Tny_loads(data, length, pos), 0); } else if (type == TNY_BIN) { HASNEXTDATA(sizeof(uint32_t)); Tny_swapBytes32(&size, (uint32_t*)(data + (*pos))); *pos += sizeof(uint32_t); HASNEXTDATA(size); tny = Tny_add(tny, type, key, (data + *pos), size); *pos += size; } else if (type == TNY_CHAR) { HASNEXTDATA(1); tny = Tny_add(tny, type, key, (data + *pos), 0); (*pos)++; } else if (type == TNY_INT32) { HASNEXTDATA(sizeof(uint32_t)); Tny_swapBytes32(&i32, (uint32_t*)(data + (*pos))); *pos += sizeof(uint32_t); tny = Tny_add(tny, type, key, &i32, 0); } else if (type == TNY_INT64) { HASNEXTDATA(sizeof(uint64_t)); Tny_swapBytes64(&i64, (uint64_t*)(data + (*pos))); *pos += sizeof(uint64_t); tny = Tny_add(tny, type, key, &i64, 0); } else if (type == TNY_DOUBLE) { HASNEXTDATA(sizeof(double)); Tny_swapBytes64((uint64_t*)&flt, (uint64_t*)(data + (*pos))); *pos += sizeof(double); tny = Tny_add(tny, type, key, &flt, 0); } counter++; if (counter >= elements) { break; } } if (Tny_calcSize(tny->root) == 0) { Tny_free(tny); tny = NULL; } else { tny = tny->root; } return tny; }