-/*
- * vim:ts=8:sw=3:sts=8:noexpandtab:cino=>5n-3f0^-2{2
- */
-
#ifdef HAVE_CONFIG_H
# include <config.h>
-#endif
-
-#if HAVE___ATTRIBUTE__
-#define __UNUSED__ __attribute__((unused))
-#else
-#define __UNUSED__
-#endif
+#endif /* ifdef HAVE_CONFIG_H */
#include <stdio.h>
#include <string.h>
#ifdef HAVE_NETINET_IN_H
# include <netinet/in.h>
-#endif
+#endif /* ifdef HAVE_NETINET_IN_H */
-#if defined(_WIN32) && ! defined(__CEGCC__)
+#ifdef _WIN32
# include <winsock2.h>
-#endif
+#endif /* ifdef _WIN32 */
#include <Eina.h>
/*---*/
-typedef struct _Eet_Data_Element Eet_Data_Element;
-typedef struct _Eet_Data_Basic_Type_Codec Eet_Data_Basic_Type_Codec;
-typedef struct _Eet_Data_Group_Type_Codec Eet_Data_Group_Type_Codec;
-typedef struct _Eet_Data_Chunk Eet_Data_Chunk;
-typedef struct _Eet_Data_Stream Eet_Data_Stream;
-typedef struct _Eet_Data_Descriptor_Hash Eet_Data_Descriptor_Hash;
-typedef struct _Eet_Data_Encode_Hash_Info Eet_Data_Encode_Hash_Info;
+typedef struct _Eet_Data_Element Eet_Data_Element;
+typedef struct _Eet_Data_Basic_Type_Codec Eet_Data_Basic_Type_Codec;
+typedef struct _Eet_Data_Group_Type_Codec Eet_Data_Group_Type_Codec;
+typedef struct _Eet_Data_Chunk Eet_Data_Chunk;
+typedef struct _Eet_Data_Stream Eet_Data_Stream;
+typedef struct _Eet_Data_Descriptor_Hash Eet_Data_Descriptor_Hash;
+typedef struct _Eet_Data_Encode_Hash_Info Eet_Data_Encode_Hash_Info;
+typedef struct _Eet_Free Eet_Free;
+typedef struct _Eet_Free_Context Eet_Free_Context;
+typedef struct _Eet_Variant_Unknow Eet_Variant_Unknow;
/*---*/
{
int size;
const char *name;
- int (*get) (const Eet_Dictionary *ed, const void *src, const void *src_end, void *dest);
- void *(*put) (Eet_Dictionary *ed, const void *src, int *size_ret);
+ int (*get)(const Eet_Dictionary *ed,
+ const void *src,
+ const void *src_end,
+ void *dest);
+ void * (*put)(Eet_Dictionary *ed, const void *src, int *size_ret);
};
struct _Eet_Data_Group_Type_Codec
{
- int (*get) (const Eet_Dictionary *ed, Eet_Data_Descriptor *edd, Eet_Data_Element *ede, Eet_Data_Chunk *echnk, int type, int group_type, void *data_in, int level, void (*dumpfunc) (void *data, const char *str), void *dumpdata, char **p, int *size);
- void (*put) (Eet_Dictionary *ed, Eet_Data_Descriptor *edd, Eet_Data_Element *ede, Eet_Data_Stream *ds, void *data_in);
+ int (*get)(Eet_Free_Context *context,
+ const Eet_Dictionary *ed,
+ Eet_Data_Descriptor *edd,
+ Eet_Data_Element *ede,
+ Eet_Data_Chunk *echnk,
+ int type,
+ int group_type,
+ void *data_in,
+ char **p,
+ int *size);
+ void (*put)(Eet_Dictionary *ed,
+ Eet_Data_Descriptor *edd,
+ Eet_Data_Element *ede,
+ Eet_Data_Stream *ds,
+ void *data_in);
};
struct _Eet_Data_Chunk
{
- char *name;
- int len;
- int size;
- int hash;
- void *data;
- unsigned char type;
- unsigned char group_type;
+ char *name;
+ int len;
+ int size;
+ int hash;
+ void *data;
+ unsigned char type;
+ unsigned char group_type;
};
struct _Eet_Data_Stream
const char *name;
const Eet_Dictionary *ed;
int size;
- struct {
- void *(*mem_alloc) (size_t size);
- void (*mem_free) (void *mem);
- char *(*str_alloc) (const char *str);
- char *(*str_direct_alloc) (const char *str);
- void (*str_free) (const char *str);
- void (*str_direct_free) (const char *str);
- void *(*list_next) (void *l);
- void *(*list_append) (void *l, void *d);
- void *(*list_data) (void *l);
- void *(*list_free) (void *l);
- void (*hash_foreach) (void *h, int (*func) (void *h, const char *k, void *dt, void *fdt), void *fdt);
- void *(*hash_add) (void *h, const char *k, void *d);
- void (*hash_free) (void *h);
+ struct
+ {
+ void * (*mem_alloc)(size_t size);
+ void (*mem_free)(void *mem);
+ char * (*str_alloc)(const char *str);
+ char * (*str_direct_alloc)(const char *str);
+ void (*str_free)(const char *str);
+ void (*str_direct_free)(const char *str);
+ void * (*list_next)(void *l);
+ void * (*list_append)(void *l, void *d);
+ void * (*list_data)(void *l);
+ void * (*list_free)(void *l);
+ void (*hash_foreach)(void *h,
+ int (*func)(void *h,
+ const char *k,
+ void *dt,
+ void *fdt),
+ void *fdt);
+ void * (*hash_add)(void *h, const char *k, void *d);
+ void (*hash_free)(void *h);
+ const char *(*type_get)(const void *data, Eina_Bool *unknow);
+ Eina_Bool (*type_set)(const char *type,
+ void *data,
+ Eina_Bool unknow);
+ void * (*array_alloc)(size_t size);
+ void (*array_free)(void *mem);
} func;
- struct {
- int num;
- Eet_Data_Element *set;
- struct {
- int size;
- Eet_Data_Descriptor_Hash *buckets;
+ struct
+ {
+ int num;
+ Eet_Data_Element *set;
+ struct
+ {
+ int size;
+ Eet_Data_Descriptor_Hash *buckets;
} hash;
} elements;
+
+ Eina_Bool unified_type : 1;
// char *strings;
// int strings_len;
};
const char *counter_name;
const char *directory_name_ptr;
Eet_Data_Descriptor *subtype;
- int offset; /* offset in bytes from the base element */
- int count; /* number of elements for a fixed array */
- int counter_offset; /* for a variable array we need the offset of the count variable */
- unsigned char type; /* EET_T_XXX */
- unsigned char group_type; /* EET_G_XXX */
+ int offset; /* offset in bytes from the base element */
+ int count; /* number of elements for a fixed array */
+ int counter_offset; /* for a variable array we need the offset of the count variable */
+ unsigned char type; /* EET_T_XXX */
+ unsigned char group_type; /* EET_G_XXX */
};
struct _Eet_Data_Encode_Hash_Info
{
- Eet_Data_Stream *ds;
- Eet_Data_Element *ede;
- Eet_Dictionary *ed;
+ Eet_Data_Stream *ds;
+ Eet_Data_Element *ede;
+ Eet_Dictionary *ed;
+};
+
+#define EET_FREE_COUNT 256
+struct _Eet_Free
+{
+ int ref;
+ Eina_Array list[EET_FREE_COUNT];
+};
+
+struct _Eet_Free_Context
+{
+ Eet_Free freelist;
+ Eet_Free freelist_array;
+ Eet_Free freelist_list;
+ Eet_Free freelist_hash;
+ Eet_Free freelist_str;
+ Eet_Free freelist_direct_str;
+};
+
+struct _Eet_Variant_Unknow
+{
+ EINA_MAGIC
+
+ int size;
+ char data[1];
};
/*---*/
-static int eet_data_get_char(const Eet_Dictionary *ed, const void *src, const void *src_end, void *dest);
-static void *eet_data_put_char(Eet_Dictionary *ed, const void *src, int *size_ret);
-static int eet_data_get_short(const Eet_Dictionary *ed, const void *src, const void *src_end, void *dest);
-static void *eet_data_put_short(Eet_Dictionary *ed, const void *src, int *size_ret);
-static inline int eet_data_get_int(const Eet_Dictionary *ed, const void *src, const void *src_end, void *dest);
-static void *eet_data_put_int(Eet_Dictionary *ed, const void *src, int *size_ret);
-static int eet_data_get_long_long(const Eet_Dictionary *ed, const void *src, const void *src_end, void *dest);
-static void *eet_data_put_long_long(Eet_Dictionary *ed, const void *src, int *size_ret);
-static int eet_data_get_float(const Eet_Dictionary *ed, const void *src, const void *src_end, void *dest);
-static void *eet_data_put_float(Eet_Dictionary *ed, const void *src, int *size_ret);
-static int eet_data_get_double(const Eet_Dictionary *ed, const void *src, const void *src_end, void *dest);
-static void *eet_data_put_double(Eet_Dictionary *ed, const void *src, int *size_ret);
-static inline int eet_data_get_string(const Eet_Dictionary *ed, const void *src, const void *src_end, void *dest);
-static void *eet_data_put_string(Eet_Dictionary *ed, const void *src, int *size_ret);
-static int eet_data_get_istring(const Eet_Dictionary *ed, const void *src, const void *src_end, void *dest);
-static void *eet_data_put_istring(Eet_Dictionary *ed, const void *src, int *size_ret);
-static int eet_data_get_null(const Eet_Dictionary *ed, const void *src, const void *src_end, void *dest);
-static void *eet_data_put_null(Eet_Dictionary *ed, const void *src, int *size_ret);
-
-static int eet_data_get_type(const Eet_Dictionary *ed, int type, const void *src, const void *src_end, void *dest);
-static void *eet_data_put_type(Eet_Dictionary *ed, int type, const void *src, int *size_ret);
-
-static int eet_data_get_unknown(const Eet_Dictionary *ed, Eet_Data_Descriptor *edd, Eet_Data_Element *ede, Eet_Data_Chunk *echnk, int type, int group_type, void *data_in, int level, void (*dumpfunc) (void *data, const char *str), void *dumpdata, char **p, int *size);
-static void eet_data_put_unknown(Eet_Dictionary *ed, Eet_Data_Descriptor *edd, Eet_Data_Element *ede, Eet_Data_Stream *ds, void *data_in);
-static void eet_data_put_array(Eet_Dictionary *ed, Eet_Data_Descriptor *edd, Eet_Data_Element *ede, Eet_Data_Stream *ds, void *data_in);
-static int eet_data_get_array(const Eet_Dictionary *ed, Eet_Data_Descriptor *edd, Eet_Data_Element *ede, Eet_Data_Chunk *echnk, int type, int group_type, void *data, int level, void (*dumpfunc) (void *data, const char *str), void *dumpdata, char **p, int *size);
-static int eet_data_get_list(const Eet_Dictionary *ed, Eet_Data_Descriptor *edd, Eet_Data_Element *ede, Eet_Data_Chunk *echnk, int type, int group_type, void *data_in, int level, void (*dumpfunc) (void *data, const char *str), void *dumpdata, char **p, int *size);
-static void eet_data_put_list(Eet_Dictionary *ed, Eet_Data_Descriptor *edd, Eet_Data_Element *ede, Eet_Data_Stream *ds, void *data_in);
-static void eet_data_put_hash(Eet_Dictionary *ed, Eet_Data_Descriptor *edd, Eet_Data_Element *ede, Eet_Data_Stream *ds, void *data_in);
-static int eet_data_get_hash(const Eet_Dictionary *ed, Eet_Data_Descriptor *edd, Eet_Data_Element *ede, Eet_Data_Chunk *echnk, int type, int group_type, void *data, int level, void (*dumpfunc) (void *data, const char *str), void *dumpdata, char **p, int *size);
-
-static void eet_data_chunk_get(const Eet_Dictionary *ed, Eet_Data_Chunk *chnk, const void *src, int size);
-static Eet_Data_Chunk *eet_data_chunk_new(void *data, int size, const char *name, int type, int group_type);
-static void eet_data_chunk_free(Eet_Data_Chunk *chnk);
-
-static Eet_Data_Stream *eet_data_stream_new(void);
-static void eet_data_stream_write(Eet_Data_Stream *ds, const void *data, int size);
-static void eet_data_stream_free(Eet_Data_Stream *ds);
-
-static void eet_data_chunk_put(Eet_Dictionary *ed, Eet_Data_Chunk *chnk, Eet_Data_Stream *ds);
-
-static int eet_data_descriptor_encode_hash_cb(void *hash, const char *key, void *hdata, void *fdata);
-static void *_eet_data_descriptor_encode(Eet_Dictionary *ed, Eet_Data_Descriptor *edd, const void *data_in, int *size_ret);
-static void *_eet_data_descriptor_decode(const Eet_Dictionary *ed,
- Eet_Data_Descriptor *edd,
- const void *data_in,
- int size_in,
- int level,
- void (*dumpfunc) (void *data, const char *str),
- void *dumpdata);
+static void
+ eet_free_context_init(Eet_Free_Context *context);
+static void
+ eet_free_context_shutdown(Eet_Free_Context *context);
+
+static int
+eet_data_get_char(const Eet_Dictionary *ed,
+ const void *src,
+ const void *src_end,
+ void *dest);
+static void *
+eet_data_put_char(Eet_Dictionary *ed,
+ const void *src,
+ int *size_ret);
+static int
+eet_data_get_short(const Eet_Dictionary *ed,
+ const void *src,
+ const void *src_end,
+ void *dest);
+static void *
+eet_data_put_short(Eet_Dictionary *ed,
+ const void *src,
+ int *size_ret);
+static inline int
+eet_data_get_int(const Eet_Dictionary *ed,
+ const void *src,
+ const void *src_end,
+ void *dest);
+static void *
+eet_data_put_int(Eet_Dictionary *ed,
+ const void *src,
+ int *size_ret);
+static int
+eet_data_get_long_long(const Eet_Dictionary *ed,
+ const void *src,
+ const void *src_end,
+ void *dest);
+static void *
+eet_data_put_long_long(Eet_Dictionary *ed,
+ const void *src,
+ int *size_ret);
+static int
+eet_data_get_float(const Eet_Dictionary *ed,
+ const void *src,
+ const void *src_end,
+ void *dest);
+static void *
+eet_data_put_float(Eet_Dictionary *ed,
+ const void *src,
+ int *size_ret);
+static int
+eet_data_get_double(const Eet_Dictionary *ed,
+ const void *src,
+ const void *src_end,
+ void *dest);
+static void *
+eet_data_put_double(Eet_Dictionary *ed,
+ const void *src,
+ int *size_ret);
+static int
+eet_data_get_f32p32(const Eet_Dictionary *ed,
+ const void *src,
+ const void *src_end,
+ void *dest);
+static void *
+eet_data_put_f32p32(Eet_Dictionary *ed,
+ const void *src,
+ int *size_ret);
+static int
+eet_data_get_f16p16(const Eet_Dictionary *ed,
+ const void *src,
+ const void *src_end,
+ void *dest);
+static void *
+eet_data_put_f16p16(Eet_Dictionary *ed,
+ const void *src,
+ int *size_ret);
+static int
+eet_data_get_f8p24(const Eet_Dictionary *ed,
+ const void *src,
+ const void *src_end,
+ void *dest);
+static void *
+eet_data_put_f8p24(Eet_Dictionary *ed,
+ const void *src,
+ int *size_ret);
+static inline int
+eet_data_get_string(const Eet_Dictionary *ed,
+ const void *src,
+ const void *src_end,
+ void *dest);
+static void *
+eet_data_put_string(Eet_Dictionary *ed,
+ const void *src,
+ int *size_ret);
+static int
+eet_data_get_istring(const Eet_Dictionary *ed,
+ const void *src,
+ const void *src_end,
+ void *dest);
+static void *
+eet_data_put_istring(Eet_Dictionary *ed,
+ const void *src,
+ int *size_ret);
+static int
+eet_data_get_null(const Eet_Dictionary *ed,
+ const void *src,
+ const void *src_end,
+ void *dest);
+static void *
+eet_data_put_null(Eet_Dictionary *ed,
+ const void *src,
+ int *size_ret);
+
+static int
+eet_data_get_type(const Eet_Dictionary *ed,
+ int type,
+ const void *src,
+ const void *src_end,
+ void *dest);
+static void *
+eet_data_put_type(Eet_Dictionary *ed,
+ int type,
+ const void *src,
+ int *size_ret);
+
+static Eet_Node *
+eet_data_node_simple_type(int type,
+ const char *name,
+ void *dd);
+
+static int
+eet_data_get_unknown(Eet_Free_Context *context,
+ const Eet_Dictionary *ed,
+ Eet_Data_Descriptor *edd,
+ Eet_Data_Element *ede,
+ Eet_Data_Chunk *echnk,
+ int type,
+ int group_type,
+ void *data_in,
+ char **p,
+ int *size);
+static void
+eet_data_put_unknown(Eet_Dictionary *ed,
+ Eet_Data_Descriptor *edd,
+ Eet_Data_Element *ede,
+ Eet_Data_Stream *ds,
+ void *data_in);
+static void
+eet_data_put_array(Eet_Dictionary *ed,
+ Eet_Data_Descriptor *edd,
+ Eet_Data_Element *ede,
+ Eet_Data_Stream *ds,
+ void *data_in);
+static int
+eet_data_get_array(Eet_Free_Context *context,
+ const Eet_Dictionary *ed,
+ Eet_Data_Descriptor *edd,
+ Eet_Data_Element *ede,
+ Eet_Data_Chunk *echnk,
+ int type,
+ int group_type,
+ void *data,
+ char **p,
+ int *size);
+static int
+eet_data_get_list(Eet_Free_Context *context,
+ const Eet_Dictionary *ed,
+ Eet_Data_Descriptor *edd,
+ Eet_Data_Element *ede,
+ Eet_Data_Chunk *echnk,
+ int type,
+ int group_type,
+ void *data_in,
+ char **p,
+ int *size);
+static void
+eet_data_put_list(Eet_Dictionary *ed,
+ Eet_Data_Descriptor *edd,
+ Eet_Data_Element *ede,
+ Eet_Data_Stream *ds,
+ void *data_in);
+static void
+eet_data_put_hash(Eet_Dictionary *ed,
+ Eet_Data_Descriptor *edd,
+ Eet_Data_Element *ede,
+ Eet_Data_Stream *ds,
+ void *data_in);
+static int
+eet_data_get_hash(Eet_Free_Context *context,
+ const Eet_Dictionary *ed,
+ Eet_Data_Descriptor *edd,
+ Eet_Data_Element *ede,
+ Eet_Data_Chunk *echnk,
+ int type,
+ int group_type,
+ void *data,
+ char **p,
+ int *size);
+static void
+eet_data_put_union(Eet_Dictionary *ed,
+ Eet_Data_Descriptor *edd,
+ Eet_Data_Element *ede,
+ Eet_Data_Stream *ds,
+ void *data_in);
+static int
+eet_data_get_union(Eet_Free_Context *context,
+ const Eet_Dictionary *ed,
+ Eet_Data_Descriptor *edd,
+ Eet_Data_Element *ede,
+ Eet_Data_Chunk *echnk,
+ int type,
+ int group_type,
+ void *data,
+ char **p,
+ int *size);
+static void
+eet_data_put_variant(Eet_Dictionary *ed,
+ Eet_Data_Descriptor *edd,
+ Eet_Data_Element *ede,
+ Eet_Data_Stream *ds,
+ void *data_in);
+static int
+eet_data_get_variant(Eet_Free_Context *context,
+ const Eet_Dictionary *ed,
+ Eet_Data_Descriptor *edd,
+ Eet_Data_Element *ede,
+ Eet_Data_Chunk *echnk,
+ int type,
+ int group_type,
+ void *data,
+ char **p,
+ int *size);
+
+static void
+eet_data_chunk_get(const Eet_Dictionary *ed,
+ Eet_Data_Chunk *chnk,
+ const void *src,
+ int size);
+static Eet_Data_Chunk *
+eet_data_chunk_new(void *data,
+ int size,
+ const char *name,
+ int type,
+ int group_type);
+static void
+eet_data_chunk_free(Eet_Data_Chunk *chnk);
+
+static Eet_Data_Stream *
+ eet_data_stream_new(void);
+static void
+ eet_data_stream_write(Eet_Data_Stream *ds,
+ const void *data,
+ int size);
+static void
+eet_data_stream_free(Eet_Data_Stream *ds);
+
+static void
+eet_data_chunk_put(Eet_Dictionary *ed,
+ Eet_Data_Chunk *chnk,
+ Eet_Data_Stream *ds);
+
+static int
+eet_data_descriptor_encode_hash_cb(void *hash,
+ const char *key,
+ void *hdata,
+ void *fdata);
+static void *_eet_data_descriptor_encode(Eet_Dictionary *ed,
+ Eet_Data_Descriptor *edd,
+ const void *data_in,
+ int *size_ret);
+static void *_eet_data_descriptor_decode(Eet_Free_Context *context,
+ const Eet_Dictionary *ed,
+ Eet_Data_Descriptor *edd,
+ const void *data_in,
+ int size_in,
+ void *data_out,
+ int size_out);
/*---*/
static const Eet_Data_Basic_Type_Codec eet_basic_codec[] =
{
- {sizeof(char), "char", eet_data_get_char, eet_data_put_char },
- {sizeof(short), "short", eet_data_get_short, eet_data_put_short },
- {sizeof(int), "int", eet_data_get_int, eet_data_put_int },
- {sizeof(long long), "long_long", eet_data_get_long_long, eet_data_put_long_long},
- {sizeof(float), "float", eet_data_get_float, eet_data_put_float },
- {sizeof(double), "double", eet_data_get_double, eet_data_put_double },
- {sizeof(char), "uchar", eet_data_get_char, eet_data_put_char },
- {sizeof(short), "ushort", eet_data_get_short, eet_data_put_short },
- {sizeof(int), "uint", eet_data_get_int, eet_data_put_int },
- {sizeof(long long), "ulong_long", eet_data_get_long_long, eet_data_put_long_long},
- {sizeof(char *), "string", eet_data_get_string, eet_data_put_string },
- {sizeof(char *), "inlined", eet_data_get_istring, eet_data_put_istring },
- {sizeof(void *), "NULL", eet_data_get_null, eet_data_put_null }
+ {sizeof(char), "char", eet_data_get_char, eet_data_put_char },
+ {sizeof(short), "short", eet_data_get_short, eet_data_put_short },
+ {sizeof(int), "int", eet_data_get_int, eet_data_put_int },
+ {sizeof(long long), "long_long", eet_data_get_long_long, eet_data_put_long_long},
+ {sizeof(float), "float", eet_data_get_float, eet_data_put_float },
+ {sizeof(double), "double", eet_data_get_double, eet_data_put_double },
+ {sizeof(char), "uchar", eet_data_get_char, eet_data_put_char },
+ {sizeof(short), "ushort", eet_data_get_short, eet_data_put_short },
+ {sizeof(int), "uint", eet_data_get_int, eet_data_put_int },
+ {sizeof(long long), "ulong_long", eet_data_get_long_long, eet_data_put_long_long},
+ {sizeof(char *), "string", eet_data_get_string, eet_data_put_string },
+ {sizeof(char *), "inlined", eet_data_get_istring, eet_data_put_istring },
+ {sizeof(void *), "NULL", eet_data_get_null, eet_data_put_null },
+ {sizeof(Eina_F32p32), "f32p32", eet_data_get_f32p32, eet_data_put_f32p32 },
+ {sizeof(Eina_F16p16), "f16p16", eet_data_get_f16p16, eet_data_put_f16p16 },
+ {sizeof(Eina_F8p24), "f8p24", eet_data_get_f8p24, eet_data_put_f8p24 }
};
static const Eet_Data_Group_Type_Codec eet_group_codec[] =
{
- { eet_data_get_unknown, eet_data_put_unknown },
- { eet_data_get_array, eet_data_put_array },
- { eet_data_get_array, eet_data_put_array },
- { eet_data_get_list, eet_data_put_list },
- { eet_data_get_hash, eet_data_put_hash }
+ { eet_data_get_unknown, eet_data_put_unknown },
+ { eet_data_get_array, eet_data_put_array },
+ { eet_data_get_array, eet_data_put_array },
+ { eet_data_get_list, eet_data_put_list },
+ { eet_data_get_hash, eet_data_put_hash },
+ { eet_data_get_union, eet_data_put_union },
+ { eet_data_get_variant, eet_data_put_variant }
};
-static int words_bigendian = -1;
+static int _eet_data_words_bigendian = -1;
/*---*/
-#define SWAP64(x) (x) = \
- ((((unsigned long long)(x) & 0x00000000000000ffULL ) << 56) |\
- (((unsigned long long)(x) & 0x000000000000ff00ULL ) << 40) |\
- (((unsigned long long)(x) & 0x0000000000ff0000ULL ) << 24) |\
- (((unsigned long long)(x) & 0x00000000ff000000ULL ) << 8) |\
- (((unsigned long long)(x) & 0x000000ff00000000ULL ) >> 8) |\
- (((unsigned long long)(x) & 0x0000ff0000000000ULL ) >> 24) |\
- (((unsigned long long)(x) & 0x00ff000000000000ULL ) >> 40) |\
- (((unsigned long long)(x) & 0xff00000000000000ULL ) >> 56))
-#define SWAP32(x) (x) = \
- ((((int)(x) & 0x000000ff ) << 24) |\
- (((int)(x) & 0x0000ff00 ) << 8) |\
- (((int)(x) & 0x00ff0000 ) >> 8) |\
- (((int)(x) & 0xff000000 ) >> 24))
-#define SWAP16(x) (x) = \
- ((((short)(x) & 0x00ff ) << 8) |\
- (((short)(x) & 0xff00 ) >> 8))
+#define SWAP64(x) (x) = \
+ ((((unsigned long long)(x) & 0x00000000000000ffULL) << 56) | \
+ (((unsigned long long)(x) & 0x000000000000ff00ULL) << 40) | \
+ (((unsigned long long)(x) & 0x0000000000ff0000ULL) << 24) | \
+ (((unsigned long long)(x) & 0x00000000ff000000ULL) << 8) | \
+ (((unsigned long long)(x) & 0x000000ff00000000ULL) >> 8) | \
+ (((unsigned long long)(x) & 0x0000ff0000000000ULL) >> 24) | \
+ (((unsigned long long)(x) & 0x00ff000000000000ULL) >> 40) | \
+ (((unsigned long long)(x) & 0xff00000000000000ULL) >> 56))
+#define SWAP32(x) (x) = \
+ ((((int)(x) & 0x000000ff) << 24) | \
+ (((int)(x) & 0x0000ff00) << 8) | \
+ (((int)(x) & 0x00ff0000) >> 8) | \
+ (((int)(x) & 0xff000000) >> 24))
+#define SWAP16(x) (x) = \
+ ((((short)(x) & 0x00ff) << 8) | \
+ (((short)(x) & 0xff00) >> 8))
+
+#ifdef CONV8
+# undef CONV8
+#endif /* ifdef CONV8 */
+#ifdef CONV16
+# undef CONV16
+#endif /* ifdef CONV16 */
+#ifdef CONV32
+# undef CONV32
+#endif /* ifdef CONV32 */
+#ifdef CONV64
+# undef CONV64
+#endif /* ifdef CONV64 */
#define CONV8(x)
-#define CONV16(x) {if (words_bigendian) SWAP16(x);}
-#define CONV32(x) {if (words_bigendian) SWAP32(x);}
-#define CONV64(x) {if (words_bigendian) SWAP64(x);}
-
-#define IS_SIMPLE_TYPE(Type) (Type > EET_T_UNKNOW && Type < EET_T_LAST)
-
+#define CONV16(x) {if (_eet_data_words_bigendian) {SWAP16(x); }}
+#define CONV32(x) {if (_eet_data_words_bigendian) {SWAP32(x); }}
+#define CONV64(x) {if (_eet_data_words_bigendian) {SWAP64(x); }}
+
+#define IS_SIMPLE_TYPE(Type) (Type > EET_T_UNKNOW && Type < EET_T_LAST)
+#define IS_POINTER_TYPE(Type) (Type >= EET_T_STRING && Type <= EET_T_NULL)
+
+#define POINTER_TYPE_DECODE(Context, \
+ Ed, \
+ Edd, \
+ Ede, \
+ Echnk, \
+ Type, \
+ Data, \
+ P, \
+ Size, \
+ Label) \
+ do { \
+ int ___r; \
+ ___r = eet_data_get_unknown(Context, \
+ Ed, \
+ Edd, Ede, \
+ Echnk, \
+ Type, EET_G_UNKNOWN, \
+ Data, P, Size); \
+ if (!___r) { goto Label; } \
+ } while (0)
+
+#define STRUCT_TYPE_DECODE(Data_Ret, Context, Ed, Ede, Data, Size, SubSize, Label) \
+ do { \
+ Data_Ret = _eet_data_descriptor_decode(Context, \
+ Ed, \
+ Ede, \
+ Data, \
+ Size, \
+ SubSize > 0 ? Data_Ret : NULL, \
+ SubSize); \
+ if (!Data_Ret) { goto Label; } \
+ } while (0)
+
+#define EET_I_STRING 1 << 4
+#define EET_I_INLINED_STRING 2 << 4
+#define EET_I_NULL 3 << 4
+
+#define EET_MAGIC_VARIANT 0xF1234BC
/*---*/
/* CHAR TYPE */
static int
-eet_data_get_char(const Eet_Dictionary *ed __UNUSED__, const void *src, const void *src_end, void *dst)
+eet_data_get_char(const Eet_Dictionary *ed __UNUSED__,
+ const void *src,
+ const void *src_end,
+ void *dst)
{
char *s, *d;
- if (((char *)src + sizeof(char)) > (char *)src_end) return -1;
+ if (((char *)src + sizeof(char)) > (char *)src_end)
+ return -1;
+
s = (char *)src;
d = (char *)dst;
*d = *s;
}
static void *
-eet_data_put_char(Eet_Dictionary *ed __UNUSED__, const void *src, int *size_ret)
+eet_data_put_char(Eet_Dictionary *ed __UNUSED__,
+ const void *src,
+ int *size_ret)
{
char *s, *d;
d = (char *)malloc(sizeof(char));
- if (!d) return NULL;
+ if (!d)
+ return NULL;
+
s = (char *)src;
*d = *s;
CONV8(*d);
/* SHORT TYPE */
static int
-eet_data_get_short(const Eet_Dictionary *ed __UNUSED__, const void *src, const void *src_end, void *dst)
+eet_data_get_short(const Eet_Dictionary *ed __UNUSED__,
+ const void *src,
+ const void *src_end,
+ void *dst)
{
short *d;
- if (((char *)src + sizeof(short)) > (char *)src_end) return -1;
+ if (((char *)src + sizeof(short)) > (char *)src_end)
+ return -1;
+
memcpy(dst, src, sizeof(short));
d = (short *)dst;
CONV16(*d);
}
static void *
-eet_data_put_short(Eet_Dictionary *ed __UNUSED__, const void *src, int *size_ret)
+eet_data_put_short(Eet_Dictionary *ed __UNUSED__,
+ const void *src,
+ int *size_ret)
{
short *s, *d;
d = (short *)malloc(sizeof(short));
- if (!d) return NULL;
+ if (!d)
+ return NULL;
+
s = (short *)src;
*d = *s;
CONV16(*d);
/* INT TYPE */
static inline int
-eet_data_get_int(const Eet_Dictionary *ed __UNUSED__, const void *src, const void *src_end, void *dst)
+eet_data_get_int(const Eet_Dictionary *ed __UNUSED__,
+ const void *src,
+ const void *src_end,
+ void *dst)
{
int *d;
- if (((char *)src + sizeof(int)) > (char *)src_end) return -1;
+ if (((char *)src + sizeof(int)) > (char *)src_end)
+ return -1;
+
memcpy(dst, src, sizeof(int));
d = (int *)dst;
CONV32(*d);
}
static void *
-eet_data_put_int(Eet_Dictionary *ed __UNUSED__, const void *src, int *size_ret)
+eet_data_put_int(Eet_Dictionary *ed __UNUSED__,
+ const void *src,
+ int *size_ret)
{
int *s, *d;
d = (int *)malloc(sizeof(int));
- if (!d) return NULL;
+ if (!d)
+ return NULL;
+
s = (int *)src;
*d = *s;
CONV32(*d);
/* LONG LONG TYPE */
static int
-eet_data_get_long_long(const Eet_Dictionary *ed __UNUSED__, const void *src, const void *src_end, void *dst)
+eet_data_get_long_long(const Eet_Dictionary *ed __UNUSED__,
+ const void *src,
+ const void *src_end,
+ void *dst)
{
unsigned long long *d;
- if (((char *)src + sizeof(unsigned long long)) > (char *)src_end) return -1;
+ if (((char *)src + sizeof(unsigned long long)) > (char *)src_end)
+ return -1;
+
memcpy(dst, src, sizeof(unsigned long long));
d = (unsigned long long *)dst;
CONV64(*d);
}
static void *
-eet_data_put_long_long(Eet_Dictionary *ed __UNUSED__, const void *src, int *size_ret)
+eet_data_put_long_long(Eet_Dictionary *ed __UNUSED__,
+ const void *src,
+ int *size_ret)
{
unsigned long long *s, *d;
d = (unsigned long long *)malloc(sizeof(unsigned long long));
- if (!d) return NULL;
+ if (!d)
+ return NULL;
+
s = (unsigned long long *)src;
*d = *s;
CONV64(*d);
/* STRING TYPE */
static inline int
-eet_data_get_string_hash(const Eet_Dictionary *ed, const void *src, const void *src_end)
+eet_data_get_string_hash(const Eet_Dictionary *ed,
+ const void *src,
+ const void *src_end)
{
if (ed)
{
- int index;
+ int idx;
- if (eet_data_get_int(ed, src, src_end, &index) < 0) return -1;
+ if (eet_data_get_int(ed, src, src_end, &idx) < 0)
+ return -1;
- return eet_dictionary_string_get_hash(ed, index);
+ return eet_dictionary_string_get_hash(ed, idx);
}
return -1;
}
static inline int
-eet_data_get_string(const Eet_Dictionary *ed, const void *src, const void *src_end, void *dst)
+eet_data_get_string(const Eet_Dictionary *ed,
+ const void *src,
+ const void *src_end,
+ void *dst)
{
char *s, **d;
if (ed)
{
- const char *str;
- int index;
+ const char *str;
+ int idx;
- if (eet_data_get_int(ed, src, src_end, &index) < 0) return -1;
+ if (eet_data_get_int(ed, src, src_end, &idx) < 0)
+ return -1;
- str = eet_dictionary_string_get_char(ed, index);
- if (str == NULL)
+ str = eet_dictionary_string_get_char(ed, idx);
+ if (!str)
return -1;
- *d = (char *) str;
- return eet_dictionary_string_get_size(ed, index);
+ *d = (char *)str;
+ return eet_dictionary_string_get_size(ed, idx);
}
s = (char *)src;
- if (s == NULL)
+ if (!s)
{
*d = NULL;
return 0;
}
static void *
-eet_data_put_string(Eet_Dictionary *ed, const void *src, int *size_ret)
+eet_data_put_string(Eet_Dictionary *ed,
+ const void *src,
+ int *size_ret)
{
char *s, *d;
int len;
if (ed)
{
- const char *str;
- int index;
+ const char *str;
+ int idx;
- str = *((const char **) src);
- if (!str) return NULL;
+ str = *((const char **)src);
+ if (!str)
+ return NULL;
- index = eet_dictionary_string_add(ed, str);
- if (index == -1) return NULL;
+ idx = eet_dictionary_string_add(ed, str);
+ if (idx == -1)
+ return NULL;
- return eet_data_put_int(ed, &index, size_ret);
+ return eet_data_put_int(ed, &idx, size_ret);
}
s = (char *)(*((char **)src));
- if (!s) return NULL;
+ if (!s)
+ return NULL;
+
len = strlen(s);
d = malloc(len + 1);
- if (!d) return NULL;
+ if (!d)
+ return NULL;
+
memcpy(d, s, len + 1);
*size_ret = len + 1;
return d;
/* ALWAYS INLINED STRING TYPE */
static int
-eet_data_get_istring(const Eet_Dictionary *ed __UNUSED__, const void *src, const void *src_end, void *dst)
+eet_data_get_istring(const Eet_Dictionary *ed __UNUSED__,
+ const void *src,
+ const void *src_end,
+ void *dst)
{
return eet_data_get_string(NULL, src, src_end, dst);
}
static void *
-eet_data_put_istring(Eet_Dictionary *ed __UNUSED__, const void *src, int *size_ret)
+eet_data_put_istring(Eet_Dictionary *ed __UNUSED__,
+ const void *src,
+ int *size_ret)
{
return eet_data_put_string(NULL, src, size_ret);
}
/* ALWAYS NULL TYPE */
static int
-eet_data_get_null(const Eet_Dictionary *ed __UNUSED__, const void *src __UNUSED__, const void *src_end __UNUSED__, void *dst)
+eet_data_get_null(const Eet_Dictionary *ed __UNUSED__,
+ const void *src __UNUSED__,
+ const void *src_end __UNUSED__,
+ void *dst)
{
char **d;
- d = (char**) dst;
+ d = (char **)dst;
*d = NULL;
- return 0;
+ return 1;
}
static void *
-eet_data_put_null(Eet_Dictionary *ed __UNUSED__, const void *src __UNUSED__, int *size_ret)
+eet_data_put_null(Eet_Dictionary *ed __UNUSED__,
+ const void *src __UNUSED__,
+ int *size_ret)
{
*size_ret = 0;
return NULL;
* values, but have a so simple math that is almost as fast.
*/
static inline int
-_eet_data_float_cache_get(const char *s, int len, float *d)
+_eet_data_float_cache_get(const char *s,
+ int len,
+ float *d)
{
/* fast handle of simple case 0xMp+E*/
- if ((len == 6) && (s[0] == '0') && (s[1] == 'x') && (s[3] == 'p'))
- {
- int mantisse = (s[2] >= 'a') ? (s[2] - 'a' + 10) : (s[2] - '0');
- int exponent = (s[5] - '0');
+ if ((len == 6) && (s[0] == '0') && (s[1] == 'x') && (s[3] == 'p'))
+ {
+ int mantisse = (s[2] >= 'a') ? (s[2] - 'a' + 10) : (s[2] - '0');
+ int exponent = (s[5] - '0');
- if (s[4] == '+') *d = (float)(mantisse << exponent);
- else *d = (float)mantisse / (float)(1 << exponent);
+ if (s[4] == '+')
+ *d = (float)(mantisse << exponent);
+ else
+ *d = (float)mantisse / (float)(1 << exponent);
- return 1;
- }
- return 0;
+ return 1;
+ }
+
+ return 0;
}
static inline int
-_eet_data_double_cache_get(const char *s, int len, double *d)
+_eet_data_double_cache_get(const char *s,
+ int len,
+ double *d)
{
/* fast handle of simple case 0xMp+E*/
- if ((len == 6) && (s[0] == '0') && (s[1] == 'x') && (s[3] == 'p'))
- {
- int mantisse = (s[2] >= 'a') ? (s[2] - 'a' + 10) : (s[2] - '0');
- int exponent = (s[5] - '0');
+ if ((len == 6) && (s[0] == '0') && (s[1] == 'x') && (s[3] == 'p'))
+ {
+ int mantisse = (s[2] >= 'a') ? (s[2] - 'a' + 10) : (s[2] - '0');
+ int exponent = (s[5] - '0');
- if (s[4] == '+') *d = (double)(mantisse << exponent);
- else *d = (double)mantisse / (double)(1 << exponent);
+ if (s[4] == '+')
+ *d = (double)(mantisse << exponent);
+ else
+ *d = (double)mantisse / (double)(1 << exponent);
- return 1;
- }
- return 0;
+ return 1;
+ }
+
+ return 0;
}
/* FLOAT TYPE */
static int
-eet_data_get_float(const Eet_Dictionary *ed, const void *src, const void *src_end, void *dst)
+eet_data_get_float(const Eet_Dictionary *ed,
+ const void *src,
+ const void *src_end,
+ void *dst)
{
- float *d;
- int index;
+ float *d;
+ int idx;
- d = (float *) dst;
+ d = (float *)dst;
if (!ed)
{
- const char *s, *p;
- long long mantisse;
- long exponent;
- int len;
+ const char *s, *p;
+ long long mantisse;
+ long exponent;
+ int len;
s = (const char *)src;
p = s;
len = 0;
- while ((p < (const char *)src_end) && (*p != 0)) {len++; p++;}
+ while ((p < (const char *)src_end) && (*p != 0)) {len++; p++; }
- if (_eet_data_float_cache_get(s, len, d) != 0) return len + 1;
+ if (_eet_data_float_cache_get(s, len, d) != 0)
+ return len + 1;
+
+ if (eina_convert_atod(s, len, &mantisse, &exponent) == EINA_FALSE)
+ return -1;
- if (eina_convert_atod(s, len, &mantisse, &exponent) == EINA_FALSE) return -1;
*d = (float)ldexp((double)mantisse, exponent);
return len + 1;
}
- if (eet_data_get_int(ed, src, src_end, &index) < 0) return -1;
+ if (eet_data_get_int(ed, src, src_end, &idx) < 0)
+ return -1;
- if (!eet_dictionary_string_get_float(ed, index, d))
+ if (!eet_dictionary_string_get_float(ed, idx, d))
return -1;
+
return 1;
}
static void *
-eet_data_put_float(Eet_Dictionary *ed, const void *src, int *size_ret)
+eet_data_put_float(Eet_Dictionary *ed,
+ const void *src,
+ int *size_ret)
{
- char buf[128];
- int index;
+ char buf[128];
+ int idx;
eina_convert_dtoa((double)(*(float *)src), buf);
if (!ed)
{
- char *d;
- int len;
+ char *d;
+ int len;
len = strlen(buf);
d = malloc(len + 1);
- if (!d) return NULL;
- memcpy(d, buf, len + 1);
+ if (!d)
+ return NULL;
+
+ memcpy(d, buf, len + 1);
*size_ret = len + 1;
return d;
}
- index = eet_dictionary_string_add(ed, buf);
- if (index == -1) return NULL;
+ idx = eet_dictionary_string_add(ed, buf);
+ if (idx == -1)
+ return NULL;
- return eet_data_put_int(ed, &index, size_ret);
+ return eet_data_put_int(ed, &idx, size_ret);
}
/* DOUBLE TYPE */
static int
-eet_data_get_double(const Eet_Dictionary *ed, const void *src, const void *src_end, void *dst)
+eet_data_get_double(const Eet_Dictionary *ed,
+ const void *src,
+ const void *src_end,
+ void *dst)
{
- double *d;
- int index;
+ double *d;
+ int idx;
- d = (double *) dst;
+ d = (double *)dst;
if (!ed)
{
- const char *s, *p;
- long long mantisse = 0;
- long exponent = 0;
- int len;
+ const char *s, *p;
+ long long mantisse = 0;
+ long exponent = 0;
+ int len;
- s = (const char *) src;
+ s = (const char *)src;
p = s;
len = 0;
- while ((p < (const char *)src_end) && (*p != 0)) {len++; p++;}
+ while ((p < (const char *)src_end) && (*p != 0)) {len++; p++; }
- if (_eet_data_double_cache_get(s, len, d) != 0) return len + 1;
+ if (_eet_data_double_cache_get(s, len, d) != 0)
+ return len + 1;
+
+ if (eina_convert_atod(s, len, &mantisse, &exponent) == EINA_FALSE)
+ return -1;
- if (eina_convert_atod(s, len, &mantisse, &exponent) == EINA_FALSE) return -1;
- *d = ldexp((double) mantisse, exponent);
+ *d = ldexp((double)mantisse, exponent);
return len + 1;
}
- if (eet_data_get_int(ed, src, src_end, &index) < 0) return -1;
+ if (eet_data_get_int(ed, src, src_end, &idx) < 0)
+ return -1;
- if (!eet_dictionary_string_get_double(ed, index, d))
+ if (!eet_dictionary_string_get_double(ed, idx, d))
return -1;
+
return 1;
}
static void *
-eet_data_put_double(Eet_Dictionary *ed, const void *src, int *size_ret)
+eet_data_put_double(Eet_Dictionary *ed,
+ const void *src,
+ int *size_ret)
{
- char buf[128];
- int index;
+ char buf[128];
+ int idx;
eina_convert_dtoa((double)(*(double *)src), buf);
if (!ed)
{
- char *d;
- int len;
+ char *d;
+ int len;
+
+ len = strlen(buf);
+ d = malloc(len + 1);
+ if (!d)
+ return NULL;
+
+ memcpy(d, buf, len + 1);
+ *size_ret = len + 1;
+
+ return d;
+ }
+
+ idx = eet_dictionary_string_add(ed, buf);
+ if (idx == -1)
+ return NULL;
+
+ return eet_data_put_int(ed, &idx, size_ret);
+}
+
+static int
+eet_data_get_f32p32(const Eet_Dictionary *ed,
+ const void *src,
+ const void *src_end,
+ void *dst)
+{
+ Eina_F32p32 *fp;
+ int idx;
+
+ fp = (Eina_F32p32 *)dst;
+
+ if (!ed)
+ {
+ const char *s, *p;
+ int len;
+
+ s = (const char *)src;
+ p = s;
+ len = 0;
+ while ((p < (const char *)src_end) && (*p != 0)) { len++; p++; }
+
+ if (!(eina_convert_atofp(s, len, fp)))
+ return -1;
+
+ return 1;
+ }
+
+ if (eet_data_get_int(ed, src, src_end, &idx) < 0)
+ return -1;
+
+ if (!eet_dictionary_string_get_fp(ed, idx, fp))
+ return -1;
+
+ return 1;
+}
+
+static void *
+eet_data_put_f32p32(Eet_Dictionary *ed,
+ const void *src,
+ int *size_ret)
+{
+ char buf[128];
+ int idx;
+
+ eina_convert_fptoa((Eina_F32p32)(*(Eina_F32p32 *)src), buf);
+
+ if (!ed)
+ {
+ char *d;
+ int len;
len = strlen(buf);
d = malloc(len + 1);
- if (!d) return NULL;
- memcpy(d, buf, len + 1);
+ if (!d)
+ return NULL;
+
+ memcpy(d, buf, len + 1);
*size_ret = len + 1;
return d;
}
- index = eet_dictionary_string_add(ed, buf);
- if (index == -1) return NULL;
+ idx = eet_dictionary_string_add(ed, buf);
+ if (idx == -1)
+ return NULL;
+
+ return eet_data_put_int(ed, &idx, size_ret);
+}
+
+static int
+eet_data_get_f16p16(const Eet_Dictionary *ed,
+ const void *src,
+ const void *src_end,
+ void *dst)
+{
+ Eina_F32p32 tmp;
+ Eina_F16p16 *fp;
+
+ fp = (Eina_F16p16 *)dst;
+
+ if (eet_data_get_f32p32(ed, src, src_end, &tmp) < 0)
+ return -1;
+
+ *fp = eina_f32p32_to_f16p16(tmp);
+ return 1;
+}
+
+static void *
+eet_data_put_f16p16(Eet_Dictionary *ed,
+ const void *src,
+ int *size_ret)
+{
+ Eina_F32p32 tmp;
+
+ tmp = eina_f16p16_to_f32p32((Eina_F16p16)(*(Eina_F16p16 *)src));
+ return eet_data_put_f32p32(ed, &tmp, size_ret);
+}
+
+static int
+eet_data_get_f8p24(const Eet_Dictionary *ed,
+ const void *src,
+ const void *src_end,
+ void *dst)
+{
+ Eina_F32p32 tmp;
+ Eina_F8p24 *fp;
+
+ fp = (Eina_F8p24 *)dst;
+
+ if (eet_data_get_f32p32(ed, src, src_end, &tmp) < 0)
+ return -1;
+
+ *fp = eina_f32p32_to_f8p24(tmp);
+ return 1;
+}
- return eet_data_put_int(ed, &index, size_ret);
+static void *
+eet_data_put_f8p24(Eet_Dictionary *ed,
+ const void *src,
+ int *size_ret)
+{
+ Eina_F32p32 tmp;
+
+ tmp = eina_f8p24_to_f32p32((Eina_F8p24)(*(Eina_F8p24 *)src));
+ return eet_data_put_f32p32(ed, &tmp, size_ret);
}
static inline int
-eet_data_get_type(const Eet_Dictionary *ed, int type, const void *src, const void *src_end, void *dest)
+eet_data_get_type(const Eet_Dictionary *ed,
+ int type,
+ const void *src,
+ const void *src_end,
+ void *dest)
{
int ret;
}
static inline void *
-eet_data_put_type(Eet_Dictionary *ed, int type, const void *src, int *size_ret)
+eet_data_put_type(Eet_Dictionary *ed,
+ int type,
+ const void *src,
+ int *size_ret)
{
void *ret;
return ret;
}
+static inline Eina_Bool
+eet_data_type_match(int type1,
+ int type2)
+{
+ if (type1 == type2)
+ return EINA_TRUE;
+
+ /* Note: All floating point type are equivalent and could be read
+ without problem by any other floating point getter. */
+ switch (type1)
+ {
+ case EET_T_FLOAT:
+ case EET_T_DOUBLE:
+ case EET_T_F32P32:
+ case EET_T_F16P16:
+ case EET_T_F8P24:
+ switch (type2)
+ {
+ case EET_T_FLOAT:
+ case EET_T_DOUBLE:
+ case EET_T_F32P32:
+ case EET_T_F16P16:
+ case EET_T_F8P24:
+ return EINA_TRUE;
+
+ default:
+ break;
+ } /* switch */
+ break;
+
+ default:
+ break;
+ }
+
+ return EINA_FALSE;
+}
+
/* chunk format...
*
* char[4] = "CHnK"; // untyped data ... or
*/
static inline void
-eet_data_chunk_get(const Eet_Dictionary *ed, Eet_Data_Chunk *chnk,
- const void *src, int size)
+eet_data_chunk_get(const Eet_Dictionary *ed,
+ Eet_Data_Chunk *chnk,
+ const void *src,
+ int size)
{
const char *s;
int ret1, ret2;
if (!src)
- {
- fprintf(stderr, "stiouf -3\n");
- return;
- }
+ return;
+
if (size <= 8)
- {
- fprintf(stderr, "stiouf -2 %i\n", size);
- return;
- }
+ return;
if (!chnk)
- {
- fprintf(stderr, "stiouf -1\n");
- return;
- }
+ return;
s = src;
if (s[2] == 'K')
{
- if ((s[0] != 'C') || (s[1] != 'H') || (s[2] != 'K'))
- {
- fprintf(stderr, "stiouf 0\n");
- return;
- }
- chnk->type = (unsigned char)(s[3]);
- if (chnk->type > EET_T_LAST)
- {
- chnk->group_type = chnk->type;
- chnk->type = EET_T_UNKNOW;
- }
- else
- chnk->group_type = EET_G_UNKNOWN;
- if ((chnk->type >= EET_T_LAST) ||
- (chnk->group_type >= EET_G_LAST))
- {
- chnk->type = 0;
- chnk->group_type = 0;
- }
- }
- else
- {
- if ((s[0] != 'C') || (s[1] != 'H') || (s[2] != 'n') || (s[3] != 'K'))
- {
- fprintf(stderr, "stiouf 1\n");
- return;
- }
+ if ((s[0] != 'C') || (s[1] != 'H') || (s[2] != 'K'))
+ return;
+
+ chnk->type = (unsigned char)(s[3]);
+ if (chnk->type >= EET_I_LIMIT)
+ {
+ chnk->group_type =
+ ((chnk->type - EET_I_LIMIT) & 0xF) + EET_G_UNKNOWN;
+ switch ((chnk->type - EET_I_LIMIT) & 0xF0)
+ {
+#define EET_UNMATCH_TYPE(Type) \
+case EET_I_ ## Type: chnk->type = EET_T_ ## Type; break;
+
+ EET_UNMATCH_TYPE(STRING);
+ EET_UNMATCH_TYPE(INLINED_STRING);
+ EET_UNMATCH_TYPE(NULL);
+
+ default:
+ return;
+ }
+ }
+ else if (chnk->type > EET_T_LAST)
+ {
+ chnk->group_type = chnk->type;
+ chnk->type = EET_T_UNKNOW;
+ }
+ else
+ chnk->group_type = EET_G_UNKNOWN;
+ if ((chnk->type >= EET_T_LAST) ||
+ (chnk->group_type >=
+ EET_G_LAST))
+ {
+ chnk->type = 0;
+ chnk->group_type = 0;
+ }
}
+ else if ((s[0] != 'C') || (s[1] != 'H') || (s[2] != 'n') || (s[3] != 'K'))
+ return;
+
ret1 = eet_data_get_type(ed, EET_T_INT, (s + 4), (s + size), &(chnk->size));
+
if (ret1 <= 0)
- {
- fprintf(stderr, "stiouf 2\n");
- return;
- }
+ return;
+
if ((chnk->size < 0) || ((chnk->size + 8) > size))
- {
- fprintf(stderr, "stiouf 3\n");
- return;
- }
+ return;
+
ret2 = eet_data_get_type(ed, EET_T_STRING, (s + 8), (s + size), &(chnk->name));
+
if (ret2 <= 0)
- {
- fprintf(stderr, "stiouf 4\n");
- return;
- }
+ return;
chnk->len = ret2;
}
static inline Eet_Data_Chunk *
-eet_data_chunk_new(void *data, int size, const char *name, int type, int group_type)
+eet_data_chunk_new(void *data,
+ int size,
+ const char *name,
+ int type,
+ int group_type)
{
Eet_Data_Chunk *chnk;
- if (!name) return NULL;
+ if (!name)
+ return NULL;
+
chnk = calloc(1, sizeof(Eet_Data_Chunk));
- if (!chnk) return NULL;
+ if (!chnk)
+ return NULL;
+
+ /* Note: Another security, so older eet library could read file
+ saved with fixed point value. */
+ if (type == EET_T_F32P32
+ || type == EET_T_F16P16
+ || type == EET_T_F8P24)
+ type = EET_T_DOUBLE;
chnk->name = strdup(name);
chnk->len = strlen(name) + 1;
static inline void
eet_data_chunk_free(Eet_Data_Chunk *chnk)
{
- if (chnk->name) free(chnk->name);
+ if (chnk->name)
+ free(chnk->name);
+
free(chnk);
}
Eet_Data_Stream *ds;
ds = calloc(1, sizeof(Eet_Data_Stream));
- if (!ds) return NULL;
+ if (!ds)
+ return NULL;
+
return ds;
}
static inline void
eet_data_stream_free(Eet_Data_Stream *ds)
{
- if (ds->data) free(ds->data);
+ if (ds->data)
+ free(ds->data);
+
+ free(ds);
+}
+
+static inline void
+eet_data_stream_flush(Eet_Data_Stream *ds)
+{
free(ds);
}
static inline void
-eet_data_stream_write(Eet_Data_Stream *ds, const void *data, int size)
+eet_data_stream_write(Eet_Data_Stream *ds,
+ const void *data,
+ int size)
{
char *p;
if ((ds->pos + size) > ds->size)
{
- ds->data = realloc(ds->data, ds->size + size + 512);
- if (!ds->data)
- {
- ds->pos = 0;
- ds->size = 0;
- return;
- }
- ds->size = ds->size + size + 512;
+ ds->data = realloc(ds->data, ds->size + size + 512);
+ if (!ds->data)
+ {
+ ds->pos = 0;
+ ds->size = 0;
+ return;
+ }
+
+ ds->size = ds->size + size + 512;
}
+
p = ds->data;
memcpy(p + ds->pos, data, size);
ds->pos += size;
}
static void
-eet_data_chunk_put(Eet_Dictionary *ed, Eet_Data_Chunk *chnk, Eet_Data_Stream *ds)
+eet_data_chunk_put(Eet_Dictionary *ed,
+ Eet_Data_Chunk *chnk,
+ Eet_Data_Stream *ds)
{
- int *size;
+ int *size;
void *string;
- int s;
- int size_ret = 0;
- int string_ret = 0;
+ int s;
+ int size_ret = 0;
+ int string_ret = 0;
unsigned char buf[4] = "CHK";
- if (!chnk->data && chnk->type != EET_T_NULL) return;
+ /* disable this check - it will allow empty chunks to be written. this is
+ * right for corner-cases when y have a struct with empty fields (empty
+ * strings or empty list ptrs etc.) */
+ /* if (!chnk->data && chnk->type != EET_T_NULL) return; */
/* chunk head */
/* eet_data_stream_write(ds, "CHnK", 4);*/
- if (chnk->type != EET_T_UNKNOW) buf[3] = chnk->type;
- else buf[3] = chnk->group_type;
+ if (chnk->type != EET_T_UNKNOW)
+ {
+ if (chnk->group_type != EET_G_UNKNOWN)
+ {
+ int type = EET_I_LIMIT + chnk->group_type - EET_G_UNKNOWN;
+
+ switch (chnk->type)
+ {
+ /* Only make sense with pointer type. */
+#define EET_MATCH_TYPE(Type) \
+case EET_T_ ## Type: type += EET_I_ ## Type; break;
+
+ EET_MATCH_TYPE(STRING);
+ EET_MATCH_TYPE(INLINED_STRING);
+ EET_MATCH_TYPE(NULL);
+
+ default:
+ return;
+ }
+
+ buf[3] = type;
+ }
+ else
+ buf[3] = chnk->type;
+ }
+ else
+ buf[3] = chnk->group_type;
string = eet_data_put_string(ed, &chnk->name, &string_ret);
if (!string)
- return ;
+ return;
/* size of chunk payload data + name */
s = chnk->size + string_ret;
eet_data_stream_write(ds, string, string_ret);
/* write payload */
- eet_data_stream_write(ds, chnk->data, chnk->size);
+ if (chnk->data)
+ eet_data_stream_write(ds, chnk->data, chnk->size);
free(string);
- on_error:
+on_error:
free(size);
}
int i;
edd->elements.hash.size = 1 << 6;
- edd->elements.hash.buckets = calloc(1, sizeof(Eet_Data_Descriptor_Hash) * edd->elements.hash.size);
+ edd->elements.hash.buckets = calloc(
+ 1,
+ sizeof(Eet_Data_Descriptor_Hash) *
+ edd->elements.hash.size);
for (i = 0; i < edd->elements.num; i++)
{
- Eet_Data_Element *ede;
- int hash;
-
- ede = &(edd->elements.set[i]);
- hash = _eet_hash_gen((char *) ede->name, 6);
- if (!edd->elements.hash.buckets[hash].element)
- edd->elements.hash.buckets[hash].element = ede;
- else
- {
- Eet_Data_Descriptor_Hash *bucket;
-
- bucket = calloc(1, sizeof(Eet_Data_Descriptor_Hash));
- bucket->element = ede;
- bucket->next = edd->elements.hash.buckets[hash].next;
- edd->elements.hash.buckets[hash].next = bucket;
- }
+ Eet_Data_Element *ede;
+ int hash;
+
+ ede = &(edd->elements.set[i]);
+ hash = _eet_hash_gen((char *)ede->name, 6);
+ if (!edd->elements.hash.buckets[hash].element)
+ edd->elements.hash.buckets[hash].element = ede;
+ else
+ {
+ Eet_Data_Descriptor_Hash *bucket;
+
+ bucket = calloc(1, sizeof(Eet_Data_Descriptor_Hash));
+ bucket->element = ede;
+ bucket->next = edd->elements.hash.buckets[hash].next;
+ edd->elements.hash.buckets[hash].next = bucket;
+ }
}
}
for (i = 0; i < edd->elements.hash.size; i++)
{
- Eet_Data_Descriptor_Hash *bucket, *pbucket;
-
- bucket = edd->elements.hash.buckets[i].next;
- while (bucket)
- {
- pbucket = bucket;
- bucket = bucket->next;
- free(pbucket);
- }
+ Eet_Data_Descriptor_Hash *bucket, *pbucket;
+
+ bucket = edd->elements.hash.buckets[i].next;
+ while (bucket)
+ {
+ pbucket = bucket;
+ bucket = bucket->next;
+ free(pbucket);
+ }
}
- if (edd->elements.hash.buckets) free(edd->elements.hash.buckets);
+ if (edd->elements.hash.buckets)
+ free(edd->elements.hash.buckets);
}
static Eet_Data_Element *
-_eet_descriptor_hash_find(Eet_Data_Descriptor *edd, char *name, int hash)
+_eet_descriptor_hash_find(Eet_Data_Descriptor *edd,
+ char *name,
+ int hash)
{
Eet_Data_Descriptor_Hash *bucket;
- if (hash < 0) hash = _eet_hash_gen(name, 6);
- else hash &= 0x3f;
- if (!edd->elements.hash.buckets[hash].element) return NULL;
- /*
- When we use the dictionnary as a source for chunk name, we will always
- have the same pointer in name. It's a good idea to just compare pointer
- instead of running strcmp on both string.
- */
+ if (hash < 0)
+ hash = _eet_hash_gen(name, 6);
+ else
+ hash &= 0x3f;
+
+ if (!edd->elements.hash.buckets[hash].element)
+ return NULL; /*
+ When we use the dictionary as a source for chunk name, we will always
+ have the same pointer in name. It's a good idea to just compare pointer
+ instead of running strcmp on both string.
+ */
+
if (edd->elements.hash.buckets[hash].element->directory_name_ptr == name)
return edd->elements.hash.buckets[hash].element;
+
if (!strcmp(edd->elements.hash.buckets[hash].element->name, name))
{
- edd->elements.hash.buckets[hash].element->directory_name_ptr = name;
- return edd->elements.hash.buckets[hash].element;
+ edd->elements.hash.buckets[hash].element->directory_name_ptr = name;
+ return edd->elements.hash.buckets[hash].element;
}
+
bucket = edd->elements.hash.buckets[hash].next;
while (bucket)
{
- if (bucket->element->directory_name_ptr == name) return bucket->element;
- if (!strcmp(bucket->element->name, name))
- {
- bucket->element->directory_name_ptr = name;
- return bucket->element;
- }
- bucket = bucket->next;
+ if (bucket->element->directory_name_ptr == name)
+ return bucket->element;
+
+ if (!strcmp(bucket->element->name, name))
+ {
+ bucket->element->directory_name_ptr = name;
+ return bucket->element;
+ }
+
+ bucket = bucket->next;
}
return NULL;
}
free((char *)str);
}
-/*---*/
-
-EAPI Eet_Data_Descriptor *
-eet_data_descriptor_new(const char *name,
- int size,
- void *(*func_list_next) (void *l),
- void *(*func_list_append) (void *l, void *d),
- void *(*func_list_data) (void *l),
- void *(*func_list_free) (void *l),
- void (*func_hash_foreach) (void *h, int (*func) (void *h, const char *k, void *dt, void *fdt), void *fdt),
- void *(*func_hash_add) (void *h, const char *k, void *d),
- void (*func_hash_free) (void *h))
+static Eina_Hash *
+_eet_eina_hash_add_alloc(Eina_Hash *hash,
+ const char *key,
+ void *data)
{
- Eet_Data_Descriptor *edd;
+ if (!hash)
+ hash = eina_hash_string_small_new(NULL);
- if (!name) return NULL;
- edd = calloc(1, sizeof(Eet_Data_Descriptor));
- if (!edd) return NULL;
+ if (!hash)
+ return NULL;
- edd->name = name;
- edd->ed = NULL;
- edd->size = size;
- edd->func.mem_alloc = _eet_mem_alloc;
- edd->func.mem_free = _eet_mem_free;
- edd->func.str_alloc = _eet_str_alloc;
- edd->func.str_direct_alloc = NULL;
- edd->func.str_direct_free = NULL;
- edd->func.str_free = _eet_str_free;
- edd->func.list_next = func_list_next;
- edd->func.list_append = func_list_append;
- edd->func.list_data = func_list_data;
- edd->func.list_free = func_list_free;
- edd->func.hash_foreach = func_hash_foreach;
- edd->func.hash_add = func_hash_add;
- edd->func.hash_free = func_hash_free;
- return edd;
+ eina_hash_add(hash, key, data);
+ return hash;
}
-/* new replcement */
-EAPI Eet_Data_Descriptor *
-eet_data_descriptor2_new(Eet_Data_Descriptor_Class *eddc)
+static Eina_Hash *
+_eet_eina_hash_direct_add_alloc(Eina_Hash *hash,
+ const char *key,
+ void *data)
{
- Eet_Data_Descriptor *edd;
+ if (!hash)
+ hash = eina_hash_string_small_new(NULL);
- if (!eddc) return NULL;
- if (eddc->version < 1) return NULL;
- edd = calloc(1, sizeof(Eet_Data_Descriptor));
- if (!edd) return NULL;
+ if (!hash)
+ return NULL;
- edd->name = eddc->name;
- edd->ed = NULL;
- edd->size = eddc->size;
- edd->func.mem_alloc = _eet_mem_alloc;
- edd->func.mem_free = _eet_mem_free;
- edd->func.str_alloc = _eet_str_alloc;
- edd->func.str_free = _eet_str_free;
- if (eddc->func.mem_alloc)
- edd->func.mem_alloc = eddc->func.mem_alloc;
- if (eddc->func.mem_free)
- edd->func.mem_free = eddc->func.mem_free;
- if (eddc->func.str_alloc)
- edd->func.str_alloc = eddc->func.str_alloc;
- if (eddc->func.str_free)
- edd->func.str_free = eddc->func.str_free;
- edd->func.list_next = eddc->func.list_next;
- edd->func.list_append = eddc->func.list_append;
- edd->func.list_data = eddc->func.list_data;
- edd->func.list_free = eddc->func.list_free;
- edd->func.hash_foreach = eddc->func.hash_foreach;
- edd->func.hash_add = eddc->func.hash_add;
- edd->func.hash_free = eddc->func.hash_free;
+ eina_hash_direct_add(hash, key, data);
+ return hash;
+}
- return edd;
+static char *
+_eet_str_direct_alloc(const char *str)
+{
+ return (char *)str;
}
-EAPI Eet_Data_Descriptor *
-eet_data_descriptor3_new(Eet_Data_Descriptor_Class *eddc)
+static void
+_eet_str_direct_free(const char *str __UNUSED__)
+{
+}
+
+static void
+_eet_eina_hash_foreach(void *hash,
+ Eina_Hash_Foreach cb,
+ void *fdata)
+{
+ if (hash)
+ eina_hash_foreach(hash, cb, fdata);
+}
+
+static void
+_eet_eina_hash_free(void *hash)
+{
+ if (hash)
+ eina_hash_free(hash);
+}
+
+/*---*/
+EAPI Eina_Bool
+eet_eina_stream_data_descriptor_class_set(Eet_Data_Descriptor_Class *eddc,
+ /* When we change the structure content in the future, we need to handle old structure type too */
+ unsigned int eddc_size,
+ const char *name,
+ int size)
+{
+ if (!eddc || !name || eddc_size != sizeof (Eet_Data_Descriptor_Class))
+ return EINA_FALSE;
+
+ eddc->name = name;
+ eddc->size = size;
+ eddc->version = EET_DATA_DESCRIPTOR_CLASS_VERSION;
+
+ eddc->func.mem_alloc = _eet_mem_alloc;
+ eddc->func.mem_free = _eet_mem_free;
+ eddc->func.str_alloc = (char *(*)(const char *))eina_stringshare_add;
+ eddc->func.str_free = eina_stringshare_del;
+ eddc->func.list_next = (void *(*)(void *))eina_list_next;
+ eddc->func.list_append = (void *(*)(void *, void *))eina_list_append;
+ eddc->func.list_data = (void *(*)(void *))eina_list_data_get;
+ eddc->func.list_free = (void *(*)(void *))eina_list_free;
+ eddc->func.hash_foreach = (void (*)(void *, int (*)(void *, const char *, void *, void *), void *))_eet_eina_hash_foreach;
+ eddc->func.hash_add = (void *(*)(void *, const char *, void *))_eet_eina_hash_add_alloc;
+ eddc->func.hash_free = (void (*)(void *))_eet_eina_hash_free;
+
+ /* This will cause an ABI incompatibility */
+ eddc->func.array_alloc = _eet_mem_alloc;
+ eddc->func.array_free = _eet_mem_free;
+
+ return EINA_TRUE;
+}
+
+EAPI Eina_Bool
+eet_eina_file_data_descriptor_class_set(Eet_Data_Descriptor_Class *eddc,
+ /* When we change the structure content in the future, we need to handle old structure type too */
+ unsigned int eddc_size,
+ const char *name,
+ int size)
+{
+ if (!eet_eina_stream_data_descriptor_class_set(eddc, eddc_size, name, size))
+ return EINA_FALSE;
+
+ eddc->version = EET_DATA_DESCRIPTOR_CLASS_VERSION;
+
+ eddc->func.hash_add = (void *(*)(void *, const char *, void *))_eet_eina_hash_direct_add_alloc;
+ eddc->func.str_direct_alloc = _eet_str_direct_alloc;
+ eddc->func.str_direct_free = _eet_str_direct_free;
+
+ return EINA_TRUE;
+}
+
+static Eet_Data_Descriptor *
+_eet_data_descriptor_new(const Eet_Data_Descriptor_Class *eddc,
+ int version)
{
Eet_Data_Descriptor *edd;
- if (!eddc) return NULL;
- if (eddc->version < 2) return NULL;
- edd = calloc(1, sizeof(Eet_Data_Descriptor));
- if (!edd) return NULL;
+ if (!eddc)
+ return NULL;
+
+ edd = calloc(1, sizeof (Eet_Data_Descriptor));
+ if (!edd)
+ return NULL;
edd->name = eddc->name;
edd->ed = NULL;
edd->func.str_free = _eet_str_free;
if (eddc->func.mem_alloc)
edd->func.mem_alloc = eddc->func.mem_alloc;
+
if (eddc->func.mem_free)
edd->func.mem_free = eddc->func.mem_free;
+
if (eddc->func.str_alloc)
edd->func.str_alloc = eddc->func.str_alloc;
+
if (eddc->func.str_free)
edd->func.str_free = eddc->func.str_free;
+
edd->func.list_next = eddc->func.list_next;
edd->func.list_append = eddc->func.list_append;
edd->func.list_data = eddc->func.list_data;
edd->func.hash_foreach = eddc->func.hash_foreach;
edd->func.hash_add = eddc->func.hash_add;
edd->func.hash_free = eddc->func.hash_free;
- edd->func.str_direct_alloc = eddc->func.str_direct_alloc;
- edd->func.str_direct_free = eddc->func.str_direct_free;
+
+ if (eddc->version > 1 && version > 1)
+ {
+ edd->func.str_direct_alloc = eddc->func.str_direct_alloc;
+ edd->func.str_direct_free = eddc->func.str_direct_free;
+ }
+
+ if (eddc->version > 2)
+ {
+ edd->func.type_get = eddc->func.type_get;
+ edd->func.type_set = eddc->func.type_set;
+ }
+
+ if (eddc->version > 3)
+ {
+ edd->func.array_alloc = eddc->func.array_alloc;
+ edd->func.array_free = eddc->func.array_free;
+ }
return edd;
}
+EAPI Eet_Data_Descriptor *
+eet_data_descriptor_new(const char *name,
+ int size,
+ Eet_Descriptor_List_Next_Callback func_list_next,
+ Eet_Descriptor_List_Append_Callback func_list_append,
+ Eet_Descriptor_List_Data_Callback func_list_data,
+ Eet_Descriptor_List_Free_Callback func_list_free,
+ Eet_Descriptor_Hash_Foreach_Callback func_hash_foreach,
+ Eet_Descriptor_Hash_Add_Callback func_hash_add,
+ Eet_Descriptor_Hash_Free_Callback func_hash_free)
+{
+ Eet_Data_Descriptor_Class eddc;
+
+ if (!name)
+ return NULL;
+
+ memset(&eddc, 0, sizeof (Eet_Data_Descriptor_Class));
+
+ eddc.name = name;
+ eddc.size = size;
+ eddc.version = 0;
+
+ eddc.func.list_next = func_list_next;
+ eddc.func.list_append = func_list_append;
+ eddc.func.list_data = func_list_data;
+ eddc.func.list_free = func_list_free;
+ eddc.func.hash_foreach = func_hash_foreach;
+ eddc.func.hash_add = func_hash_add;
+ eddc.func.hash_free = func_hash_free;
+
+ return _eet_data_descriptor_new(&eddc, 0);
+}
+
+EAPI Eet_Data_Descriptor *
+eet_data_descriptor2_new(const Eet_Data_Descriptor_Class *eddc)
+{
+ return _eet_data_descriptor_new(eddc, 1);
+}
+
+EAPI Eet_Data_Descriptor *
+eet_data_descriptor3_new(const Eet_Data_Descriptor_Class *eddc)
+{
+ return _eet_data_descriptor_new(eddc, 2);
+}
+
+EAPI Eet_Data_Descriptor *
+eet_data_descriptor_stream_new(const Eet_Data_Descriptor_Class *eddc)
+{
+ return _eet_data_descriptor_new(eddc, 1);
+}
+
+EAPI Eet_Data_Descriptor *
+eet_data_descriptor_file_new(const Eet_Data_Descriptor_Class *eddc)
+{
+ return _eet_data_descriptor_new(eddc, 2);
+}
+
EAPI void
eet_data_descriptor_free(Eet_Data_Descriptor *edd)
{
+ if (!edd)
+ return;
+
_eet_descriptor_hash_free(edd);
- if (edd->elements.set) free(edd->elements.set);
+ if (edd->elements.set)
+ free(edd->elements.set);
+
free(edd);
}
EAPI void
eet_data_descriptor_element_add(Eet_Data_Descriptor *edd,
- const char *name,
- int type,
- int group_type,
- int offset,
- int count,
-/* int counter_offset, */
- const char *counter_name /* Useless should go on a major release */,
- Eet_Data_Descriptor *subtype)
+ const char *name,
+ int type,
+ int group_type,
+ int offset,
+ int count,
+/* int counter_offset, */
+ const char *counter_name /* FIXME: Useless should go on a major release */,
+ Eet_Data_Descriptor *subtype)
{
Eet_Data_Element *ede;
- /* int l1, l2, p1, p2, i;
- char *ps;*/
+ Eet_Data_Element *tmp;
- /* FIXME: Fail safely when realloc fail. */
+ /* Sanity check to avoid crash later at runtime */
+ if (type < EET_T_UNKNOW ||
+ type >= EET_T_LAST)
+ {
+ CRIT("Preventing later bug due to unknow type: %i", type);
+ return ;
+ }
+ if (offset < 0)
+ {
+ CRIT("Preventing later buffer underrun : offset = %i", offset);
+ return ;
+ }
+ if (offset > edd->size)
+ {
+ CRIT("Preventing later buffer overrun : offset = %i in a structure of %i bytes", offset, edd->size);
+ return ;
+ }
+ if (group_type == EET_G_UNKNOWN && type != EET_T_UNKNOW)
+ {
+ if (offset + eet_basic_codec[type - 1].size > edd->size)
+ {
+ CRIT("Preventing later buffer overrun : offset = %i, size = %i in a structure of %i bytes", offset, eet_basic_codec[type - 1].size, edd->size);
+ return ;
+ }
+ }
+ else if ((offset + sizeof (void*)) > (unsigned int) edd->size)
+ {
+ CRIT("Preventing later buffer overrun : offset = %i, estimated size = %i in a structure of %i bytes", offset, sizeof (void*), edd->size);
+ return ;
+ }
+
+ /* UNION, VARIANT type would not work with simple type, we need a way to map the type. */
+ if ((group_type == EET_G_UNION
+ || group_type == EET_G_VARIANT)
+ &&
+ (type != EET_T_UNKNOW
+ || !subtype
+ || !subtype->func.type_get
+ || !subtype->func.type_set))
+ return;
+
+ /* VARIANT type will only work if the map only contains EET_G_*, but not UNION, VARIANT and ARRAY. */
+ if (group_type == EET_G_VARIANT)
+ {
+ int i;
+
+ for (i = 0; i < subtype->elements.num; ++i)
+ if (subtype->elements.set[i].type != EET_T_UNKNOW
+ && subtype->elements.set[i].group_type > EET_G_VAR_ARRAY
+ && subtype->elements.set[i].group_type < EET_G_UNION)
+ return;
+
+ subtype->unified_type = EINA_TRUE;
+ }
+
+ if (subtype
+ && subtype->unified_type
+ && (type != EET_T_UNKNOW
+ || group_type < EET_G_UNION))
+ return;
+
+ /* Sanity check done, let allocate ! */
edd->elements.num++;
- edd->elements.set = realloc(edd->elements.set, edd->elements.num * sizeof(Eet_Data_Element));
- if (!edd->elements.set) return;
+ tmp = realloc(edd->elements.set, edd->elements.num * sizeof(Eet_Data_Element));
+ if (!tmp)
+ return;
+
+ edd->elements.set = tmp;
ede = &(edd->elements.set[edd->elements.num - 1]);
ede->name = name;
ede->directory_name_ptr = NULL;
* Instead of handling it in encode/decode/dump/undump, we create an
* implicit structure with only the simple type.
*/
- if (group_type > EET_G_UNKNOWN
- && group_type < EET_G_LAST
- && type > EET_T_UNKNOW && type < EET_T_STRING
- && subtype == NULL)
+ if ((group_type > EET_G_UNKNOWN)
+ && (group_type < EET_G_LAST)
+ && (((type > EET_T_UNKNOW) && (type < EET_T_STRING))
+ || ((type > EET_T_NULL) && (type < EET_T_LAST)))
+ && (!subtype))
{
- subtype = calloc(1, sizeof (Eet_Data_Descriptor));
- if (!subtype) return ;
- subtype->name = "implicit";
- subtype->size = eet_basic_codec[type - 1].size;
- memcpy(&subtype->func, &edd->func, sizeof(subtype->func));
-
- eet_data_descriptor_element_add(subtype, eet_basic_codec[type - 1].name, type,
- EET_G_UNKNOWN, 0, 0, /* 0, */NULL, NULL);
- type = EET_T_UNKNOW;
+ subtype = calloc(1, sizeof (Eet_Data_Descriptor));
+ if (!subtype)
+ return;
+
+ subtype->name = "implicit";
+ subtype->size = eet_basic_codec[type - 1].size;
+ memcpy(&subtype->func, &edd->func, sizeof(subtype->func));
+
+ eet_data_descriptor_element_add(subtype,
+ eet_basic_codec[type - 1].name,
+ type,
+ EET_G_UNKNOWN,
+ 0,
+ 0,
+ /* 0, */ NULL,
+ NULL);
+ type = EET_T_UNKNOW;
}
ede->type = type;
ede->group_type = group_type;
ede->offset = offset;
ede->count = count;
- /* FIXME: For the time being, EET_G_VAR_ARRAY will put the counter_offset in count. */
+ /* FIXME: For the time being, VAR_ARRAY, UNION and VARIANT will put the counter_offset in count. */
ede->counter_offset = count;
/* ede->counter_offset = counter_offset; */
ede->counter_name = counter_name;
}
EAPI void *
-eet_data_read_cipher(Eet_File *ef, Eet_Data_Descriptor *edd, const char *name, const char *key)
+eet_data_read_cipher(Eet_File *ef,
+ Eet_Data_Descriptor *edd,
+ const char *name,
+ const char *cipher_key)
{
const Eet_Dictionary *ed = NULL;
- const void *data = NULL;
- void *data_dec;
- int required_free = 0;
- int size;
+ const void *data = NULL;
+ void *data_dec;
+ Eet_Free_Context context;
+ int required_free = 0;
+ int size;
ed = eet_dictionary_get(ef);
- if (!key)
+ if (!cipher_key)
data = eet_read_direct(ef, name, &size);
+
if (!data)
{
- required_free = 1;
- data = eet_read_cipher(ef, name, &size, key);
- if (!data) return NULL;
+ required_free = 1;
+ data = eet_read_cipher(ef, name, &size, cipher_key);
+ if (!data)
+ return NULL;
}
- data_dec = _eet_data_descriptor_decode(ed, edd, data, size, 0, NULL, NULL);
+ eet_free_context_init(&context);
+ data_dec = _eet_data_descriptor_decode(&context, ed, edd, data, size, NULL, 0);
+ eet_free_context_shutdown(&context);
+
if (required_free)
- free((void*)data);
+ free((void *)data);
return data_dec;
}
+EAPI Eet_Node *
+eet_data_node_read_cipher(Eet_File *ef,
+ const char *name,
+ const char *cipher_key)
+{
+ const Eet_Dictionary *ed = NULL;
+ const void *data = NULL;
+ Eet_Node *result;
+ Eet_Free_Context context;
+ int required_free = 0;
+ int size;
+
+ ed = eet_dictionary_get(ef);
+
+ if (!cipher_key)
+ data = eet_read_direct(ef, name, &size);
+
+ if (!data)
+ {
+ required_free = 1;
+ data = eet_read_cipher(ef, name, &size, cipher_key);
+ if (!data)
+ return NULL;
+ }
+
+ eet_free_context_init(&context);
+ result = _eet_data_descriptor_decode(&context, ed, NULL, data, size, NULL, 0);
+ eet_free_context_shutdown(&context);
+
+ if (required_free)
+ free((void *)data);
+
+ return result;
+}
+
EAPI void *
-eet_data_read(Eet_File *ef, Eet_Data_Descriptor *edd, const char *name)
+eet_data_read(Eet_File *ef,
+ Eet_Data_Descriptor *edd,
+ const char *name)
{
return eet_data_read_cipher(ef, edd, name, NULL);
}
EAPI int
-eet_data_write_cipher(Eet_File *ef, Eet_Data_Descriptor *edd, const char *name, const char *key, const void *data, int compress)
+eet_data_write_cipher(Eet_File *ef,
+ Eet_Data_Descriptor *edd,
+ const char *name,
+ const char *cipher_key,
+ const void *data,
+ int comp)
{
- Eet_Dictionary *ed;
- void *data_enc;
- int size;
- int val;
+ Eet_Dictionary *ed;
+ void *data_enc;
+ int size;
+ int val;
ed = eet_dictionary_get(ef);
data_enc = _eet_data_descriptor_encode(ed, edd, data, &size);
- if (!data_enc) return 0;
- val = eet_write_cipher(ef, name, data_enc, size, compress, key);
+ if (!data_enc)
+ return 0;
+
+ val = eet_write_cipher(ef, name, data_enc, size, comp, cipher_key);
free(data_enc);
return val;
}
EAPI int
-eet_data_write(Eet_File *ef, Eet_Data_Descriptor *edd, const char *name, const void *data, int compress)
+eet_data_write(Eet_File *ef,
+ Eet_Data_Descriptor *edd,
+ const char *name,
+ const void *data,
+ int comp)
{
- return eet_data_write_cipher(ef, edd, name, NULL, data, compress);
+ return eet_data_write_cipher(ef, edd, name, NULL, data, comp);
}
-typedef struct _Eet_Free Eet_Free;
-struct _Eet_Free
+static void
+eet_free_context_init(Eet_Free_Context *context)
{
- int ref;
- int len[256];
- int num[256];
- void **list[256];
-};
+ unsigned int i = 0;
+
+ memset(context, 0, sizeof (Eet_Free_Context));
+ for (i = 0; i < EET_FREE_COUNT; ++i)
+ {
+ eina_array_step_set(&context->freelist.list[i],
+ sizeof (context->freelist.list[i]),
+ 32);
+ eina_array_step_set(&context->freelist_array.list[i],
+ sizeof (context->freelist.list[i]),
+ 32);
+ eina_array_step_set(&context->freelist_list.list[i],
+ sizeof (context->freelist.list[i]),
+ 32);
+ eina_array_step_set(&context->freelist_hash.list[i],
+ sizeof (context->freelist.list[i]),
+ 32);
+ eina_array_step_set(&context->freelist_str.list[i],
+ sizeof (context->freelist.list[i]),
+ 32);
+ eina_array_step_set(&context->freelist_direct_str.list[i],
+ sizeof (context->freelist.list[i]),
+ 32);
+ }
+}
+
+static void
+eet_free_context_shutdown(Eet_Free_Context *context)
+{
+ unsigned int i = 0;
+
+ for (i = 0; i < EET_FREE_COUNT; ++i)
+ {
+ eina_array_flush(&context->freelist.list[i]);
+ eina_array_flush(&context->freelist_array.list[i]);
+ eina_array_flush(&context->freelist_list.list[i]);
+ eina_array_flush(&context->freelist_hash.list[i]);
+ eina_array_flush(&context->freelist_str.list[i]);
+ eina_array_flush(&context->freelist_direct_str.list[i]);
+ }
+}
static int
_eet_free_hash(void *data)
{
+#ifdef _WIN64
+ __int64 ptr = (UINT_PTR)data;
+#else /* ifdef _WIN64 */
unsigned long ptr = (unsigned long)(data);
+#endif /* ifdef _WIN64 */
int hash;
hash = ptr;
hash ^= ptr >> 16;
hash ^= ptr >> 24;
-#if LONG_BIT != 32
+#if defined (_WIN64) || ((!defined (_WIN32)) && (LONG_BIT != 32))
hash ^= ptr >> 32;
hash ^= ptr >> 40;
hash ^= ptr >> 48;
hash ^= ptr >> 56;
-#endif
+#endif /* if defined (_WIN64) || ((!defined (_WIN32)) && (LONG_BIT != 32)) */
return hash & 0xFF;
}
static void
-_eet_free_add(Eet_Free *ef, void *data)
+_eet_free_add(Eet_Free *ef,
+ void *data)
{
+ void *track;
+ Eina_Array_Iterator it;
+ unsigned int i;
int hash;
- int i;
hash = _eet_free_hash(data);
- for (i = 0; i < ef->num[hash]; ++i)
- if (ef->list[hash][i] == data) return;
+ EINA_ARRAY_ITER_NEXT(&ef->list[hash], i, track, it)
+ if (track == data)
+ return;
- ef->num[hash]++;
- if (ef->num[hash] > ef->len[hash])
- {
- void **tmp;
+ eina_array_push(&ef->list[hash], data);
+}
- tmp = realloc(ef->list[hash], (ef->len[hash] + 16) * sizeof(void*));
- if (!tmp) return ;
+#if 0
+static void
+_eet_free_del(Eet_Free *ef,
+ void *data)
+{
+ void *track;
+ Eina_Array_Iterator it;
+ unsigned int i;
+ int hash;
- ef->len[hash] += 16;
- ef->list[hash] = tmp;
+ hash = _eet_free_hash(data);
+
+ EINA_ARRAY_ITER_NEXT(&ef->list[hash], i, track, it)
+ if (track == data)
+ {
+ eina_array_data_set(&ef->list[hash], i, NULL);
+ return;
}
- ef->list[hash][ef->num[hash] - 1] = data;
}
+
+#endif
+
static void
_eet_free_reset(Eet_Free *ef)
{
- int i;
+ unsigned int i;
- if (ef->ref > 0) return ;
- for (i = 0; i < 256; ++i)
- {
- ef->len[i] = 0;
- ef->num[i] = 0;
- if (ef->list[i]) free(ef->list[i]);
- ef->list[i] = NULL;
- }
+ if (ef->ref > 0)
+ return;
+
+ for (i = 0; i < EET_FREE_COUNT; ++i)
+ eina_array_clean(&ef->list[i]);
}
+
static void
_eet_free_ref(Eet_Free *ef)
{
ef->ref++;
}
+
static void
_eet_free_unref(Eet_Free *ef)
{
ef->ref--;
}
-static Eet_Free freelist = { 0, { 0 }, { 0 }, { NULL } };
-
-#define _eet_freelist_add(Data) _eet_free_add(&freelist, Data);
-#define _eet_freelist_reset() _eet_free_reset(&freelist);
-#define _eet_freelist_ref() _eet_free_ref(&freelist);
-#define _eet_freelist_unref() _eet_free_unref(&freelist);
+#define _eet_freelist_add(Ctx, Data) _eet_free_add(&Ctx->freelist, Data);
+#define _eet_freelist_del(Ctx, Data) _eet_free_del(&Ctx->freelist, Data);
+#define _eet_freelist_reset(Ctx) _eet_free_reset(&Ctx->freelist);
+#define _eet_freelist_ref(Ctx) _eet_free_ref(&Ctx->freelist);
+#define _eet_freelist_unref(Ctx) _eet_free_unref(&Ctx->freelist);
static void
-_eet_freelist_free(Eet_Data_Descriptor *edd)
+_eet_freelist_free(Eet_Free_Context *context,
+ Eet_Data_Descriptor *edd)
{
- int j;
- int i;
+ void *track;
+ Eina_Array_Iterator it;
+ unsigned int j;
+ unsigned int i;
+
+ if (context->freelist.ref > 0)
+ return;
- if (freelist.ref > 0) return;
- for (j = 0; j < 256; ++j)
- for (i = 0; i < freelist.num[j]; ++i)
+ for (j = 0; j < EET_FREE_COUNT; ++j)
+ EINA_ARRAY_ITER_NEXT(&context->freelist.list[j], i, track, it)
+ if (track)
{
- if (edd)
- edd->func.mem_free(freelist.list[j][i]);
- else
- free(freelist.list[j][i]);
+ if (edd)
+ edd->func.mem_free(track);
+ else
+ free(track);
}
- _eet_free_reset(&freelist);
+ _eet_free_reset(&context->freelist);
}
-static Eet_Free freeleak = { 0, { 0 }, { 0 }, { NULL } };
-
-#define _eet_freeleak_add(Data) _eet_free_add(&freeleak, Data);
-#define _eet_freeleak_reset() _eet_free_reset(&freeleak);
-#define _eet_freeleak_ref() _eet_free_ref(&freeleak);
-#define _eet_freeleak_unref() _eet_free_unref(&freeleak);
+#define _eet_freelist_array_add(Ctx, Data) _eet_free_add(&Ctx->freelist_array, Data);
+#define _eet_freelist_array_del(Ctx, Data) _eet_free_del(&Ctx->freelist_array, Data);
+#define _eet_freelist_array_reset(Ctx) _eet_free_reset(&Ctx->freelist_array);
+#define _eet_freelist_array_ref(Ctx) _eet_free_ref(&Ctx->freelist_array);
+#define _eet_freelist_array_unref(Ctx) _eet_free_unref(&Ctx->freelist_array);
static void
-_eet_freeleak_free(Eet_Data_Descriptor *edd)
+_eet_freelist_array_free(Eet_Free_Context *context,
+ Eet_Data_Descriptor *edd)
{
- int j;
- int i;
+ void *track;
+ Eina_Array_Iterator it;
+ unsigned int j;
+ unsigned int i;
+
+ if (context->freelist_array.ref > 0)
+ return;
- if (freeleak.ref > 0) return;
- for (j = 0; j < 256; ++j)
- for (i = 0; i < freeleak.num[j]; ++i)
+ for (j = 0; j < EET_FREE_COUNT; ++j)
+ EINA_ARRAY_ITER_NEXT(&context->freelist_array.list[j], i, track, it)
+ if (track)
{
- if (edd)
- edd->func.mem_free(freeleak.list[j][i]);
- else
- free(freeleak.list[j][i]);
+ if (edd)
+ {
+ if (edd->func.array_free)
+ edd->func.array_free(track);
+ else
+ edd->func.mem_free(track);
+ }
+ else
+ free(track);
}
- _eet_free_reset(&freeleak);
+ _eet_free_reset(&context->freelist_array);
}
-static Eet_Free freelist_list = { 0, { 0 }, { 0 }, { NULL } };
-
-#define _eet_freelist_list_add(Data) _eet_free_add(&freelist_list, Data);
-#define _eet_freelist_list_reset() _eet_free_reset(&freelist_list);
-#define _eet_freelist_list_ref() _eet_free_ref(&freelist_list);
-#define _eet_freelist_list_unref() _eet_free_unref(&freelist_list);
+#define _eet_freelist_list_add(Ctx, Data) _eet_free_add(&Ctx->freelist_list, Data);
+#define _eet_freelist_list_del(Ctx, Data) _eet_free_del(&Ctx->freelist_list, Data);
+#define _eet_freelist_list_reset(Ctx) _eet_free_reset(&Ctx->freelist_list);
+#define _eet_freelist_list_ref(Ctx) _eet_free_ref(&Ctx->freelist_list);
+#define _eet_freelist_list_unref(Ctx) _eet_free_unref(&Ctx->freelist_list);
static void
-_eet_freelist_list_free(Eet_Data_Descriptor *edd)
+_eet_freelist_list_free(Eet_Free_Context *context,
+ Eet_Data_Descriptor *edd)
{
- int j;
- int i;
+ void *track;
+ Eina_Array_Iterator it;
+ unsigned int j;
+ unsigned int i;
+
+ if (context->freelist_list.ref > 0)
+ return;
- if (freelist_list.ref > 0) return;
- for (j = 0; j < 256; ++j)
- for (i = 0; i < freelist_list.num[j]; ++i)
+ for (j = 0; j < EET_FREE_COUNT; ++j)
+ EINA_ARRAY_ITER_NEXT(&context->freelist_list.list[j], i, track, it)
+ if (track)
{
- if (edd)
- edd->func.list_free(*((void**)(freelist_list.list[j][i])));
+ if (edd)
+ edd->func.list_free(*((void **)(track)));
}
- _eet_free_reset(&freelist_list);
+ _eet_free_reset(&context->freelist_list);
}
-static Eet_Free freelist_str = { 0, { 0 }, { 0 }, { NULL } };
-
-#define _eet_freelist_str_add(Data) _eet_free_add(&freelist_str, Data);
-#define _eet_freelist_str_reset() _eet_free_reset(&freelist_str);
-#define _eet_freelist_str_ref() _eet_free_ref(&freelist_str);
-#define _eet_freelist_str_unref() _eet_free_unref(&freelist_str);
+#define _eet_freelist_str_add(Ctx, Data) _eet_free_add(&Ctx->freelist_str, Data);
+#define _eet_freelist_str_del(Ctx, Data) _eet_free_del(&Ctx->freelist_str, Data);
+#define _eet_freelist_str_reset(Ctx) _eet_free_reset(&Ctx->freelist_str);
+#define _eet_freelist_str_ref(Ctx) _eet_free_ref(&Ctx->freelist_str);
+#define _eet_freelist_str_unref(Ctx) _eet_free_unref(&Ctx->freelist_str);
static void
-_eet_freelist_str_free(Eet_Data_Descriptor *edd)
+_eet_freelist_str_free(Eet_Free_Context *context,
+ Eet_Data_Descriptor *edd)
{
- int j;
- int i;
+ void *track;
+ Eina_Array_Iterator it;
+ unsigned int j;
+ unsigned int i;
- if (freelist_str.ref > 0) return;
- for (j = 0; j < 256; ++j)
- for (i = 0; i < freelist_str.num[j]; ++i)
+ if (context->freelist_str.ref > 0)
+ return;
+
+ for (j = 0; j < EET_FREE_COUNT; ++j)
+ EINA_ARRAY_ITER_NEXT(&context->freelist_str.list[j], i, track, it)
+ if (track)
{
- if (edd)
- edd->func.str_free(freelist_str.list[j][i]);
- else
- free(freelist_str.list[j][i]);
+ if (edd)
+ edd->func.str_free(track);
+ else
+ free(track);
}
- _eet_free_reset(&freelist_str);
+ _eet_free_reset(&context->freelist_str);
}
-static Eet_Free freelist_direct_str = { 0, { 0 }, { 0 }, { NULL } };
+#define _eet_freelist_direct_str_add(Ctx, Data) _eet_free_add(&Ctx->freelist_direct_str, Data);
+#define _eet_freelist_direct_str_del(Ctx, Data) _eet_free_del(&Ctx->freelist_direct_str, Data);
+#define _eet_freelist_direct_str_reset(Ctx) _eet_free_reset(&Ctx->freelist_direct_str);
+#define _eet_freelist_direct_str_ref(Ctx) _eet_free_ref(&Ctx->freelist_direct_str);
+#define _eet_freelist_direct_str_unref(Ctx) _eet_free_unref(&Ctx->freelist_direct_str);
+
+static void
+_eet_freelist_direct_str_free(Eet_Free_Context *context,
+ Eet_Data_Descriptor *edd)
+{
+ void *track;
+ Eina_Array_Iterator it;
+ unsigned int j;
+ unsigned int i;
-#define _eet_freelist_direct_str_add(Data) _eet_free_add(&freelist_direct_str, Data);
-#define _eet_freelist_direct_str_reset() _eet_free_reset(&freelist_direct_str);
-#define _eet_freelist_direct_str_ref() _eet_free_ref(&freelist_direct_str);
-#define _eet_freelist_direct_str_unref() _eet_free_unref(&freelist_direct_str);
+ if (context->freelist_direct_str.ref > 0)
+ return;
+
+ for (j = 0; j < EET_FREE_COUNT; ++j)
+ EINA_ARRAY_ITER_NEXT(&context->freelist_str.list[j], i, track, it)
+ if (track)
+ {
+ if (edd)
+ edd->func.str_direct_free(track);
+ else
+ free(track);
+ }
+ _eet_free_reset(&context->freelist_direct_str);
+}
+
+#define _eet_freelist_hash_add(Ctx, Data) _eet_free_add(&Ctx->freelist_hash, Data);
+#define _eet_freelist_hash_del(Ctx, Data) _eet_free_del(&Ctx->freelist_hash, Data);
+#define _eet_freelist_hash_reset(Ctx) _eet_free_reset(&Ctx->freelist_hash);
+#define _eet_freelist_hash_ref(Ctx) _eet_free_ref(&Ctx->freelist_hash);
+#define _eet_freelist_hash_unref(Ctx) _eet_free_unref(&Ctx->freelist_hash);
static void
-_eet_freelist_direct_str_free(Eet_Data_Descriptor *edd)
+_eet_freelist_hash_free(Eet_Free_Context *context,
+ Eet_Data_Descriptor *edd)
{
- int j;
- int i;
+ void *track;
+ Eina_Array_Iterator it;
+ unsigned int j;
+ unsigned int i;
+
+ if (context->freelist_hash.ref > 0)
+ return;
- if (freelist_str.ref > 0) return;
- for (j = 0; j < 256; ++j)
- for (i = 0; i < freelist_str.num[j]; ++i)
+ for (j = 0; j < EET_FREE_COUNT; ++j)
+ EINA_ARRAY_ITER_NEXT(&context->freelist_hash.list[j], i, track, it)
+ if (track)
{
- if (edd)
- edd->func.str_direct_free(freelist_str.list[j][i]);
- else
- free(freelist_str.list[j][i]);
+ if (edd)
+ edd->func.hash_free(track);
+ else
+ free(track);
}
- _eet_free_reset(&freelist_str);
+ _eet_free_reset(&context->freelist_hash);
+}
+
+static void
+_eet_freelist_all_ref(Eet_Free_Context *freelist_context)
+{
+ _eet_freelist_ref(freelist_context);
+ _eet_freelist_str_ref(freelist_context);
+ _eet_freelist_list_ref(freelist_context);
+ _eet_freelist_hash_ref(freelist_context);
+ _eet_freelist_direct_str_ref(freelist_context);
+}
+
+static void
+_eet_freelist_all_unref(Eet_Free_Context *freelist_context)
+{
+ _eet_freelist_unref(freelist_context);
+ _eet_freelist_str_unref(freelist_context);
+ _eet_freelist_list_unref(freelist_context);
+ _eet_freelist_hash_unref(freelist_context);
+ _eet_freelist_direct_str_unref(freelist_context);
}
static int
-eet_data_descriptor_encode_hash_cb(void *hash __UNUSED__, const char *key, void *hdata, void *fdata)
+eet_data_descriptor_encode_hash_cb(void *hash __UNUSED__,
+ const char *cipher_key,
+ void *hdata,
+ void *fdata)
{
- Eet_Dictionary *ed;
- Eet_Data_Encode_Hash_Info *edehi;
- Eet_Data_Stream *ds;
- Eet_Data_Element *ede;
- Eet_Data_Chunk *echnk;
- void *data = NULL;
- int size;
+ Eet_Dictionary *ed;
+ Eet_Data_Encode_Hash_Info *edehi;
+ Eet_Data_Stream *ds;
+ Eet_Data_Element *ede;
+ Eet_Data_Chunk *echnk;
+ void *data = NULL;
+ int size;
edehi = fdata;
ede = edehi->ede;
/* Store key */
data = eet_data_put_type(ed,
EET_T_STRING,
- &key,
- &size);
+ &cipher_key,
+ &size);
if (data)
{
- echnk = eet_data_chunk_new(data, size, ede->name, ede->type, ede->group_type);
- eet_data_chunk_put(ed, echnk, ds);
- eet_data_chunk_free(echnk);
- free(data);
- data = NULL;
+ echnk = eet_data_chunk_new(data,
+ size,
+ ede->name,
+ ede->type,
+ ede->group_type);
+ eet_data_chunk_put(ed, echnk, ds);
+ eet_data_chunk_free(echnk);
+ free(data);
+ data = NULL;
}
EET_ASSERT(!((ede->type > EET_T_UNKNOW) && (ede->type < EET_T_STRING)), return );
eet_data_put_unknown(ed, NULL, ede, ds, &hdata);
else
{
- if (ede->subtype)
- data = _eet_data_descriptor_encode(ed,
- ede->subtype,
- hdata,
- &size);
- if (data)
- {
- echnk = eet_data_chunk_new(data, size, ede->name, ede->type, ede->group_type);
- eet_data_chunk_put(ed, echnk, ds);
- eet_data_chunk_free(echnk);
- free(data);
- data = NULL;
- }
+ if (ede->subtype)
+ data = _eet_data_descriptor_encode(ed,
+ ede->subtype,
+ hdata,
+ &size);
+
+ if (data)
+ {
+ echnk = eet_data_chunk_new(data,
+ size,
+ ede->name,
+ ede->type,
+ ede->group_type);
+ eet_data_chunk_put(ed, echnk, ds);
+ eet_data_chunk_free(echnk);
+ free(data);
+ data = NULL;
+ }
}
return 1;
}
static char *
-_eet_data_string_escape(const char *str)
-{
- char *s, *sp;
- const char *strp;
- int sz = 0;
-
- for (strp = str; *strp; strp++)
- {
- if (*strp == '\"') sz += 2;
- else if (*strp == '\\') sz += 2;
- else sz += 1;
- }
- s = malloc(sz + 1);
- if (!s) return NULL;
- for (strp = str, sp = s; *strp; strp++, sp++)
- {
- if (*strp == '\"')
- {
- *sp = '\\';
- sp++;
- }
- else if (*strp == '\\')
- {
- *sp = '\\';
- sp++;
- }
- *sp = *strp;
- }
- *sp = 0;
- return s;
-}
-
-static void
-_eet_data_dump_string_escape(void *dumpdata, void dumpfunc(void *data, const char *str), const char *str)
-{
- char *s;
-
- s = _eet_data_string_escape(str);
- if (s)
- {
- dumpfunc(dumpdata, s);
- free(s);
- }
-}
-
-static char *
-_eet_data_dump_token_get(const char *src, int *len)
+_eet_data_dump_token_get(const char *src,
+ int *len)
{
const char *p;
char *tok = NULL;
int in_quote = 0;
int tlen = 0, tsize = 0;
-#define TOK_ADD(x) \
- { \
- tlen++; \
- if (tlen >= tsize) \
- { \
- tsize += 32; \
- tok = realloc(tok, tsize); \
- } \
- tok[tlen - 1] = x; \
- }
+#define TOK_ADD(x) \
+ do { \
+ tlen++; \
+ if (tlen >= tsize) \
+ { \
+ tsize += 32; \
+ tok = realloc(tok, tsize); \
+ } \
+ tok[tlen - 1] = x; \
+ } while (0)
for (p = src; *len > 0; p++, (*len)--)
{
- if (in_token)
- {
- if (in_quote)
- {
- if ((p[0] == '\"') && (p > src) && (p[-1] != '\\'))
- {
- in_quote = 0;
- }
- else if ((p[0] == '\\') && (*len > 1) && (p[1] == '\"'))
- {
- /* skip */
- }
- else if ((p[0] == '\\') && (p > src) && (p[-1] == '\\'))
- {
- /* skip */
- }
- else
- TOK_ADD(p[0]);
- }
- else
- {
- if (p[0] == '\"') in_quote = 1;
- else
- {
- if ((isspace(p[0])) || (p[0] == ';')) /* token ends here */
- {
- TOK_ADD(0);
- (*len)--;
- return tok;
- }
- else
- TOK_ADD(p[0]);
- }
- }
- }
- else
- {
- if (!((isspace(p[0])) || (p[0] == ';')))
- {
- in_token = 1;
- (*len)++;
- p--;
- }
- }
+ if (in_token)
+ {
+ if (in_quote)
+ {
+ if ((p[0] == '\"') && (p > src) && (p[-1] != '\\'))
+ in_quote = 0;
+ else if ((p[0] == '\\') && (*len > 1) &&
+ (p[1] == '\"'))
+ {
+/* skip */
+ }
+ else if ((p[0] == '\\') && (p > src) && (p[-1] == '\\'))
+ {
+/* skip */
+ }
+ else if ((p[0] == '\\') && (*len > 1) && (p[1] == 'n'))
+ {
+/* skip */
+ }
+ else if ((p[0] == 'n') && (p > src) && (p[-1] == '\\'))
+ TOK_ADD('\n');
+ else
+ TOK_ADD(p[0]);
+ }
+ else
+ {
+ if (p[0] == '\"')
+ in_quote = 1;
+ else
+ {
+ if ((isspace(p[0])) || (p[0] == ';')) /* token ends here */
+ {
+ TOK_ADD(0);
+ (*len)--;
+ return tok;
+ }
+ else
+ TOK_ADD(p[0]);
+ }
+ }
+ }
+ else if (!((isspace(p[0])) || (p[0] == ';')))
+ {
+ in_token = 1;
+ (*len)++;
+ p--;
+ }
}
if (in_token)
{
- TOK_ADD(0);
- return tok;
+ TOK_ADD(0);
+ return tok;
}
- if (tok) free(tok);
+
+ if (tok)
+ free(tok);
+
return NULL;
}
-typedef struct _Node Node;
-
-struct _Node
-{
- int type;
- int count;
- char *name;
- char *key;
- Node *values;
- Node *prev;
- Node *next;
- Node *parent;
- union {
- char c;
- short s;
- int i;
- long long l;
- float f;
- double d;
- unsigned char uc;
- unsigned short us;
- unsigned int ui;
- unsigned long long ul;
- char *str;
- } data;
-};
-
static void
-_eet_data_dump_free(Node *node)
+eet_data_encode(Eet_Dictionary *ed,
+ Eet_Data_Stream *ds,
+ void *data,
+ const char *name,
+ int size,
+ int type,
+ int group_type)
{
- Node *n, *n2;
+ Eet_Data_Chunk *echnk;
- switch (node->type)
- {
- case EET_G_UNKNOWN:
- case EET_G_ARRAY:
- case EET_G_VAR_ARRAY:
- case EET_G_LIST:
- case EET_G_HASH:
- if (node->key) free(node->key);
- for (n = node->values; n;)
- {
- n2 = n;
- n = n->next;
- _eet_data_dump_free(n2);
- }
- break;
- case EET_T_CHAR:
- case EET_T_SHORT:
- case EET_T_INT:
- case EET_T_LONG_LONG:
- case EET_T_FLOAT:
- case EET_T_DOUBLE:
- case EET_T_UCHAR:
- case EET_T_USHORT:
- case EET_T_UINT:
- case EET_T_ULONG_LONG:
- case EET_T_NULL:
- break;
- case EET_T_INLINED_STRING:
- case EET_T_STRING:
- if (node->data.str) free(node->data.str);
- break;
- default:
- break;
- }
- free(node);
+ if (!data)
+ type = EET_T_NULL;
+
+ if (group_type != EET_G_UNKNOWN)
+ if (type >= EET_T_LAST)
+ type = EET_T_UNKNOW;
+
+ echnk = eet_data_chunk_new(data, size, name, type, group_type);
+ eet_data_chunk_put(ed, echnk, ds);
+ eet_data_chunk_free(echnk);
+ free(data);
}
static void *
-_eet_data_dump_encode(Eet_Dictionary *ed,
- Node *node,
- int *size_ret)
+_eet_data_dump_encode(int parent_type,
+ Eet_Dictionary *ed,
+ Eet_Node *node,
+ int *size_ret)
{
- Eet_Data_Chunk *chnk = NULL, *echnk = NULL;
+ Eet_Data_Chunk *chnk = NULL;
Eet_Data_Stream *ds;
void *cdata, *data;
int csize, size;
- Node *n;
+ int count;
+ int child_type;
+ Eet_Node *n;
- if (words_bigendian == -1)
+ if (_eet_data_words_bigendian == -1)
{
- unsigned long int v;
+ unsigned long int v;
- v = htonl(0x12345678);
- if (v == 0x12345678) words_bigendian = 1;
- else words_bigendian = 0;
+ v = htonl(0x12345678);
+ if (v == 0x12345678)
+ _eet_data_words_bigendian = 1;
+ else
+ _eet_data_words_bigendian = 0;
}
+ if (!node)
+ return NULL;
+
ds = eet_data_stream_new();
- if (!ds) return NULL;
+ if (!ds)
+ return NULL;
switch (node->type)
{
case EET_G_UNKNOWN:
- for (n = node->values; n; n = n->next)
- {
- data = _eet_data_dump_encode(ed, n, &size);
- if (data)
- {
- eet_data_stream_write(ds, data, size);
- free(data);
- }
- }
- break;
+ for (n = node->values; n; n = n->next)
+ {
+ data = _eet_data_dump_encode(node->type, ed, n, &size);
+ if (data)
+ {
+ eet_data_stream_write(ds, data, size);
+ free(data);
+ }
+ }
+ break;
+
case EET_G_ARRAY:
case EET_G_VAR_ARRAY:
- data = eet_data_put_type(ed,
- EET_T_INT,
- &node->count,
- &size);
- if (data)
- {
- echnk = eet_data_chunk_new(data, size, node->name, node->type, node->type);
- eet_data_chunk_put(ed, echnk, ds);
- eet_data_chunk_free(echnk);
- free(data);
- }
- for (n = node->values; n; n = n->next)
- {
- data = _eet_data_dump_encode(ed, n, &size);
- if (data)
- {
- echnk = eet_data_chunk_new(data, size, node->name, node->type, node->type);
- eet_data_chunk_put(ed, echnk, ds);
- eet_data_chunk_free(echnk);
- free(data);
- }
- }
-
- /* Array is somekind of special case, so we should embed it inside another chunk. */
- *size_ret = ds->pos;
- cdata = ds->data;
-
- ds->data = NULL;
- ds->size = 0;
- eet_data_stream_free(ds);
-
- return cdata;
+ for (child_type = EET_T_NULL, n = node->values; n; n = n->next)
+ {
+ if (n->type != EET_T_NULL)
+ {
+ child_type = n->type;
+ break;
+ }
+ }
+
+ data = eet_data_put_type(ed,
+ EET_T_INT,
+ &node->count,
+ &size);
+ eet_data_encode(ed,
+ ds,
+ data,
+ node->name,
+ size,
+ child_type,
+ node->type);
+
+ count = node->count;
+
+ for (n = node->values; n; n = n->next)
+ {
+ int pos = ds->pos;
+
+ switch (n->type)
+ {
+ case EET_T_STRING:
+ case EET_T_INLINED_STRING:
+ data = eet_data_put_type(ed,
+ n->type,
+ &(n->data.value.str),
+ &size);
+ if (data)
+ eet_data_encode(ed,
+ ds,
+ data,
+ node->name,
+ size,
+ n->type,
+ node->type);
+
+ break;
+
+ case EET_T_NULL:
+ continue;
+
+ default:
+ data = _eet_data_dump_encode(n->type, ed, n, &size);
+ eet_data_encode(ed,
+ ds,
+ data,
+ node->name,
+ size,
+ n->type,
+ node->type);
+ break;
+ } /* switch */
+ if (ds->pos != pos)
+ count--;
+ }
+
+ for (; count; count--)
+ {
+ eet_data_encode(ed,
+ ds,
+ NULL,
+ node->name,
+ 0,
+ EET_T_NULL,
+ node->type);
+ }
+
+ /* Array is somekind of special case, so we should embed it inside another chunk. */
+ *size_ret = ds->pos;
+ cdata = ds->data;
+
+ ds->data = NULL;
+ ds->size = 0;
+ eet_data_stream_free(ds);
+
+ return cdata;
+ break;
+
case EET_G_LIST:
- for (n = node->values; n; n = n->next)
- {
- data = _eet_data_dump_encode(ed, n, &size);
- if (data)
- {
- eet_data_stream_write(ds, data, size);
- free(data);
- }
- }
- break;
+ for (n = node->values; n; n = n->next)
+ {
+ switch (n->type)
+ {
+ case EET_T_STRING:
+ case EET_T_INLINED_STRING:
+ data = eet_data_put_type(ed,
+ n->type,
+ &(n->data.value.str),
+ &size);
+ if (data)
+ eet_data_encode(ed,
+ ds,
+ data,
+ node->name,
+ size,
+ n->type,
+ node->type);
+
+ break;
+
+ case EET_T_NULL:
+ continue;
+
+ default:
+ data = _eet_data_dump_encode(node->type, ed, n, &size);
+ eet_data_encode(ed,
+ ds,
+ data,
+ node->name,
+ size,
+ n->type,
+ node->type);
+ } /* switch */
+ }
+
+ /* List is another somekind of special case, every chunk is embed inside a list chunk. */
+ *size_ret = ds->pos;
+ cdata = ds->data;
+
+ ds->data = NULL;
+ ds->size = 0;
+ eet_data_stream_free(ds);
+
+ return cdata;
+ break;
+
case EET_G_HASH:
- if (node->key)
- {
- data = eet_data_put_type(ed,
+ if (node->key)
+ {
+ data = eet_data_put_type(ed,
EET_T_STRING,
- &node->key,
- &size);
- if (data)
- {
- echnk = eet_data_chunk_new(data, size, node->name, node->type, node->type);
- eet_data_chunk_put(ed, echnk, ds);
- eet_data_chunk_free(echnk);
- free(data);
- }
- }
- for (n = node->values; n; n = n->next)
- {
- data = _eet_data_dump_encode(ed, n, &size);
- if (data)
- {
- echnk = eet_data_chunk_new(data, size, node->name, node->type, node->type);
- eet_data_chunk_put(ed, echnk, ds);
- eet_data_chunk_free(echnk);
- free(data);
- }
- }
-
- /* Hash is somekind of special case, so we should embed it inside another chunk. */
- *size_ret = ds->pos;
- cdata = ds->data;
-
- ds->data = NULL;
- ds->size = 0;
- eet_data_stream_free(ds);
-
- return cdata;
+ &node->key,
+ &size);
+ eet_data_encode(ed,
+ ds,
+ data,
+ node->name,
+ size,
+ node->type,
+ node->type);
+ }
+ else
+ /* A Hash without key will not decode correctly. */
+ return NULL;
+
+ for (n = node->values; n; n = n->next)
+ {
+ switch (n->type)
+ {
+ case EET_T_STRING:
+ case EET_T_INLINED_STRING:
+ data = eet_data_put_type(ed,
+ n->type,
+ &(n->data.value.str),
+ &size);
+ if (data)
+ eet_data_encode(ed,
+ ds,
+ data,
+ node->name,
+ size,
+ n->type,
+ node->type);
+
+ break;
+
+ case EET_T_NULL:
+ continue;
+
+ default:
+ data = _eet_data_dump_encode(node->type, ed, n, &size);
+ eet_data_encode(ed,
+ ds,
+ data,
+ node->name,
+ size,
+ n->type,
+ node->type);
+ } /* switch */
+ }
+
+ /* Hash is somekind of special case, so we should embed it inside another chunk. */
+ *size_ret = ds->pos;
+ cdata = ds->data;
+
+ eet_data_stream_flush(ds);
+
+ return cdata;
+
case EET_T_NULL:
- break;
- case EET_T_CHAR:
- data = eet_data_put_type(ed, node->type, &(node->data.c), &size);
- if (data)
- {
- eet_data_stream_write(ds, data, size);
- free(data);
- }
- break;
- case EET_T_SHORT:
- data = eet_data_put_type(ed, node->type, &(node->data.s), &size);
- if (data)
- {
- eet_data_stream_write(ds, data, size);
- free(data);
- }
- break;
- case EET_T_INT:
- data = eet_data_put_type(ed, node->type, &(node->data.i), &size);
- if (data)
- {
- eet_data_stream_write(ds, data, size);
- free(data);
- }
- break;
- case EET_T_LONG_LONG:
- data = eet_data_put_type(ed, node->type, &(node->data.l), &size);
- if (data)
- {
- eet_data_stream_write(ds, data, size);
- free(data);
- }
- break;
- case EET_T_FLOAT:
- data = eet_data_put_type(ed, node->type, &(node->data.f), &size);
- if (data)
- {
- eet_data_stream_write(ds, data, size);
- free(data);
- }
- break;
- case EET_T_DOUBLE:
- data = eet_data_put_type(ed, node->type, &(node->data.d), &size);
- if (data)
- {
- eet_data_stream_write(ds, data, size);
- free(data);
- }
- break;
- case EET_T_UCHAR:
- data = eet_data_put_type(ed, node->type, &(node->data.uc), &size);
- if (data)
- {
- eet_data_stream_write(ds, data, size);
- free(data);
- }
- break;
- case EET_T_USHORT:
- data = eet_data_put_type(ed, node->type, &(node->data.us), &size);
- if (data)
- {
- eet_data_stream_write(ds, data, size);
- free(data);
- }
- break;
- case EET_T_UINT:
- data = eet_data_put_type(ed, node->type, &(node->data.ui), &size);
- if (data)
- {
- eet_data_stream_write(ds, data, size);
- free(data);
- }
- break;
- case EET_T_ULONG_LONG:
- data = eet_data_put_type(ed, node->type, &(node->data.ul), &size);
- if (data)
- {
- eet_data_stream_write(ds, data, size);
- free(data);
- }
- break;
- case EET_T_INLINED_STRING:
- data = eet_data_put_type(ed, node->type, &(node->data.str), &size);
- if (data)
- {
- eet_data_stream_write(ds, data, size);
- free(data);
- }
- break;
- case EET_T_STRING:
- data = eet_data_put_type(ed, node->type, &(node->data.str), &size);
- if (data)
- {
- eet_data_stream_write(ds, data, size);
- free(data);
- }
- break;
+ break;
+
+#define EET_DATA_NODE_ENCODE(Eet_Type, Type) \
+case Eet_Type: \
+ data = eet_data_put_type(ed, node->type, &(node->data.value.Type), &size); \
+ if (data) \
+ { \
+ eet_data_encode(ed, \
+ ds, \
+ data, \
+ node->name, \
+ size, \
+ node->type, \
+ parent_type); \
+ cdata = ds->data; \
+ *size_ret = ds->pos; \
+ eet_data_stream_flush(ds); \
+ return cdata; \
+ } /* switch */ \
+ break;
+
+ EET_DATA_NODE_ENCODE(EET_T_CHAR, c);
+ EET_DATA_NODE_ENCODE(EET_T_SHORT, s);
+ EET_DATA_NODE_ENCODE(EET_T_INT, i);
+ EET_DATA_NODE_ENCODE(EET_T_LONG_LONG, l);
+ EET_DATA_NODE_ENCODE(EET_T_FLOAT, f);
+ EET_DATA_NODE_ENCODE(EET_T_DOUBLE, d);
+ EET_DATA_NODE_ENCODE(EET_T_UCHAR, uc);
+ EET_DATA_NODE_ENCODE(EET_T_USHORT, us);
+ EET_DATA_NODE_ENCODE(EET_T_UINT, ui);
+ EET_DATA_NODE_ENCODE(EET_T_ULONG_LONG, ul);
+ EET_DATA_NODE_ENCODE(EET_T_INLINED_STRING, str);
+ EET_DATA_NODE_ENCODE(EET_T_STRING, str);
+
default:
- break;
+ break;
}
if ((node->type >= EET_G_UNKNOWN) && (node->type < EET_G_LAST))
- chnk = eet_data_chunk_new(ds->data, ds->pos, node->name, EET_T_UNKNOW, node->type);
+ chnk = eet_data_chunk_new(ds->data,
+ ds->pos,
+ node->name,
+ EET_T_UNKNOW,
+ node->type);
else
- chnk = eet_data_chunk_new(ds->data, ds->pos, node->name, node->type, EET_G_UNKNOWN);
- ds->data = NULL;
- ds->size = 0;
- eet_data_stream_free(ds);
+ chnk = eet_data_chunk_new(ds->data,
+ ds->pos,
+ node->name,
+ node->type,
+ EET_G_UNKNOWN);
+
+ eet_data_stream_flush(ds);
ds = eet_data_stream_new();
eet_data_chunk_put(ed, chnk, ds);
cdata = ds->data;
csize = ds->pos;
- ds->data = NULL;
- ds->size = 0;
- eet_data_stream_free(ds);
+ eet_data_stream_flush(ds);
*size_ret = csize;
free(chnk->data);
static void *
_eet_data_dump_parse(Eet_Dictionary *ed,
- int *size_ret,
- const char *src,
- int size)
+ int *size_ret,
+ const char *src,
+ int size)
{
void *cdata = NULL;
- const char *p;
-#define M_NONE 0
+ const char *p = NULL;
+#define M_NONE 0
#define M_STRUCT 1
-#define M_ 2
+#define M_ 2
int left, jump;
- Node *node_base = NULL;
- Node *node = NULL;
- Node *n, *nn;
+ Eet_Node *node_base = NULL;
+ Eet_Node *node = NULL;
+ Eet_Node *n = NULL, *nn = NULL;
/* FIXME; handle parse errors */
#define TOK_GET(t) \
- jump = left; t = _eet_data_dump_token_get(p, &left); p += jump - left;
+ jump = left; t = _eet_data_dump_token_get(p, &left); p += jump - left;
left = size;
- for (p = src; p < (src + size);)
- {
- char *tok1, *tok2, *tok3, *tok4;
-
- TOK_GET(tok1);
- if (tok1)
- {
- if (!strcmp(tok1, "group"))
- {
- TOK_GET(tok2);
- if (tok2)
- {
- TOK_GET(tok3);
- if (tok3)
- {
- TOK_GET(tok4);
- if (tok4)
- {
- if (!strcmp(tok4, "{"))
- {
- /* we have 'group NAM TYP {' */
- n = calloc(1, sizeof(Node));
- if (n)
- {
- n->parent = node;
- if (!node_base)
- {
- node_base = n;
- }
- if (node)
- {
- /* append node */
- if (!node->values)
- node->values = n;
- else
- {
- for (nn = node->values; nn; nn = nn->next)
- {
- if (!nn->next)
- {
- nn->next = n;
- n->prev = nn;
- break;
- }
- }
- }
- }
- n->name = strdup(tok2);
- if (!strcmp(tok3, "struct")) n->type = EET_G_UNKNOWN;
- else if (!strcmp(tok3, "array")) n->type = EET_G_ARRAY;
- else if (!strcmp(tok3, "var_array")) n->type = EET_G_VAR_ARRAY;
- else if (!strcmp(tok3, "list")) n->type = EET_G_LIST;
- else if (!strcmp(tok3, "hash")) n->type = EET_G_HASH;
- else
- {
- printf("ERROR: group type '%s' invalid.\n", tok3);
- }
- node = n;
- }
- }
- free(tok4);
- }
- free(tok3);
- }
- free(tok2);
- }
- }
- else if (!strcmp(tok1, "value"))
- {
- TOK_GET(tok2);
- if (tok2)
- {
- TOK_GET(tok3);
- if (tok3)
- {
- TOK_GET(tok4);
- if (tok4)
- {
- /* we have 'value NAME TYP XXX' */
- if (node_base)
- {
- n = calloc(1, sizeof(Node));
- if (n)
- {
- n->parent = node;
- /* append node */
- if (!node->values)
- node->values = n;
- else
- {
- for (nn = node->values; nn; nn = nn->next)
- {
- if (!nn->next)
- {
- nn->next = n;
- n->prev = nn;
- break;
- }
- }
- }
- n->name = strdup(tok2);
- if (!strcmp(tok3, "char:"))
- {
- n->type = EET_T_CHAR;
- sscanf(tok4, "%hhi", &(n->data.c));
- }
- else if (!strcmp(tok3, "short:"))
- {
- n->type = EET_T_SHORT;
- sscanf(tok4, "%hi", &(n->data.s));
- }
- else if (!strcmp(tok3, "int:"))
- {
- n->type = EET_T_INT;
- sscanf(tok4, "%i", &(n->data.i));
- }
- else if (!strcmp(tok3, "long_long:"))
- {
- n->type = EET_T_LONG_LONG;
- sscanf(tok4, "%lli", &(n->data.l));
- }
- else if (!strcmp(tok3, "float:"))
- {
- n->type = EET_T_FLOAT;
- sscanf(tok4, "%f", &(n->data.f));
- }
- else if (!strcmp(tok3, "double:"))
- {
- n->type = EET_T_DOUBLE;
- sscanf(tok4, "%lf", &(n->data.d));
- }
- else if (!strcmp(tok3, "uchar:"))
- {
- n->type = EET_T_UCHAR;
- sscanf(tok4, "%hhu", &(n->data.uc));
- }
- else if (!strcmp(tok3, "ushort:"))
- {
- n->type = EET_T_USHORT;
- sscanf(tok4, "%hu", &(n->data.us));
- }
- else if (!strcmp(tok3, "uint:"))
- {
- n->type = EET_T_UINT;
- sscanf(tok4, "%u", &(n->data.ui));
- }
- else if (!strcmp(tok3, "ulong_long:"))
- {
- n->type = EET_T_ULONG_LONG;
- sscanf(tok4, "%llu", &(n->data.ul));
- }
- else if (!strcmp(tok3, "string:"))
- {
- n->type = EET_T_STRING;
- n->data.str = strdup(tok4);
- }
- else if (!strcmp(tok3, "inlined:"))
- {
- n->type = EET_T_INLINED_STRING;
- n->data.str = strdup(tok4);
- }
- else if (!strcmp(tok3, "null"))
- {
- n->type = EET_T_NULL;
- n->data.str = NULL;
- }
- else
- {
- printf("ERROR: value type '%s' invalid.\n", tok4);
- }
- }
- }
- free(tok4);
- }
- free(tok3);
- }
- free(tok2);
- }
- }
- else if (!strcmp(tok1, "key"))
- {
- TOK_GET(tok2);
- if (tok2)
- {
- /* we have 'key NAME' */
- if (node)
- {
- node->key = strdup(tok2);
- }
- free(tok2);
- }
- }
- else if (!strcmp(tok1, "count"))
- {
- TOK_GET(tok2);
- if (tok2)
- {
- /* we have a 'count COUNT' */
- if (node)
- {
- sscanf(tok2, "%i", &(node->count));
- }
- free(tok2);
- }
- }
- else if (!strcmp(tok1, "}"))
- {
- /* we have an end of the group */
- if (node) node = node->parent;
- }
- free(tok1);
- }
+ for (p = src; p < (src + size); )
+ {
+ char *tok1, *tok2, *tok3, *tok4;
+
+ TOK_GET(tok1);
+ if (tok1)
+ {
+ if (!strcmp(tok1, "group"))
+ {
+ TOK_GET(tok2);
+ if (tok2)
+ {
+ TOK_GET(tok3);
+ if (tok3)
+ {
+ TOK_GET(tok4);
+ if (tok4)
+ {
+ if (!strcmp(tok4, "{"))
+ {
+/* we have 'group NAM TYP {' */
+ n = eet_node_new();
+ if (n)
+ {
+ n->parent = node;
+ if (!node_base)
+ node_base = n;
+
+ if (node)
+ {
+/* append node */
+ if (!node->values)
+ node->values = n;
+ else
+ for (nn = node->values; nn;
+ nn = nn->next)
+ {
+ if (!nn->next)
+ {
+ nn->next = n;
+ break;
+ }
+ }
+ }
+
+ n->name = eina_stringshare_add(tok2);
+ if (!strcmp(tok3, "struct"))
+ n->type = EET_G_UNKNOWN;
+ else if (!strcmp(tok3, "array"))
+ n->type = EET_G_ARRAY;
+ else if (!strcmp(tok3, "var_array"))
+ n->type = EET_G_VAR_ARRAY;
+ else if (!strcmp(tok3, "list"))
+ n->type = EET_G_LIST;
+ else if (!strcmp(tok3, "hash"))
+ n->type = EET_G_HASH;
+ else
+ ERR(
+ "ERROR: group type '%s' invalid.",
+ tok3);
+
+ node = n;
+ }
+ }
+
+ free(tok4);
+ }
+
+ free(tok3);
+ }
+
+ free(tok2);
+ }
+ }
+ else if (!strcmp(tok1, "value"))
+ {
+ TOK_GET(tok2);
+ if (tok2)
+ {
+ TOK_GET(tok3);
+ if (tok3)
+ {
+ TOK_GET(tok4);
+ if (tok4)
+ {
+/* we have 'value NAME TYP XXX' */
+ if (node_base)
+ {
+ n = eet_node_new();
+ if (n)
+ {
+ n->parent = node;
+/* append node */
+ if (!node->values)
+ node->values = n;
+ else
+ for (nn = node->values; nn;
+ nn = nn->next)
+ {
+ if (!nn->next)
+ {
+ nn->next = n;
+ break;
+ }
+ }
+
+ n->name = eina_stringshare_add(tok2);
+ if (!strcmp(tok3, "char:"))
+ {
+ n->type = EET_T_CHAR;
+ sscanf(tok4, "%hhi",
+ &(n->data.value.c));
+ }
+ else if (!strcmp(tok3, "short:"))
+ {
+ n->type = EET_T_SHORT;
+ sscanf(tok4, "%hi",
+ &(n->data.value.s));
+ }
+ else if (!strcmp(tok3, "int:"))
+ {
+ n->type = EET_T_INT;
+ sscanf(tok4, "%i",
+ &(n->data.value.i));
+ }
+ else if (!strcmp(tok3, "long_long:"))
+ {
+ n->type = EET_T_LONG_LONG;
+ sscanf(tok4, "%lli",
+ &(n->data.value.l));
+ }
+ else if (!strcmp(tok3, "float:"))
+ {
+ n->type = EET_T_FLOAT;
+ sscanf(tok4, "%f",
+ &(n->data.value.f));
+ }
+ else if (!strcmp(tok3, "double:"))
+ {
+ n->type = EET_T_DOUBLE;
+ sscanf(tok4, "%lf",
+ &(n->data.value.d));
+ }
+ else if (!strcmp(tok3, "uchar:"))
+ {
+ n->type = EET_T_UCHAR;
+ sscanf(tok4, "%hhu",
+ &(n->data.value.uc));
+ }
+ else if (!strcmp(tok3, "ushort:"))
+ {
+ n->type = EET_T_USHORT;
+ sscanf(tok4, "%hu",
+ &(n->data.value.us));
+ }
+ else if (!strcmp(tok3, "uint:"))
+ {
+ n->type = EET_T_UINT;
+ sscanf(tok4, "%u",
+ &(n->data.value.ui));
+ }
+ else if (!strcmp(tok3, "ulong_long:"))
+ {
+ n->type = EET_T_ULONG_LONG;
+ sscanf(tok4, "%llu",
+ &(n->data.value.ul));
+ }
+ else if (!strcmp(tok3, "string:"))
+ {
+ n->type = EET_T_STRING;
+ n->data.value.str =
+ eina_stringshare_add(tok4);
+ }
+ else if (!strcmp(tok3, "inlined:"))
+ {
+ n->type = EET_T_INLINED_STRING;
+ n->data.value.str =
+ eina_stringshare_add(tok4);
+ }
+ else if (!strcmp(tok3, "null"))
+ {
+ n->type = EET_T_NULL;
+ n->data.value.str = NULL;
+ }
+ else
+ ERR(
+ "ERROR: value type '%s' invalid.",
+ tok4);
+ }
+ }
+
+ free(tok4);
+ }
+
+ free(tok3);
+ }
+
+ free(tok2);
+ }
+ }
+ else if (!strcmp(tok1, "key"))
+ {
+ TOK_GET(tok2);
+ if (tok2)
+ {
+/* we have 'key NAME' */
+ if (node)
+ node->key = eina_stringshare_add(tok2);
+
+ free(tok2);
+ }
+ }
+ else if (!strcmp(tok1, "count"))
+ {
+ TOK_GET(tok2);
+ if (tok2)
+ {
+/* we have a 'count COUNT' */
+ if (node)
+ sscanf(tok2, "%i", &(node->count));
+
+ free(tok2);
+ }
+ }
+ else if (!strcmp(tok1, "}"))
+ /* we have an end of the group */
+ if (node)
+ node = node->parent;
+
+ free(tok1);
+ }
}
if (node_base)
{
- cdata = _eet_data_dump_encode(ed, node_base, size_ret);
- _eet_data_dump_free(node_base);
+ cdata = _eet_data_dump_encode(EET_G_UNKNOWN, ed, node_base, size_ret);
+ eet_node_del(node_base);
}
+
return cdata;
}
-#define NEXT_CHUNK(P, Size, Echnk, Ed) \
- { \
- int tmp; \
- tmp = Ed ? (int) (sizeof(int) * 2) : Echnk.len + 4;\
- P += (4 + Echnk.size + tmp); \
- Size -= (4 + Echnk.size + tmp); \
+#define NEXT_CHUNK(P, Size, Echnk, Ed) \
+ { \
+ int __tmp; \
+ __tmp = Ed ? (int)(sizeof(int) * 2) : Echnk.len + 4; \
+ P += (4 + Echnk.size + __tmp); \
+ Size -= (4 + Echnk.size + __tmp); \
}
static void *
-_eet_data_descriptor_decode(const Eet_Dictionary *ed,
- Eet_Data_Descriptor *edd,
- const void *data_in,
- int size_in,
- int level,
- void (*dumpfunc) (void *data, const char *str),
- void *dumpdata)
+_eet_data_descriptor_decode(Eet_Free_Context *context,
+ const Eet_Dictionary *ed,
+ Eet_Data_Descriptor *edd,
+ const void *data_in,
+ int size_in,
+ void *data_out,
+ int size_out)
{
+ Eet_Node *result = NULL;
void *data = NULL;
- char *p, tbuf[256];
- int size, i, dump;
+ char *p;
+ int size, i;
Eet_Data_Chunk chnk;
- if (words_bigendian == -1)
+ if (_eet_data_words_bigendian == -1)
{
- unsigned long int v;
+ unsigned long int v;
- v = htonl(0x12345678);
- if (v == 0x12345678) words_bigendian = 1;
- else words_bigendian = 0;
+ v = htonl(0x12345678);
+ if (v == 0x12345678)
+ _eet_data_words_bigendian = 1;
+ else
+ _eet_data_words_bigendian = 0;
}
if (edd)
{
- data = edd->func.mem_alloc(edd->size);
- if (!data) return NULL;
- if (edd->ed != ed)
- {
- for (i = 0; i < edd->elements.num; i++)
- edd->elements.set[i].directory_name_ptr = NULL;
- edd->ed = ed;
- }
- }
- _eet_freelist_ref();
- _eet_freeleak_ref();
- _eet_freelist_str_ref();
- _eet_freelist_list_ref();
- if (data) _eet_freelist_add(data);
- dump = 0;
+ if (data_out)
+ {
+ if (size_out <= edd->size)
+ data = data_out;
+ }
+ else
+ {
+ data = edd->func.mem_alloc(edd->size);
+ }
+
+ if (!data)
+ return NULL;
+
+ if (edd->ed != ed)
+ {
+ for (i = 0; i < edd->elements.num; i++)
+ edd->elements.set[i].directory_name_ptr = NULL;
+ edd->ed = ed;
+ }
+ }
+
+ _eet_freelist_all_ref(context);
+ if (data && !data_out)
+ _eet_freelist_add(context, data);
+
memset(&chnk, 0, sizeof(Eet_Data_Chunk));
eet_data_chunk_get(ed, &chnk, data_in, size_in);
- if (!chnk.name) goto error;
+ if (!chnk.name)
+ goto error;
+
if (edd)
- {
- if (strcmp(chnk.name, edd->name)) goto error;
- }
+ if (strcmp(chnk.name, edd->name))
+ goto error;
+
p = chnk.data;
if (ed)
size = size_in - (4 + sizeof(int) * 2);
else
- size = size_in - (4 + 4 + chnk.len);
- if (edd)
+ size = size_in - (4 + 4 + chnk.len);
+
+ if (edd)
+ {
+ if (!edd->elements.hash.buckets)
+ _eet_descriptor_hash_new(edd);
+ }
+ else
{
- if (!edd->elements.hash.buckets) _eet_descriptor_hash_new(edd);
- }
- if (dumpfunc)
- {
- dump = 1;
- if (chnk.type == EET_T_UNKNOW)
- {
- for (i = 0; i < level; i++) dumpfunc(dumpdata, " ");
- dumpfunc(dumpdata, "group \"");
- _eet_data_dump_string_escape(dumpdata, dumpfunc, chnk.name);
- dumpfunc(dumpdata, "\" ");
- switch (chnk.group_type)
- {
- case EET_G_UNKNOWN:
- dumpfunc(dumpdata, "struct");
- break;
- case EET_G_ARRAY:
- dumpfunc(dumpdata, "array");
- break;
- case EET_G_VAR_ARRAY:
- dumpfunc(dumpdata, "var_array");
- break;
- case EET_G_LIST:
- dumpfunc(dumpdata, "list");
- break;
- case EET_G_HASH:
- dumpfunc(dumpdata, "hash");
- break;
- default:
- dumpfunc(dumpdata, "???");
- break;
- }
- dumpfunc(dumpdata, " {\n");
- }
+ switch (chnk.group_type)
+ {
+ case EET_G_UNKNOWN:
+ switch (chnk.type)
+ {
+ case EET_T_STRING:
+ return eet_node_string_new(chnk.name, chnk.data);
+
+ case EET_T_INLINED_STRING:
+ return eet_node_inlined_string_new(chnk.name, chnk.data);
+
+ case EET_T_NULL:
+ return eet_node_null_new(chnk.name);
+
+ default:
+ result = eet_node_struct_new(chnk.name, NULL);
+ } /* switch */
+ break;
+
+ case EET_G_VAR_ARRAY:
+ return eet_node_var_array_new(chnk.name, NULL);
+
+ case EET_G_LIST:
+ case EET_G_HASH:
+ case EET_G_ARRAY:
+ case EET_G_UNION:
+ case EET_G_VARIANT:
+ default:
+ goto error;
+ }
}
+
while (size > 0)
{
- Eet_Data_Chunk echnk;
- Eet_Data_Element *ede;
-
- /* get next data chunk */
- memset(&echnk, 0, sizeof(Eet_Data_Chunk));
- eet_data_chunk_get(ed, &echnk, p, size);
- if (!echnk.name) goto error;
- /* FIXME: don't REPLY on edd - work without */
- if ((edd) && (!dumpfunc))
- {
- ede = _eet_descriptor_hash_find(edd, echnk.name, echnk.hash);
- if (ede)
- {
- int group_type = EET_G_UNKNOWN, type = EET_T_UNKNOW;
- int ret = 0;
-
- group_type = ede->group_type;
- type = ede->type;
- if ((echnk.type == 0) && (echnk.group_type == 0))
- {
- type = ede->type;
- group_type = ede->group_type;
- }
- else
- {
- if (IS_SIMPLE_TYPE(echnk.type) &&
- (echnk.type == ede->type))
- type = echnk.type;
- else if ((echnk.group_type > EET_G_UNKNOWN) &&
- (echnk.group_type < EET_G_LAST) &&
- (echnk.group_type == ede->group_type))
- group_type = echnk.group_type;
- }
- /* hashes doesnt fit well with the table */
- ret = eet_group_codec[group_type - 100].get(ed, edd, ede, &echnk, type, group_type, ((char *)data) + ede->offset, level, dumpfunc, dumpdata, &p, &size);
- if (ret <= 0) goto error;
- }
- }
- /*...... dump func */
- else if (dumpfunc)
- {
- unsigned char dd[128];
- int group_type = EET_G_UNKNOWN, type = EET_T_UNKNOW;
-
- if ((echnk.type > EET_T_UNKNOW) &&
- (echnk.type < EET_T_LAST))
- type = echnk.type;
- else if ((echnk.group_type > EET_G_UNKNOWN) &&
- (echnk.group_type < EET_G_LAST))
- group_type = echnk.group_type;
- if (group_type == EET_G_UNKNOWN)
- {
- int ret;
- void *data_ret;
-
- if (IS_SIMPLE_TYPE(type))
- {
- ret = eet_data_get_type(ed,
- type,
- echnk.data,
- ((char *)echnk.data) + echnk.size,
- dd);
- if (ret <= 0) goto error;
-
- for (i = 0; i < level; i++) dumpfunc(dumpdata, " ");
- dumpfunc(dumpdata, " value \"");
- _eet_data_dump_string_escape(dumpdata, dumpfunc, echnk.name);
- dumpfunc(dumpdata, "\" ");
- switch (type)
- {
- case EET_T_CHAR:
- dumpfunc(dumpdata, "char: ");
- snprintf(tbuf, sizeof(tbuf), "%hhi", *((char *)dd));
- dumpfunc(dumpdata, tbuf); break;
- case EET_T_SHORT:
- dumpfunc(dumpdata, "short: ");
- snprintf(tbuf, sizeof(tbuf), "%hi", *((short *)dd));
- dumpfunc(dumpdata, tbuf); break;
- case EET_T_INT:
- dumpfunc(dumpdata, "int: ");
- snprintf(tbuf, sizeof(tbuf), "%i", *((int *)dd));
- dumpfunc(dumpdata, tbuf); break;
- case EET_T_LONG_LONG:
- dumpfunc(dumpdata, "long_long: ");
- snprintf(tbuf, sizeof(tbuf), "%lli", *((long long *)dd));
- dumpfunc(dumpdata, tbuf); break;
- case EET_T_FLOAT:
- dumpfunc(dumpdata, "float: ");
- snprintf(tbuf, sizeof(tbuf), "%1.25f", *((float *)dd));
- dumpfunc(dumpdata, tbuf); break;
- case EET_T_DOUBLE:
- dumpfunc(dumpdata, "double: ");
- snprintf(tbuf, sizeof(tbuf), "%1.25f", *((double *)dd));
- dumpfunc(dumpdata, tbuf); break;
- case EET_T_UCHAR:
- dumpfunc(dumpdata, "uchar: ");
- snprintf(tbuf, sizeof(tbuf), "%hhu", *((unsigned char *)dd));
- dumpfunc(dumpdata, tbuf); break;
- case EET_T_USHORT:
- dumpfunc(dumpdata, "ushort: ");
- snprintf(tbuf, sizeof(tbuf), "%i", *((unsigned short *)dd));
- dumpfunc(dumpdata, tbuf); break;
- case EET_T_UINT:
- dumpfunc(dumpdata, "uint: ");
- snprintf(tbuf, sizeof(tbuf), "%u", *((unsigned int *)dd));
- dumpfunc(dumpdata, tbuf); break;
- case EET_T_ULONG_LONG:
- dumpfunc(dumpdata, "ulong_long: ");
- snprintf(tbuf, sizeof(tbuf), "%llu", *((unsigned long long *)dd));
- dumpfunc(dumpdata, tbuf); break;
- case EET_T_INLINED_STRING:
- {
- char *s;
-
- s = *((char **)dd);
- if (s)
- {
- dumpfunc(dumpdata, "inlined: \"");
- _eet_data_dump_string_escape(dumpdata, dumpfunc, s);
- dumpfunc(dumpdata, "\"");
- }
- }
- break;
- case EET_T_STRING:
- {
- char *s;
-
- s = *((char **)dd);
- if (s)
- {
- dumpfunc(dumpdata, "string: \"");
- _eet_data_dump_string_escape(dumpdata, dumpfunc, s);
- dumpfunc(dumpdata, "\"");
- }
- }
- break;
- case EET_T_NULL:
- dumpfunc(dumpdata, "null");
- break;
- default:
- dumpfunc(dumpdata, "???: ???"); break;
- break;
- }
- dumpfunc(dumpdata, ";\n");
- }
- else
- {
- data_ret = _eet_data_descriptor_decode(ed,
- NULL,
- echnk.data,
- echnk.size,
- level + 1,
- dumpfunc,
- dumpdata);
- if (!data_ret) goto error;
- }
- }
- else
- {
- for (i = 0; i < level; i++) dumpfunc(dumpdata, " ");
- dumpfunc(dumpdata, " group \"");
- _eet_data_dump_string_escape(dumpdata, dumpfunc, echnk.name);
- dumpfunc(dumpdata, "\" ");
- switch (echnk.group_type)
- {
- case EET_G_UNKNOWN:
- dumpfunc(dumpdata, "struct");break;
- case EET_G_ARRAY:
- dumpfunc(dumpdata, "array");break;
- case EET_G_VAR_ARRAY:
- dumpfunc(dumpdata, "var_array");break;
- case EET_G_LIST:
- dumpfunc(dumpdata, "list");break;
- case EET_G_HASH:
- dumpfunc(dumpdata, "hash");break;
- default:
- dumpfunc(dumpdata, "???");break;
- break;
- }
- dumpfunc(dumpdata, " {\n");
- switch (group_type)
- {
- case EET_G_ARRAY:
- case EET_G_VAR_ARRAY:
- {
- int count;
- int ret;
- int i;
-
- EET_ASSERT(!IS_SIMPLE_TYPE(type), goto error);
-
- ret = eet_data_get_type(ed,
- EET_T_INT,
- echnk.data,
- ((char *)echnk.data) + echnk.size,
- &count);
- if (ret <= 0) goto error;
-
- for (i = 0; i < level; i++) dumpfunc(dumpdata, " ");
- dumpfunc(dumpdata, " count ");
- snprintf(tbuf, sizeof(tbuf), "%i", count);
- dumpfunc(dumpdata, tbuf);
- dumpfunc(dumpdata, ";\n");
-
- /* get all array elements */
- for (i = 0; i < count; i++)
- {
- void *data_ret = NULL;
-
- /* Advance to next chunk */
- NEXT_CHUNK(p, size, echnk, ed);
- memset(&echnk, 0, sizeof(Eet_Data_Chunk));
-
- eet_data_chunk_get(ed, &echnk, p, size);
- if (!echnk.name) goto error;
- /* get the data */
- data_ret = _eet_data_descriptor_decode(ed,
- NULL,
- echnk.data,
- echnk.size,
- level + 2,
- dumpfunc,
- dumpdata);
- if (!data_ret) goto error;
- }
- }
- break;
- case EET_G_LIST:
- {
- void *data_ret = NULL;
-
- EET_ASSERT(!IS_SIMPLE_TYPE(type), goto error);
-
- data_ret = _eet_data_descriptor_decode(ed,
- NULL,
- echnk.data,
- echnk.size,
- level + 2,
- dumpfunc,
- dumpdata);
- if (!data_ret) goto error;
- }
- break;
- case EET_G_HASH:
- {
- int ret;
- char *key = NULL;
- void *data_ret = NULL;
-
- /* Read key */
- ret = eet_data_get_type(ed,
- EET_T_STRING,
- echnk.data,
- ((char *)echnk.data) + echnk.size,
- &key);
- if (ret <= 0) goto error;
-
- /* Advance to next chunk */
- NEXT_CHUNK(p, size, echnk, ed);
- memset(&echnk, 0, sizeof(Eet_Data_Chunk));
-
- /* Read value */
- eet_data_chunk_get(ed, &echnk, p, size);
- if (!echnk.name) goto error;
-
- EET_ASSERT(!IS_SIMPLE_TYPE(type), goto error);
-
- {
- char *s;
-
- s = key;
- if (s)
- {
- for (i = 0; i < level; i++) dumpfunc(dumpdata, " ");
- dumpfunc(dumpdata, " key \"");
- _eet_data_dump_string_escape(dumpdata, dumpfunc, s);
- dumpfunc(dumpdata, "\";\n");
- }
- data_ret = _eet_data_descriptor_decode(ed,
- NULL,
- echnk.data,
- echnk.size,
- level + 2,
- dumpfunc,
- dumpdata);
- }
- if (!data_ret)
- {
- goto error;
- }
- }
- break;
- default:
- break;
- }
- if (dumpfunc)
- {
- for (i = 0; i < level; i++) dumpfunc(dumpdata, " ");
- dumpfunc(dumpdata, " }\n");
- }
- }
- }
- /* advance to next chunk */
+ Eet_Data_Chunk echnk;
+ Eet_Data_Element *ede = NULL;
+ Eet_Node *child = NULL;
+ int group_type = EET_G_UNKNOWN, type = EET_T_UNKNOW;
+ int ret = 0;
+
+ /* get next data chunk */
+ memset(&echnk, 0, sizeof(Eet_Data_Chunk));
+ eet_data_chunk_get(ed, &echnk, p, size);
+ if (!echnk.name)
+ goto error; /* FIXME: don't REPLY on edd - work without */
+
+ if (edd)
+ {
+ ede = _eet_descriptor_hash_find(edd, echnk.name, echnk.hash);
+ if (ede)
+ {
+ group_type = ede->group_type;
+ type = ede->type;
+ if ((echnk.type == 0) && (echnk.group_type == 0))
+ {
+ type = ede->type;
+ group_type = ede->group_type;
+ }
+ else
+ {
+ if (IS_SIMPLE_TYPE(echnk.type) &&
+ eet_data_type_match(echnk.type, ede->type))
+/* Needed when converting on the fly from FP to Float */
+ type = ede->type;
+ else if ((echnk.group_type > EET_G_UNKNOWN) &&
+ (echnk.group_type < EET_G_LAST) &&
+ (echnk.group_type == ede->group_type))
+ group_type = echnk.group_type;
+ }
+ }
+ }
+ /*...... dump to node */
+ else
+ {
+ type = echnk.type;
+ group_type = echnk.group_type;
+ }
+
+ if (!edd && group_type == EET_G_UNKNOWN && IS_SIMPLE_TYPE(type))
+ {
+ unsigned char dd[128];
+
+ ret = eet_data_get_type(ed,
+ type,
+ echnk.data,
+ ((char *)echnk.data) + echnk.size,
+ dd);
+ if (ret <= 0)
+ goto error;
+
+ child = eet_data_node_simple_type(type, echnk.name, dd);
+
+ eet_node_struct_append(result, echnk.name, child);
+ }
+ else
+ {
+ ret = eet_group_codec[group_type - 100].get(
+ context,
+ ed,
+ edd,
+ ede,
+ &echnk,
+ type,
+ group_type,
+ ede ? (void *)(((char *)data) + ede->offset) : (void **)&result,
+ &p,
+ &size);
+
+ if (ret <= 0)
+ goto error;
+ }
+
+ /* advance to next chunk */
NEXT_CHUNK(p, size, echnk, ed);
}
- _eet_freelist_unref();
- _eet_freeleak_unref();
- _eet_freelist_str_unref();
- _eet_freelist_list_unref();
- if (dumpfunc)
+ _eet_freelist_all_unref(context);
+ if (!edd)
{
- _eet_freelist_str_free(edd);
- _eet_freelist_direct_str_free(edd);
- _eet_freelist_list_free(edd);
- _eet_freelist_free(edd);
- _eet_freeleak_reset();
+ _eet_freelist_str_free(context, edd);
+ _eet_freelist_direct_str_free(context, edd);
+ _eet_freelist_list_free(context, edd);
+ _eet_freelist_hash_free(context, edd);
+ _eet_freelist_array_free(context, edd);
+ _eet_freelist_free(context, edd);
}
else
{
- _eet_freelist_reset();
- _eet_freeleak_free(edd);
- _eet_freelist_str_reset();
- _eet_freelist_list_reset();
- _eet_freelist_direct_str_reset();
- }
- if (dumpfunc)
- {
- if (dump)
- {
- if (chnk.type == EET_T_UNKNOW)
- {
- for (i = 0; i < level; i++) dumpfunc(dumpdata, " ");
- dumpfunc(dumpdata, "}\n");
- }
- }
- return (void *)1;
+ _eet_freelist_reset(context);
+ _eet_freelist_str_reset(context);
+ _eet_freelist_list_reset(context);
+ _eet_freelist_hash_reset(context);
+ _eet_freelist_direct_str_reset(context);
+ _eet_freelist_array_reset(context);
}
+
+ if (!edd)
+ return result;
+
return data;
error:
- _eet_freelist_unref();
- _eet_freeleak_unref();
- _eet_freelist_str_unref();
- _eet_freelist_list_unref();
- _eet_freelist_str_free(edd);
- _eet_freelist_direct_str_free(edd);
- _eet_freelist_list_free(edd);
- _eet_freelist_free(edd);
- _eet_freeleak_reset();
- if (dumpfunc)
- {
- if (dump)
- {
- if (chnk.type == EET_T_UNKNOW)
- {
- for (i = 0; i < level; i++) dumpfunc(dumpdata, " ");
- dumpfunc(dumpdata, "}\n");
- }
- }
- }
+ eet_node_del(result);
+
+ _eet_freelist_all_unref(context);
+ _eet_freelist_str_free(context, edd);
+ _eet_freelist_direct_str_free(context, edd);
+ _eet_freelist_list_free(context, edd);
+ _eet_freelist_hash_free(context, edd);
+ _eet_freelist_array_free(context, edd);
+ _eet_freelist_free(context, edd);
+
+ /* FIXME: Warn that something goes wrong here. */
return NULL;
}
static int
-eet_data_get_list(const Eet_Dictionary *ed, Eet_Data_Descriptor *edd, Eet_Data_Element *ede, Eet_Data_Chunk *echnk,
- int type __UNUSED__, int group_type __UNUSED__, void *data,
- int level, void (*dumpfunc) (void *data, const char *str), void *dumpdata,
- char **p __UNUSED__, int *size __UNUSED__)
+eet_data_get_list(Eet_Free_Context *context,
+ const Eet_Dictionary *ed,
+ Eet_Data_Descriptor *edd,
+ Eet_Data_Element *ede,
+ Eet_Data_Chunk *echnk,
+ int type,
+ int group_type __UNUSED__,
+ void *data,
+ char **p,
+ int *size)
{
+ Eet_Data_Descriptor *subtype = NULL;
void *list = NULL;
void **ptr;
void *data_ret;
EET_ASSERT(!((type > EET_T_UNKNOW) && (type < EET_T_STRING)), return 0);
+ if (ede)
+ {
+ subtype = ede->subtype;
+
+ if (type != ede->type)
+ return 0;
+ }
+
ptr = (void **)data;
list = *ptr;
data_ret = NULL;
- if (ede->type >= EET_T_STRING)
- {
- int ret;
-
- ret = eet_data_get_unknown(ed, edd, ede, echnk, ede->type, EET_G_UNKNOWN,
- &data_ret, level, dumpfunc, dumpdata, p, size);
- if (!ret) return 0;
- }
+ if (IS_POINTER_TYPE(type))
+ POINTER_TYPE_DECODE(context,
+ ed,
+ edd,
+ ede,
+ echnk,
+ type,
+ &data_ret,
+ p,
+ size,
+ on_error);
else
+ STRUCT_TYPE_DECODE(data_ret,
+ context,
+ ed,
+ subtype,
+ echnk->data,
+ echnk->size,
+ -1,
+ on_error);
+
+ if (edd)
{
- data_ret = _eet_data_descriptor_decode(ed, ede->subtype, echnk->data, echnk->size, level + 2, dumpfunc, dumpdata);
- if (!data_ret) return 0;
+ list = edd->func.list_append(list, data_ret);
+ *ptr = list;
+ _eet_freelist_list_add(context, ptr);
}
-
- list = edd->func.list_append(list, data_ret);
- *ptr = list;
- _eet_freelist_list_add(ptr);
+ else
+ eet_node_list_append(*((Eet_Node **)data), echnk->name, data_ret);
return 1;
+
+on_error:
+ return 0;
}
static int
-eet_data_get_hash(const Eet_Dictionary *ed, Eet_Data_Descriptor *edd, Eet_Data_Element *ede, Eet_Data_Chunk *echnk,
- int type, int group_type __UNUSED__, void *data,
- int level, void (*dumpfunc) (void *data, const char *str), void *dumpdata,
- char **p, int *size)
+eet_data_get_hash(Eet_Free_Context *context,
+ const Eet_Dictionary *ed,
+ Eet_Data_Descriptor *edd,
+ Eet_Data_Element *ede,
+ Eet_Data_Chunk *echnk,
+ int type,
+ int group_type __UNUSED__,
+ void *data,
+ char **p,
+ int *size)
{
void **ptr;
void *hash = NULL;
/* Read key */
ret = eet_data_get_type(ed,
- EET_T_STRING,
- echnk->data,
- ((char *)echnk->data) + echnk->size,
- &key);
- if (ret <= 0) goto on_error;
+ EET_T_STRING,
+ echnk->data,
+ ((char *)echnk->data) + echnk->size,
+ &key);
+ if (ret <= 0)
+ goto on_error;
+
+ if (!key)
+ goto on_error;
/* Advance to next chunk */
NEXT_CHUNK((*p), (*size), (*echnk), ed);
/* Read value */
eet_data_chunk_get(ed, echnk, *p, *size);
- if (!echnk->name) goto on_error;
-
- if (type >= EET_T_STRING)
- {
- int ret;
+ if (!echnk->name)
+ goto on_error;
- ret = eet_data_get_unknown(ed, edd, ede, echnk, ede->type, EET_G_UNKNOWN,
- &data_ret, level, dumpfunc, dumpdata, p, size);
- if (!ret) return 0;
- }
+ if (ede)
+ if ((ede->group_type != echnk->group_type)
+ || (ede->type != echnk->type))
+ goto on_error;
+
+ if (IS_POINTER_TYPE(echnk->type))
+ POINTER_TYPE_DECODE(context,
+ ed,
+ edd,
+ ede,
+ echnk,
+ echnk->type,
+ &data_ret,
+ p,
+ size,
+ on_error);
else
+ STRUCT_TYPE_DECODE(data_ret,
+ context,
+ ed,
+ ede ? ede->subtype : NULL,
+ echnk->data,
+ echnk->size,
+ -1,
+ on_error);
+
+ if (edd)
{
- data_ret = _eet_data_descriptor_decode(ed,
- ede->subtype,
- echnk->data,
- echnk->size,
- level + 2,
- dumpfunc,
- dumpdata);
- if (!data_ret) goto on_error;
+ hash = edd->func.hash_add(hash, key, data_ret);
+ *ptr = hash;
+ _eet_freelist_hash_add(context, hash);
}
+ else
+ eet_node_hash_add(*((Eet_Node **)data), echnk->name, key, data_ret);
- hash = edd->func.hash_add(hash, key, data_ret);
- *ptr = hash;
- _eet_freelist_list_add(ptr);
return 1;
- on_error:
- return ret;
+on_error:
+ return 0;
}
/* var arrays and fixed arrays have to
* each chunk is pointless.
*/
static int
-eet_data_get_array(const Eet_Dictionary *ed, Eet_Data_Descriptor *edd __UNUSED__,
- Eet_Data_Element *ede, Eet_Data_Chunk *echnk,
- int type, int group_type, void *data,
- int level, void (*dumpfunc) (void *data, const char *str), void *dumpdata,
- char **p, int *size)
+eet_data_get_array(Eet_Free_Context *context,
+ const Eet_Dictionary *ed,
+ Eet_Data_Descriptor *edd,
+ Eet_Data_Element *ede,
+ Eet_Data_Chunk *echnk,
+ int type,
+ int group_type,
+ void *data,
+ char **p,
+ int *size)
{
+ Eina_List *childs = NULL;
const char *name;
+ Eet_Node *tmp;
void *ptr;
int count;
int ret;
- int subsize;
+ int subsize = 0;
int i;
EET_ASSERT(!((type > EET_T_UNKNOW) && (type < EET_T_STRING)), return 0);
ptr = data;
/* read the number of elements */
ret = eet_data_get_type(ed,
- EET_T_INT,
- echnk->data,
- ((char *)echnk->data) + echnk->size,
- &count);
- if (ret <= 0) return ret;
-
- if (type >= EET_T_STRING)
- subsize = eet_basic_codec[ede->type].size;
- else
- subsize = ede->subtype->size;
+ EET_T_INT,
+ echnk->data,
+ ((char *)echnk->data) + echnk->size,
+ &count);
+ if (ret <= 0)
+ return ret;
name = echnk->name;
- if (group_type == EET_G_VAR_ARRAY)
+ if (ede)
{
- /* store the number of elements
- * on the counter offset */
- *(int *)(((char *)data) + ede->count - ede->offset) = count;
- /* allocate space for the array of elements */
- *(void **)ptr = calloc(count, subsize);
-
- if (!*(void **)ptr) return 0;
-
- _eet_freelist_add(*(void **)ptr);
+ if (IS_POINTER_TYPE(type))
+ subsize = eet_basic_codec[ede->type - 1].size;
+ else
+ subsize = ede->subtype->size;
+
+ if (group_type == EET_G_VAR_ARRAY)
+ {
+ /* store the number of elements
+ * on the counter offset */
+ *(int *)(((char *)data) + ede->count - ede->offset) = count;
+ /* allocate space for the array of elements */
+ if (edd->func.array_alloc)
+ *(void **)ptr = edd->func.array_alloc(count * subsize);
+ else
+ *(void **)ptr = edd->func.mem_alloc(count * subsize);
+
+ if (!*(void **)ptr)
+ return 0;
+
+ memset(*(void **)ptr, 0, count * subsize);
+
+ _eet_freelist_array_add(context, *(void **)ptr);
+ }
}
/* get all array elements */
for (i = 0; i < count; i++)
{
- void *dst;
- void *data_ret = NULL;
-
- /* Advance to next chunk */
- NEXT_CHUNK((*p), (*size), (*echnk), ed);
- memset(echnk, 0, sizeof(Eet_Data_Chunk));
-
- eet_data_chunk_get(ed, echnk, *p, *size);
- if (!echnk->name || strcmp(echnk->name, name) != 0) return 0;
- /* get the data */
-
- /* get the destination pointer */
- if (group_type == EET_G_ARRAY)
- dst = (char *)ptr + (subsize * i);
- else
- dst = *(char **)ptr + (subsize * i);
-
- if (type >= EET_T_STRING)
- {
- int ret;
-
- ret = eet_data_get_unknown(ed,
- edd,
- ede,
- echnk,
- ede->type,
- EET_G_UNKNOWN,
- &data_ret,
- level,
- dumpfunc,
- dumpdata,
- p,
- size);
- if (!ret) return 0;
- memcpy(dst, &data_ret, subsize);
- }
- else
- {
- data_ret = _eet_data_descriptor_decode(ed,
- ede->subtype,
- echnk->data,
- echnk->size,
- level + 2,
- dumpfunc,
- dumpdata);
- if (!data_ret) return 0;
- memcpy(dst, data_ret, subsize);
- _eet_freeleak_add(data_ret);
- }
+ void *dst = NULL;
+
+ /* Advance to next chunk */
+ NEXT_CHUNK((*p), (*size), (*echnk), ed);
+ memset(echnk, 0, sizeof(Eet_Data_Chunk));
+
+ eet_data_chunk_get(ed, echnk, *p, *size);
+ if (!echnk->name || strcmp(echnk->name, name) != 0)
+ goto on_error; /* get the data */
+
+ if ((echnk->group_type != group_type)
+ || ((echnk->type != type) && (echnk->type != EET_T_NULL)))
+ goto on_error;
+
+ if (ede)
+ if ((ede->group_type != echnk->group_type)
+ || ((echnk->type != ede->type) && (echnk->type != EET_T_NULL)))
+ goto on_error;
+
+ /* get the destination pointer */
+ if (ede)
+ {
+ if (group_type == EET_G_ARRAY)
+ dst = (char *)ptr + (subsize * i);
+ else
+ dst = *(char **)ptr + (subsize * i);
+ }
+
+ if (IS_POINTER_TYPE(echnk->type))
+ {
+ void *data_ret = NULL;
+
+ POINTER_TYPE_DECODE(context,
+ ed,
+ edd,
+ ede,
+ echnk,
+ echnk->type,
+ &data_ret,
+ p,
+ size,
+ on_error);
+ if (dst)
+ memcpy(dst, &data_ret, subsize);
+
+ if (!edd)
+ childs = eina_list_append(childs, data_ret);
+ }
+ else
+ {
+ STRUCT_TYPE_DECODE(dst,
+ context,
+ ed,
+ ede ? ede->subtype : NULL,
+ echnk->data,
+ echnk->size,
+ subsize,
+ on_error);
+
+ if (!edd)
+ childs = eina_list_append(childs, dst);
+ }
+ }
+
+ if (!edd)
+ {
+ Eet_Node *parent = *((Eet_Node **)data);
+ Eet_Node *array;
+
+ if (group_type == EET_G_ARRAY)
+ array = eet_node_array_new(name, count, childs);
+ else
+ array = eet_node_var_array_new(name, childs);
+
+ if (!array)
+ goto on_error;
+
+ eet_node_struct_append(parent, name, array);
}
+
return 1;
+
+on_error:
+ EINA_LIST_FREE(childs, tmp)
+ eet_node_del(tmp);
+
+ return 0;
+}
+
+static void
+eet_data_put_union(Eet_Dictionary *ed,
+ Eet_Data_Descriptor *edd __UNUSED__,
+ Eet_Data_Element *ede,
+ Eet_Data_Stream *ds,
+ void *data_in)
+{
+ const char *union_type;
+ int i;
+
+ EET_ASSERT(!((ede->type != EET_T_UNKNOW) || (!ede->subtype)), return );
+
+ union_type = ede->subtype->func.type_get(
+ ((char *)data_in) + ede->count - ede->offset,
+ NULL);
+
+ if (!union_type)
+ return;
+
+ /* Search the structure of the union to encode. */
+ for (i = 0; i < ede->subtype->elements.num; ++i)
+ if (strcmp(ede->subtype->elements.set[i].name, union_type) == 0)
+ {
+ Eet_Data_Element *sede;
+ void *data;
+ int size;
+
+ /* Yeah we found it ! */
+ data = eet_data_put_type(ed, EET_T_STRING, &union_type, &size);
+ if (data)
+ eet_data_encode(ed,
+ ds,
+ data,
+ ede->name,
+ size,
+ ede->type,
+ ede->group_type);
+
+ sede = &(ede->subtype->elements.set[i]);
+ data = _eet_data_descriptor_encode(ed,
+ sede->subtype,
+ data_in,
+ &size);
+ if (data)
+ eet_data_encode(ed,
+ ds,
+ data,
+ ede->name,
+ size,
+ ede->type,
+ ede->group_type);
+
+ break;
+ }
}
static int
-eet_data_get_unknown(const Eet_Dictionary *ed, Eet_Data_Descriptor *edd, Eet_Data_Element *ede, Eet_Data_Chunk *echnk,
- int type, int group_type __UNUSED__, void *data,
- int level, void (*dumpfunc) (void *data, const char *str), void *dumpdata,
- char **p __UNUSED__, int *size __UNUSED__)
+eet_data_get_union(Eet_Free_Context *context,
+ const Eet_Dictionary *ed,
+ Eet_Data_Descriptor *edd __UNUSED__,
+ Eet_Data_Element *ede,
+ Eet_Data_Chunk *echnk,
+ int type,
+ int group_type,
+ void *data,
+ char **p,
+ int *size)
{
- int ret;
- void *data_ret;
+ const char *union_type;
+ void *data_ret = NULL;
+ int ret = 0;
+ int i;
- if (IS_SIMPLE_TYPE(type))
+ /* Read type */
+ ret = eet_data_get_type(ed,
+ EET_T_STRING,
+ echnk->data,
+ ((char *)echnk->data) + echnk->size,
+ &union_type);
+ if (ret <= 0)
+ goto on_error;
+
+ /* Advance to next chunk */
+ NEXT_CHUNK((*p), (*size), (*echnk), ed);
+ memset(echnk, 0, sizeof(Eet_Data_Chunk));
+
+ /* Read value */
+ eet_data_chunk_get(ed, echnk, *p, *size);
+ if (!echnk->name)
+ goto on_error;
+
+ if (ede)
{
- ret = eet_data_get_type(ed, type, echnk->data, ((char *)echnk->data) + echnk->size, ((char *)data));
- if (ret <= 0) return ret;
-
- if (type == EET_T_STRING)
- {
- char **str;
-
- str = (char **)(((char *)data));
- if (*str)
- {
- if ((ed == NULL) || (edd->func.str_direct_alloc == NULL))
- {
- *str = edd->func.str_alloc(*str);
- _eet_freelist_str_add(*str);
- }
- else
- {
- *str = edd->func.str_direct_alloc(*str);
- _eet_freelist_direct_str_add(*str);
- }
- }
- }
- else if (type == EET_T_INLINED_STRING)
- {
- char **str;
-
- str = (char **)(((char *)data));
- if (*str)
- {
- *str = edd->func.str_alloc(*str);
- _eet_freelist_str_add(*str);
- }
- }
+ EET_ASSERT(!(ede->group_type != group_type || ede->type != type),
+ goto on_error);
+
+ /* Search the structure of the union to decode */
+ for (i = 0; i < ede->subtype->elements.num; ++i)
+ if (strcmp(ede->subtype->elements.set[i].name, union_type) == 0)
+ {
+ Eet_Data_Element *sede;
+ char *ut;
+
+ /* Yeah we found it ! */
+ sede = &(ede->subtype->elements.set[i]);
+ EET_ASSERT(sede->subtype, goto on_error);
+
+ data_ret = _eet_data_descriptor_decode(context,
+ ed,
+ sede->subtype,
+ echnk->data,
+ echnk->size,
+ data,
+ sede->subtype->size);
+ if (!data_ret)
+ goto on_error;
+
+ /* Set union type. */
+ if ((!ed) || (!ede->subtype->func.str_direct_alloc))
+ {
+ ut = ede->subtype->func.str_alloc(union_type);
+ _eet_freelist_str_add(context, ut);
+ }
+ else
+ {
+ ut = ede->subtype->func.str_direct_alloc(union_type);
+ _eet_freelist_direct_str_add(context, ut);
+ }
+
+ ede->subtype->func.type_set(
+ ut,
+ ((char *)data) + ede->count -
+ ede->offset,
+ EINA_FALSE);
+
+ break;
+ }
}
- else if (ede->subtype)
+ else
+ {
+ /* FIXME: generate node structure. */
+ data_ret = _eet_data_descriptor_decode(context,
+ ed, NULL,
+ echnk->data, echnk->size,
+ NULL, 0);
+ goto on_error;
+ }
+
+ return 1;
+
+on_error:
+ return 0;
+}
+
+static void
+eet_data_put_variant(Eet_Dictionary *ed,
+ Eet_Data_Descriptor *edd __UNUSED__,
+ Eet_Data_Element *ede,
+ Eet_Data_Stream *ds,
+ void *data_in)
+{
+ const char *union_type;
+ void *data;
+ Eina_Bool unknow = EINA_FALSE;
+ int size;
+ int i;
+
+ EET_ASSERT(!((ede->type != EET_T_UNKNOW) || (!ede->subtype)), return );
+
+ union_type = ede->subtype->func.type_get(
+ ((char *)data_in) + ede->count - ede->offset,
+ &unknow);
+
+ if (!union_type && unknow == EINA_FALSE)
+ return;
+
+ if (unknow)
{
- void **ptr;
+ /* Handle opaque internal representation */
+ Eet_Variant_Unknow *evu;
+
+ data = eet_data_put_type(ed, EET_T_STRING, &union_type, &size);
+ if (data)
+ eet_data_encode(ed,
+ ds,
+ data,
+ ede->name,
+ size,
+ ede->type,
+ ede->group_type);
+
+ evu = (Eet_Variant_Unknow *)data_in;
+ if (evu && EINA_MAGIC_CHECK(evu, EET_MAGIC_VARIANT))
+ eet_data_encode(ed,
+ ds,
+ evu->data,
+ ede->name,
+ evu->size,
+ ede->type,
+ ede->group_type);
+ }
+ else
+ /* Search the structure of the union to encode. */
+ for (i = 0; i < ede->subtype->elements.num; ++i)
+ if (strcmp(ede->subtype->elements.set[i].name, union_type) == 0)
+ {
+ Eet_Data_Element *sede;
+
+ /* Yeah we found it ! */
+ data = eet_data_put_type(ed, EET_T_STRING, &union_type, &size);
+ if (data)
+ eet_data_encode(ed,
+ ds,
+ data,
+ ede->name,
+ size,
+ ede->type,
+ ede->group_type);
+
+ sede = &(ede->subtype->elements.set[i]);
+
+ if (sede->group_type != EET_G_UNKNOWN)
+ {
+ Eet_Data_Stream *lds;
+
+ lds = eet_data_stream_new();
+ eet_group_codec[sede->group_type - 100].put(ed,
+ sede->subtype,
+ sede,
+ lds,
+ data_in);
+ if (lds->size != 0)
+ {
+ eet_data_encode(ed, ds, lds->data, ede->name, lds->pos,
+ ede->type, ede->group_type);
+
+ lds->data = NULL;
+ lds->size = 0;
+ }
+ else
+ eet_data_encode(ed, ds, NULL, ede->name, 0,
+ EET_T_NULL, ede->group_type);
+
+ eet_data_stream_free(lds);
+ }
+ else
+ {
+ data = _eet_data_descriptor_encode(ed,
+ sede->subtype,
+ *(void **)data_in,
+ &size);
+ if (data)
+ eet_data_encode(ed,
+ ds,
+ data,
+ ede->name,
+ size,
+ ede->type,
+ ede->group_type);
+ }
+
+ break;
+ }
+}
+
+static int
+eet_data_get_variant(Eet_Free_Context *context,
+ const Eet_Dictionary *ed,
+ Eet_Data_Descriptor *edd __UNUSED__,
+ Eet_Data_Element *ede,
+ Eet_Data_Chunk *echnk,
+ int type __UNUSED__,
+ int group_type __UNUSED__,
+ void *data,
+ char **p,
+ int *size)
+{
+ const char *union_type;
+ void *data_ret = NULL;
+ int ret = 0;
+ int i;
+
+ /* Read type */
+ ret = eet_data_get_type(ed,
+ EET_T_STRING,
+ echnk->data,
+ ((char *)echnk->data) + echnk->size,
+ &union_type);
+ if (ret <= 0)
+ goto on_error;
+
+ /* Advance to next chunk */
+ NEXT_CHUNK((*p), (*size), (*echnk), ed);
+ memset(echnk, 0, sizeof(Eet_Data_Chunk));
- data_ret = _eet_data_descriptor_decode(ed, ede->subtype, echnk->data, echnk->size, level + 1, dumpfunc, dumpdata);
- if (!data_ret) return 0;
+ /* Read value */
+ eet_data_chunk_get(ed, echnk, *p, *size);
+ if (!echnk->name)
+ goto on_error;
- ptr = (void **)(((char *)data));
- *ptr = (void *)data_ret;
+ if (ede)
+ {
+ char *ut;
+
+ EET_ASSERT(ede->subtype, goto on_error);
+
+ if ((!ed) || (!ede->subtype->func.str_direct_alloc))
+ {
+ ut = ede->subtype->func.str_alloc(union_type);
+ _eet_freelist_str_add(context, ut);
+ }
+ else
+ {
+ ut = ede->subtype->func.str_direct_alloc(union_type);
+ _eet_freelist_direct_str_add(context, ut);
+ }
+
+ /* Search the structure of the union to decode */
+ for (i = 0; i < ede->subtype->elements.num; ++i)
+ if (strcmp(ede->subtype->elements.set[i].name, union_type) == 0)
+ {
+ Eet_Data_Element *sede;
+
+ /* Yeah we found it ! */
+ sede = &(ede->subtype->elements.set[i]);
+
+ if (sede->group_type != EET_G_UNKNOWN)
+ {
+ Eet_Data_Chunk chnk;
+ char *p2;
+ int size2;
+
+ p2 = echnk->data;
+ size2 = echnk->size;
+
+ /* Didn't find a proper way to provide this
+ without duplicating code */
+ while (size2 > 0)
+ {
+ memset(&chnk, 0, sizeof(Eet_Data_Chunk));
+ eet_data_chunk_get(ed, &chnk, p2, size2);
+
+ if (!chnk.name)
+ goto on_error;
+
+ ret = eet_group_codec[sede->group_type - 100].get
+ (context, ed, sede->subtype, sede, &chnk, sede->type,
+ sede->group_type, data, &p2, &size2);
+
+ if (ret <= 0)
+ goto on_error;
+
+/* advance to next chunk */
+ NEXT_CHUNK(p2, size2, chnk, ed);
+ }
+
+ /* Put garbage so that we will not put eet_variant_unknow in it */
+ data_ret = (void *)data;
+
+ /* Set variant type. */
+ ede->subtype->func.type_set
+ (ut, ((char *)data) + ede->count - ede->offset,
+ EINA_FALSE);
+ break;
+ }
+
+ data_ret = _eet_data_descriptor_decode(context,
+ ed,
+ sede->subtype,
+ echnk->data,
+ echnk->size,
+ NULL, 0);
+ if (!data_ret)
+ break;
+
+ /* And point to the variant data. */
+ *(void **)data = data_ret;
+
+ /* Set variant type. */
+ ede->subtype->func.type_set
+ (ut, ((char *)data) + ede->count - ede->offset, EINA_FALSE);
+ break;
+ }
+
+ if (!data_ret)
+ {
+ Eet_Variant_Unknow *evu;
+
+ evu = calloc(1, sizeof (Eet_Variant_Unknow) + echnk->size - 1);
+ if (!evu)
+ goto on_error;
+
+ evu->size = echnk->size;
+ memcpy(evu->data, echnk->data, evu->size);
+ EINA_MAGIC_SET(evu, EET_MAGIC_VARIANT);
+
+ /* And point to the opaque internal data scructure */
+ *(void **)data = evu;
+
+ /* Set variant type. */
+ ede->subtype->func.type_set
+ (ut, ((char *)data) + ede->count - ede->offset, EINA_TRUE);
+ }
+ }
+ else
+ {
+ /* FIXME: dump node structure. */
+ data_ret = _eet_data_descriptor_decode(context,
+ ed, NULL,
+ echnk->data, echnk->size,
+ NULL, 0);
+ goto on_error;
}
return 1;
+
+on_error:
+ return 0;
}
-static void
-eet_data_encode(Eet_Dictionary *ed, Eet_Data_Stream *ds, void *data, const char *name, int size, int type, int group_type)
+static Eet_Node *
+eet_data_node_simple_type(int type,
+ const char *name,
+ void *dd)
{
- Eet_Data_Chunk *echnk;
+#ifdef EET_T_TYPE
+# undef EET_T_TYPE
+#endif /* ifdef EET_T_TYPE */
- echnk = eet_data_chunk_new(data, size, name, type, group_type);
- eet_data_chunk_put(ed, echnk, ds);
- eet_data_chunk_free(echnk);
- if (data) free(data);
+#define EET_T_TYPE(Eet_Type, Eet_Node_Type, Type) \
+case Eet_Type: \
+ return eet_node_ ## Eet_Node_Type ## _new(name, *((Type *)dd)); \
+
+ switch (type)
+ {
+ EET_T_TYPE(EET_T_CHAR, char, char);
+ EET_T_TYPE(EET_T_SHORT, short, short);
+ EET_T_TYPE(EET_T_INT, int, int);
+ EET_T_TYPE(EET_T_LONG_LONG, long_long, long long);
+ EET_T_TYPE(EET_T_FLOAT, float, float);
+ EET_T_TYPE(EET_T_DOUBLE, double, double);
+ EET_T_TYPE(EET_T_UCHAR, unsigned_char, unsigned char);
+ EET_T_TYPE(EET_T_USHORT, unsigned_short, unsigned short);
+ EET_T_TYPE(EET_T_UINT, unsigned_int, unsigned int);
+ EET_T_TYPE(EET_T_ULONG_LONG, unsigned_long_long, unsigned long long);
+ EET_T_TYPE(EET_T_STRING, string, char *);
+ EET_T_TYPE(EET_T_INLINED_STRING, inlined_string, char *);
+
+ case EET_T_NULL:
+ return eet_node_null_new(name);
+
+ default:
+ ERR("Unknow type passed to eet_data_node_simple_type");
+ return NULL;
+ }
+}
+
+static int
+eet_data_get_unknown(Eet_Free_Context *context,
+ const Eet_Dictionary *ed,
+ Eet_Data_Descriptor *edd,
+ Eet_Data_Element *ede,
+ Eet_Data_Chunk *echnk,
+ int type,
+ int group_type __UNUSED__,
+ void *data,
+ char **p __UNUSED__,
+ int *size __UNUSED__)
+{
+ int ret;
+ void *data_ret;
+
+ if (IS_SIMPLE_TYPE(type))
+ {
+ unsigned char dd[128];
+
+ ret = eet_data_get_type(ed,
+ type,
+ echnk->data,
+ ((char *)echnk->data) + echnk->size,
+ edd ? (char *)data : (char *)dd);
+ if (ret <= 0)
+ return ret;
+
+ if (!edd)
+ {
+ Eet_Node **parent = data;
+ Eet_Node *node;
+
+ node = eet_data_node_simple_type(type, echnk->name, dd);
+
+ if (*parent)
+ eet_node_struct_append(*parent, echnk->name, node);
+ else
+ *parent = node;
+ }
+ else
+ {
+ if (type == EET_T_STRING)
+ {
+ char **str;
+
+ str = (char **)(((char *)data));
+ if (*str)
+ {
+ if ((!ed) || (!edd->func.str_direct_alloc))
+ {
+ *str = edd->func.str_alloc(*str);
+ _eet_freelist_str_add(context, *str);
+ }
+ else
+ {
+ *str = edd->func.str_direct_alloc(*str);
+ _eet_freelist_direct_str_add(context, *str);
+ }
+ }
+ }
+ else if (edd && type == EET_T_INLINED_STRING)
+ {
+ char **str;
+
+ str = (char **)(((char *)data));
+ if (*str)
+ {
+ *str = edd->func.str_alloc(*str);
+ _eet_freelist_str_add(context, *str);
+ }
+ }
+ }
+ }
+ else
+ {
+ Eet_Data_Descriptor *subtype;
+
+ subtype = ede ? ede->subtype : NULL;
+
+ if (subtype || !edd)
+ {
+ Eet_Node **parent = data;
+ void **ptr;
+
+ data_ret = _eet_data_descriptor_decode(context,
+ ed,
+ subtype,
+ echnk->data,
+ echnk->size,
+ NULL, 0);
+ if (!data_ret)
+ return 0;
+
+ if (edd)
+ {
+ ptr = (void **)(((char *)data));
+ *ptr = (void *)data_ret;
+ }
+ else
+ {
+ Eet_Node *node = data_ret;
+
+ if (*parent)
+ {
+ node = eet_node_struct_child_new(echnk->name, node);
+ eet_node_struct_append(*parent, echnk->name, node);
+ }
+ else
+ *parent = node;
+ }
+ }
+ }
+
+ return 1;
}
static void
-eet_data_put_array(Eet_Dictionary *ed, Eet_Data_Descriptor *edd __UNUSED__, Eet_Data_Element *ede, Eet_Data_Stream *ds, void *data_in)
+eet_data_put_array(Eet_Dictionary *ed,
+ Eet_Data_Descriptor *edd __UNUSED__,
+ Eet_Data_Element *ede,
+ Eet_Data_Stream *ds,
+ void *data_in)
{
void *data;
int offset = 0;
int size;
int j;
- EET_ASSERT(!((ede->type > EET_T_UNKNOW) && (ede->type < EET_T_STRING)), return );
+ EET_ASSERT(!((ede->type > EET_T_UNKNOW) && (ede->type < EET_T_STRING)),
+ return );
if (ede->group_type == EET_G_ARRAY)
count = ede->counter_offset;
else
count = *(int *)(((char *)data_in) + ede->count - ede->offset);
- if (count <= 0) return;
- /* Store number of elements */
+ if (count <= 0)
+ return; /* Store number of elements */
+
data = eet_data_put_type(ed, EET_T_INT, &count, &size);
- if (data) eet_data_encode(ed, ds, data, ede->name, size, ede->type, ede->group_type);
+ if (data)
+ eet_data_encode(ed, ds, data, ede->name, size, ede->type, ede->group_type);
- if (ede->type >= EET_T_STRING)
- subsize = eet_basic_codec[ede->type].size;
+ if (IS_POINTER_TYPE(ede->type))
+ subsize = eet_basic_codec[ede->type - 1].size;
else
subsize = ede->subtype->size;
for (j = 0; j < count; j++)
{
- void *d;
- int pos = ds->pos;
-
- if (ede->group_type == EET_G_ARRAY)
- d = (void *)(((char *)data_in) + offset);
- else
- d = *(((char **)data_in)) + offset;
-
- if (ede->type >= EET_T_STRING)
- eet_data_put_unknown(ed, NULL, ede, ds, d);
- else
- {
- data = _eet_data_descriptor_encode(ed, ede->subtype, d, &size);
- if (data) eet_data_encode(ed, ds, data, ede->name, size, ede->type, ede->group_type);
- }
-
- if (pos == ds->pos)
- {
- /* Add a NULL element just to have the correct array layout. */
- eet_data_encode(ed, ds, NULL, ede->name, 0, EET_T_NULL, ede->group_type);
- }
-
- offset += subsize;
+ void *d;
+ int pos = ds->pos;
+
+ if (ede->group_type == EET_G_ARRAY)
+ d = (void *)(((char *)data_in) + offset);
+ else
+ d = *(((char **)data_in)) + offset;
+
+ if (IS_POINTER_TYPE(ede->type))
+ {
+ if (*(char **)d)
+ eet_data_put_unknown(ed, NULL, ede, ds, d);
+ }
+ else
+ {
+ data = _eet_data_descriptor_encode(ed, ede->subtype, d, &size);
+ if (data)
+ eet_data_encode(ed,
+ ds,
+ data,
+ ede->name,
+ size,
+ ede->type,
+ ede->group_type);
+ }
+
+ if (pos == ds->pos)
+ /* Add a NULL element just to have the correct array layout. */
+ eet_data_encode(ed,
+ ds,
+ NULL,
+ ede->name,
+ 0,
+ EET_T_NULL,
+ ede->group_type);
+
+ offset += subsize;
}
}
static void
-eet_data_put_unknown(Eet_Dictionary *ed, Eet_Data_Descriptor *edd __UNUSED__, Eet_Data_Element *ede, Eet_Data_Stream *ds, void *data_in)
+eet_data_put_unknown(Eet_Dictionary *ed,
+ Eet_Data_Descriptor *edd __UNUSED__,
+ Eet_Data_Element *ede,
+ Eet_Data_Stream *ds,
+ void *data_in)
{
void *data = NULL;
int size;
if (IS_SIMPLE_TYPE(ede->type))
data = eet_data_put_type(ed, ede->type, data_in, &size);
else if (ede->subtype)
- {
- if (*((char **)data_in))
- data = _eet_data_descriptor_encode(ed,
- ede->subtype,
- *((char **)((char *)(data_in))),
- &size);
- }
- if (data) eet_data_encode(ed, ds, data, ede->name, size, ede->type, ede->group_type);
+ if (*((char **)data_in))
+ data = _eet_data_descriptor_encode(ed,
+ ede->subtype,
+ *((char **)((char *)(data_in))),
+ &size);
+
+ if (data)
+ eet_data_encode(ed,
+ ds,
+ data,
+ ede->name,
+ size,
+ ede->type,
+ ede->group_type);
}
static void
-eet_data_put_list(Eet_Dictionary *ed, Eet_Data_Descriptor *edd, Eet_Data_Element *ede, Eet_Data_Stream *ds, void *data_in)
+eet_data_put_list(Eet_Dictionary *ed,
+ Eet_Data_Descriptor *edd,
+ Eet_Data_Element *ede,
+ Eet_Data_Stream *ds,
+ void *data_in)
{
void *data;
void *l;
int size;
- EET_ASSERT(!((ede->type > EET_T_UNKNOW) && (ede->type < EET_T_STRING)), return );
+ EET_ASSERT(!(((ede->type > EET_T_UNKNOW) && (ede->type < EET_T_STRING))
+ || ((ede->type > EET_T_NULL) && (ede->type < EET_T_LAST))),
+ return );
l = *((void **)(((char *)data_in)));
for (; l; l = edd->func.list_next(l))
{
- if (ede->type >= EET_T_STRING)
- {
- const char *str = edd->func.list_data(l);
- eet_data_put_unknown(ed, NULL, ede, ds, &str);
- }
- else
- {
- data = _eet_data_descriptor_encode(ed,
- ede->subtype,
- edd->func.list_data(l),
- &size);
- if (data) eet_data_encode(ed, ds, data, ede->name, size, ede->type, ede->group_type);
- }
+ if (IS_POINTER_TYPE(ede->type))
+ {
+ const void *str = edd->func.list_data(l);
+ eet_data_put_unknown(ed, NULL, ede, ds, &str);
+ }
+ else
+ {
+ data = _eet_data_descriptor_encode(ed,
+ ede->subtype,
+ edd->func.list_data(l),
+ &size);
+ if (data)
+ eet_data_encode(ed,
+ ds,
+ data,
+ ede->name,
+ size,
+ ede->type,
+ ede->group_type);
+ }
}
}
static void
-eet_data_put_hash(Eet_Dictionary *ed, Eet_Data_Descriptor *edd, Eet_Data_Element *ede, Eet_Data_Stream *ds, void *data_in)
+eet_data_put_hash(Eet_Dictionary *ed,
+ Eet_Data_Descriptor *edd,
+ Eet_Data_Element *ede,
+ Eet_Data_Stream *ds,
+ void *data_in)
{
Eet_Data_Encode_Hash_Info fdata;
void *l;
}
EAPI int
-eet_data_dump_cipher(Eet_File *ef,
- const char *name, const char *key,
- void (*dumpfunc) (void *data, const char *str),
- void *dumpdata)
+eet_data_dump_cipher(Eet_File *ef,
+ const char *name,
+ const char *cipher_key,
+ Eet_Dump_Callback dumpfunc,
+ void *dumpdata)
{
const Eet_Dictionary *ed = NULL;
- const void *data = NULL;
- int ret = 0;
- int required_free = 0;
- int size;
+ const void *data = NULL;
+ Eet_Node *result;
+ Eet_Free_Context context;
+ int required_free = 0;
+ int size;
ed = eet_dictionary_get(ef);
- if (!key)
+ if (!cipher_key)
data = eet_read_direct(ef, name, &size);
+
if (!data)
{
- required_free = 1;
- data = eet_read_cipher(ef, name, &size, key);
- if (!data) return 0;
+ required_free = 1;
+ data = eet_read_cipher(ef, name, &size, cipher_key);
+ if (!data)
+ return 0;
}
- if (_eet_data_descriptor_decode(ed, NULL, data, size, 0,
- dumpfunc, dumpdata))
- ret = 1;
+ eet_free_context_init(&context);
+ result = _eet_data_descriptor_decode(&context, ed, NULL, data, size, NULL, 0);
+ eet_free_context_shutdown(&context);
+
+ eet_node_dump(result, 0, dumpfunc, dumpdata);
+
+ eet_node_del(result);
if (required_free)
- free((void*)data);
+ free((void *)data);
- return ret;
+ return result ? 1 : 0;
}
EAPI int
-eet_data_dump(Eet_File *ef,
- const char *name,
- void (*dumpfunc) (void *data, const char *str),
- void *dumpdata)
+eet_data_dump(Eet_File *ef,
+ const char *name,
+ Eet_Dump_Callback dumpfunc,
+ void *dumpdata)
{
return eet_data_dump_cipher(ef, name, NULL, dumpfunc, dumpdata);
}
-
EAPI int
-eet_data_text_dump_cipher(const void *data_in,
- const char *key, int size_in,
- void (*dumpfunc) (void *data, const char *str),
- void *dumpdata)
+eet_data_text_dump_cipher(const void *data_in,
+ const char *cipher_key,
+ int size_in,
+ Eet_Dump_Callback dumpfunc,
+ void *dumpdata)
{
void *ret = NULL;
+ Eet_Node *result;
+ Eet_Free_Context context;
unsigned int ret_len = 0;
- if (data_in && key)
- {
- if (eet_decipher(data_in, size_in, key, strlen(key), &ret, &ret_len))
- {
- if (ret) free(ret);
- return 1;
- }
- if (_eet_data_descriptor_decode(NULL, NULL, ret, ret_len, 0,
- dumpfunc, dumpdata))
- {
- free(ret);
- return 1;
- }
- free(ret);
- return 0;
- }
- if (_eet_data_descriptor_decode(NULL, NULL, data_in, size_in, 0,
- dumpfunc, dumpdata))
- return 1;
- return 0;
+ if (!data_in)
+ return 0;
+
+ if (cipher_key)
+ {
+ if (eet_decipher(data_in, size_in, cipher_key,
+ strlen(cipher_key), &ret, &ret_len))
+ {
+ if (ret)
+ free(ret);
+
+ return 0;
+ }
+ }
+ else
+ {
+ ret = (void *)data_in;
+ ret_len = size_in;
+ }
+
+ eet_free_context_init(&context);
+ result = _eet_data_descriptor_decode(&context, NULL, NULL, ret, ret_len, NULL, 0);
+ eet_free_context_shutdown(&context);
+
+ eet_node_dump(result, 0, dumpfunc, dumpdata);
+
+ eet_node_del(result);
+ if (cipher_key)
+ free(ret);
+
+ return result ? 1 : 0;
}
EAPI int
-eet_data_text_dump(const void *data_in,
- int size_in,
- void (*dumpfunc) (void *data, const char *str),
- void *dumpdata)
+eet_data_text_dump(const void *data_in,
+ int size_in,
+ Eet_Dump_Callback dumpfunc,
+ void *dumpdata)
{
return eet_data_text_dump_cipher(data_in, NULL, size_in, dumpfunc, dumpdata);
}
EAPI void *
eet_data_text_undump_cipher(const char *text,
- const char *key,
- int textlen,
- int *size_ret)
+ const char *cipher_key,
+ int textlen,
+ int *size_ret)
{
void *ret = NULL;
ret = _eet_data_dump_parse(NULL, size_ret, text, textlen);
- if (ret && key)
- {
- void *ciphered = NULL;
- unsigned int ciphered_len;
-
- if (eet_cipher(ret, *size_ret, key, strlen(key), &ciphered, &ciphered_len))
- {
- if (ciphered) free(ciphered);
- size_ret = 0;
- free(ret);
- return NULL;
- }
- free(ret);
- *size_ret = ciphered_len;
- ret = ciphered;
+ if (ret && cipher_key)
+ {
+ void *ciphered = NULL;
+ unsigned int ciphered_len;
+
+ if (eet_cipher(ret, *size_ret, cipher_key,
+ strlen(cipher_key), &ciphered, &ciphered_len))
+ {
+ if (ciphered)
+ free(ciphered);
+
+ size_ret = 0;
+ free(ret);
+ return NULL;
+ }
+
+ free(ret);
+ *size_ret = ciphered_len;
+ ret = ciphered;
}
+
return ret;
}
EAPI void *
eet_data_text_undump(const char *text,
- int textlen,
- int *size_ret)
+ int textlen,
+ int *size_ret)
{
return eet_data_text_undump_cipher(text, NULL, textlen, size_ret);
}
EAPI int
-eet_data_undump_cipher(Eet_File *ef,
- const char *name,
- const char *key,
- const char *text,
- int textlen,
- int compress)
-{
- Eet_Dictionary *ed;
- void *data_enc;
- int size;
- int val;
+eet_data_undump_cipher(Eet_File *ef,
+ const char *name,
+ const char *cipher_key,
+ const char *text,
+ int textlen,
+ int comp)
+{
+ Eet_Dictionary *ed;
+ void *data_enc;
+ int size;
+ int val;
ed = eet_dictionary_get(ef);
data_enc = _eet_data_dump_parse(ed, &size, text, textlen);
- if (!data_enc) return 0;
- val = eet_write_cipher(ef, name, data_enc, size, compress, key);
+ if (!data_enc)
+ return 0;
+
+ val = eet_write_cipher(ef, name, data_enc, size, comp, cipher_key);
free(data_enc);
return val;
}
EAPI int
-eet_data_undump(Eet_File *ef,
- const char *name,
- const char *text,
- int textlen,
- int compress)
+eet_data_undump(Eet_File *ef,
+ const char *name,
+ const char *text,
+ int textlen,
+ int comp)
{
- return eet_data_undump_cipher(ef, name, NULL, text, textlen, compress);
+ return eet_data_undump_cipher(ef, name, NULL, text, textlen, comp);
}
EAPI void *
eet_data_descriptor_decode_cipher(Eet_Data_Descriptor *edd,
- const void *data_in,
- const char *key,
- int size_in)
+ const void *data_in,
+ const char *cipher_key,
+ int size_in)
{
- void *deciphered = NULL;
- unsigned int deciphered_len = 0;
+ void *deciphered = (void *)data_in;
void *ret;
+ Eet_Free_Context context;
+ unsigned int deciphered_len = size_in;
- if (key && data_in)
- {
- if (eet_decipher(data_in, size_in, key, strlen(key), &deciphered, &deciphered_len))
- {
- if (deciphered) free(deciphered);
- return NULL;
- }
- ret = _eet_data_descriptor_decode(NULL, edd, deciphered, deciphered_len, 0,
- NULL, NULL);
- free(deciphered);
- return ret;
- }
- return _eet_data_descriptor_decode(NULL, edd, data_in, size_in, 0,
- NULL, NULL);
+ if (cipher_key && data_in)
+ if (eet_decipher(data_in, size_in, cipher_key,
+ strlen(cipher_key), &deciphered, &deciphered_len))
+ {
+ if (deciphered)
+ free(deciphered);
+
+ return NULL;
+ }
+
+ eet_free_context_init(&context);
+ ret = _eet_data_descriptor_decode(&context,
+ NULL,
+ edd,
+ deciphered,
+ deciphered_len,
+ NULL, 0);
+ eet_free_context_shutdown(&context);
+
+ if (data_in != deciphered)
+ free(deciphered);
+
+ return ret;
}
EAPI void *
eet_data_descriptor_decode(Eet_Data_Descriptor *edd,
- const void *data_in,
- int size_in)
+ const void *data_in,
+ int size_in)
{
return eet_data_descriptor_decode_cipher(edd, data_in, NULL, size_in);
}
+EAPI Eet_Node *
+eet_data_node_decode_cipher(const void *data_in,
+ const char *cipher_key,
+ int size_in)
+{
+ void *deciphered = (void *)data_in;
+ Eet_Node *ret;
+ Eet_Free_Context context;
+ unsigned int deciphered_len = size_in;
+
+ if (cipher_key && data_in)
+ if (eet_decipher(data_in, size_in, cipher_key,
+ strlen(cipher_key), &deciphered, &deciphered_len))
+ {
+ if (deciphered)
+ free(deciphered);
+
+ return NULL;
+ }
+
+ eet_free_context_init(&context);
+ ret = _eet_data_descriptor_decode(&context,
+ NULL,
+ NULL,
+ deciphered,
+ deciphered_len,
+ NULL, 0);
+ eet_free_context_shutdown(&context);
+
+ if (data_in != deciphered)
+ free(deciphered);
+
+ return ret;
+}
+
static void *
-_eet_data_descriptor_encode(Eet_Dictionary *ed,
+_eet_data_descriptor_encode(Eet_Dictionary *ed,
Eet_Data_Descriptor *edd,
- const void *data_in,
- int *size_ret)
+ const void *data_in,
+ int *size_ret)
{
- Eet_Data_Stream *ds;
- Eet_Data_Chunk *chnk;
- void *cdata;
- int csize;
- int i;
+ Eet_Data_Stream *ds;
+ Eet_Data_Chunk *chnk;
+ void *cdata;
+ int csize;
+ int i;
- if (words_bigendian == -1)
+ if (_eet_data_words_bigendian == -1)
{
- unsigned long int v;
+ unsigned long int v;
- v = htonl(0x12345678);
- if (v == 0x12345678) words_bigendian = 1;
- else words_bigendian = 0;
+ v = htonl(0x12345678);
+ if (v == 0x12345678)
+ _eet_data_words_bigendian = 1;
+ else
+ _eet_data_words_bigendian = 0;
}
ds = eet_data_stream_new();
for (i = 0; i < edd->elements.num; i++)
{
- Eet_Data_Element *ede;
-
- ede = &(edd->elements.set[i]);
- eet_group_codec[ede->group_type - 100].put(ed, edd, ede, ds, ((char *)data_in) + ede->offset);
+ Eet_Data_Element *ede;
+
+ ede = &(edd->elements.set[i]);
+ eet_group_codec[ede->group_type - 100].put(
+ ed,
+ edd,
+ ede,
+ ds,
+ ((char *)data_in) +
+ ede->offset);
}
- chnk = eet_data_chunk_new(ds->data, ds->pos, edd->name, EET_T_UNKNOW, EET_G_UNKNOWN);
+ chnk = eet_data_chunk_new(ds->data,
+ ds->pos,
+ edd->name,
+ EET_T_UNKNOW,
+ EET_G_UNKNOWN);
ds->data = NULL;
ds->size = 0;
eet_data_stream_free(ds);
return cdata;
}
+EAPI int
+eet_data_node_write_cipher(Eet_File *ef,
+ const char *name,
+ const char *cipher_key,
+ Eet_Node *node,
+ int comp)
+{
+ Eet_Dictionary *ed;
+ void *data_enc;
+ int size;
+ int val;
+
+ ed = eet_dictionary_get(ef);
+
+ data_enc = _eet_data_dump_encode(EET_G_UNKNOWN, ed, node, &size);
+ if (!data_enc)
+ return 0;
+
+ val = eet_write_cipher(ef, name, data_enc, size, comp, cipher_key);
+ free(data_enc);
+ return val;
+}
+
+EAPI void *
+eet_data_node_encode_cipher(Eet_Node *node,
+ const char *cipher_key,
+ int *size_ret)
+{
+ void *ret = NULL;
+ void *ciphered = NULL;
+ unsigned int ciphered_len = 0;
+ int size;
+
+ ret = _eet_data_dump_encode(EET_G_UNKNOWN, NULL, node, &size);
+ if (cipher_key && ret)
+ {
+ if (eet_cipher(ret, size, cipher_key,
+ strlen(cipher_key), &ciphered, &ciphered_len))
+ {
+ if (ciphered)
+ free(ciphered);
+
+ if (size_ret)
+ *size_ret = 0;
+
+ free(ret);
+ return NULL;
+ }
+
+ free(ret);
+ size = (int)ciphered_len;
+ ret = ciphered;
+ }
+
+ if (size_ret)
+ *size_ret = size;
+
+ return ret;
+}
+
EAPI void *
eet_data_descriptor_encode_cipher(Eet_Data_Descriptor *edd,
- const void *data_in,
- const char *key,
- int *size_ret)
+ const void *data_in,
+ const char *cipher_key,
+ int *size_ret)
{
void *ret = NULL;
void *ciphered = NULL;
unsigned int ciphered_len = 0;
+ int size;
- ret = _eet_data_descriptor_encode(NULL, edd, data_in, size_ret);
- if (key && ret)
+ ret = _eet_data_descriptor_encode(NULL, edd, data_in, &size);
+ if (cipher_key && ret)
{
- if (eet_cipher(ret, *size_ret, key, strlen(key), &ciphered, &ciphered_len))
- {
- if (ciphered) free(ciphered);
- size_ret = 0;
- free(ret);
- return NULL;
- }
- free(ret);
- *size_ret = ciphered_len;
- ret = ciphered;
+ if (eet_cipher(ret, size, cipher_key,
+ strlen(cipher_key), &ciphered, &ciphered_len))
+ {
+ if (ciphered)
+ free(ciphered);
+
+ if (size_ret)
+ *size_ret = 0;
+
+ free(ret);
+ return NULL;
+ }
+
+ free(ret);
+ size = ciphered_len;
+ ret = ciphered;
}
+
+ if (size_ret)
+ *size_ret = size;
+
return ret;
}
EAPI void *
eet_data_descriptor_encode(Eet_Data_Descriptor *edd,
- const void *data_in,
- int *size_ret)
+ const void *data_in,
+ int *size_ret)
{
return eet_data_descriptor_encode_cipher(edd, data_in, NULL, size_ret);
}
+
+EAPI void *
+eet_data_xattr_cipher_get(const char *filename,
+ const char *attribute,
+ Eet_Data_Descriptor *edd,
+ const char *cipher_key)
+{
+ void *blob;
+ void *ret;
+ ssize_t size;
+
+ blob = eina_xattr_get(filename, attribute, &size);
+ if (!blob) return NULL;
+
+ ret = eet_data_descriptor_decode_cipher(edd, blob, cipher_key, size);
+ free(blob);
+
+ return ret;
+}
+
+EAPI Eina_Bool
+eet_data_xattr_cipher_set(const char *filename,
+ const char *attribute,
+ Eet_Data_Descriptor *edd,
+ const char *cipher_key,
+ const void *data,
+ Eina_Xattr_Flags flags)
+{
+ void *blob;
+ int size;
+ Eina_Bool ret;
+
+ blob = eet_data_descriptor_encode_cipher(edd, data, cipher_key, &size);
+ if (!blob) return EINA_FALSE;
+
+ ret = eina_xattr_set(filename, attribute, blob, size, flags);
+ free(blob);
+
+ return ret;
+}