tbuffer.h 6.8 KB
Newer Older
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15
/*
 * Copyright (c) 2020 TAOS Data, Inc. <jhtao@taosdata.com>
 *
 * 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 <http://www.gnu.org/licenses/>.
 */

S
tbuffer  
Shengliang Guan 已提交
16 17
#ifndef _TD_UTIL_BUFFER_H_
#define _TD_UTIL_BUFFER_H_
18

H
more  
Hongze Cheng 已提交
19 20
#include "os.h"

21 22 23
#ifdef __cplusplus
extern "C" {
#endif
24

weixin_48148422's avatar
weixin_48148422 已提交
25 26 27 28
////////////////////////////////////////////////////////////////////////////////
// usage example
/*
#include <stdio.h>
S
Shengliang Guan 已提交
29
#include "texception.h"
weixin_48148422's avatar
weixin_48148422 已提交
30

S
Shengliang Guan 已提交
31
int32_t main( int32_t argc, char** argv ) {
weixin_48148422's avatar
weixin_48148422 已提交
32 33 34 35 36 37 38 39 40 41
  SBufferWriter bw = tbufInitWriter( NULL, false );

  TRY( 1 ) {
    //--------------------- write ------------------------
    // reserve 1024 bytes for the buffer to improve performance
    tbufEnsureCapacity( &bw, 1024 );

    // reserve space for the interger count
    size_t pos = tbufReserve( &bw, sizeof(int32_t) );
    // write 5 integers to the buffer
S
Shengliang Guan 已提交
42
    for( int32_t i = 0; i < 5; i++) {
weixin_48148422's avatar
weixin_48148422 已提交
43 44 45 46 47 48 49 50 51 52 53 54 55 56 57
      tbufWriteInt32( &bw, i );
    }
    // write the integer count to buffer at reserved position
    tbufWriteInt32At( &bw, pos, 5 );

    // write a string to the buffer
    tbufWriteString( &bw, "this is a string.\n" );
    // acquire the result and close the write buffer
    size_t size = tbufTell( &bw );
    char*  data = tbufGetData( &bw, false );

    //------------------------ read -----------------------
    SBufferReader br = tbufInitReader( data, size, false );
    // read & print out all integers
    int32_t count = tbufReadInt32( &br );
S
Shengliang Guan 已提交
58
    for( int32_t i = 0; i < count; i++ ) {
weixin_48148422's avatar
weixin_48148422 已提交
59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74
      printf( "%d\n", tbufReadInt32(&br) );
    }
    // read & print out a string
    puts( tbufReadString(&br, NULL) );
    // try read another integer, this result in an error as there no this integer
    tbufReadInt32( &br );
    printf( "you should not see this message.\n" );
  } CATCH( code ) {
    printf( "exception code is: %d, you will see this message after print out 5 integers and a string.\n", code );
  } END_TRY

  tbufCloseWriter( &bw );
  return 0;
}
*/

H
Haojun Liao 已提交
75
typedef struct SBufferReader {
H
refact  
Hongze Cheng 已提交
76
  bool        endian;
77
  const char* data;
H
refact  
Hongze Cheng 已提交
78 79
  size_t      pos;
  size_t      size;
80
} SBufferReader;
weixin_48148422's avatar
weixin_48148422 已提交
81

H
Haojun Liao 已提交
82
typedef struct SBufferWriter {
H
refact  
Hongze Cheng 已提交
83 84
  bool   endian;
  char*  data;
85 86
  size_t pos;
  size_t size;
H
refact  
Hongze Cheng 已提交
87
  void* (*allocator)(void*, size_t);
88 89 90
} SBufferWriter;

// common functions & macros for both reader & writer
91

H
refact  
Hongze Cheng 已提交
92
#define tbufTell(buf) ((buf)->pos)
93

H
refact  
Hongze Cheng 已提交
94
/* ------------------------ BUFFER WRITER FUNCTIONS AND MACROS ------------------------ */
95 96
// *Allocator*, function to allocate memory, will use 'realloc' if NULL
// *Endian*, if true, writer functions of primitive types will do 'hton' automatically
H
refact  
Hongze Cheng 已提交
97 98 99
#define tbufInitWriter(Allocator, Endian) \
  { .endian = (Endian), .data = NULL, .pos = 0, .size = 0, .allocator = ((Allocator) == NULL ? realloc : (Allocator)) }

H
refact  
Hongze Cheng 已提交
100
void   tbufCloseWriter(SBufferWriter* buf);
H
refact  
Hongze Cheng 已提交
101 102 103
void   tbufEnsureCapacity(SBufferWriter* buf, size_t size);
size_t tbufReserve(SBufferWriter* buf, size_t size);
char*  tbufGetData(SBufferWriter* buf, bool takeOver);
H
refact  
Hongze Cheng 已提交
104 105 106 107
void   tbufWrite(SBufferWriter* buf, const void* data, size_t size);
void   tbufWriteAt(SBufferWriter* buf, size_t pos, const void* data, size_t size);
void   tbufWriteStringLen(SBufferWriter* buf, const char* str, size_t len);
void   tbufWriteString(SBufferWriter* buf, const char* str);
108 109
// the prototype of tbufWriteBinary and tbufWrite are identical
// the difference is: tbufWriteBinary writes the length of the data to the buffer
weixin_48148422's avatar
weixin_48148422 已提交
110 111 112
// first, then the actual data, which means the reader don't need to know data
// size before read. Write only write the data itself, which means the reader
// need to know data size before read.
H
refact  
Hongze Cheng 已提交
113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137
void tbufWriteBinary(SBufferWriter* buf, const void* data, size_t len);
void tbufWriteBool(SBufferWriter* buf, bool data);
void tbufWriteBoolAt(SBufferWriter* buf, size_t pos, bool data);
void tbufWriteChar(SBufferWriter* buf, char data);
void tbufWriteCharAt(SBufferWriter* buf, size_t pos, char data);
void tbufWriteInt8(SBufferWriter* buf, int8_t data);
void tbufWriteInt8At(SBufferWriter* buf, size_t pos, int8_t data);
void tbufWriteUint8(SBufferWriter* buf, uint8_t data);
void tbufWriteUint8At(SBufferWriter* buf, size_t pos, uint8_t data);
void tbufWriteInt16(SBufferWriter* buf, int16_t data);
void tbufWriteInt16At(SBufferWriter* buf, size_t pos, int16_t data);
void tbufWriteUint16(SBufferWriter* buf, uint16_t data);
void tbufWriteUint16At(SBufferWriter* buf, size_t pos, uint16_t data);
void tbufWriteInt32(SBufferWriter* buf, int32_t data);
void tbufWriteInt32At(SBufferWriter* buf, size_t pos, int32_t data);
void tbufWriteUint32(SBufferWriter* buf, uint32_t data);
void tbufWriteUint32At(SBufferWriter* buf, size_t pos, uint32_t data);
void tbufWriteInt64(SBufferWriter* buf, int64_t data);
void tbufWriteInt64At(SBufferWriter* buf, size_t pos, int64_t data);
void tbufWriteUint64(SBufferWriter* buf, uint64_t data);
void tbufWriteUint64At(SBufferWriter* buf, size_t pos, uint64_t data);
void tbufWriteFloat(SBufferWriter* buf, float data);
void tbufWriteFloatAt(SBufferWriter* buf, size_t pos, float data);
void tbufWriteDouble(SBufferWriter* buf, double data);
void tbufWriteDoubleAt(SBufferWriter* buf, size_t pos, double data);
138

H
refact  
Hongze Cheng 已提交
139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163
/* ------------------------ BUFFER READER FUNCTIONS AND MACROS ------------------------ */
// *Endian*, if true, reader functions of primitive types will do 'ntoh' automatically
#define tbufInitReader(Data, Size, Endian) \
  { .endian = (Endian), .data = (Data), .pos = 0, .size = ((Data) == NULL ? 0 : (Size)) }

size_t      tbufSkip(SBufferReader* buf, size_t size);
const char* tbufRead(SBufferReader* buf, size_t size);
void        tbufReadToBuffer(SBufferReader* buf, void* dst, size_t size);
const char* tbufReadString(SBufferReader* buf, size_t* len);
size_t      tbufReadToString(SBufferReader* buf, char* dst, size_t size);
const char* tbufReadBinary(SBufferReader* buf, size_t* len);
size_t      tbufReadToBinary(SBufferReader* buf, void* dst, size_t size);
bool        tbufReadBool(SBufferReader* buf);
char        tbufReadChar(SBufferReader* buf);
int8_t      tbufReadInt8(SBufferReader* buf);
uint8_t     tbufReadUint8(SBufferReader* buf);
int16_t     tbufReadInt16(SBufferReader* buf);
uint16_t    tbufReadUint16(SBufferReader* buf);
int32_t     tbufReadInt32(SBufferReader* buf);
uint32_t    tbufReadUint32(SBufferReader* buf);
int64_t     tbufReadInt64(SBufferReader* buf);
uint64_t    tbufReadUint64(SBufferReader* buf);
float       tbufReadFloat(SBufferReader* buf);
double      tbufReadDouble(SBufferReader* buf);

164 165 166
#ifdef __cplusplus
}
#endif
167

S
tbuffer  
Shengliang Guan 已提交
168
#endif /*_TD_UTIL_BUFFER_H_*/