1 /* General header for the Gedcom object model.
2 Copyright (C) 2002 The Genes Development Team
3 This file is part of the Gedcom parser library.
4 Contributed by Peter Verthez <Peter.Verthez@advalvas.be>, 2002.
6 The Gedcom parser library is free software; you can redistribute it
7 and/or modify it under the terms of the GNU Lesser General Public
8 License as published by the Free Software Foundation; either
9 version 2.1 of the License, or (at your option) any later version.
11 The Gedcom parser library is distributed in the hope that it will be
12 useful, but WITHOUT ANY WARRANTY; without even the implied warranty of
13 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
14 Lesser General Public License for more details.
16 You should have received a copy of the GNU Lesser General Public
17 License along with the Gedcom parser library; if not, write to the
18 Free Software Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA
24 #ifndef __GOM_INTERNAL_H
25 #define __GOM_INTERNAL_H
36 #define _(string) dgettext(PACKAGE, string)
37 #define N_(string) (string)
40 #define UNUSED __attribute__((unused))
48 T_header, T_submission, T_submitter, T_family, T_individual,
49 T_multimedia, T_note, T_repository, T_source, T_user_rec,
51 T_address, T_event, T_place, T_source_citation, T_text,
52 T_note_sub, T_multimedia_link, T_lds_event, T_user_ref_number,
53 T_change_date, T_personal_name, T_family_link, T_pedigree,
54 T_association, T_source_event, T_source_description
57 /* Assumptions for context:
58 - In case of error, NULL is passed as context
59 - If not NULL, the ctxt_ptr of the context is not NULL also
60 - UNEXPECTED_CONTEXT is not treated as an error, but as a warning
63 struct Gom_ctxt_struct {
69 typedef struct Gom_ctxt_struct *Gom_ctxt;
71 Gom_ctxt make_gom_ctxt(int ctxt_type, OBJ_TYPE obj_type, void *ctxt_ptr);
72 void destroy_gom_ctxt(Gom_ctxt ctxt);
73 void gom_cast_error(const char* file, int line,
74 OBJ_TYPE expected, OBJ_TYPE found);
75 void gom_no_context(const char* file, int line);
76 void gom_unexpected_context(const char* file, int line, OBJ_TYPE found);
78 int gom_write_xref_list(Gedcom_write_hndl hndl,
79 Gedcom_elt elt, int tag, int parent_rec_or_elt,
80 struct xref_list* val);
82 #define MAKE_GOM_CTXT(CTXT_TYPE, STRUCTTYPE, CTXT_PTR) \
83 make_gom_ctxt(CTXT_TYPE, T_ ## STRUCTTYPE, CTXT_PTR)
85 #define SAFE_CTXT_CAST(STRUCTTYPE, VAL) \
86 (((VAL)->obj_type == T_ ## STRUCTTYPE) ? \
88 (gom_cast_error(__FILE__, __LINE__, T_ ## STRUCTTYPE, (VAL)->obj_type), \
91 #define SAFE_FREE(PTR) \
97 #define UNEXPECTED_CONTEXT(CTXT_TYPE) \
98 gom_unexpected_context(__FILE__, __LINE__, CTXT_TYPE)
101 gom_no_context(__FILE__, __LINE__)
103 void gom_mem_error(const char *filename, int line);
105 #define MEMORY_ERROR gom_mem_error(__FILE__, __LINE__)
107 void def_rec_end(Gedcom_rec rec, Gedcom_ctxt self, Gedcom_val parsed_value);
108 void def_elt_end(Gedcom_elt elt, Gedcom_ctxt parent,
109 Gedcom_ctxt self, Gedcom_val parsed_value);
110 void set_xref_type(struct xref_value *xr, const char* str);
112 struct date_value* dup_date(struct date_value dv);
113 struct age_value* dup_age(struct age_value age);
115 /* Doubly-linked list, but last rec->next is NULL (doesn't go to first rec) */
116 #define LINK_CHAIN_ELT(STRUCTTYPE, FIRSTVAL, VAL) \
118 struct STRUCTTYPE *_local_obj = VAL; \
121 VAL->previous = _local_obj; \
126 FIRSTVAL->previous->next = VAL; \
127 VAL->previous = FIRSTVAL->previous; \
128 FIRSTVAL->previous = VAL; \
132 #define MAKE_CHAIN_ELT(STRUCTTYPE, FIRSTVAL, VAL) \
134 VAL = (struct STRUCTTYPE*) malloc(sizeof(struct STRUCTTYPE)); \
138 memset (VAL, 0, sizeof(struct STRUCTTYPE)); \
139 LINK_CHAIN_ELT(STRUCTTYPE, FIRSTVAL, VAL) \
143 void NULL_DESTROY(void* anything);
145 #define DESTROY_CHAIN_ELTS(STRUCTTYPE, FIRSTVAL, DESTROYFUNC) \
148 struct STRUCTTYPE *runner, *next; \
151 next = runner->next; \
152 DESTROYFUNC(runner); \
159 #define _REC_PARAMS_ Gedcom_rec rec UNUSED, int level UNUSED, \
160 Gedcom_val xref UNUSED, char *tag UNUSED, \
161 char *raw_value UNUSED, int parsed_tag UNUSED, \
162 Gedcom_val parsed_value UNUSED
164 #define _REC_END_PARAMS_ Gedcom_rec rec UNUSED, Gedcom_ctxt self UNUSED, \
165 Gedcom_val parsed_value UNUSED
167 #define _ELT_PARAMS_ Gedcom_elt elt UNUSED, Gedcom_ctxt parent UNUSED, \
168 int level UNUSED, char *tag UNUSED, \
169 char *raw_value UNUSED, int parsed_tag UNUSED, \
170 Gedcom_val parsed_value UNUSED
172 #define _ELT_END_PARAMS_ Gedcom_elt elt UNUSED, Gedcom_ctxt parent UNUSED, \
173 Gedcom_ctxt self UNUSED, \
174 Gedcom_val parsed_value UNUSED
176 #define REC_CB(STRUCTTYPE,CB_NAME,FUNC) \
177 Gedcom_ctxt CB_NAME(_REC_PARAMS_) \
179 struct xref_value* xr = GEDCOM_XREF_PTR(xref); \
181 xr->object = (Gedcom_ctxt) FUNC(xr->string); \
183 return (Gedcom_ctxt) MAKE_GOM_CTXT(rec, STRUCTTYPE, xr->object); \
188 #define GET_REC_BY_XREF(STRUCTTYPE,XREF_TYPE,FUNC_NAME) \
189 struct STRUCTTYPE *FUNC_NAME(const char *xrefstr) \
191 struct xref_value* xr = gedcom_get_by_xref(xrefstr); \
192 if (xr && (xr->type == XREF_TYPE) && xr->object) \
193 return (struct STRUCTTYPE*)(xr->object); \
198 #define STRING_CB(STRUCTTYPE,CB_NAME,FIELD) \
199 Gedcom_ctxt CB_NAME(_ELT_PARAMS_) \
201 Gom_ctxt result = NULL; \
205 struct STRUCTTYPE *obj \
206 = SAFE_CTXT_CAST(STRUCTTYPE, (Gom_ctxt)parent); \
208 char *str = GEDCOM_STRING(parsed_value); \
209 obj->FIELD = strdup(str); \
213 result = MAKE_GOM_CTXT(elt, STRUCTTYPE, obj); \
216 return (Gedcom_ctxt)result; \
219 #define STRING_END_CB(STRUCTTYPE,CB_NAME,FIELD) \
220 void CB_NAME(_ELT_END_PARAMS_) \
222 Gom_ctxt ctxt = (Gom_ctxt)self; \
226 struct STRUCTTYPE *obj = SAFE_CTXT_CAST(STRUCTTYPE, ctxt); \
228 char *str = GEDCOM_STRING(parsed_value); \
229 char *newvalue = strdup(str); \
233 obj->FIELD = newvalue; \
235 destroy_gom_ctxt(ctxt); \
239 #define STRING_END_REC_CB(STRUCTTYPE,CB_NAME,FIELD) \
240 void CB_NAME(_REC_END_PARAMS_) \
242 Gom_ctxt ctxt = (Gom_ctxt)self; \
246 struct STRUCTTYPE *obj = SAFE_CTXT_CAST(STRUCTTYPE, ctxt); \
248 char *str = GEDCOM_STRING(parsed_value); \
249 char *newvalue = strdup(str); \
253 obj->FIELD = newvalue; \
255 destroy_gom_ctxt(ctxt); \
259 #define DATE_CB(STRUCTTYPE,CB_NAME,FIELD) \
260 Gedcom_ctxt CB_NAME(_ELT_PARAMS_) \
262 Gom_ctxt result = NULL; \
266 struct STRUCTTYPE *obj \
267 = SAFE_CTXT_CAST(STRUCTTYPE, (Gom_ctxt)parent); \
269 struct date_value dv = GEDCOM_DATE(parsed_value); \
270 obj->FIELD = dup_date(dv); \
274 result = MAKE_GOM_CTXT(elt, STRUCTTYPE, obj); \
277 return (Gedcom_ctxt)result; \
280 #define AGE_CB(STRUCTTYPE,CB_NAME,FIELD) \
281 Gedcom_ctxt CB_NAME(_ELT_PARAMS_) \
283 Gom_ctxt result = NULL; \
287 struct STRUCTTYPE *obj \
288 = SAFE_CTXT_CAST(STRUCTTYPE, (Gom_ctxt)parent); \
290 struct age_value age = GEDCOM_AGE(parsed_value); \
291 obj->FIELD = dup_age(age); \
295 result = MAKE_GOM_CTXT(elt, STRUCTTYPE, obj); \
298 return (Gedcom_ctxt)result; \
301 #define XREF_CB(STRUCTTYPE,CB_NAME,FIELD,FUNC) \
302 Gedcom_ctxt CB_NAME(_ELT_PARAMS_) \
304 Gom_ctxt result = NULL; \
308 struct STRUCTTYPE *obj \
309 = SAFE_CTXT_CAST(STRUCTTYPE, (Gom_ctxt)parent); \
310 struct xref_value *xr = GEDCOM_XREF_PTR(parsed_value); \
312 xr->object = (Gedcom_ctxt) FUNC(xr->string); \
315 result = MAKE_GOM_CTXT(elt, STRUCTTYPE, obj); \
318 return (Gedcom_ctxt)result; \
321 #define XREF_LIST_CB(STRUCTTYPE,CB_NAME,FIELD,FUNC) \
322 Gedcom_ctxt CB_NAME(_ELT_PARAMS_) \
324 Gom_ctxt result = NULL; \
328 struct STRUCTTYPE *obj \
329 = SAFE_CTXT_CAST(STRUCTTYPE, (Gom_ctxt)parent); \
330 struct xref_value *xr = GEDCOM_XREF_PTR(parsed_value); \
331 struct xref_list *xrl; \
333 xr->object = (Gedcom_ctxt) FUNC(xr->string); \
335 MAKE_CHAIN_ELT(xref_list, obj->FIELD, xrl); \
338 result = MAKE_GOM_CTXT(elt, STRUCTTYPE, obj); \
342 return (Gedcom_ctxt)result; \
345 #define NULL_CB(STRUCTTYPE,CB_NAME) \
346 Gedcom_ctxt CB_NAME(_ELT_PARAMS_) \
348 Gom_ctxt result = NULL; \
352 struct STRUCTTYPE *obj \
353 = SAFE_CTXT_CAST(STRUCTTYPE, (Gom_ctxt)parent); \
355 result = MAKE_GOM_CTXT(elt, STRUCTTYPE, obj); \
357 return (Gedcom_ctxt)result; \
360 #endif /* __GOM_INTERNAL_H */