1 /* This program is free software; you can redistribute it and/or modify *
2 * it under the terms of the GNU General Public License as published by *
3 * the Free Software Foundation; either version 2 of the License, or *
4 * (at your option) any later version. *
6 (C) 2001 by The Genes Development Team
7 Original author: Peter Verthez (Peter.Verthez@advalvas.be)
13 /* WARNING: THIS PARSER RELIES HEAVILY ON SOME FEATURES OF BISON.
14 DON'T TRY TO USE IT WITH YACC, IT WON'T WORK...
17 /* Design of the parser:
19 In general, a GEDCOM file contains records, each consisting of a line
20 (which we'll call a section), hierarchically containing other lines
21 (subsections of the section).
23 This means that in general we have:
25 A 'record' is a 'section' (sect) containing 'subsections' (subs)
26 Each 'subsection' (sub) is again a specific 'section' (sect)
28 In parser notation, this means:
32 sect : <some prefix> subs <some suffix>
34 subs : <empty> | subs sub
36 sub : sect_a | sect_b | ...
38 This pattern is repeated throughout the parser for the different types of
42 Cardinality of the subsections:
43 -------------------------------
44 Note that in the above, the order of the subsections is of no importance.
45 Indeed, this is the case in the GEDCOM grammar. However, this also makes
46 it difficult to check whether there are not too many subsections of a
47 specific type, or whether a mandatory subsection is indeed there.
49 Suppose there is a section A that can contain 0 or 1 B section and
52 This can be expressed in parser notation as follows:
54 A : CC | BCC | CBC | CCB
56 So, cardinality is indeed expressable. However, as the number of subsection
57 types and the limits grow bigger (and even theoretically limitless), listing
58 all possible permutations becomes quickly unfeasible.
60 Much simpler is to say:
63 subs : <empty> | subs sub
66 and then check the cardinality in the semantic actions, which is the
67 solution chosen in the parser below, using the following macros:
70 Make a new context for the <parent> tag to count child tags in
72 - OCCUR2(<child>, <min>, <max>)
73 Express that the <child> tag should occur at least <min> times and
74 at most <max> tags within its parent
76 What this actually does is the following. It increments the counter
77 for that tag and then checks whether the maximum is exceeded. If so,
78 then a parser error is produced. The minimum is not actually checked
79 by this macro, but it makes the statements more declarative.
81 - OCCUR1(<child>, <min>)
82 Express that the <child> tag should occur at least <min> times within
83 its parent (no upper limit)
85 Actually, this only increments the counter for the tag, but it looks
86 very like the previous macro.
88 If the minimum is 0, it is not necessary to express this constraint.
90 - CHECKn(<child1>, ..., <childn>)
91 This closes the context for the parent tag and checks whether the
92 given <child> tags did effectively occur within the parent (i.e.
93 these are the tags that were mandatory).
95 Since the <min> values above are always 0 or 1 in GEDCOM, this is
96 sufficient. All sub-tags that declare a minimum of 1 in the OCCUR
97 macros should be listed in this macro here.
99 The macros CHECK0 to CHECK4 are defined like this (the first one
100 has no arguments and is only used to close the parent context; note
101 that this is necessary for correct functioning).
105 Only sections that have subsections need to use these macros. This can
106 be done like this (the OPEN and CHECK macros are used as mid-rule
107 actions around the subsections):
109 head_sect : OPEN DELIM TAG_HEAD
113 CLOSE { <semantic actions> }
119 head_sub : head_sour_sect { OCCUR2(SOUR, 1, 1) }
120 | head_dest_sect { OCCUR2(DEST, 0, 1) }
121 | head_date_sect { OCCUR2(DATE, 0, 1) }
127 - The syntax analysis doesn't handle the contents of the line values;
128 this is done in the semantic analysis.
133 #include "gedcom_internal.h"
134 #include "multilex.h"
135 #include "encoding.h"
136 #include "interface.h"
140 int compat_enabled = 1;
141 int gedcom_high_level_debug = 0;
142 int compatibility = 0;
143 Gedcom_err_mech error_mechanism = IMMED_FAIL;
145 char line_item_buf[MAXGEDCLINELEN * UTF_FACTOR + 1];
146 char *line_item_buf_ptr;
152 /* These are defined at the bottom of the file */
153 void push_countarray();
154 void set_parenttag(char* tag);
155 char* get_parenttag();
156 void set_parentctxt(Gedcom_ctxt ctxt);
157 Gedcom_ctxt get_parentctxt();
158 void pop_countarray();
159 int count_tag(int tag);
160 int check_occurrence(int tag);
161 void set_compatibility(char* program);
162 int compat_mode(int flags);
164 #define CLEAR_BUFFER(BUF) \
165 memset(BUF, 0, sizeof(BUF));
167 #define HANDLE_ERROR \
168 { if (error_mechanism == IMMED_FAIL) { \
171 else if (error_mechanism == DEFER_FAIL) { \
174 else if (error_mechanism == IGNORE_ERRORS) { \
178 #define START(PARENTTAG,PARENTCTXT) \
180 set_parenttag(#PARENTTAG); \
181 set_parentctxt(PARENTCTXT); \
187 { if (!check_occurrence(TAG_##TAG)) { \
188 char* parenttag = get_parenttag(); \
189 gedcom_error("The tag '%s' is mandatory within '%s', but missing", \
195 { pop_countarray(); \
199 #define CHECK1(TAG1) { CHK(TAG1); POP; }
200 #define CHECK2(TAG1,TAG2) \
201 { CHK(TAG1); CHK(TAG2); POP; }
202 #define CHECK3(TAG1,TAG2,TAG3) \
203 { CHK(TAG1); CHK(TAG2); CHK(TAG3); POP; }
204 #define CHECK4(TAG1,TAG2,TAG3,TAG4) \
205 { CHK(TAG1); CHK(TAG2); CHK(TAG3); CHK(TAG4); POP; }
206 #define OCCUR1(CHILDTAG, MIN) { count_tag(TAG_##CHILDTAG); }
207 #define OCCUR2(CHILDTAG, MIN, MAX) \
208 { int num = count_tag(TAG_##CHILDTAG); \
210 char* parenttag = get_parenttag(); \
211 gedcom_error("The tag '%s' can maximally occur %d " \
212 "time(s) within '%s'", \
213 #CHILDTAG, MAX, parenttag); \
217 #define INVALID_TAG(CHILDTAG) \
218 { char* parenttag = get_parenttag(); \
219 gedcom_error("The tag '%s' is not a valid tag within '%s'", \
220 CHILDTAG, parenttag); \
223 #define INVALID_TOP_TAG(CHILDTAG) \
224 { gedcom_error("The tag '%s' is not a valid top-level tag", \
240 %token <string> BADTOKEN
242 %token <string> CLOSE
243 %token <string> ESCAPE
244 %token <string> DELIM
245 %token <string> ANYCHAR
246 %token <string> POINTER
247 %token <string> USERTAG
248 %token <string> TAG_ABBR
249 %token <string> TAG_ADDR
250 %token <string> TAG_ADR1
251 %token <string> TAG_ADR2
252 %token <string> TAG_ADOP
253 %token <string> TAG_AFN
254 %token <string> TAG_AGE
255 %token <string> TAG_AGNC
256 %token <string> TAG_ALIA
257 %token <string> TAG_ANCE
258 %token <string> TAG_ANCI
259 %token <string> TAG_ANUL
260 %token <string> TAG_ASSO
261 %token <string> TAG_AUTH
262 %token <string> TAG_BAPL
263 %token <string> TAG_BAPM
264 %token <string> TAG_BARM
265 %token <string> TAG_BASM
266 %token <string> TAG_BIRT
267 %token <string> TAG_BLES
268 %token <string> TAG_BLOB
269 %token <string> TAG_BURI
270 %token <string> TAG_CALN
271 %token <string> TAG_CAST
272 %token <string> TAG_CAUS
273 %token <string> TAG_CENS
274 %token <string> TAG_CHAN
275 %token <string> TAG_CHAR
276 %token <string> TAG_CHIL
277 %token <string> TAG_CHR
278 %token <string> TAG_CHRA
279 %token <string> TAG_CITY
280 %token <string> TAG_CONC
281 %token <string> TAG_CONF
282 %token <string> TAG_CONL
283 %token <string> TAG_CONT
284 %token <string> TAG_COPR
285 %token <string> TAG_CORP
286 %token <string> TAG_CREM
287 %token <string> TAG_CTRY
288 %token <string> TAG_DATA
289 %token <string> TAG_DATE
290 %token <string> TAG_DEAT
291 %token <string> TAG_DESC
292 %token <string> TAG_DESI
293 %token <string> TAG_DEST
294 %token <string> TAG_DIV
295 %token <string> TAG_DIVF
296 %token <string> TAG_DSCR
297 %token <string> TAG_EDUC
298 %token <string> TAG_EMIG
299 %token <string> TAG_ENDL
300 %token <string> TAG_ENGA
301 %token <string> TAG_EVEN
302 %token <string> TAG_FAM
303 %token <string> TAG_FAMC
304 %token <string> TAG_FAMF
305 %token <string> TAG_FAMS
306 %token <string> TAG_FCOM
307 %token <string> TAG_FILE
308 %token <string> TAG_FORM
309 %token <string> TAG_GEDC
310 %token <string> TAG_GIVN
311 %token <string> TAG_GRAD
312 %token <string> TAG_HEAD
313 %token <string> TAG_HUSB
314 %token <string> TAG_IDNO
315 %token <string> TAG_IMMI
316 %token <string> TAG_INDI
317 %token <string> TAG_LANG
318 %token <string> TAG_LEGA
319 %token <string> TAG_MARB
320 %token <string> TAG_MARC
321 %token <string> TAG_MARL
322 %token <string> TAG_MARR
323 %token <string> TAG_MARS
324 %token <string> TAG_MEDI
325 %token <string> TAG_NAME
326 %token <string> TAG_NATI
327 %token <string> TAG_NATU
328 %token <string> TAG_NCHI
329 %token <string> TAG_NICK
330 %token <string> TAG_NMR
331 %token <string> TAG_NOTE
332 %token <string> TAG_NPFX
333 %token <string> TAG_NSFX
334 %token <string> TAG_OBJE
335 %token <string> TAG_OCCU
336 %token <string> TAG_ORDI
337 %token <string> TAG_ORDN
338 %token <string> TAG_PAGE
339 %token <string> TAG_PEDI
340 %token <string> TAG_PHON
341 %token <string> TAG_PLAC
342 %token <string> TAG_POST
343 %token <string> TAG_PROB
344 %token <string> TAG_PROP
345 %token <string> TAG_PUBL
346 %token <string> TAG_QUAY
347 %token <string> TAG_REFN
348 %token <string> TAG_RELA
349 %token <string> TAG_RELI
350 %token <string> TAG_REPO
351 %token <string> TAG_RESI
352 %token <string> TAG_RESN
353 %token <string> TAG_RETI
354 %token <string> TAG_RFN
355 %token <string> TAG_RIN
356 %token <string> TAG_ROLE
357 %token <string> TAG_SEX
358 %token <string> TAG_SLGC
359 %token <string> TAG_SLGS
360 %token <string> TAG_SOUR
361 %token <string> TAG_SPFX
362 %token <string> TAG_SSN
363 %token <string> TAG_STAE
364 %token <string> TAG_STAT
365 %token <string> TAG_SUBM
366 %token <string> TAG_SUBN
367 %token <string> TAG_SURN
368 %token <string> TAG_TEMP
369 %token <string> TAG_TEXT
370 %token <string> TAG_TIME
371 %token <string> TAG_TITL
372 %token <string> TAG_TRLR
373 %token <string> TAG_TYPE
374 %token <string> TAG_VERS
375 %token <string> TAG_WIFE
376 %token <string> TAG_WILL
378 %type <string> anystdtag
379 %type <string> anytoptag
380 %type <string> line_item
381 %type <string> line_value
382 %type <string> mand_line_item
383 %type <string> mand_pointer
384 %type <string> note_line_item
385 %type <string> anychar
386 %type <string> opt_xref
387 %type <string> opt_value
388 %type <ctxt> head_sect
392 file : head_sect records trlr_sect
393 { if (fail == 1) YYABORT; }
396 records : /* empty */
411 /*********************************************************************/
413 /*********************************************************************/
414 head_sect : OPEN DELIM TAG_HEAD
415 { $<ctxt>$ = start_record(REC_HEAD, $1, NULL, $3);
416 START(HEAD, $<ctxt>$) }
418 { if (compat_mode(C_FTREE))
419 CHECK3(SOUR, GEDC, CHAR)
421 CHECK4(SOUR, SUBM, GEDC, CHAR)
424 { end_record(REC_HEAD, $<ctxt>4); }
427 head_subs : /* empty */
431 head_sub : head_sour_sect { OCCUR2(SOUR, 1, 1) }
432 | head_dest_sect { OCCUR2(DEST, 0, 1) }
433 | head_date_sect { OCCUR2(DATE, 0, 1) }
434 | head_subm_sect { OCCUR2(SUBM, 1, 1) }
435 | head_subn_sect { OCCUR2(SUBN, 0, 1) }
436 | head_file_sect { OCCUR2(FILE, 0, 1) }
437 | head_copr_sect { OCCUR2(COPR, 0, 1) }
438 | head_gedc_sect { OCCUR2(GEDC, 1, 1) }
439 | head_char_sect { OCCUR2(CHAR, 1, 1) }
440 | head_lang_sect { OCCUR2(LANG, 0, 1) }
441 | head_plac_sect { OCCUR2(PLAC, 0, 1) }
442 | head_note_sect { OCCUR2(NOTE, 0, 1) }
447 head_sour_sect : OPEN DELIM TAG_SOUR mand_line_item
448 { set_compatibility($4);
449 $<ctxt>$ = start_element(ELT_HEAD_SOUR, PARENT,
451 START(SOUR, $<ctxt>$)
456 { end_element(ELT_HEAD_SOUR, PARENT, $<ctxt>5, NULL); }
459 head_sour_subs : /* empty */
460 | head_sour_subs head_sour_sub
463 head_sour_sub : head_sour_vers_sect { OCCUR2(VERS, 0, 1) }
464 | head_sour_name_sect { OCCUR2(NAME, 0, 1) }
465 | head_sour_corp_sect { OCCUR2(CORP, 0, 1) }
466 | head_sour_data_sect { OCCUR2(DATA, 0, 1) }
470 head_sour_vers_sect : OPEN DELIM TAG_VERS mand_line_item
471 { $<ctxt>$ = start_element(ELT_HEAD_SOUR_VERS, PARENT,
473 START(VERS, $<ctxt>$)
478 { end_element(ELT_HEAD_SOUR_VERS,
479 PARENT, $<ctxt>5, NULL);
482 head_sour_name_sect : OPEN DELIM TAG_NAME mand_line_item
483 { $<ctxt>$ = start_element(ELT_HEAD_SOUR_NAME, PARENT,
485 START(NAME, $<ctxt>$)
490 { end_element(ELT_HEAD_SOUR_NAME,
491 PARENT, $<ctxt>5, NULL);
494 head_sour_corp_sect : OPEN DELIM TAG_CORP mand_line_item
495 { $<ctxt>$ = start_element(ELT_HEAD_SOUR_CORP, PARENT,
497 START(CORP, $<ctxt>$)
502 { end_element(ELT_HEAD_SOUR_CORP,
503 PARENT, $<ctxt>5, NULL);
507 head_sour_corp_subs : /* empty */
508 | head_sour_corp_subs head_sour_corp_sub
511 head_sour_corp_sub : addr_struc_sub /* 0:1 */
515 head_sour_data_sect : OPEN DELIM TAG_DATA mand_line_item
516 { $<ctxt>$ = start_element(ELT_HEAD_SOUR_DATA, PARENT,
518 START(DATA, $<ctxt>$)
523 { end_element(ELT_HEAD_SOUR_DATA,
524 PARENT, $<ctxt>5, NULL);
528 head_sour_data_subs : /* empty */
529 | head_sour_data_subs head_sour_data_sub
532 head_sour_data_sub : head_sour_data_date_sect { OCCUR2(DATE, 0, 1) }
533 | head_sour_data_copr_sect { OCCUR2(COPR, 0, 1) }
537 head_sour_data_date_sect : OPEN DELIM TAG_DATE mand_line_item
538 { $<ctxt>$ = start_element(ELT_HEAD_SOUR_DATA_DATE,
539 PARENT, $1, $3, $4, $4);
540 START(DATE, $<ctxt>$)
545 { end_element(ELT_HEAD_SOUR_DATA_DATE,
546 PARENT, $<ctxt>5, NULL);
549 head_sour_data_copr_sect : OPEN DELIM TAG_COPR mand_line_item
550 { $<ctxt>$ = start_element(ELT_HEAD_SOUR_DATA_COPR,
551 PARENT, $1, $3, $4, $4);
552 START(COPR, $<ctxt>$)
557 { end_element(ELT_HEAD_SOUR_DATA_COPR,
558 PARENT, $<ctxt>5, NULL);
563 head_dest_sect : OPEN DELIM TAG_DEST mand_line_item
564 { $<ctxt>$ = start_element(ELT_HEAD_DEST,
565 PARENT, $1, $3, $4, $4);
566 START(DEST, $<ctxt>$)
571 { end_element(ELT_HEAD_DEST,
572 PARENT, $<ctxt>5, NULL);
577 head_date_sect : OPEN DELIM TAG_DATE mand_line_item
578 { $<ctxt>$ = start_element(ELT_HEAD_DATE,
579 PARENT, $1, $3, $4, $4);
580 START(DATE, $<ctxt>$)
585 { end_element(ELT_HEAD_DATE,
586 PARENT, $<ctxt>5, NULL);
590 head_date_subs : /* empty */
591 | head_date_subs head_date_sub
594 head_date_sub : head_date_time_sect { OCCUR2(TIME, 0, 1) }
598 head_date_time_sect : OPEN DELIM TAG_TIME mand_line_item
599 { $<ctxt>$ = start_element(ELT_HEAD_DATE_TIME,
600 PARENT, $1, $3, $4, $4);
601 START(TIME, $<ctxt>$)
606 { end_element(ELT_HEAD_DATE_TIME,
607 PARENT, $<ctxt>5, NULL);
612 head_subm_sect : OPEN DELIM TAG_SUBM mand_pointer
613 { $<ctxt>$ = start_element(ELT_HEAD_SUBM,
614 PARENT, $1, $3, $4, $4);
615 START(SUBM, $<ctxt>$)
620 { end_element(ELT_HEAD_SUBM,
621 PARENT, $<ctxt>5, NULL);
625 head_subn_sect : OPEN DELIM TAG_SUBN mand_pointer
626 { $<ctxt>$ = start_element(ELT_HEAD_SUBN,
627 PARENT, $1, $3, $4, $4);
628 START(SUBN, $<ctxt>$)
633 { end_element(ELT_HEAD_SUBN,
634 PARENT, $<ctxt>5, NULL);
638 head_file_sect : OPEN DELIM TAG_FILE mand_line_item
639 { $<ctxt>$ = start_element(ELT_HEAD_FILE,
640 PARENT, $1, $3, $4, $4);
641 START(FILE, $<ctxt>$)
646 { end_element(ELT_HEAD_FILE, PARENT, $<ctxt>5, NULL);
650 head_copr_sect : OPEN DELIM TAG_COPR mand_line_item
651 { $<ctxt>$ = start_element(ELT_HEAD_COPR,
652 PARENT, $1, $3, $4, $4);
653 START(COPR, $<ctxt>$)
658 { end_element(ELT_HEAD_COPR, PARENT, $<ctxt>5, NULL);
662 head_gedc_sect : OPEN DELIM TAG_GEDC
663 { $<ctxt>$ = start_element(ELT_HEAD_GEDC,
664 PARENT, $1, $3, NULL, NULL);
665 START(GEDC, $<ctxt>$)
668 { CHECK2(VERS, FORM) }
670 { end_element(ELT_HEAD_GEDC, PARENT, $<ctxt>4, NULL);
674 head_gedc_subs : /* empty */
675 | head_gedc_subs head_gedc_sub
678 head_gedc_sub : head_gedc_vers_sect { OCCUR2(VERS, 1, 1) }
679 | head_gedc_form_sect { OCCUR2(FORM, 1, 1) }
682 head_gedc_vers_sect : OPEN DELIM TAG_VERS mand_line_item
683 { $<ctxt>$ = start_element(ELT_HEAD_GEDC_VERS,
684 PARENT, $1, $3, $4, $4);
685 START(VERS, $<ctxt>$)
690 { end_element(ELT_HEAD_GEDC_VERS,
691 PARENT, $<ctxt>5, NULL);
694 head_gedc_form_sect : OPEN DELIM TAG_FORM mand_line_item
695 { $<ctxt>$ = start_element(ELT_HEAD_GEDC_FORM,
696 PARENT, $1, $3, $4, $4);
697 START(FORM, $<ctxt>$)
702 { end_element(ELT_HEAD_GEDC_FORM,
703 PARENT, $<ctxt>5, NULL);
708 head_char_sect : OPEN DELIM TAG_CHAR mand_line_item
709 { if (open_conv_to_internal($4) == 0) YYERROR;
710 $<ctxt>$ = start_element(ELT_HEAD_CHAR,
711 PARENT, $1, $3, $4, $4);
712 START(CHAR, $<ctxt>$)
717 { end_element(ELT_HEAD_CHAR, PARENT, $<ctxt>5, NULL);
721 head_char_subs : /* empty */
722 | head_char_subs head_char_sub
725 head_char_sub : head_char_vers_sect { OCCUR2(VERS, 0, 1) }
728 head_char_vers_sect : OPEN DELIM TAG_VERS mand_line_item
729 { $<ctxt>$ = start_element(ELT_HEAD_CHAR_VERS,
730 PARENT, $1, $3, $4, $4);
731 START(VERS, $<ctxt>$)
736 { end_element(ELT_HEAD_CHAR_VERS,
737 PARENT, $<ctxt>5, NULL);
742 head_lang_sect : OPEN DELIM TAG_LANG mand_line_item
743 { $<ctxt>$ = start_element(ELT_HEAD_LANG,
744 PARENT, $1, $3, $4, $4);
745 START(LANG, $<ctxt>$)
750 { end_element(ELT_HEAD_LANG, PARENT, $<ctxt>5, NULL);
754 head_plac_sect : OPEN DELIM TAG_PLAC
755 { $<ctxt>$ = start_element(ELT_HEAD_PLAC,
756 PARENT, $1, $3, NULL, NULL);
757 START(PLAC, $<ctxt>$)
762 { end_element(ELT_HEAD_PLAC, PARENT, $<ctxt>4, NULL);
766 head_plac_subs : /* empty */
767 | head_plac_subs head_plac_sub
770 head_plac_sub : head_plac_form_sect { OCCUR2(FORM, 1, 1) }
773 head_plac_form_sect : OPEN DELIM TAG_FORM mand_line_item
774 { $<ctxt>$ = start_element(ELT_HEAD_PLAC_FORM,
775 PARENT, $1, $3, $4, $4);
776 START(FORM, $<ctxt>$)
781 { end_element(ELT_HEAD_PLAC_FORM,
782 PARENT, $<ctxt>5, NULL);
787 head_note_sect : OPEN DELIM TAG_NOTE mand_line_item
788 { $<ctxt>$ = start_element(ELT_HEAD_NOTE,
789 PARENT, $1, $3, $4, $4);
790 START(NOTE, $<ctxt>$)
795 { end_element(ELT_HEAD_NOTE, PARENT, $<ctxt>5, NULL);
799 head_note_subs : /* empty */
800 | head_note_subs head_note_sub
803 head_note_sub : continuation_sub /* 0:M */
807 /*********************************************************************/
809 /*********************************************************************/
810 /* Don't need callbacks here, there is no information... */
811 trlr_sect : OPEN DELIM TAG_TRLR CLOSE { }
814 /*********************************************************************/
815 /**** Family record ****/
816 /*********************************************************************/
817 fam_rec : OPEN DELIM POINTER DELIM TAG_FAM
818 { $<ctxt>$ = start_record(REC_FAM, $1, $3, $5);
819 START(FAM, $<ctxt>$) }
823 { end_record(REC_FAM, $<ctxt>6); }
826 fam_subs : /* empty */
830 fam_sub : fam_event_struc_sub /* 0:M */
831 | fam_husb_sect { OCCUR2(HUSB, 0, 1) }
832 | fam_wife_sect { OCCUR2(WIFE, 0, 1) }
833 | fam_chil_sect /* 0:M */
834 | fam_nchi_sect { OCCUR2(NCHI, 0, 1) }
835 | fam_subm_sect /* 0:M */
836 | lds_spouse_seal_sub /* 0:M */
837 | source_cit_sub /* 0:M */
838 | multim_link_sub /* 0:M */
839 | note_struc_sub /* 0:M */
840 | ident_struc_sub /* 0:1 */
841 | change_date_sub /* 0:1 */
846 fam_husb_sect : OPEN DELIM TAG_HUSB mand_pointer
847 { START(HUSB, NULL) } no_std_subs { CHECK0 } CLOSE
852 fam_wife_sect : OPEN DELIM TAG_WIFE mand_pointer
853 { START(WIFE, NULL) } no_std_subs { CHECK0 } CLOSE
858 fam_chil_sect : OPEN DELIM TAG_CHIL mand_pointer
859 { START(CHIL, NULL) } no_std_subs { CHECK0 } CLOSE
864 fam_nchi_sect : OPEN DELIM TAG_NCHI mand_line_item
865 { START(NCHI, NULL) } no_std_subs { CHECK0 } CLOSE
870 fam_subm_sect : OPEN DELIM TAG_SUBM mand_pointer
871 { START(SUBM, NULL) } no_std_subs { CHECK0 } CLOSE
875 /*********************************************************************/
876 /**** Individual record ****/
877 /*********************************************************************/
878 indiv_rec : OPEN DELIM POINTER DELIM TAG_INDI
879 { $<ctxt>$ = start_record(REC_INDI, $1, $3, $5);
880 START(INDI, $<ctxt>$) }
884 { end_record(REC_INDI, $<ctxt>6); }
887 indi_subs : /* empty */
891 indi_sub : indi_resn_sect { OCCUR2(RESN, 0, 1) }
892 | pers_name_struc_sub /* 0:M */
893 | indi_sex_sect { OCCUR2(SEX, 0, 1) }
894 | indiv_even_struc_sub /* 0:M */
895 | indiv_attr_struc_sub /* 0:M */
896 | lds_indiv_ord_sub /* 0:M */
897 | chi_fam_link_sub /* 0:M */
898 | spou_fam_link_sub /* 0:M */
899 | indi_subm_sect /* 0:M */
900 | assoc_struc_sub /* 0:M */
901 | indi_alia_sect /* 0:M */
902 | indi_anci_sect /* 0:M */
903 | indi_desi_sect /* 0:M */
904 | source_cit_sub /* 0:M */
905 | multim_link_sub /* 0:M */
906 | note_struc_sub /* 0:M */
907 | indi_rfn_sect { OCCUR2(RFN, 0, 1) }
908 | indi_afn_sect /* 0:M */
909 | ident_struc_sub /* 0:1 */
910 | change_date_sub /* 0:1 */
911 | ftree_addr_sect { if (!compat_mode(C_FTREE))
918 indi_resn_sect : OPEN DELIM TAG_RESN mand_line_item
919 { START(RESN, NULL) } no_std_subs { CHECK0 } CLOSE { }
923 indi_sex_sect : OPEN DELIM TAG_SEX mand_line_item
924 { START(SEX, NULL) } no_std_subs { CHECK0 } CLOSE { }
928 indi_subm_sect : OPEN DELIM TAG_SUBM mand_pointer
929 { START(SUBM, NULL) } no_std_subs { CHECK0 } CLOSE { }
933 indi_alia_sect : OPEN DELIM TAG_ALIA mand_pointer
934 { START(ALIA, NULL) } no_std_subs { CHECK0 } CLOSE { }
938 indi_anci_sect : OPEN DELIM TAG_ANCI mand_pointer
939 { START(ANCI, NULL) } no_std_subs { CHECK0 } CLOSE { }
943 indi_desi_sect : OPEN DELIM TAG_DESI mand_pointer
944 { START(DESI, NULL) } no_std_subs { CHECK0 } CLOSE { }
948 indi_rfn_sect : OPEN DELIM TAG_RFN mand_line_item
949 { START(RFN, NULL) } no_std_subs { CHECK0 } CLOSE { }
953 indi_afn_sect : OPEN DELIM TAG_AFN mand_line_item
954 { START(AFN, NULL) } no_std_subs { CHECK0 } CLOSE { }
957 /* INDI.ADDR (Only for 'ftree' compatibility) */
958 ftree_addr_sect : OPEN DELIM TAG_ADDR opt_line_item
959 { START(ADDR, NULL) } no_std_subs { CHECK0 } CLOSE { }
961 /*********************************************************************/
962 /**** Multimedia record ****/
963 /*********************************************************************/
964 multim_rec : OPEN DELIM POINTER DELIM TAG_OBJE
965 { $<ctxt>$ = start_record(REC_OBJE, $1, $3, $5);
966 START(OBJE, $<ctxt>$) }
968 { CHECK2(FORM, BLOB) }
970 { end_record(REC_OBJE, $<ctxt>6); }
973 obje_subs : /* empty */
977 obje_sub : obje_form_sect { OCCUR2(FORM, 1, 1) }
978 | obje_titl_sect { OCCUR2(TITL, 0, 1) }
979 | note_struc_sub /* 0:M */
980 | obje_blob_sect { OCCUR2(BLOB, 1, 1) }
981 | obje_obje_sect { OCCUR2(OBJE, 0, 1) }
982 | ident_struc_sub /* 0:1 */
983 | change_date_sub /* 0:1 */
988 obje_form_sect : OPEN DELIM TAG_FORM mand_line_item
989 { START(FORM, NULL) } no_std_subs { CHECK0 } CLOSE { }
993 obje_titl_sect : OPEN DELIM TAG_TITL mand_line_item
994 { START(TITL, NULL) } no_std_subs { CHECK0 } CLOSE { }
998 obje_blob_sect : OPEN DELIM TAG_BLOB
999 { START(BLOB, NULL) }
1005 obje_blob_subs : /* empty */
1006 | obje_blob_subs obje_blob_sub
1009 obje_blob_sub : obje_blob_cont_sect { OCCUR1(CONT, 1) }
1013 obje_blob_cont_sect : OPEN DELIM TAG_CONT mand_line_item
1014 { START(CONT, NULL) } no_std_subs { CHECK0 } CLOSE { }
1018 obje_obje_sect : OPEN DELIM TAG_OBJE mand_pointer
1019 { START(OBJE, NULL) } no_std_subs { CHECK0 } CLOSE { }
1022 /*********************************************************************/
1023 /**** Note record ****/
1024 /*********************************************************************/
1025 note_rec : OPEN DELIM POINTER DELIM TAG_NOTE note_line_item
1026 { $<ctxt>$ = start_record(REC_NOTE, $1, $3, $5);
1027 START(NOTE, $<ctxt>$) }
1031 { end_record(REC_NOTE, $<ctxt>6); }
1034 note_line_item : /* empty */
1035 { if (!compat_mode(C_FTREE)) {
1036 gedcom_error("Missing value"); YYERROR;
1040 { gedcom_debug_print("==Val: %s==\n", $2);
1044 note_subs : /* empty */
1045 | note_subs note_sub
1048 note_sub : continuation_sub /* 0:M */
1049 | source_cit_sub /* 0:M */
1050 | ident_struc_sub /* 0:1 */
1051 | change_date_sub /* 0:1 */
1055 /*********************************************************************/
1056 /**** Repository record ****/
1057 /*********************************************************************/
1058 repos_rec : OPEN DELIM POINTER DELIM TAG_REPO
1059 { $<ctxt>$ = start_record(REC_REPO, $1, $3, $5);
1060 START(REPO, $<ctxt>$) }
1064 { end_record(REC_REPO, $<ctxt>6); }
1067 repo_subs : /* empty */
1068 | repo_subs repo_sub
1071 repo_sub : repo_name_sect { OCCUR2(NAME, 0, 1) }
1072 | addr_struc_sub /* 0:1 */
1073 | note_struc_sub /* 0:M */
1074 | ident_struc_sub /* 0:1 */
1075 | change_date_sub /* 0:1 */
1080 repo_name_sect : OPEN DELIM TAG_NAME mand_line_item
1081 { START(NAME, NULL) } no_std_subs { CHECK0 } CLOSE {}
1084 /*********************************************************************/
1085 /**** Source record ****/
1086 /*********************************************************************/
1087 source_rec : OPEN DELIM POINTER DELIM TAG_SOUR
1088 { $<ctxt>$ = start_record(REC_SOUR, $1, $3, $5);
1089 START(SOUR, $<ctxt>$) }
1093 { end_record(REC_SOUR, $<ctxt>6); }
1096 sour_subs : /* empty */
1097 | sour_subs sour_sub
1100 sour_sub : sour_data_sect { OCCUR2(DATA, 0, 1) }
1101 | sour_auth_sect { OCCUR2(AUTH, 0, 1) }
1102 | sour_titl_sect { OCCUR2(TITL, 0, 1) }
1103 | sour_abbr_sect { OCCUR2(ABBR, 0, 1) }
1104 | sour_publ_sect { OCCUR2(PUBL, 0, 1) }
1105 | sour_text_sect { OCCUR2(TEXT, 0, 1) }
1106 | source_repos_cit_sub /* 0:1 */
1107 | multim_link_sub /* 0:M */
1108 | note_struc_sub /* 0:M */
1109 | ident_struc_sub /* 0:1 */
1110 | change_date_sub /* 0:1 */
1115 sour_data_sect : OPEN DELIM TAG_DATA
1116 { START(DATA, NULL) }
1122 sour_data_subs : /* empty */
1123 | sour_data_subs sour_data_sub
1126 sour_data_sub : sour_data_even_sect /* 0:M */
1127 | sour_data_agnc_sect { OCCUR2(AGNC, 0, 1) }
1128 | note_struc_sub /* 0:M */
1132 sour_data_even_sect : OPEN DELIM TAG_EVEN mand_line_item
1133 { START(EVEN, NULL) }
1139 sour_data_even_subs : /* empty */
1140 | sour_data_even_subs sour_data_even_sub
1143 sour_data_even_sub : sour_data_even_date_sect { OCCUR2(DATE, 0, 1) }
1144 | sour_data_even_plac_sect { OCCUR2(PLAC, 0, 1) }
1148 sour_data_even_date_sect : OPEN DELIM TAG_DATE mand_line_item
1149 { START(DATE, NULL) } no_std_subs { CHECK0 } CLOSE { }
1152 sour_data_even_plac_sect : OPEN DELIM TAG_PLAC mand_line_item
1153 { START(PLAC, NULL) } no_std_subs { CHECK0 } CLOSE { }
1156 sour_data_agnc_sect : OPEN DELIM TAG_AGNC mand_line_item
1157 { START(AGNC, NULL) } no_std_subs { CHECK0 } CLOSE { }
1161 sour_auth_sect : OPEN DELIM TAG_AUTH mand_line_item
1162 { START(AUTH, NULL) }
1168 sour_auth_subs : /* empty */
1169 | sour_auth_subs sour_auth_sub
1172 sour_auth_sub : continuation_sub /* 0:M */
1177 sour_titl_sect : OPEN DELIM TAG_TITL mand_line_item
1178 { START(TITL, NULL) }
1184 sour_titl_subs : /* empty */
1185 | sour_titl_subs sour_titl_sub
1188 sour_titl_sub : continuation_sub /* 0:M */
1193 sour_abbr_sect : OPEN DELIM TAG_ABBR mand_line_item
1194 { START(ABBR, NULL) } no_std_subs { CHECK0 } CLOSE { }
1198 sour_publ_sect : OPEN DELIM TAG_PUBL mand_line_item
1199 { START(PUBL, NULL) }
1205 sour_publ_subs : /* empty */
1206 | sour_publ_subs sour_publ_sub
1209 sour_publ_sub : continuation_sub /* 0:M */
1214 sour_text_sect : OPEN DELIM TAG_TEXT mand_line_item
1215 { START(TEXT, NULL) }
1221 sour_text_subs : /* empty */
1222 | sour_text_subs sour_text_sub
1225 sour_text_sub : continuation_sub /* 0:M */
1229 /*********************************************************************/
1230 /**** Submission record ****/
1231 /*********************************************************************/
1232 submis_rec : OPEN DELIM POINTER DELIM TAG_SUBN
1233 { $<ctxt>$ = start_record(REC_SUBN, $1, $3, $5);
1234 START(SUBN, $<ctxt>$) }
1238 { end_record(REC_SUBN, $<ctxt>6); }
1241 subn_subs : /* empty */
1242 | subn_subs subn_sub
1245 subn_sub : subn_subm_sect { OCCUR2(SUBM, 0, 1) }
1246 | subn_famf_sect { OCCUR2(FAMF, 0, 1) }
1247 | subn_temp_sect { OCCUR2(TEMP, 0, 1) }
1248 | subn_ance_sect { OCCUR2(ANCE, 0, 1) }
1249 | subn_desc_sect { OCCUR2(DESC, 0, 1) }
1250 | subn_ordi_sect { OCCUR2(ORDI, 0, 1) }
1251 | subn_rin_sect { OCCUR2(RIN, 0, 1) }
1256 subn_subm_sect : OPEN DELIM TAG_SUBM mand_pointer
1257 { START(SUBM, NULL) } no_std_subs { CHECK0 } CLOSE { }
1261 subn_famf_sect : OPEN DELIM TAG_FAMF mand_line_item
1262 { START(FAMF, NULL) } no_std_subs { CHECK0 } CLOSE { }
1266 subn_temp_sect : OPEN DELIM TAG_TEMP mand_line_item
1267 { START(TEMP, NULL) } no_std_subs { CHECK0 } CLOSE { }
1271 subn_ance_sect : OPEN DELIM TAG_ANCE mand_line_item
1272 { START(ANCE, NULL) } no_std_subs { CHECK0 } CLOSE { }
1276 subn_desc_sect : OPEN DELIM TAG_DESC mand_line_item
1277 { START(DESC, NULL) } no_std_subs { CHECK0 } CLOSE { }
1281 subn_ordi_sect : OPEN DELIM TAG_ORDI mand_line_item
1282 { START(ORDI, NULL) } no_std_subs { CHECK0 } CLOSE { }
1286 subn_rin_sect : OPEN DELIM TAG_RIN mand_line_item
1287 { START(RIN, NULL) } no_std_subs { CHECK0 } CLOSE { }
1290 /*********************************************************************/
1291 /**** Submitter record ****/
1292 /*********************************************************************/
1293 submit_rec : OPEN DELIM POINTER DELIM TAG_SUBM
1294 { $<ctxt>$ = start_record(REC_SUBM, $1, $3, $5);
1295 START(SUBM, $<ctxt>$) }
1299 { end_record(REC_SUBM, $<ctxt>6); }
1302 subm_subs : /* empty */
1303 | subm_subs subm_sub
1306 subm_sub : subm_name_sect { OCCUR2(NAME, 0, 1) }
1307 | addr_struc_sub /* 0:1 */
1308 | multim_link_sub /* 0:M */
1309 | subm_lang_sect { OCCUR2(LANG, 0, 3) }
1310 | subm_rfn_sect { OCCUR2(RFN, 0, 1) }
1311 | subm_rin_sect { OCCUR2(RIN, 0, 1) }
1312 | change_date_sub /* 0:1 */
1317 subm_name_sect : OPEN DELIM TAG_NAME mand_line_item
1318 { START(NAME, NULL) } no_std_subs { CHECK0 } CLOSE { }
1322 subm_lang_sect : OPEN DELIM TAG_LANG mand_line_item
1323 { START(LANG, NULL) } no_std_subs { CHECK0 } CLOSE { }
1327 subm_rfn_sect : OPEN DELIM TAG_RFN mand_line_item
1328 { START(RFN, NULL) } no_std_subs { CHECK0 } CLOSE { }
1332 subm_rin_sect : OPEN DELIM TAG_RIN mand_line_item
1333 { START(RIN, NULL) } no_std_subs { CHECK0 } CLOSE { }
1336 /*********************************************************************/
1337 /**** Substructures ****/
1338 /*********************************************************************/
1340 /* ADDRESS STRUCTURE */
1341 addr_struc_sub : addr_sect { OCCUR2(ADDR, 0, 1) }
1342 | phon_sect { OCCUR2(PHON, 0, 3) }
1345 addr_sect : OPEN DELIM TAG_ADDR mand_line_item
1346 { START(ADDR, NULL) }
1352 addr_subs : /* empty */
1353 | addr_subs addr_sub
1356 addr_sub : addr_cont_sect /* 0:M */
1357 | addr_adr1_sect { OCCUR2(ADR1, 0, 1) }
1358 | addr_adr2_sect { OCCUR2(ADR2, 0, 1) }
1359 | addr_city_sect { OCCUR2(CITY, 0, 1) }
1360 | addr_stae_sect { OCCUR2(STAE, 0, 1) }
1361 | addr_post_sect { OCCUR2(POST, 0, 1) }
1362 | addr_ctry_sect { OCCUR2(CTRY, 0, 1) }
1366 addr_cont_sect : OPEN DELIM TAG_CONT mand_line_item
1367 { START(CONT, NULL) } no_std_subs { CHECK0 } CLOSE { }
1369 addr_adr1_sect : OPEN DELIM TAG_ADR1 mand_line_item
1370 { START(ADR1, NULL) } no_std_subs { CHECK0 } CLOSE { }
1372 addr_adr2_sect : OPEN DELIM TAG_ADR2 mand_line_item
1373 { START(ADR2, NULL) } no_std_subs { CHECK0 } CLOSE { }
1375 addr_city_sect : OPEN DELIM TAG_CITY mand_line_item
1376 { START(CITY, NULL) } no_std_subs { CHECK0 } CLOSE { }
1378 addr_stae_sect : OPEN DELIM TAG_STAE mand_line_item
1379 { START(STAE, NULL) } no_std_subs { CHECK0 } CLOSE { }
1381 addr_post_sect : OPEN DELIM TAG_POST mand_line_item
1382 { START(POST, NULL) } no_std_subs { CHECK0 } CLOSE { }
1384 addr_ctry_sect : OPEN DELIM TAG_CTRY mand_line_item
1385 { START(CTRY, NULL) } no_std_subs { CHECK0 } CLOSE { }
1388 phon_sect : OPEN DELIM TAG_PHON mand_line_item
1389 { START(PHON, NULL) } no_std_subs { CHECK0 } CLOSE { }
1392 /* ASSOCIATION STRUCTURE */
1393 assoc_struc_sub : asso_sect /* 0:M */
1396 asso_sect : OPEN DELIM TAG_ASSO mand_pointer
1397 { START(ASSO, NULL) }
1399 { CHECK2(TYPE,RELA) }
1403 asso_subs : /* empty */
1404 | asso_type_sect { OCCUR2(TYPE, 1, 1) }
1405 | asso_rela_sect { OCCUR2(RELA, 1, 1) }
1411 asso_type_sect : OPEN DELIM TAG_TYPE mand_line_item
1412 { START(TYPE, NULL) } no_std_subs { CHECK0 } CLOSE { }
1415 asso_rela_sect : OPEN DELIM TAG_RELA mand_line_item
1416 { START(RELA, NULL) } no_std_subs { CHECK0 } CLOSE { }
1420 change_date_sub : change_date_chan_sect { OCCUR2(CHAN, 0, 1) }
1423 change_date_chan_sect : OPEN DELIM TAG_CHAN
1424 { START(CHAN, NULL) }
1425 change_date_chan_subs
1430 change_date_chan_subs : /* empty */
1431 | change_date_chan_subs change_date_chan_sub
1434 change_date_chan_sub : change_date_date_sect { OCCUR2(DATE, 1, 1) }
1439 change_date_date_sect : OPEN DELIM TAG_DATE mand_line_item
1440 { START(DATE, NULL) }
1441 change_date_date_subs
1446 change_date_date_subs : /* empty */
1447 | change_date_date_subs change_date_date_sub
1450 change_date_date_sub : change_date_date_time_sect { OCCUR2(TIME, 0, 1) }
1454 change_date_date_time_sect : OPEN DELIM TAG_TIME mand_line_item
1455 { START(TIME, NULL) } no_std_subs { CHECK0 } CLOSE { }
1458 /* CHILD TO FAMILY LINK */
1459 chi_fam_link_sub : famc_sect /* 0:M */
1462 famc_sect : OPEN DELIM TAG_FAMC mand_pointer
1463 { START(FAMC, NULL) }
1469 famc_subs : /* empty */
1470 | famc_subs famc_sub
1473 famc_sub : famc_pedi_sect /* 0:M */
1478 famc_pedi_sect : OPEN DELIM TAG_PEDI mand_line_item
1479 { START(PEDI, NULL) } no_std_subs { CHECK0 } CLOSE { }
1482 /* CONTINUATION SUBSECTIONS */
1483 continuation_sub : cont_sect /* 0:M */
1484 | conc_sect /* 0:M */
1487 cont_sect : OPEN DELIM TAG_CONT mand_line_item
1488 { START(CONT, NULL) } no_std_subs { CHECK0 } CLOSE { }
1491 conc_sect : OPEN DELIM TAG_CONC mand_line_item
1492 { START(CONC, NULL) } no_std_subs { CHECK0 } CLOSE { }
1496 event_detail_sub : event_detail_type_sect { OCCUR2(TYPE, 0, 1) }
1497 | event_detail_date_sect { OCCUR2(DATE, 0, 1) }
1500 | event_detail_age_sect { OCCUR2(AGE, 0, 1) }
1501 | event_detail_agnc_sect { OCCUR2(AGNC, 0, 1) }
1502 | event_detail_caus_sect { OCCUR2(CAUS, 0, 1) }
1508 event_detail_type_sect : OPEN DELIM TAG_TYPE mand_line_item
1509 { START(TYPE, NULL) } no_std_subs { CHECK0 } CLOSE { }
1511 event_detail_date_sect : OPEN DELIM TAG_DATE mand_line_item
1512 { START(DATE, NULL) } no_std_subs { CHECK0 } CLOSE { }
1514 event_detail_age_sect : OPEN DELIM TAG_AGE mand_line_item
1515 { START(AGE, NULL) } no_std_subs { CHECK0 } CLOSE { }
1517 event_detail_agnc_sect : OPEN DELIM TAG_AGNC mand_line_item
1518 { START(AGNC, NULL) } no_std_subs { CHECK0 } CLOSE { }
1520 event_detail_caus_sect : OPEN DELIM TAG_CAUS mand_line_item
1521 { START(CAUS, NULL) } no_std_subs { CHECK0 } CLOSE { }
1524 /* FAMILY EVENT STRUCTURE */
1525 fam_event_struc_sub : fam_event_sect
1526 | fam_gen_even_sect /* 0:M */
1529 fam_event_sect : OPEN DELIM fam_event_tag opt_value fam_event_subs
1534 fam_event_tag : TAG_ANUL { START(ANUL, NULL) }
1535 | TAG_CENS { START(CENS, NULL) }
1536 | TAG_DIV { START(DIV, NULL) }
1537 | TAG_DIVF { START(DIVF, NULL) }
1538 | TAG_ENGA { START(ENGA, NULL) }
1539 | TAG_MARR { START(MARR, NULL) }
1540 | TAG_MARB { START(MARB, NULL) }
1541 | TAG_MARC { START(MARC, NULL) }
1542 | TAG_MARL { START(MARL, NULL) }
1543 | TAG_MARS { START(MARS, NULL) }
1546 fam_event_subs : /* empty */
1547 | fam_event_subs fam_event_sub
1550 fam_event_sub : event_detail_sub
1551 | fam_even_husb_sect { OCCUR2(HUSB, 0, 1) }
1552 | fam_even_wife_sect { OCCUR2(WIFE, 0, 1) }
1556 fam_even_husb_sect : OPEN DELIM TAG_HUSB
1557 { START(HUSB, NULL) }
1563 fam_even_husb_subs : /* empty */
1564 | fam_even_husb_subs fam_even_husb_sub
1567 fam_even_husb_sub : fam_even_husb_age_sect { OCCUR2(AGE, 1, 1) }
1571 fam_even_husb_age_sect : OPEN DELIM TAG_AGE mand_line_item
1572 { START(AGE, NULL) } no_std_subs { CHECK0 } CLOSE { }
1575 fam_even_wife_sect : OPEN DELIM TAG_WIFE
1576 { START(HUSB, NULL) }
1582 fam_gen_even_sect : OPEN DELIM TAG_EVEN
1583 { START(EVEN, NULL) }
1589 fam_gen_even_subs : /* empty */
1590 | fam_gen_even_subs fam_gen_even_sub
1593 fam_gen_even_sub : event_detail_sub
1594 | fam_even_husb_sect { OCCUR2(HUSB, 0, 1) }
1595 | fam_even_wife_sect { OCCUR2(WIFE, 0, 1) }
1599 /* IDENTIFICATION STRUCTURE */
1600 ident_struc_sub : ident_refn_sect /* 0:M */
1601 | ident_rin_sect { OCCUR2(RIN, 0, 1) }
1604 ident_refn_sect : OPEN DELIM TAG_REFN mand_line_item
1605 { START(REFN, NULL) }
1611 ident_refn_subs : /* empty */
1612 | ident_refn_subs ident_refn_sub
1615 ident_refn_sub : ident_refn_type_sect { OCCUR2(TYPE, 0, 1) }
1619 ident_refn_type_sect : OPEN DELIM TAG_TYPE mand_line_item
1620 { START(TYPE, NULL) } no_std_subs { CHECK0 } CLOSE { }
1623 ident_rin_sect : OPEN DELIM TAG_RIN mand_line_item
1624 { START(RIN, NULL) } no_std_subs { CHECK0 } CLOSE { }
1627 /* INDIVIDUAL ATTRIBUTE STRUCTURE */
1628 indiv_attr_struc_sub : indiv_cast_sect /* 0:M */
1629 | indiv_dscr_sect /* 0:M */
1630 | indiv_educ_sect /* 0:M */
1631 | indiv_idno_sect /* 0:M */
1632 | indiv_nati_sect /* 0:M */
1633 | indiv_nchi_sect /* 0:M */
1634 | indiv_nmr_sect /* 0:M */
1635 | indiv_occu_sect /* 0:M */
1636 | indiv_prop_sect /* 0:M */
1637 | indiv_reli_sect /* 0:M */
1638 | indiv_resi_sect /* 0:M */
1639 | indiv_ssn_sect /* 0:M */
1640 | indiv_titl_sect /* 0:M */
1643 indiv_cast_sect : OPEN DELIM TAG_CAST mand_line_item
1644 { START(CAST, NULL) }
1645 indiv_attr_event_subs
1649 indiv_dscr_sect : OPEN DELIM TAG_DSCR mand_line_item
1650 { START(DSCR, NULL) }
1651 indiv_attr_event_subs
1655 indiv_educ_sect : OPEN DELIM TAG_EDUC mand_line_item
1656 { START(EDUC, NULL) }
1657 indiv_attr_event_subs
1661 indiv_idno_sect : OPEN DELIM TAG_IDNO mand_line_item
1662 { START(IDNO, NULL) }
1663 indiv_attr_event_subs
1667 indiv_nati_sect : OPEN DELIM TAG_NATI mand_line_item
1668 { START(NATI, NULL) }
1669 indiv_attr_event_subs
1673 indiv_nchi_sect : OPEN DELIM TAG_NCHI mand_line_item
1674 { START(NCHI, NULL) }
1675 indiv_attr_event_subs
1679 indiv_nmr_sect : OPEN DELIM TAG_NMR mand_line_item
1680 { START(NMR, NULL) }
1681 indiv_attr_event_subs
1685 indiv_occu_sect : OPEN DELIM TAG_OCCU mand_line_item
1686 { START(OCCU, NULL) }
1687 indiv_attr_event_subs
1691 indiv_prop_sect : OPEN DELIM TAG_PROP mand_line_item
1692 { START(PROP, NULL) }
1693 indiv_attr_event_subs
1697 indiv_reli_sect : OPEN DELIM TAG_RELI mand_line_item
1698 { START(RELI, NULL) }
1699 indiv_attr_event_subs
1703 indiv_resi_sect : OPEN DELIM TAG_RESI
1704 { START(RESI, NULL) }
1705 indiv_attr_event_subs
1709 indiv_ssn_sect : OPEN DELIM TAG_SSN mand_line_item
1710 { START(SSN, NULL) }
1711 indiv_attr_event_subs
1715 indiv_titl_sect : OPEN DELIM TAG_TITL mand_line_item
1716 { START(TITL, NULL) }
1717 indiv_attr_event_subs
1722 indiv_attr_event_subs : /* empty */
1723 | indiv_attr_event_subs indiv_attr_event_sub
1726 indiv_attr_event_sub : event_detail_sub
1730 /* INDIVIDUAL EVENT STRUCTURE */
1731 indiv_even_struc_sub : indiv_birt_sect
1733 | indiv_adop_sect /* 0:M */
1734 | indiv_even_sect /* 0:M */
1737 indiv_birt_sect : OPEN DELIM indiv_birt_tag opt_value indiv_birt_subs
1742 indiv_birt_tag : TAG_BIRT { START(BIRT, NULL) }
1743 | TAG_CHR { START(CHR, NULL) }
1746 indiv_birt_subs : /* empty */
1747 | indiv_birt_subs indiv_birt_sub
1750 indiv_birt_sub : event_detail_sub
1751 | indiv_birt_famc_sect { OCCUR2(FAMC,0, 1) }
1755 indiv_birt_famc_sect : OPEN DELIM TAG_FAMC mand_pointer
1756 { START(FAMC, NULL) } no_std_subs { CHECK0 } CLOSE { }
1759 indiv_gen_sect : OPEN DELIM indiv_gen_tag opt_value indiv_gen_subs
1764 indiv_gen_tag : TAG_DEAT { START(DEAT, NULL) }
1765 | TAG_BURI { START(BURI, NULL) }
1766 | TAG_CREM { START(CREM, NULL) }
1767 | TAG_BAPM { START(BAPM, NULL) }
1768 | TAG_BARM { START(BARM, NULL) }
1769 | TAG_BASM { START(BASM, NULL) }
1770 | TAG_BLES { START(BLES, NULL) }
1771 | TAG_CHRA { START(CHRA, NULL) }
1772 | TAG_CONF { START(CONF, NULL) }
1773 | TAG_FCOM { START(FCOM, NULL) }
1774 | TAG_ORDN { START(ORDN, NULL) }
1775 | TAG_NATU { START(NATU, NULL) }
1776 | TAG_EMIG { START(EMIG, NULL) }
1777 | TAG_IMMI { START(IMMI, NULL) }
1778 | TAG_CENS { START(CENS, NULL) }
1779 | TAG_PROB { START(PROB, NULL) }
1780 | TAG_WILL { START(WILL, NULL) }
1781 | TAG_GRAD { START(GRAD, NULL) }
1782 | TAG_RETI { START(RETI, NULL) }
1785 indiv_gen_subs : /* empty */
1786 | indiv_gen_subs indiv_gen_sub
1789 indiv_gen_sub : event_detail_sub
1793 indiv_adop_sect : OPEN DELIM TAG_ADOP opt_value
1794 { START(ADOP, NULL) }
1800 indiv_adop_subs : /* empty */
1801 | indiv_adop_subs indiv_adop_sub
1804 indiv_adop_sub : event_detail_sub
1805 | indiv_adop_famc_sect { OCCUR2(FAMC,0, 1) }
1809 indiv_adop_famc_sect : OPEN DELIM TAG_FAMC mand_pointer
1810 { START(FAMC, NULL) }
1811 indiv_adop_famc_subs
1816 indiv_adop_famc_subs : /* empty */
1817 | indiv_adop_famc_subs indiv_adop_famc_sub
1820 indiv_adop_famc_sub : indiv_adop_famc_adop_sect { OCCUR2(ADOP,0, 1) }
1824 indiv_adop_famc_adop_sect : OPEN DELIM TAG_ADOP mand_line_item
1825 { START(ADOP, NULL) } no_std_subs { CHECK0 } CLOSE { }
1828 indiv_even_sect : OPEN DELIM TAG_EVEN
1829 { START(EVEN, NULL) }
1835 /* LDS INDIVIDUAL ORDINANCE */
1836 lds_indiv_ord_sub : lio_bapl_sect /* 0:M */
1837 | lio_slgc_sect /* 0:M */
1840 lio_bapl_sect : OPEN DELIM lio_bapl_tag lio_bapl_subs
1845 lio_bapl_tag : TAG_BAPL { START(BAPL, NULL) }
1846 | TAG_CONL { START(CONL, NULL) }
1847 | TAG_ENDL { START(ENDL, NULL) }
1850 lio_bapl_subs : /* empty */
1851 | lio_bapl_subs lio_bapl_sub
1854 lio_bapl_sub : lio_bapl_stat_sect { OCCUR2(STAT, 0, 1) }
1855 | lio_bapl_date_sect { OCCUR2(DATE, 0, 1) }
1856 | lio_bapl_temp_sect { OCCUR2(TEMP, 0, 1) }
1857 | lio_bapl_plac_sect { OCCUR2(PLAC, 0, 1) }
1863 lio_bapl_stat_sect : OPEN DELIM TAG_STAT mand_line_item
1864 { START(STAT, NULL) } no_std_subs { CHECK0 } CLOSE { }
1866 lio_bapl_date_sect : OPEN DELIM TAG_DATE mand_line_item
1867 { START(DATE, NULL) } no_std_subs { CHECK0 } CLOSE { }
1869 lio_bapl_temp_sect : OPEN DELIM TAG_TEMP mand_line_item
1870 { START(TEMP, NULL) } no_std_subs { CHECK0 } CLOSE { }
1872 lio_bapl_plac_sect : OPEN DELIM TAG_PLAC mand_line_item
1873 { START(PLAC, NULL) } no_std_subs { CHECK0 } CLOSE { }
1876 lio_slgc_sect : OPEN DELIM TAG_SLGC
1877 { START(SLGC, NULL) }
1883 lio_slgc_subs : /* empty */
1884 | lio_slgc_subs lio_slgc_sub
1887 lio_slgc_sub : lio_bapl_sub
1888 | lio_slgc_famc_sect { OCCUR2(FAMC, 1, 1) }
1891 lio_slgc_famc_sect : OPEN DELIM TAG_FAMC mand_pointer
1892 { START(FAMC, NULL) } no_std_subs { CHECK0 } CLOSE { }
1895 /* LDS SPOUSE SEALING */
1896 lds_spouse_seal_sub : lss_slgs_sect
1899 lss_slgs_sect : OPEN DELIM TAG_SLGS
1900 { START(SLGS, NULL) }
1906 lss_slgs_subs : /* empty */
1907 | lss_slgs_subs lss_slgs_sub
1910 lss_slgs_sub : lss_slgs_stat_sect { OCCUR2(STAT, 0, 1) }
1911 | lss_slgs_date_sect { OCCUR2(DATE, 0, 1) }
1912 | lss_slgs_temp_sect { OCCUR2(TEMP, 0, 1) }
1913 | lss_slgs_plac_sect { OCCUR2(PLAC, 0, 1) }
1919 lss_slgs_stat_sect : OPEN DELIM TAG_STAT mand_line_item
1920 { START(STAT, NULL) } no_std_subs { CHECK0 } CLOSE { }
1922 lss_slgs_date_sect : OPEN DELIM TAG_DATE mand_line_item
1923 { START(DATE, NULL) } no_std_subs { CHECK0 } CLOSE { }
1925 lss_slgs_temp_sect : OPEN DELIM TAG_TEMP mand_line_item
1926 { START(TEMP, NULL) } no_std_subs { CHECK0 } CLOSE { }
1928 lss_slgs_plac_sect : OPEN DELIM TAG_PLAC mand_line_item
1929 { START(PLAC, NULL) } no_std_subs { CHECK0 } CLOSE { }
1932 /* MULTIMEDIA LINK */
1933 multim_link_sub : multim_obje_link_sect
1934 | multim_obje_emb_sect
1937 multim_obje_link_sect : OPEN DELIM TAG_OBJE DELIM POINTER
1938 { START(OBJE, NULL) } no_std_subs { CHECK0 } CLOSE { }
1941 multim_obje_emb_sect : OPEN DELIM TAG_OBJE
1942 { START(OBJE, NULL) }
1943 multim_obje_emb_subs
1944 { CHECK2(FORM,FILE) }
1948 multim_obje_emb_subs : /* empty */
1949 | multim_obje_emb_subs multim_obje_emb_sub
1952 multim_obje_emb_sub : multim_obje_form_sect { OCCUR2(FORM, 1, 1) }
1953 | multim_obje_titl_sect { OCCUR2(TITL, 0, 1) }
1954 | multim_obje_file_sect { OCCUR2(FILE, 1, 1) }
1959 multim_obje_form_sect : OPEN DELIM TAG_FORM mand_line_item
1960 { START(FORM, NULL) } no_std_subs { CHECK0 } CLOSE { }
1962 multim_obje_titl_sect : OPEN DELIM TAG_TITL mand_line_item
1963 { START(TITL, NULL) } no_std_subs { CHECK0 } CLOSE { }
1965 multim_obje_file_sect : OPEN DELIM TAG_FILE mand_line_item
1966 { START(FILE, NULL) } no_std_subs { CHECK0 } CLOSE { }
1969 /* NOTE STRUCTURE */
1970 note_struc_sub : note_struc_link_sect /* 0:M */
1971 | note_struc_emb_sect /* 0:M */
1974 note_struc_link_sect : OPEN DELIM TAG_NOTE DELIM POINTER
1975 { START(NOTE, NULL) }
1976 note_struc_link_subs
1981 note_struc_link_subs : /* empty */
1982 | note_struc_link_subs note_struc_link_sub
1985 note_struc_link_sub : source_cit_sub
1989 note_struc_emb_sect : OPEN DELIM TAG_NOTE opt_line_item
1990 { START(NOTE, NULL) }
1996 note_struc_emb_subs : /* empty */
1997 | note_struc_emb_subs note_struc_emb_sub
2000 note_struc_emb_sub : continuation_sub
2005 /* PERSONAL NAME STRUCTURE */
2006 pers_name_struc_sub : pers_name_sect /* 0:M */
2009 pers_name_sect : OPEN DELIM TAG_NAME mand_line_item
2010 { START(NAME, NULL) }
2016 pers_name_subs : /* empty */
2017 | pers_name_subs pers_name_sub
2020 pers_name_sub : pers_name_npfx_sect { OCCUR2(NPFX, 0, 1) }
2021 | pers_name_givn_sect { OCCUR2(GIVN, 0, 1) }
2022 | pers_name_nick_sect { OCCUR2(NICK, 0, 1) }
2023 | pers_name_spfx_sect { OCCUR2(SPFX, 0, 1) }
2024 | pers_name_surn_sect { OCCUR2(SURN, 0, 1) }
2025 | pers_name_nsfx_sect { OCCUR2(NSFX, 0, 1) }
2031 pers_name_npfx_sect : OPEN DELIM TAG_NPFX mand_line_item
2032 { START(NPFX, NULL) } no_std_subs { CHECK0 } CLOSE { }
2034 pers_name_givn_sect : OPEN DELIM TAG_GIVN mand_line_item
2035 { START(GIVN, NULL) } no_std_subs { CHECK0 } CLOSE { }
2037 pers_name_nick_sect : OPEN DELIM TAG_NICK mand_line_item
2038 { START(NICK, NULL) } no_std_subs { CHECK0 } CLOSE { }
2040 pers_name_spfx_sect : OPEN DELIM TAG_SPFX mand_line_item
2041 { START(SPFX, NULL) } no_std_subs { CHECK0 } CLOSE { }
2043 pers_name_surn_sect : OPEN DELIM TAG_SURN mand_line_item
2044 { START(SURN, NULL) } no_std_subs { CHECK0 } CLOSE { }
2046 pers_name_nsfx_sect : OPEN DELIM TAG_NSFX mand_line_item
2047 { START(NSFX, NULL) } no_std_subs { CHECK0 } CLOSE { }
2050 /* PLACE STRUCTURE */
2051 place_struc_sub : place_struc_plac_sect /* 0:M */
2054 place_struc_plac_sect : OPEN DELIM TAG_PLAC mand_line_item
2055 { START(PLAC, NULL) }
2056 place_struc_plac_subs
2061 place_struc_plac_subs : /* empty */
2062 | place_struc_plac_subs place_struc_plac_sub
2065 place_struc_plac_sub : place_plac_form_sect { OCCUR2(FORM, 0, 1) }
2071 place_plac_form_sect : OPEN DELIM TAG_FORM mand_line_item
2072 { START(FORM, NULL) } no_std_subs { CHECK0 } CLOSE { }
2075 /* SOURCE_CITATION */
2076 source_cit_sub : source_cit_link_sect /* 0:M */
2077 | source_cit_emb_sect /* 0:M */
2080 source_cit_link_sect : OPEN DELIM TAG_SOUR DELIM POINTER
2081 { START(SOUR, NULL) }
2082 source_cit_link_subs
2087 source_cit_link_subs : /* empty */
2088 | source_cit_link_subs source_cit_link_sub
2091 source_cit_link_sub : source_cit_page_sect { OCCUR2(PAGE, 0, 1) }
2092 | source_cit_even_sect { OCCUR2(EVEN, 0, 1) }
2093 | source_cit_data_sect { OCCUR2(DATA, 0, 1) }
2094 | source_cit_quay_sect { OCCUR2(QUAY, 0, 1) }
2100 source_cit_page_sect : OPEN DELIM TAG_PAGE mand_line_item
2101 { START(PAGE, NULL) } no_std_subs { CHECK0 } CLOSE { }
2104 source_cit_even_sect : OPEN DELIM TAG_EVEN mand_line_item
2105 { START(EVEN, NULL) }
2106 source_cit_even_subs
2111 source_cit_even_subs : /* empty */
2112 | source_cit_even_subs source_cit_even_sub
2115 source_cit_even_sub : source_cit_even_role_sect { OCCUR2(ROLE, 0, 1) }
2119 source_cit_even_role_sect : OPEN DELIM TAG_ROLE mand_line_item
2120 { START(ROLE, NULL) } no_std_subs { CHECK0 } CLOSE { }
2123 source_cit_data_sect : OPEN DELIM TAG_DATA
2124 { START(DATA, NULL) }
2125 source_cit_data_subs
2130 source_cit_data_subs : /* empty */
2131 | source_cit_data_subs source_cit_data_sub
2134 source_cit_data_sub : source_cit_data_date_sect { OCCUR2(DATE, 0, 1) }
2135 | source_cit_text_sect /* 0:M */
2139 source_cit_data_date_sect : OPEN DELIM TAG_DATE mand_line_item
2140 { START(DATE, NULL) } no_std_subs { CHECK0 } CLOSE { }
2143 source_cit_text_sect : OPEN DELIM TAG_TEXT mand_line_item
2144 { START(TEXT, NULL) }
2145 source_cit_text_subs
2150 source_cit_text_subs : /* empty */
2151 | source_cit_text_subs source_cit_text_sub
2154 source_cit_text_sub : continuation_sub
2158 source_cit_quay_sect : OPEN DELIM TAG_QUAY mand_line_item
2159 { START(QUAY, NULL) } no_std_subs { CHECK0 } CLOSE { }
2162 source_cit_emb_sect : OPEN DELIM TAG_SOUR mand_line_item
2163 { START(SOUR, NULL) }
2169 source_cit_emb_subs : /* empty */
2170 | source_cit_emb_subs source_cit_emb_sub
2173 source_cit_emb_sub : continuation_sub
2174 | source_cit_text_sect /* 0:M */
2179 /* SOURCE REPOSITORY CITATION */
2180 source_repos_cit_sub : source_repos_repo_sect { OCCUR2(REPO, 0, 1) }
2183 source_repos_repo_sect : OPEN DELIM TAG_REPO mand_pointer
2184 { START(REPO, NULL) }
2185 source_repos_repo_subs
2190 source_repos_repo_subs : /* empty */
2191 | source_repos_repo_subs source_repos_repo_sub
2194 source_repos_repo_sub : note_struc_sub
2195 | caln_sect /* 0:M */
2199 caln_sect : OPEN DELIM TAG_CALN mand_line_item
2200 { START(CALN, NULL) }
2206 caln_subs : /* empty */
2207 | caln_subs caln_sub
2210 caln_sub : caln_medi_sect { OCCUR2(MEDI, 0, 1) }
2214 caln_medi_sect : OPEN DELIM TAG_MEDI mand_line_item
2215 { START(MEDI, NULL) } no_std_subs { CHECK0 } CLOSE { }
2218 /* SPOUSE TO FAMILY LINK */
2219 spou_fam_link_sub : spou_fam_fams_sect /* 0:M */
2222 spou_fam_fams_sect : OPEN DELIM TAG_FAMS mand_pointer
2223 { START(FAMS, NULL) }
2229 spou_fam_fams_subs : /* empty */
2230 | spou_fam_fams_subs spou_fam_fams_sub
2233 spou_fam_fams_sub : note_struc_sub
2237 /*********************************************************************/
2239 /*********************************************************************/
2241 no_std_subs : /* empty */
2242 | no_std_subs no_std_sub
2245 no_std_sub : user_sect /* 0:M */
2247 | error error_subs CLOSE { HANDLE_ERROR }
2250 no_std_rec : user_rec /* 0:M */
2252 | error error_subs CLOSE { HANDLE_ERROR }
2255 user_rec : OPEN DELIM opt_xref USERTAG
2256 { if ($4[0] != '_') {
2257 gedcom_error("Undefined tag (and not a valid user tag): %s",
2263 { $<ctxt>$ = start_record(REC_USER, $1, $3, $4);
2269 { end_record(REC_USER, $<ctxt>7); }
2271 user_sect : OPEN DELIM opt_xref USERTAG
2272 { if ($4[0] != '_') {
2273 gedcom_error("Undefined tag (and not a valid user tag): %s",
2279 { $<ctxt>$ = start_element(ELT_USER, PARENT, $1, $4, $6, $6);
2280 START($4, $<ctxt>$);
2285 { end_element(ELT_USER, PARENT, $<ctxt>7, NULL);
2289 user_sects : /* empty */ { }
2290 | user_sects user_sect { }
2293 opt_xref : /* empty */ { $$ = NULL; }
2294 | POINTER DELIM { $$ = $1; }
2297 opt_value : /* empty */ { $$ = NULL; }
2298 | DELIM line_value { $$ = $2; }
2301 line_value : POINTER { $$ = $1; }
2302 | line_item { $$ = $1; }
2305 mand_pointer : /* empty */ { gedcom_error("Missing pointer"); YYERROR; }
2306 | DELIM POINTER { gedcom_debug_print("==Ptr: %s==\n", $2);
2310 mand_line_item : /* empty */ { gedcom_error("Missing value"); YYERROR; }
2311 | DELIM line_item { gedcom_debug_print("==Val: %s==\n", $2);
2315 opt_line_item : /* empty */ { }
2316 | DELIM line_item { }
2319 line_item : anychar { size_t i;
2320 CLEAR_BUFFER(line_item_buf);
2321 line_item_buf_ptr = line_item_buf;
2322 /* The following also takes care of '@@' */
2323 if (!strncmp($1, "@@", 3))
2324 *line_item_buf_ptr++ = '@';
2326 for (i=0; i < strlen($1); i++)
2327 *line_item_buf_ptr++ = $1[i];
2330 | ESCAPE { CLEAR_BUFFER(line_item_buf);
2331 line_item_buf_ptr = line_item_buf;
2332 /* For now, ignore escapes */
2337 /* The following also takes care of '@@' */
2338 if (!strncmp($2, "@@", 3))
2339 *line_item_buf_ptr++ = '@';
2341 for (i=0; i < strlen($2); i++)
2342 *line_item_buf_ptr++ = $2[i];
2346 { /* For now, ignore escapes */
2351 anychar : ANYCHAR { }
2355 error_subs : /* empty */
2356 | error_subs error_sect
2359 error_sect : OPEN DELIM opt_xref anytag opt_value error_subs CLOSE { }
2361 gen_sect : OPEN DELIM opt_xref anystdtag
2362 { INVALID_TAG($4); }
2363 opt_value opt_sects CLOSE
2367 gen_rec : gen_rec_top
2371 gen_rec_norm : OPEN DELIM opt_xref anystdtag
2372 { INVALID_TOP_TAG($4) }
2373 opt_value opt_sects CLOSE
2377 gen_rec_top : OPEN DELIM anytoptag
2378 { gedcom_error("Missing cross-reference"); YYERROR; }
2379 opt_value opt_sects CLOSE
2383 opt_sects : /* empty */ { }
2384 | opt_sects gen_sect { }
2387 anytag : USERTAG { }
2401 anystdtag : TAG_ABBR
2531 /* Functions that handle the counting of subtags */
2533 int* count_arrays[MAXGEDCLEVEL+1];
2534 char tag_stack[MAXGEDCLEVEL+1][MAXSTDTAGLEN+1];
2535 Gedcom_ctxt ctxt_stack[MAXGEDCLEVEL+1];
2537 void push_countarray()
2540 if (count_level > MAXGEDCLEVEL) {
2541 gedcom_error("Internal error: count array overflow");
2545 count = (int *)calloc(YYNTOKENS, sizeof(int));
2546 if (count == NULL) {
2547 gedcom_error("Internal error: count array calloc error");
2551 count_arrays[count_level] = count;
2556 void set_parenttag(char* tag)
2558 strncpy(tag_stack[count_level], tag, MAXSTDTAGLEN+1);
2561 void set_parentctxt(Gedcom_ctxt ctxt)
2563 ctxt_stack[count_level] = ctxt;
2566 char* get_parenttag()
2568 return tag_stack[count_level];
2571 Gedcom_ctxt get_parentctxt()
2573 return ctxt_stack[count_level];
2576 int count_tag(int tag)
2578 int *count = count_arrays[count_level];
2579 return ++count[tag - GEDCOMTAGOFFSET];
2582 int check_occurrence(int tag)
2584 int *count = count_arrays[count_level];
2585 return (count[tag - GEDCOMTAGOFFSET] > 0);
2588 void pop_countarray()
2591 if (count_level < 0) {
2592 gedcom_error("Internal error: count array underflow");
2596 count = count_arrays[count_level];
2598 count_arrays[count_level] = NULL;
2602 /* Enabling debug mode */
2603 /* level 0: no debugging */
2604 /* level 1: only internal */
2605 /* level 2: also bison */
2608 void gedcom_set_debug_level(int level, FILE* f)
2613 trace_output = stderr;
2615 gedcom_high_level_debug = 1;
2624 int gedcom_debug_print(char* s, ...)
2627 if (gedcom_high_level_debug) {
2630 res = vfprintf(trace_output, s, ap);
2636 /* Setting the error mechanism */
2637 void gedcom_set_error_handling(Gedcom_err_mech mechanism)
2639 error_mechanism = mechanism;
2642 /* Compatibility handling */
2644 void gedcom_set_compat_handling(int enable_compat)
2646 compat_enabled = enable_compat;
2649 void set_compatibility(char* program)
2651 if (compat_enabled) {
2652 gedcom_debug_print("==== Program: %s\n", program);
2653 if (! strncmp(program, "ftree", 6)) {
2654 gedcom_warning("Enabling compatibility with 'ftree'");
2655 compatibility = C_FTREE;
2663 int compat_mode(int compat_flags)
2665 return (compat_flags & compatibility);