]> mj.ucw.cz Git - moe.git/blob - sherlock/objread.h
Cleanups in mop/score/.
[moe.git] / sherlock / objread.h
1 /*
2  *      Sherlock Library -- Nested Object Reading Functions
3  *
4  *      (c) 2005 Martin Mares <mj@ucw.cz>
5  *
6  *      This software may be freely distributed and used according to the terms
7  *      of the GNU Lesser General Public License.
8  */
9
10 #ifndef _SHERLOCK_OBJREAD_H
11 #define _SHERLOCK_OBJREAD_H
12
13 #include "sherlock/object.h"
14
15 struct obj_read_state {
16   struct odes *root, *obj;
17   void (*error_callback)(struct obj_read_state *st, char *msg);
18   void *user;
19   int errors;
20 };
21
22 void default_obj_read_error(struct obj_read_state *st, char *msg);
23
24 static inline void
25 obj_read_start(struct obj_read_state *st, struct odes *obj)
26 {
27   st->root = st->obj = obj;
28   st->errors = 0;
29   st->error_callback = default_obj_read_error;
30 }
31
32 static inline void
33 obj_read_push(struct obj_read_state *st, byte *ptr)
34 {
35   if (unlikely(!ptr[0] || ptr[1]))
36     {
37       if (!st->errors++)
38         st->error_callback(st, "Malformed object: bad `(' attribute");
39     }
40   else
41     st->obj = obj_add_son(st->obj, ptr[0] + OBJ_ATTR_SON);
42 }
43
44 static inline void
45 obj_read_pop(struct obj_read_state *st, byte *ptr)
46 {
47   if (unlikely(ptr[0]))
48     {
49       if (!st->errors++)
50         st->error_callback(st, "Malformed object: bad ')' attribute");
51     }
52   else if (unlikely(!st->obj->parent))
53     {
54       if (!st->errors++)
55         st->error_callback(st, "Malformed object: improper nesting of `( ... )' blocks");
56     }
57   else
58     st->obj = st->obj->parent;
59 }
60
61 static inline void
62 obj_read_attr(struct obj_read_state *st, uns type, byte *val)
63 {
64   if (type == '(')
65     obj_read_push(st, val);
66   else if (type == ')')
67     obj_read_pop(st, val);
68   else
69     obj_add_attr(st->obj, type, val);
70 }
71
72 static inline void
73 obj_read_attr_ref(struct obj_read_state *st, uns type, byte *val)
74 {
75   if (type == '(')
76     obj_read_push(st, val);
77   else if (type == ')')
78     obj_read_pop(st, val);
79   else
80     obj_add_attr_ref(st->obj, type, val);
81 }
82
83 static inline int
84 obj_read_end(struct obj_read_state *st)
85 {
86   if (unlikely(st->obj != st->root))
87     {
88       if (!st->errors++)
89         st->error_callback(st, "Malformed object: truncated `( ... )' block");
90     }
91   return st->errors;
92 }
93
94 #endif