+int compat_matrix[] =
+{
+ /* C_NO_SUBMITTER */ C_FTREE | C_LIFELINES | C_PAF2,
+ /* C_INDI_ADDR */ C_FTREE,
+ /* C_NOTE_NO_VALUE */ C_FTREE,
+ /* C_NO_GEDC */ C_LIFELINES | C_PAF2,
+ /* C_NO_CHAR */ C_LIFELINES,
+ /* C_HEAD_TIME */ C_LIFELINES,
+ /* C_NO_DOUBLE_AT */ C_LIFELINES | C_PAF5 | C_PAF2 | C_FAMORIG,
+ /* C_NO_REQUIRED_VALUES */ C_LIFELINES,
+ /* C_551_TAGS */ C_PAF5,
+ /* C_NO_SLGC_FAMC */ C_PAF5,
+ /* C_SUBM_COMM */ C_PAF2,
+ /* C_DOUBLE_DATES_4 */ C_PAF2
+};
+
+int compat_state[C_NR_OF_RULES];
+
+/* Compatibility handling */
+
+void gedcom_set_compat_handling(int enable_compat)
+{
+ compat_enabled = enable_compat;
+}
+
+void enable_compat_msg(const char* program_name, int version)
+{
+ if (version > 0)
+ gedcom_warning(_("Enabling compatibility with '%s', version %d"),
+ program_name, version);
+ else
+ gedcom_warning(_("Enabling compatibility with '%s'"),
+ program_name);
+}
+
+int program_equal(const char* program, const char* compare)
+{
+ return !strncmp(program, compare, strlen(compare)+1);
+}
+
+int program_equal_continued(const char* program, const char* compare)
+{
+ size_t len = strlen(compare);
+ int result = strncmp(program, compare, len);
+ if (result == 0) {
+ if (strlen(program) > len)
+ set_compatibility_version(program + len);
+ }
+ return !result;
+}
+
+void set_compatibility_program(const char* program)
+{
+ compatibility_program = 0;
+ if (compat_enabled) {
+ if (program_equal(program, "ftree")) {
+ compatibility_program = CP_FTREE;
+ }
+ else if (program_equal_continued(program, "LIFELINES")) {
+ compatibility_program = CP_LIFELINES;
+ }
+ else if (program_equal_continued(program, "PAF")) {
+ compatibility_program = CP_PAF;
+ }
+ else if (program_equal(program, "FamilyOrigins")) {
+ compatibility_program = CP_FAMORIG;
+ }
+ }
+}
+
+void compute_compatibility()
+{
+ /* Reinitialize compatibility */
+ int i;
+ int version = 0;
+ default_charset = "";
+ compatibility = 0;
+ for (i = 0; i < C_NR_OF_RULES; i++)
+ compat_state[i] = 0;
+
+ switch (compatibility_program) {
+ case CP_FTREE:
+ compatibility = C_FTREE;
+ break;
+ case CP_LIFELINES:
+ compatibility = C_LIFELINES;
+ default_charset = "ANSI";
+ break;
+ case CP_PAF:
+ if (compatibility_version >= 20000 && compatibility_version < 30000) {
+ compatibility = C_PAF2;
+ version = 2;
+ }
+ else if (compatibility_version >= 50000) {
+ compatibility = C_PAF5;
+ version = 5;
+ }
+ break;
+ case CP_FAMORIG:
+ compatibility = C_FAMORIG;
+ break;
+ default:
+ break;
+ }
+ if (compatibility)
+ enable_compat_msg(program_name[compatibility_program], version);
+}
+
+void set_compatibility_version(const char* version)
+{
+ if (compat_enabled) {
+ unsigned int major=0, minor=0, patch=0;
+ int result;
+
+ result = sscanf(version, " %u.%u.%u", &major, &minor, &patch);
+ if (result > 0) {
+ gedcom_debug_print("Setting compat version to %u.%u.%u",
+ major, minor, patch);
+ compatibility_version = major * 10000 + minor * 100 + patch;
+ }
+ }
+}
+
+int compat_mode(Compat_rule rule)
+{
+ return (compat_matrix[rule] & compatibility);
+}
+
+/********************************************************************/
+/* C_NO_SUBMITTER */
+/********************************************************************/
+