/* * Copyright (c) 2019 TAOS Data, Inc. * * This program is free software: you can use, redistribute, and/or modify * it under the terms of the GNU Affero General Public License, version 3 * or later ("AGPL"), as published by the Free Software Foundation. * * This program is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or * FITNESS FOR A PARTICULAR PURPOSE. * * You should have received a copy of the GNU Affero General Public License * along with this program. If not, see . */ #include "encode.h" #if __STDC_VERSION__ >= 201112L static_assert(sizeof(float) == sizeof(uint32_t), "sizeof(float) must equal to sizeof(uint32_t)"); static_assert(sizeof(double) == sizeof(uint64_t), "sizeof(double) must equal to sizeof(uint64_t)"); #endif void tCoderInit(SCoder* pCoder, td_endian_t endian, uint8_t* data, int32_t size, td_coder_t type) { if (type == TD_ENCODER) { if (data == NULL) size = 0; } else { ASSERT(data && size > 0); } pCoder->type = type; pCoder->endian = endian; pCoder->data = data; pCoder->size = size; pCoder->pos = 0; tFreeListInit(&(pCoder->fl)); TD_SLIST_INIT(&(pCoder->stack)); } void tCoderClear(SCoder* pCoder) { tFreeListClear(&(pCoder->fl)); struct SCoderNode* pNode; for (;;) { pNode = TD_SLIST_HEAD(&(pCoder->stack)); if (pNode == NULL) break; TD_SLIST_POP(&(pCoder->stack)); free(pNode); } } bool tDecodeIsEnd(SCoder* pCoder) { return (pCoder->size == pCoder->pos); } int tStartEncode(SCoder* pCoder) { struct SCoderNode* pNode; if (pCoder->data) { if (pCoder->size - pCoder->pos < sizeof(int32_t)) return -1; pNode = malloc(sizeof(*pNode)); if (pNode == NULL) return -1; pNode->data = pCoder->data; pNode->pos = pCoder->pos; pNode->size = pCoder->size; pCoder->data = pNode->data + sizeof(int32_t); pCoder->pos = 0; pCoder->size = pNode->size - pNode->pos - sizeof(int32_t); TD_SLIST_PUSH(&(pCoder->stack), pNode); } else { pCoder->pos += sizeof(int32_t); } return 0; } void tEndEncode(SCoder* pCoder) { struct SCoderNode* pNode; if (pCoder->data) { pNode = TD_SLIST_HEAD(&(pCoder->stack)); ASSERT(pNode); TD_SLIST_POP(&(pCoder->stack)); // TODO: tEncodeI32(pNode, pCoder->pos); pCoder->data = pNode->data; pCoder->size = pNode->size; pCoder->pos = pNode->pos + pCoder->pos; free(pNode); } } int tStartDecode(SCoder* pCoder) { int32_t size; struct SCoderNode* pNode; // TODO: if (tDecodeI32(pCoder, &size) < 0) return -1; pNode = malloc(sizeof(*pNode)); if (pNode == NULL) return -1; pNode->data = pCoder->data; pNode->pos = pCoder->pos; pNode->size = pCoder->size; pCoder->data = pCoder->data; pCoder->size = size; pCoder->pos = 0; TD_SLIST_PUSH(&(pCoder->stack), pNode); return 0; } void tEndDecode(SCoder* pCoder) { ASSERT(tDecodeIsEnd(pCoder)); struct SCoderNode* pNode; pNode = TD_SLIST_HEAD(&(pCoder->stack)); ASSERT(pNode); TD_SLIST_POP(&(pCoder->stack)); pCoder->data = pNode->data; pCoder->size = pNode->size; pCoder->pos = pCoder->pos + pNode->pos; free(pNode); }