]> git.tdb.fi Git - gldbg.git/blob - source/gldecoder.c
f61e327aa92a9217a589ebb8f7174680f8125a7c
[gldbg.git] / source / gldecoder.c
1 /* $Id$
2
3 This file is part of gldbg
4 Copyright © 2009  Mikko Rasa, Mikkosoft Productions
5 Distributed under the GPL
6 */
7
8 #include <stdlib.h>
9 #include <string.h>
10 #include "functions.h"
11 #include "gldecoder.h"
12 #include "tmpalloc.h"
13
14 static unsigned read_short(short *, const char *);
15 static unsigned read_int(int *, const char *);
16 static int decode_func(GlDecoder *, unsigned short, const char *);
17 static int decode_gldfunc(GlDecoder *, unsigned short, const char *);
18
19 GlDecoder *gldecoder_new(void *user_data, void (*destroy)(void *))
20 {
21         GlDecoder *dec;
22
23         dec = (GlDecoder *)malloc(sizeof(GlDecoder));
24         memset(dec, 0, sizeof(GlDecoder));
25         dec->user_data = user_data;
26         dec->destroy = destroy;
27
28         return dec;
29 }
30
31 void gldecoder_delete(GlDecoder *dec)
32 {
33         if(dec->destroy)
34                 dec->destroy(dec->user_data);
35         free(dec);
36 }
37
38 int gldecoder_decode(GlDecoder *dec, const char *data, unsigned len)
39 {
40         unsigned pos = 0;
41         unsigned pktlen;
42         unsigned short func;
43         int ret;
44
45         if(len<sizeof(int)+sizeof(short))
46                 return -1;
47         pos += read_int((int *)&pktlen, data);
48         if(len<pktlen)
49                 return -1;
50         pos += read_short((short *)&func, data+pos);
51         if(dec)
52         {
53                 if(func&0x8000)
54                         ret = decode_gldfunc(dec, func, data+pos);
55                 else
56                         ret = decode_func(dec, func, data+pos);
57                 if(ret<0)
58                         return -1;
59         }
60         return pktlen;
61 }
62
63 static unsigned read_char(char *v, const char *data)
64 {
65         *v = *data;
66         return 1;
67 }
68
69 static unsigned read_short(short *v, const char *data)
70 {
71         *v = *(short *)data;
72         return sizeof(short);
73 }
74
75 static unsigned read_int(int *v, const char *data)
76 {
77         *v = *(int *)data;
78         return sizeof(int);
79 }
80
81 static unsigned read_long(long *v, const char *data)
82 {
83         *v = *(long *)data;
84         return sizeof(long);
85 }
86
87 static unsigned read_long_long(long long *v, const char *data)
88 {
89         *v = *(long long *)data;
90         return sizeof(long long);
91 }
92
93 static unsigned read_float(float *v, const char *data)
94 {
95         *v = *(float *)data;
96         return sizeof(float);
97 }
98
99 static unsigned read_double(double *v, const char *data)
100 {
101         *v = *(double *)data;
102         return sizeof(double);
103 }
104
105 typedef void *pointer;
106
107 static unsigned read_pointer(pointer *v, const char *data)
108 {
109         *v = *(void **)data;
110         return sizeof(void *);
111 }
112
113 static unsigned read_data(const void **v, const char *data)
114 {
115         int vlen;
116         unsigned pos = 0;
117         pos += read_int(&vlen, data);
118         if(vlen)
119                 *v = data+pos;
120         else
121                 *v = NULL;
122         return pos+vlen;
123 }
124
125 typedef const char *string;
126
127 static unsigned read_string(string *v, const char *data)
128 {
129         return read_data((const void **)v, data);
130 }
131
132 static unsigned read_string_array(string **v, const char *data)
133 {
134         int count;
135         unsigned pos = 0;
136         int i;
137         pos += read_int(&count, data);
138         *v = (string *)tmpalloc(count*sizeof(string));
139         for(i=0; i<count; ++i)
140                 pos += read_string(*v+i, data+pos);
141         return pos;
142 }
143
144 #include "gensrc/gldecoder.funcs"
145
146 static int decode_gldError(GlDecoder *dec, const char *data)
147 {
148         unsigned pos = 0;
149         GLenum code;
150         pos += read_int((int *)&code, data);
151         if(dec->gldError)
152                 dec->gldError(dec->user_data, code);
153         return pos;
154 }
155
156 static int decode_gldfunc(GlDecoder *dec, unsigned short func, const char *data)
157 {
158         switch(func)
159         {
160         case FUNC_GLDERROR: return decode_gldError(dec, data);
161         default: return -1;
162         }
163 }