X-Git-Url: https://git.llucax.com/z.facultad/75.06/jacu.git/blobdiff_plain/d69c7c58de649932f607cbfb6e7f44a1364078f5..64d649ff0b05d95cdd40ee1a59fff0ba2100bc52:/src/zerogrouping/zerogrouping.c?ds=sidebyside diff --git a/src/zerogrouping/zerogrouping.c b/src/zerogrouping/zerogrouping.c index b7e8c2c..569b9ad 100644 --- a/src/zerogrouping/zerogrouping.c +++ b/src/zerogrouping/zerogrouping.c @@ -22,7 +22,7 @@ * Autores: Leandro Lucarella *---------------------------------------------------------------------------- * - * $Id: vfile.c 748 2004-06-21 00:46:08Z llucare $ + * $Id$ * */ @@ -36,51 +36,97 @@ * */ +void zg_init(ZG* zg) +{ + zg->in_zero = 0; +} + /** FIXME - * El dst se asume que tiene reservada al menos ceil(size/2.0)+size bytes de - * memoria por si se llegara a expandir. size es el tamaño a leer de src. Se + * El dst se asume que tiene al menos 2 bytes reservados para escribir, + * por si se llegara a expandir. src es el caracter a encodear. Se * devuelve la cantidad de bytes escritos en dst. */ -size_t zg_group(char* dst, char *src, size_t size) +size_t zg_group(ZG* zg, unsigned char *dst, unsigned char src) { - char count; - size_t i; - size_t total = 0; - int in_zero = 0; - for (i = 0; i < size; ++i) + if (src == 0) { - if (src[i] == '\0') + if (zg->in_zero) { - if (in_zero) + if (++(zg->count) == 255u) /* si es 255, salgo de serie de ceros */ { - ++count; /* FIXME verificar que no pase 255 */ - } - else - { - in_zero = 1; /* entramos en serie de ceros */ - count = 0; /* reiniciamos contador de ceros */ + zg->in_zero = 0; /* salgo de serie de ceros */ + *dst = zg->count; /* devuelvo cantidad de ceros */ + return 1; /* indico que hay un caracter */ } + return 0; /* indico que no hay nada */ } else { - if (in_zero) - { - in_zero = 0; - dst[total++] = '\0'; - dst[total++] = count; - } - dst[total++] = src[i]; + zg->in_zero = 1; /* entramos en serie de ceros */ + zg->count = 0; /* reiniciamos contador de ceros */ + *dst = 0; /* devuelvo el cero */ + return 1; /* indico que hay un caracter */ } } - if (in_zero) /* si estaba en una serie de ceros, terminamos de escribir. */ + else /* no es un cero */ + { + size_t ret = 1; + if (zg->in_zero) + { + zg->in_zero = 0; /* salgo de serie de ceros */ + *dst = zg->count; /* devuelvo cantidad de ceros */ + dst++; /* me muevo al siguiente caracter */ + ret++; /* indico que hay un caracter más */ + } + *dst = src; /* devuelvo el caracter */ + return ret; /* indico la cantidad de caracteres devueltos */ + } +} + +/** A lo sumo puede devolver un unsigned char */ +size_t zg_group_finish(ZG* zg, unsigned char *dst) +{ + if (zg->in_zero) /* sólo me interesa si estaba en una serie de ceros */ { - dst[total++] = '\0'; - dst[total++] = count; + zg->in_zero = 0; /* salgo de serie de ceros */ + *dst = zg->count; /* devuelvo cantidad de ceros */ + return 1; /* indico que hay un caracter */ } - return total; + return 0; /* no había nada */ } -size_t zg_ungroup(char* dst, char *src, size_t size) +/** FIXME + * dst debe tener reservado al menos 256 bytes, src es el caracter a desencodear + * y se devuelven la cantidad de bytes desencodeados en dst. */ +size_t zg_ungroup(ZG* zg, unsigned char *dst, unsigned char src) { - return 0; + if (src == 0) + { + if (zg->in_zero) /* eran 2 ceros seguidos (1 cero orig. expandido) */ + { + zg->in_zero = 0; /* saldo de serie de ceros */ + return 0; /* indico que no hay nada */ + } + else /* empieza serie de ceros */ + { + zg->in_zero = 1; /* entramos en serie de ceros */ + *dst = 0; /* devuelvo el cero */ + return 1; /* indico que hay un caracter */ + } + } + else /* no es un cero */ + { + if (zg->in_zero) /* era una serie de ceros comprimida */ + { + unsigned char ret = src; + zg->in_zero = 0; /* salgo de serie de ceros */ + while (src--) dst[(size_t)src] = 0; /* devuelve src cantidad de ceros */ + return ret; /* indica que se devolvieron src cantidad de ceros */ + } + else + { + *dst = src; /* devuelvo el caracter */ + return 1; /* indico que se devolvió un caracter */ + } + } }