#include "netbytes.h" int nb_u8_create( nb_u8 *s, uint8_t val ) { if ( s == NULL ) return -1; s->type = NBT_U8; s->val = val; return 0; } int nb_u8arr_create( nb_u8arr *s, __NBT_U8ARR_LEN len, uint8_t *val ) { if ( s == NULL ) return -1; s->type = NBT_U8ARRAY; s->len = len; s->val = val; return 0; } int nb_u16_create( nb_u16 *s, uint16_t val ) { if ( s == NULL ) return -1; s->type = NBT_U16; s->val = val; return 0; } int nb_u16arr_create( nb_u16arr *s, __NBT_U16ARR_LEN len, uint16_t *val ) { if ( s == NULL ) return -1; s->type = NBT_U16ARRAY; s->len = len; s->val = val; return 0; } int nb_u32_create( nb_u32 *s, uint32_t val ) { if ( s == NULL ) return -1; s->type = NBT_U32; s->val = val; return 0; } int nb_u32arr_create( nb_u32arr *s, __NBT_U32ARR_LEN len, uint32_t *val ) { if ( s == NULL ) return -1; s->type = NBT_U32ARRAY; s->len = len; s->val = val; return 0; } int nb_u64_create( nb_u64 *s, uint64_t val ) { if ( s == NULL ) return -1; s->type = NBT_U64; s->val = val; return 0; } int nb_u64arr_create( nb_u64arr *s, __NBT_U64ARR_LEN len, uint64_t *val ) { if ( s == NULL ) return -1; s->type = NBT_U64ARRAY; s->len = len; s->val = val; return 0; } int nb_init( netbyte_store *store ) { if ( store == NULL ) return -1; memset( store, 0, sizeof(netbyte_store) ); /* we know that they allready zero, but philosophy more important */ store->size = 0; store->count = 0; return 0; } int nb_add_u8( netbyte_store *store, nb_u8 *u8 ) { nb_u8 *new_u8=NULL; if ( store->count >= __NBT_MAX_TYPES - 1 ) { return -1; } if ( u8->type != NBT_U8 ) { return -2; } store->types[store->count].type = NBT_U8; new_u8 = malloc(sizeof(nb_u8)); memcpy(new_u8, u8, sizeof(nb_u8)); store->types[store->count].nb_val = (uint8_t *)new_u8; store->count += 1; return 0; } int nb_add_u8arr( netbyte_store *store, nb_u8arr *u8arr ) { nb_u8arr *new_u8arr = NULL; if ( store->count >= __NBT_MAX_TYPES - 1 ) return -1; if ( u8arr->type != NBT_U8ARRAY ) return -2; store->types[store->count].type = NBT_U8ARRAY; new_u8arr = malloc(sizeof(nb_u8arr)); memcpy(new_u8arr, u8arr, sizeof(nb_u8arr)); new_u8arr->val = malloc(sizeof(nb_u8arr)*u8arr->len); memcpy(new_u8arr->val, u8arr->val, u8arr->len); store->types[store->count].nb_val = (uint8_t *)new_u8arr; store->count += 1; return 0; } int nb_add_u16( netbyte_store *store, nb_u16 *u16 ) { nb_u16 *new_u16 = NULL; if ( store->count >= __NBT_MAX_TYPES - 1 ) return -1; if ( u16->type != NBT_U16 ) return -2; store->types[store->count].type = NBT_U16; new_u16 = malloc(sizeof(nb_u16)); memcpy(new_u16, u16, sizeof(nb_u16)); store->types[store->count].nb_val = (uint8_t *)new_u16; store->count += 1; return 0; } int nb_add_u16arr( netbyte_store *store, nb_u16arr *u16arr ) { if ( store->count >= __NBT_MAX_TYPES - 1 ) return -1; if ( u16arr->type != NBT_U16ARRAY ) return -2; store->types[store->count].type = NBT_U16ARRAY; store->types[store->count].nb_val = (uint8_t *)u16arr; store->count += 1; return 0; } int nb_add_u32( netbyte_store *store, nb_u32 *u32 ) { nb_u32 *new_u32 = NULL; if ( store->count >= __NBT_MAX_TYPES - 1 ) return -1; if ( u32->type != NBT_U32 ) return -2; store->types[store->count].type = NBT_U32; new_u32 = malloc(sizeof(nb_u32)); memcpy(new_u32, u32, sizeof(nb_u32)); store->types[store->count].nb_val = (uint8_t *)new_u32; store->count += 1; return 0; } int nb_add_u32arr( netbyte_store *store, nb_u32arr *u32arr ) { if ( store->count >= __NBT_MAX_TYPES - 1 ) return -1; if ( u32arr->type != NBT_U32ARRAY ) return -2; store->types[store->count].type = NBT_U32ARRAY; store->types[store->count].nb_val = (uint8_t *)u32arr; store->count += 1; return 0; } int nb_add_u64( netbyte_store *store, nb_u64 *u64 ) { nb_u64 *new_u64 = NULL; if ( store->count >= __NBT_MAX_TYPES - 1 ) return -1; if ( u64->type != NBT_U64 ) return -2; store->types[store->count].type = NBT_U64; new_u64 = malloc(sizeof(nb_u64)); memcpy(new_u64, u64, sizeof(nb_u64)); store->types[store->count].nb_val = (uint8_t *)new_u64; store->count += 1; return 0; } int nb_add_u64arr( netbyte_store *store, nb_u64arr *u64arr ) { if ( store->count >= __NBT_MAX_TYPES - 1 ) return -1; if ( u64arr->type != NBT_U64ARRAY ) return -2; store->types[store->count].type = NBT_U64ARRAY; store->types[store->count].nb_val = (uint8_t *)u64arr; store->count += 1; return 0; } uint8_t *nb_create( netbyte_store *store ) { uint8_t *ret = NULL; uint8_t *buf = NULL; uint8_t *c = NULL; int i; if ( store == NULL ) return NULL; if ( store->count < 1 ) return NULL; store->size = 0; /* precalc needed size starting from zero not metter what */ store->size += sizeof(__NBT_SIZE); for (i=0; i < store->count; i++) { __nb_type iter = store->types[i]; switch( iter.type ) { case NBT_U8: store->size += sizeof(__NBT_TYPED) + sizeof(uint8_t); break; case NBT_U8ARRAY: { nb_u8arr *u8arr = (nb_u8arr *)iter.nb_val; store->size += sizeof(__NBT_TYPED) + sizeof(__NBT_U8ARR_LEN) + u8arr->len; } break; case NBT_U16: store->size += sizeof(__NBT_TYPED) + sizeof(uint16_t); break; case NBT_U16ARRAY: { nb_u16arr *u16arr = (nb_u16arr *)iter.nb_val; store->size += sizeof(__NBT_TYPED) + sizeof(__NBT_U16ARR_LEN) + u16arr->len*sizeof(uint16_t); } break; case NBT_U32: store->size += sizeof(__NBT_TYPED) + sizeof(uint32_t); break; case NBT_U32ARRAY: { nb_u32arr *u32arr = (nb_u32arr *)iter.nb_val; store->size += sizeof(__NBT_TYPED) + sizeof(__NBT_U32ARR_LEN) + u32arr->len*sizeof(uint32_t); } break; case NBT_U64: store->size += sizeof(__NBT_TYPED) + sizeof(uint64_t); break; case NBT_U64ARRAY: { nb_u64arr *u64arr = (nb_u64arr *)iter.nb_val; store->size += sizeof(__NBT_TYPED) + sizeof(__NBT_U64ARR_LEN) + u64arr->len*sizeof(uint64_t); } break; default: printf("Unknow type be carefull1\n"); } } /* create netbyte memory chunk */ buf = malloc( store->size ); if ( buf == NULL ) { return NULL; } c = buf; /* write size of netbytes */ memcpy( c, &store->size, sizeof(__NBT_SIZE) ); c += sizeof(__NBT_SIZE); /* per each type copy stuff */ for ( i = 0; i < store->count; i++ ) { __nb_type iter = store->types[i]; switch ( iter.type ) { case NBT_U8: memcpy( c, &iter.type, sizeof(__NBT_TYPED) ); c += sizeof(__NBT_TYPED); memcpy( c, &((nb_u8 *)(iter.nb_val))->val, sizeof(uint8_t) ); c += sizeof(uint8_t); break; case NBT_U8ARRAY: { nb_u8arr *u8arr = (nb_u8arr *)iter.nb_val; memcpy( c, &iter.type, sizeof(__NBT_TYPED) ); c += sizeof(__NBT_TYPED); memcpy( c, &u8arr->len, sizeof(__NBT_U8ARR_LEN)); c += sizeof(__NBT_U8ARR_LEN); memcpy( c, u8arr->val, u8arr->len ); c += u8arr->len; break; } case NBT_U16: memcpy( c, &iter.type, sizeof(__NBT_TYPED) ); c += sizeof(__NBT_TYPED); memcpy( c, &((nb_u16 *)(iter.nb_val))->val, sizeof(uint16_t) ); c += sizeof(uint16_t); break; case NBT_U16ARRAY: { nb_u16arr *u16arr = (nb_u16arr *)iter.nb_val; memcpy( c, &iter.type, sizeof(__NBT_TYPED) ); c += sizeof(__NBT_TYPED); memcpy( c, &u16arr->len, sizeof(__NBT_U16ARR_LEN)); c += sizeof(__NBT_U16ARR_LEN); memcpy( c, u16arr->val, u16arr->len ); c += u16arr->len*sizeof(uint16_t); break; } case NBT_U32: memcpy( c, &iter.type, sizeof(__NBT_TYPED) ); c += sizeof(__NBT_TYPED); memcpy( c, &((nb_u32 *)(iter.nb_val))->val, sizeof(uint32_t) ); c += sizeof(uint32_t); break; case NBT_U32ARRAY: { nb_u32arr *u32arr = (nb_u32arr *)iter.nb_val; memcpy( c, &iter.type, sizeof(__NBT_TYPED) ); c += sizeof(__NBT_TYPED); memcpy( c, &u32arr->len, sizeof(__NBT_U32ARR_LEN)); c += sizeof(__NBT_U32ARR_LEN); memcpy( c, u32arr->val, u32arr->len ); c += u32arr->len*sizeof(uint32_t); break; } case NBT_U64: memcpy( c, &iter.type, sizeof(__NBT_TYPED) ); c += sizeof(__NBT_TYPED); memcpy( c, &((nb_u64 *)(iter.nb_val))->val, sizeof(uint64_t) ); c += sizeof(uint64_t); break; case NBT_U64ARRAY: { nb_u64arr *u64arr = (nb_u64arr *)iter.nb_val; memcpy( c, &iter.type, sizeof(__NBT_TYPED) ); c += sizeof(__NBT_TYPED); memcpy( c, &u64arr->len, sizeof(__NBT_U64ARR_LEN)); c += sizeof(__NBT_U64ARR_LEN); memcpy( c, u64arr->val, u64arr->len ); c += u64arr->len*sizeof(uint64_t); break; } default: printf("Unknow type be carefull2\n"); } } if ( c-buf-1 > store->size ) { printf("Something went wrong while created netbytes\n"); free(buf); return NULL; } ret = buf; return ret; } int nb_free(netbyte_store *store) { int i; if (!store) { return -1; } for (i=0;icount;i++) { __NBT_TYPED type = store->types[i].type; uint8_t *val = store->types[i].nb_val; switch(type) { case NBT_U8: { nb_u8 *u8 = (nb_u8 *)val; free(u8); u8=NULL; store->types[i].nb_val=NULL; store->types[i].type=0; break; } case NBT_U8ARRAY: { nb_u8arr *u8arr = (nb_u8arr *)val; free(u8arr->val); free(u8arr); store->types[i].nb_val=NULL; store->types[i].type=0; break; } case NBT_U32: { //nb_u32 *u32 = (nb_u32 *)val; //free(u32); //u32 = NULL; store->types[i].nb_val=NULL; store->types[i].type=0; break; } default: printf("Unknown type\n"); } } free(store); store = NULL; return 0; } int nb_load( netbyte_store *store, uint8_t *data ) { __NBT_TYPED type; int iter=1; uint8_t *c = data; //int count; if ( store == NULL ) { return -1; } if ( data == NULL ) { return -2; } __NBT_SIZE size; memcpy( &size, c, sizeof(__NBT_SIZE) ); printf("NB_LOAD size: %d\n", size); size -= sizeof(__NBT_SIZE); c += sizeof(__NBT_SIZE); if (c == data) { store->size = size; return 0; } //count = 0; memset( store, 0, sizeof(netbyte_store) ); while ( iter ) { type = (__NBT_TYPED)c[0]; switch( type ) { case NBT_U8: { nb_u8 u8; memcpy( &u8, c, sizeof(nb_u8) ); c += sizeof(nb_u8); nb_add_u8( store, &u8 ); break; } case NBT_U8ARRAY: { nb_u8arr *u8arr = malloc( sizeof(nb_u8arr) ); memcpy( u8arr, c, sizeof(__NBT_TYPED)); c += sizeof(__NBT_TYPED); memcpy( &u8arr->len, c, sizeof(__NBT_U8ARR_LEN) ); c += sizeof(__NBT_U8ARR_LEN); u8arr->val = c; //printf("->2 %s\n",c ); c += u8arr->len; nb_add_u8arr( store, u8arr ); free(u8arr); break; } case NBT_U16: { nb_u16 u16; memcpy( &u16, c, sizeof(nb_u16) ); c += sizeof(nb_u16); nb_add_u16( store, &u16 ); break; } case NBT_U16ARRAY: { nb_u16arr *u16arr = malloc( sizeof(nb_u16arr) ); memcpy( u16arr, c, sizeof(__NBT_TYPED)); c += sizeof(__NBT_TYPED); memcpy( &u16arr->len, c, sizeof(__NBT_U16ARR_LEN) ); c += sizeof(__NBT_U16ARR_LEN); u16arr->val = (uint16_t *)c; //printf("->2 %s\n",c ); c += u16arr->len*sizeof(uint16_t); nb_add_u16arr( store, u16arr ); break; } case NBT_U32: { nb_u32 u32; memcpy( &u32, c, sizeof(nb_u32) ); c += sizeof(nb_u32); nb_add_u32( store, &u32 ); break; } case NBT_U32ARRAY: { nb_u32arr *u32arr = malloc( sizeof(nb_u32arr) ); memcpy( u32arr, c, sizeof(__NBT_TYPED)); c += sizeof(__NBT_TYPED); memcpy( &u32arr->len, c, sizeof(__NBT_U32ARR_LEN) ); c += sizeof(__NBT_U32ARR_LEN); u32arr->val = (uint32_t *)c; //printf("->2 %s\n",c ); c += u32arr->len*sizeof(uint32_t); nb_add_u32arr( store, u32arr ); break; } case NBT_U64: { nb_u64 u64; memcpy( &u64, c, sizeof(nb_u64) ); c += sizeof(nb_u64); nb_add_u64( store, &u64 ); break; } case NBT_U64ARRAY: { nb_u64arr *u64arr = malloc( sizeof(nb_u64arr) ); memcpy( u64arr, c, sizeof(__NBT_TYPED)); c += sizeof(__NBT_TYPED); memcpy( &u64arr->len, c, sizeof(__NBT_U64ARR_LEN) ); c += sizeof(__NBT_U64ARR_LEN); u64arr->val = (uint64_t *)c; //printf("->2 %s\n",c ); c += u64arr->len; nb_add_u64arr( store, u64arr ); break; } default: printf("Unknown type\n"); //FIX non freed structures, if this happends in middle of transfer return -1; } if ( c >= data + size ) { iter = 0; } } return 0; } int nb_count( netbyte_store *store ) { if ( store == NULL ) { return -1; } return store->count; } int nb_type( netbyte_store *store, int count, __NBT_TYPED **type ) { //__NBT_TYPED nbt; if ( store == NULL ) { return -1; } if ( store->count < count ) { return -2; } //nbt = (__NBT_TYPED)store->types[count].type; //warnign? who cares //*type = nbt; #warning "Looks like real error" *type = store->types[count].type; return 0; } int nb_val( netbyte_store *store, int count, __nb_type **type ) { if (!store) { return -1; } if ((count < 0)||(count > store->count)) { return -1; } *type = &store->types[count]; return 0; } int nb_fread( netbyte_store *store, int fd) { __NBT_SIZE size; //ssize_t ret; off_t old_seek; uint8_t *nb; if ( store == NULL ) { return -1; } if ( fd < 1 ) { return -2; } nb_init( store ); old_seek = lseek( fd, 0, SEEK_CUR); if ( read( fd, &size, sizeof(__NBT_SIZE) ) != sizeof(__NBT_SIZE) ) { printf("Couldn read netbyte size\n"); return -3; } if ( lseek( fd, old_seek, SEEK_SET ) == -1 ) { return -4; } //different endianess can blow this up muahaha nb = malloc( size ); if ( read( fd, nb, size ) != size ) { return -5; } if ( nb_load( store, nb ) != 0 ) { printf("Cannot read nebyte from file\n"); return -6; } free(nb); nb=NULL; return 0; } /* Return: 1 - looks like data are netbyte buffer 0 - data isnot netbyte buffer */ int nb_check_buf(uint8_t *data, int len, int *detected_size) { __NBT_SIZE size; if (len < sizeof(__NBT_SIZE)) { printf("if (len > sizeof(__NBT_SIZE))\n"); return 0; } memcpy(&size, data, sizeof(__NBT_SIZE)); if (lensize, store->count); for (i=0;icount;i++) { printf("\t[%x] -> ", i); switch (store->types[i].type) { case NBT_U8: { nb_u8 *u8 = (nb_u8 *)store->types[i].nb_val; printf("u8: t=0x%x v=0x%x", u8->type, u8->val); break; } case NBT_U8ARRAY: { nb_u8arr *u8arr = (nb_u8arr *)store->types[i].nb_val; printf("u8arr: t=0x%x l=0x%x v=0x%x", u8arr->type, u8arr->len, u8arr->val); break; } case NBT_U32: { nb_u32 *u32 = (nb_u32 *)store->types[i].nb_val; printf("u32: t=0x%x v=0x%x", u32->type, u32->val); break; } default: printf("Unknown"); } printf("\n"); } return 0; } int nb_match(netbyte_store *store, nb_tok_arr *pattern) { int i; int ret = 0; if (store == NULL) { return -1; } if (pattern == NULL) { return -1; } if (store->count != pattern->len) { return 1; } printf("pat->len%d\n",pattern->len); for (i=0;i < pattern->len;i++) { printf("[%d]\n",i); __NBT_TYPED type = store->types[i].type; //void *val = store->types[i].nb_val; nb_tok pat_tok = pattern->tok[i]; int eq = 0; switch (type) { case NBT_U8: { printf("NBT_U8\n"); //nb_u8 *u8 = (nb_u8 *)val; if ((pat_tok.type_size == 8)&& (pat_tok.sign == SIGN_UNSIGNED)&& (pat_tok.arr == 0)) { eq = 1; } break; } //if array 0 then its same as [] == [0]! case NBT_U8ARRAY: { printf("NBT_U8ARRAY\n"); //nb_u8arr *u8arr = (nb_u8arr *)val; if ((pat_tok.type_size == 8)&& (pat_tok.sign == SIGN_UNSIGNED)&& (pat_tok.arr == 1)) //&& //(u8arr->len == pat_tok.len)) //could be bug with []/[0] { eq = 1; } break; } case NBT_I32: { printf("NBT_I32\n"); if ((pat_tok.type_size == 32)&& (pat_tok.sign == SIGN_SIGNED)) { eq = 1; } break; } default: printf(">>nb_match ERROR<<\n"); } if (eq==0) { ret = 1; break; } } return ret; } nb_tok_arr *nb_tok_create(int size) { nb_tok_arr *ret=NULL; ret = malloc(sizeof(nb_tok_arr)); memset(ret,0,sizeof(nb_tok_arr)); ret->tok = malloc(sizeof(nb_tok)*size); memset(ret->tok, 0, sizeof(nb_tok)*size); ret->size = size; ret->len = 0; return ret; } int nb_tok_add(nb_tok_arr *arr, int sign, int type_size, int len, int farr) { if (arr==NULL) { return -1; } if (arr->len >= arr->size-1) { return -1; } arr->tok[arr->len].sign = sign; arr->tok[arr->len].type_size = type_size; arr->tok[arr->len].len = len; arr->tok[arr->len].arr = farr; arr->len += 1; return 0; } void nb_tok_destroy(nb_tok_arr *arr) { if (arr == NULL) { return; } if (arr->tok) { free(arr->tok); arr->tok = NULL; } free(arr); arr = NULL; } #define S_START 1 #define S_SIGN 2 #define S_SIZE 3 #define S_NUMBER 4 #define S_COMM 5 #define S_ERR 6 #define S_LBREAK 7 #define S_RBREAK 8 #define S_ARRSIZE 9 #define S_END 10 #define S_STARTE 11 #define NB_MATCH(CH) ((*c)==(CH)) #define NB_MATCHDIG() (isdigit(*c)) #define NB_MOVE() (c++); int nb_parse_num(char *s, char *e) { const int num_sz = 17; int str_sz=-1; char num[num_sz]; memset(num, 0, num_sz); str_sz = e-s; if (str_sz>num_sz-1) { printf("ERROR\n"); return -1; } memcpy(num,s,str_sz); return atoi(num); } int nb_parse(char *str, nb_tok_arr *arr) { int cnt=0; nb_tok tok; int state = S_START; char *c; c = str; char *st=NULL,*en=NULL; int ret = 0; memset(&tok, 0, sizeof(tok)); printf("\"%s\"\n",str); while (*c!=0) { printf("[%c] ",*c); switch (state) { case S_START: { printf("START\n"); if (NB_MATCH('u')) { printf("!1\n"); tok.sign = SIGN_UNSIGNED; state = S_SIGN; } else if (NB_MATCH('i')) { printf("!2\n"); tok.sign = SIGN_SIGNED; state = S_SIGN; } else { printf("!3\n"); state = S_ERR; } printf("!\n"); break; } case S_STARTE: { printf("STARTE\n"); printf("S:%d TS:%d L:%d A:%d\n", tok.sign, tok.type_size, tok.len, tok.arr ); nb_tok_add(arr, tok.sign, tok.type_size, tok.len, tok.arr); memset(&tok,0,sizeof(nb_tok)); state = S_START; break; } case S_SIGN: { printf("SIGN\n"); if (NB_MATCH('i')) { state = S_SIZE; NB_MOVE(); } else if (NB_MATCH('u')) { state = S_SIZE; NB_MOVE(); } else { state = S_ERR; } break; } case S_SIZE: { printf("SIZE\n"); if (NB_MATCHDIG()) { if (st==NULL) st=c; NB_MOVE(); } else if (NB_MATCH(',')) { en=c; tok.type_size = nb_parse_num(st,en); en=NULL; st=NULL; state = S_STARTE; NB_MOVE(); } else if (NB_MATCH('[')) { en=c; tok.type_size = nb_parse_num(st,en); en=NULL; st=NULL; state = S_LBREAK; NB_MOVE(); } else if (NB_MATCH(' ')) { en=c; tok.type_size = nb_parse_num(st,en); en=NULL; st=NULL; state = S_END; } else { state = S_ERR; } break; } case S_NUMBER: { printf("NUMBER\n"); if (NB_MATCHDIG()) { if(st==NULL) st=c; NB_MOVE(); } else if (NB_MATCH(']')) { en=c; tok.type_size = nb_parse_num(st,en); tok.arr = 1; en=NULL; st=NULL; state = S_RBREAK; NB_MOVE(); } break; } case S_COMM: { printf("COMM\n"); state = S_STARTE; NB_MOVE(); break; } case S_ERR: { printf("ERR\n"); state = -1; break; } case S_LBREAK: { printf("LBREAK\n"); if (NB_MATCHDIG()) { state = S_NUMBER; } else if (NB_MATCH(']')) { state = S_RBREAK; tok.arr = 1; NB_MOVE(); } else { state = S_ERR; } break; } case S_RBREAK: { printf("RBREAK\n"); if (NB_MATCH(',')) { state = S_COMM; } else { state = S_END; } break; } case S_ARRSIZE: { printf("ARRSIZE\n"); break; } case S_END: { printf("END\n"); printf("S:%d TS:%d L:%d A:%d\n", tok.sign, tok.type_size, tok.len, tok.arr ); nb_tok_add(arr, tok.sign, tok.type_size, tok.len, tok.arr); memset(&tok,0,sizeof(nb_tok)); state = -1; break; } default: { printf("Unknown state\n"); } } cnt++; if (cnt>32) { printf("Loop\n"); break; } if (state == -1) { printf("state\n"); break; } } return ret; }