private void initLanguageTable() {
            using (var langstream = new StreamReader(Assembly.GetExecutingAssembly().GetManifestResourceStream("EbookObjects.Misc.langtable.csv"))) {
                var langs = langstream.FromCsv<LangData>().ToArray();
                var existNames = LanguageNames.Select(n => n.Name).ToArray();
                var newNames = new List<Models.LanguageName>(langs.Select(l => l.Name).Distinct().Except(existNames).Select(n => new Models.LanguageName { Name = n }));

                var newCodes = new List<Models.LanguageCode>();
                foreach (var lang in langs) {
                    var langcode = newCodes.SingleOrDefault(c => c.Code == lang.Code);
                    if (langcode == null) langcode = LanguageCodes.SingleOrDefault(c => c.Code == lang.Code);
                    if (langcode == null) {
                        var langName = newNames.SingleOrDefault(n => n.Name == lang.Name);
                        if (langName == null) langName = LanguageNames.SingleOrDefault(n => n.Name == lang.Name);
                        var newCode = new Models.LanguageCode { Code = lang.Code };
                        if (newCode.LanguageNames == null) newCode.LanguageNames = new List<Models.LanguageName>();
                        newCode.LanguageNames.Add(langName);
                        newCodes.Add(newCode);
                    } else if (!langcode.LanguageNames.Any(n => n.Name == lang.Name)) {
                        var langName = newNames.SingleOrDefault(n => n.Name == lang.Name);
                        if (langName == null) langName = LanguageNames.SingleOrDefault(n => n.Name == lang.Name);
                        langcode.LanguageNames.Add(langName);
                    }
                }
                LanguageNames.AddRange(newNames);
                LanguageCodes.AddRange(newCodes);
            }
        }