// MorgenGrauen MUDlib
//
// - Prototypen und Properties in thing/material.h
// - Liste in materials.h
//
// TODO: properties.h um materials.h erweitern
//
// - implizite Gruppenzuordnung entfernen, da jetzt explizit in
//   Definitionsdateien vorhanden
// - Materialdoku ueberarbeiten, dabei Hinweis auf nicht mehr implizite
//   Gruppenzuordnung
// /p/daemon/materialdb.c -- Materialdatenbank
//
// $Id: materialdb.c 8755 2014-04-26 13:13:40Z Zesstra $

#pragma strong_types
#pragma no_clone
#pragma no_inherit
#pragma no_shadow
#pragma pedantic

#include <debug_message.h>

// Die Propertydefinition reinholen
#include <language.h>
#include <thing/description.h>
// Materialliste nicht mit reinziehen
#define _SKIP_MATERIALS_
#include <thing/material.h>
#include <player/description.h>
#include <rtlimits.h>
#include <living/comm.h>

// Basisverzeichnis der Materialien
#define MAT_DIR "/doc/materials"

// Ausgabeverzeichnis fuer Doku
#define DOC_DIR(x) ("/doc/materials/"+x)

// Dateiname des Headers mit Materialdefinitionen
#define HEADERFILE "/sys/materials.h"

// Savefile.
#define SAVEFILE DOC_DIR("materialdb")

// Rein intern verwendete Namen
#define P_RECOC "recognizability"
#define P_ID    "id"
#define P_DEFSTR "defstr"
#define P_MEMBERS "members"
#define P_MG_FRACTIONS "mg_fractions"

#define LOG_ERROR(x) if (this_player()) this_player()->ReceiveMsg(\
    x, MT_DEBUG|MSG_DONT_IGNORE, MA_UNKNOWN, "MDB-Error: ",\
    "MatDB")
#define LOG_WARN(x) if (this_player()) this_player()->ReceiveMsg(\
    x, MT_DEBUG|MSG_DONT_IGNORE, MA_UNKNOWN, "MDB-Warn: ",\
    "MatDB")

// Prototypes:
// (Liefert den Anteil der Materialgruppe grp an mats)
int MaterialGroup(mapping mats, string grp);
// Konvertiert eine Liste von Materialien zu ihren Namen, dabei wird die
// Erkennungsfaehigkeit beruecksichtigt und evtl. falsch erkannt
varargs string ConvMaterialList(mixed mats, int casus, mixed idinf);
varargs string MaterialName(string mat, int casus, mixed idinf);
// Gibt den Namen einer Materialgruppe zurueck
string GroupName(string grp);
// Gibt alle Materialien zurueck
string *AllMaterials();
// Gibt alle Gruppen zurueck
string *AllGroups();
// Gibt alle Gruppen zurueck, in denen mat enthalten ist
string *GetMatMembership(string mat);
// Gibt alle Materialien zurueck, die in grp enthalten sind
string *GetGroupMembers(string grp);
// Erneuert die Materialien durch Scannen des Materialverzeichnisses
void Update();
// generiert Headerfile aus den Daten
varargs void GenHeaderFile(string fn);

mapping materials;
mapping material_groups;
private status initialized;
mapping old_mat_keys;     // Alter Materialkey -> neuer Key (Kompatibilitaet)
nosave mapping new_materials;       // Materialien waehrend des Scannens
nosave mapping new_material_groups; // Materialgruppen waehrend des Scannens
private nosave status isScanning;
private nosave int updateTicks;

void create() {
  seteuid(getuid());
  // Savefile einlesen, falls moeglich, damit die DB direkt initialisert ist,
  // wenn auch ggf. mit alten Daten.
  restore_object(SAVEFILE);
  if (initialized) {
    // falls erfolgreich, direkt Header fuer die Mudlib schreiben
    GenHeaderFile();
  }
  // jetzt Update der Daten durchfuehren.
  Update();
}

//==================== Umwandeln der Strings aus der thing/material.h
private string getMatId(string key) {
  // Alte Bezeichner umwandeln
  if (!member(materials, key))
    key = old_mat_keys[key];
  return key;
}
private string getMatGroupId(string key) {
  // Alte Bezeichner umwandeln
  if (!member(material_groups, key))
    key = "MATGROUP_"+upperstring(key[3..]);
  return key;
}
private string matKey2Defstr(string key, mapping mats) {
  string id;
  if (member(mats[key], P_DEFSTR))
    id = mats[key][P_DEFSTR];
  else
    id = key;
  return id;
}
private string groupKey2Defstr(string key) {
  if (sizeof(key) > 9)
    key = "mg_"+lowerstring(key[9..]);
  else
    key = "";
  return key;
}

//==================== Schnittstellenfunktionen zur Verwendung der DB
varargs string MaterialName(string mat, int casus, mixed idinf) {
  if (initialized) {
    string *names;
    mapping props;
    mixed *dif;
    // Anpassen der Materialid
    mat = getMatId(mat);

    if (!mappingp(props=materials[mat]))
      props=([]);

    // Je nach Koennen des Spielers kann man das exakte Material
    // mehr oder weniger gut erkennen:
    if (pointerp(dif=props[P_RECOC])
&& (!intp(idinf)||idinf<100) ) { // 100=exakte Erkennung
      int i, n, recval;
      mixed tmp, x;

      recval=0;
      mapping grps=props[P_MG_FRACTIONS];
      if (!pointerp(idinf))
        idinf=({idinf});

      // Zunaechst die Faehigkeit des Spielers (da koennen noch
      // Gildenfaehigkeiten hinzu kommen) ermitteln, dieses
      // Material zu erkennen:
      i=sizeof(idinf);
      while(i--) {
        tmp=idinf[i];
        if (objectp(tmp)) // Diese Property ist hauptsaechlich fuer Rassen:
          tmp=tmp->QueryProp(P_MATERIAL_KNOWLEDGE);
        if (intp(tmp)) {
          recval+=tmp; // Allgemeine Erkennungsfaehigkeit
          break;
        }
        if (closurep(tmp) && intp(x=funcall(tmp,mat,grps))) {
          recval+=x;
          break; // Closures koennen immer nuetzlich sein :)
        }
        if (mappingp(tmp)) {
          int j;
          if ((x=tmp[mat]) && intp(x)){
            // Erkennung von speziell diesem Material
            recval+=x;
            break;
          }
          // Erkennung von Gruppen
          j=sizeof(grps);
          while(j--)
            if((x=tmp[grps[j]]) && intp(x))
              recval+=x;
          if (pointerp(tmp=tmp[MATERIAL_SYMMETRIC_RECOGNIZABILITY])) {
            for (j=sizeof(tmp)-2;j>=0;j-=2) {
              if (!intp(x=tmp[j+1]))
                raise_error("materialdb: illegal sym.recoc. format\n");
              if (props[tmp[j]])
                recval+=x;
              else // bei passenden Gruppen +, bei anderen -
                recval-=x;
            }
          }
        }
      }

      // Jetzt wird ermittelt, ob vielleicht eine ungenauere
      // Beschreibung gegeben werden soll:
      x=dif[0];
      n = sizeof(dif)-1;
      for (i=2;i<=n;i+=2) {
        if (recval>=dif[i-1])
          x=dif[i];
      }
      // Wenn die Faehigkeiten des Spielers nicht fuer den echten Klarnamen
      // ausreichen, gib die Alternative zurueck:
      if (x!=mat)
        return MaterialName(x, casus, 100);
    }

    if (!pointerp(names=props[P_NAME]) || sizeof(names)<4)
      names=({"unbekanntes Material", "unbekannten Materials",
              "unbekanntem Material", "unbekannten Material"});
    if (casus<0 || casus>3)
      casus=0;
    return names[casus];
  }
}

varargs string ConvMaterialList(mixed mats, int casus, mixed idinf) {
  if (initialized) {
    string *ms,ml;
    int i;

    ml="";
    if (mappingp(mats))
      ms=m_indices(mats);
    else if (stringp(mats))
      ms=({mats});
    else if (pointerp(mats))
      ms=mats;
    else
      ms=({});
    i=sizeof(ms);
    while(i) {
      ml+=MaterialName(ms[--i],casus,idinf);
      if (i)
        ml+=((i>1)?", ":" und ");
    }
    return ml;
  }
}

int MaterialGroup(mapping mats, string grp) {
   if (initialized) {
     string *ms;
     int i,res;

     res=0;
     if (!mappingp(mats) || !stringp(grp))
       return res;
     ms=m_indices(mats);
     i=sizeof(ms);
     while(i--) {
       string mat;
       mapping props;
       mat=ms[i];
       if (mappingp(props=materials[getMatId(mat)]))
         res+=(mats[mat]*props[P_MG_FRACTIONS][getMatGroupId(grp)])/100;
     }
     if (res<-100) // Vielleicht noch Antimaterie zulassen
       res=-100;   // (noch nicht sicher ob das so bleiben wird oder 0 sein wird)
     if (res>100)
       res=100;
     return res;
   }
}

string *AllMaterials() {
  if (initialized) {
    // Aus Kompatibilitaetsgruenden die alten Schluessel (#define-String)
    // zurueckgeben
    return m_indices(old_mat_keys);
  }
  return 0;
}

string *AllGroups() {
  if (initialized) {
    // Aus Kompatibilitaetsgruenden die alten Schluessel (#define-String)
    // zurueckgeben
    return map(m_indices(material_groups), #'groupKey2Defstr);
  }
  return 0;
}

string *GetMatMembership(string mat) {
  if (initialized) {
    mapping props;
    // Anpassen der Materialid
    mat = getMatId(mat);

    if (!mappingp(props=materials[mat]))
      return ({});
    return map(m_indices(props[P_MG_FRACTIONS]), #'groupKey2Defstr);
  }
  return 0;
}

string *GetGroupMembers(string grp) {
  if (initialized) {
    string *mats;
    // Anpassen der Materialid
    grp = getMatGroupId(grp);
    if (!member(material_groups, grp) ||
	!pointerp(mats=material_groups[grp][P_MEMBERS]))
      return ({});
    return map(mats, #'matKey2Defstr, materials);
  }
  return 0;
}

string GroupName(string grp) {
  if (initialized) {
    if (member(material_groups, getMatGroupId(grp)))
      return material_groups[getMatGroupId(grp)][P_NAME];
    else
      return "Unbekanntes";
  }
}

string GroupDescription(string grp) {
  if (initialized) {
    if (member(material_groups, getMatGroupId(grp)))
      return material_groups[getMatGroupId(grp)][P_DESCRIPTION];
    else
      return "Gruppe unbekannt";
  }
}

//==================== Generieren von Headerfile und Manpages
private string *get_ordered_groups()
{
  return ({"MATGROUP_WOOD", "MATGROUP_JEWEL", "MATGROUP_STONE", "MATGROUP_MAGNETIC",
           "MATGROUP_METAL", "MATGROUP_DRUG", "MATGROUP_HERBAL", "MATGROUP_FLEXIBLE",
           "MATGROUP_BIO", "MATGROUP_ACIDIC", "MATGROUP_BASIC", "MATGROUP_POISONOUS",
           "MATGROUP_EXPLOSIVE", "MATGROUP_INFLAMMABLE",
           "MATGROUP_ELEMENTAL", "MATGROUP_ELECTRICAL", "MATGROUP_MAGIC",
           "MATGROUP_HOLY", "MATGROUP_UNHOLY", "MATGROUP_INVIS",
           "MATGROUP_SOLID", "MATGROUP_FLUID", "MATGROUP_GAS"});
}
private string gen_material_h_head()
{
  return
    "// MorgenGrauen MUDlib\n//\n"
    "// materials.h -- material definitions\n//\n"
    "// This file is generated by /secure/materialdb.c\n//\n"
    "// DO NOT EDIT!\n//\n"
    "// $Id: materialdb.c 8755 2014-04-26 13:13:40Z Zesstra $\n\n"
    "#ifndef __MATERIALS_H__\n"
    "#define __MATERIALS_H__\n\n";
}
private string gen_material_h_material(string mat, string last_grp)
{
  mat = old_mat_keys[mat];
  return sprintf("#define %-24s\"%-20s // %s\n", mat,
                (member(materials[mat], P_DEFSTR)?materials[mat][P_DEFSTR]:mat)+"\"",
                materials[mat][P_DESCRIPTION]||materials[mat][P_NAME][WER]);
}
private string gen_material_h_materials_grp(string grp, string *left)
{
  string txt, *mats;
  txt = sprintf("\n// Gruppe: %s\n", GroupName(grp));
  mats = GetGroupMembers(grp) - (GetGroupMembers(grp) - left);
  txt += sprintf("%@s", map(sort_array(mats, #'>), #'gen_material_h_material));
  left -= GetGroupMembers(grp);
  return txt;
}
private string gen_material_h_materials()
{
  string txt, last_grp;
  string *grps, *mats;
  txt = "// ****************************** Materialien ******************************\n";
  // Gruppenweise ordnen
  grps = get_ordered_groups();
  mats = AllMaterials();
  txt += sprintf("%@s", map(grps, #'gen_material_h_materials_grp,
                                  &mats));
  // Uebriggebliene Materialien ausgeben
  txt += "// sonstige Materialien:\n";
  txt += sprintf("%@s", map(mats, #'gen_material_h_material));
  return txt;
}
private string gen_material_h_group(string grp)
{
  return sprintf("#define %-27s\"%-18s // %s\n",
                 grp, groupKey2Defstr(grp)+"\"", GroupName(grp));
}
private string gen_material_h_groups()
{
  string txt;
  txt = "\n// **************************** Materialgruppen ****************************\n\n"
    "#ifndef _IS_MATERIALDB_\n";
  txt += sprintf("%@s\n", map(sort_array(m_indices(material_groups), #'>),
                                    #'gen_material_h_group));
  txt += "\n#endif // _IS_MATERIALDB_\n";
  return txt;
}
private string gen_material_h_foot()
{
  return
    "#endif // __THING_MATERIAL_H__\n";
}
private int dump_material_h(string fn)
{
  return (write_file(fn, gen_material_h_head()) &&
          write_file(fn, gen_material_h_materials()) &&
          write_file(fn, gen_material_h_groups()) &&
          write_file(fn, gen_material_h_foot()));
}
private string gen_material_list_material(string mat)
{
  mat = old_mat_keys[mat];
  return sprintf("  %-28s%=-45s\n", mat,
                 materials[mat][P_DESCRIPTION]||materials[mat][P_NAME][WER]);
}
private string gen_material_list_materials_grp(string grp, string *left)
{
  string txt, *mats;
  txt = sprintf("%s:\n", capitalize(GroupName(grp)));
  mats = sort_array(GetGroupMembers(grp) - (GetGroupMembers(grp) - left), #'>);
  txt += sprintf("%@s\n", map(mats, #'gen_material_list_material));
  left -= GetGroupMembers(grp);
  return txt;
}
private void dump_material(string fn)
{
  string txt;
  string *grps, *mats;
  // Gruppenweise ordnen
  grps = get_ordered_groups();
  mats = AllMaterials();
  txt = sprintf("%@s", map(grps, #'gen_material_list_materials_grp,
                                 &mats));
  // Uebriggebliene Materialien ausgeben
  txt += "sonstige Materialien:\n";
  txt += sprintf("%@s", map(mats, #'gen_material_list_material));
  write_file(fn, txt) ||
    raise_error(sprintf("Konnte Liste nicht weiter in Datei %s schreiben,"
                        " Abbruch\n", fn));
}
private void dump_group(string grp, string fn)
{
  // upperstring langsame simul_efun, warum?
  write_file(fn, sprintf("  %-28s%=-48s\n", (grp),
                         GroupName(grp))) ||
    raise_error(sprintf("Konnte Liste nicht weiter in Datei %s schreiben,"
                        " Abbruch\n", fn));
}
private string gen_doc_foot(string other)
{
  return sprintf("\nSIEHE AUCH:\n"
                 "     Konzepte:    material, materialerkennung\n"
                 "     Grundlegend: P_MATERIAL, /sys/materials.h, /sys/thing/material.h\n"
                 "     Methoden:    QueryMaterial(), QueryMaterialGroup(), MaterialList(),\n"
                 "     Listen:      AllMaterials(), AllGroups()\n"
                 "                  %s\n"
                 "     Master:      ConvMaterialList(), MaterialGroup(),\n"
                 "                  GroupName(), MaterialName(),\n"
                 "                  GetGroupMembers(), GetMatMembership()\n"
                 "     Sonstiges:   P_MATERIAL_KNOWLEDGE\n\n"
                 "%s generiert aus /secure/materialdb\n", other, dtime(time()));
}

/* GenMatList
 *
 * Generiert Datei mit registrierten Materialien fuer die Dokumentation,
 */
varargs void GenMatList(string fn)
{
  if (initialized) {
    string txt;
    if (!stringp(fn) || !sizeof(fn))
      fn = DOC_DIR("materialliste");
    if (file_size(fn) >= 0) {
      debug_message(
          sprintf("Datei %s existiert bereits, loesche sie\n", fn),
          DMSG_STAMP);
      rm(fn);
    }
    if (write_file(fn, "Material Liste\n==============\n\n"))
    {
      dump_material(fn);
      write_file(fn, gen_doc_foot("materialgruppen"));
      debug_message(
        sprintf("Materialliste erfolgreich in Datei %s geschrieben\n", fn),
        DMSG_STAMP);
    }
    else
      debug_message(
          sprintf("Konnte Liste nicht in Datei %s schreiben, Abbruch\n", fn),
          DMSG_STAMP);
  }
}

/* GenMatGroupList
 *
 * Generiert Datei mit registrierten Materialgruppen fuer die Dokumentation,
 */
varargs void GenMatGroupList(string fn)
{
  if (initialized) {
    string txt;
    if (!stringp(fn) || !sizeof(fn))
      fn = DOC_DIR("materialgruppen");
    if (file_size(fn) >= 0) {
      debug_message(
          sprintf("Datei %s existiert bereits, loesche sie\n", fn),
          DMSG_STAMP);
      rm(fn);
    }
    if (write_file(fn, "Materialgruppen\n===============\n"))
    {
      map(sort_array(m_indices(material_groups), #'>), #'dump_group, fn);
      write_file(fn, gen_doc_foot("materialliste"));
      debug_message(
        sprintf("Materialliste erfolgreich in Datei %s geschrieben\n", fn),
        DMSG_STAMP);
    }
    else
      debug_message(
          sprintf("Konnte Liste nicht in Datei %s schreiben, Abbruch\n", fn),
          DMSG_STAMP);
  }
}

/* GenHeaderFile
 *
 * Generiert Headerfile mit Definitionen der moeglichen Materialien und
 * Gruppen
 */
varargs void GenHeaderFile(string fn)
{
  if (initialized) {
    string txt;
    if (!stringp(fn) || !sizeof(fn))
      fn = HEADERFILE;
    if (file_size(fn) >= 0)
    {
      debug_message(
          sprintf("Datei %s existiert bereits, loesche sie\n", fn),
          DMSG_STAMP);
      rm(fn);
    }
    if (dump_material_h(fn))
      debug_message(
          sprintf("Headerdatei erfolgreich in %s geschrieben\n", fn),
          DMSG_STAMP);
    else
      debug_message(
        sprintf("Konnte Headerdatei nicht in Datei %s schreiben, Abbruch\n",
                fn), DMSG_STAMP);
  }
}

//==================== Pruef- und Hilfsfunktionen fuer Materialien
private void updateGroupMembers(mapping groups, string mat_id, mapping mat) {
  mixed *addgrps; // Array zum Ableiten von Gruppenzugehoerigkeiten
  string *h;
  int i, val;
  mapping fractions; // Mapping mit Anteilen an Gruppen
  fractions = mat[P_MG_FRACTIONS];
  if (!mappingp(fractions))
    fractions = ([]);
  addgrps=({ // Reihenfolge wird rueckwaerts abgearbeitet
    // Ableitungen sind z.T. abenteuerlich gewesen, mal ordentlich
    // ausmisten. Die Zugehoerigkeit gehoert explizit in die
    // Materialdefinition
    // Gase sieht man normalerweise nicht:
    ({"MATGROUP_INVIS", "MATGROUP_GAS"}),
    // Mineralien sind auch Steine
    ({"MATGROUP_STONE","MATGROUP_MINERAL"}),
    // Edelmetalle sind Metalle:
    ({"MATGROUP_METAL","MATGROUP_PRECIOUS_METAL"}),
    // Lebewesen und deren Ueberreste, Paiere und Stoffe sind biologisch
    ({"MATGROUP_BIO","MATGROUP_LIVING","MATGROUP_DEAD",
      "MATGROUP_PAPER"}),
    // Holz ist pflanzlich:
    ({"MATGROUP_HERBAL", "MATGROUP_WOOD"}),
    // Holz ist meistens tot:
    ({"MATGROUP_DEAD","MATGROUP_WOOD"}),
    // Holz, Papier und Stoffe brennen:
    ({"MATGROUP_INFLAMMABLE","MATGROUP_WOOD","MATGROUP_PAPER"}),
    // Laubhoelzer, Nadelhoelzer und Tropenhoelzer sind Holz
    ({"MATGROUP_WOOD","MATGROUP_TROPICAL_WOOD","MATGROUP_DECIDUOUS_WOOD",
      "MATGROUP_CONIFER_WOOD"}),
    // Explosive Dinge sind immer entzuendlich:
    ({"MATGROUP_INFLAMMABLE","MATGROUP_EXPLOSIVE"})
  });
  i=sizeof(addgrps);
  while(i--) {
    int j;
    h=addgrps[i];
    if (member(fractions,h[0])) // Existiert schon eigener Eintrag?
      continue; // Automatische Eintragung unnoetig
    val=0;
    for (j=sizeof(h)-1;j>=1;j--)
      val+=fractions[h[j]];
    if (!val)
      continue;
    if (val>100)
      val=100;
    else if (val<-100)
      val=-100;
    fractions[h[0]]=val;
  }
  if (fractions["MATGROUP_LIVING"]) // Im Falle von lebendem Holz, tot loeschen
    m_delete(fractions,"MATGROUP_DEAD");
  // Alles, was nicht als gasfoerming, fluessig oder fest eingeordnet ist, ist
  // sonstwas:
  if (!member(fractions, "MATGROUP_FLUID")
      && !member(fractions, "MATGROUP_GAS")
      && !member(fractions, "MATGROUP_SOLID"))
    fractions["MATGROUP_MISC"]=100;
  // Materialien als Mitglieder in die Gruppen eintragen
  addgrps=m_indices(fractions);
  i=sizeof(addgrps);
  while(i--) {
    mixed ind;
    ind=addgrps[i];
    if (!fractions[ind] || !member(groups, ind)) {
      // Unbekannte Gruppe und Gruppe ohne Anteil aus Mapping loeschen
      m_delete(fractions,ind);
      continue;
    }
    if (!pointerp(h=groups[ind][P_MEMBERS]))
      h=({});
    h+=({mat_id});
    groups[ind][P_MEMBERS]=h;
  }
  mat[P_MG_FRACTIONS] = fractions;
}

//==================== Einlesen der Mappings aus Dateien

#define MDESC_ERROR(x, y) LOG_ERROR(sprintf("Materialbeschreibung '%s': %s\n", x, y))
#define MDESC_WARN(x, y) //LOG_WARN(sprintf("Materialbeschreibung '%s': %s\n", x, y))

private mapping getDescParts(string s) {
  string* lines;
  string key, val;
  int i, n;
  mapping m;
  m = ([]);
  val = "";
  lines = explode(s, "\n");
  n = sizeof(lines);
  if (n > 0) {
    while (i < n) {
      if (sscanf(lines[i], "%s:", key)) {
        status multiline;
        multiline = 0;
        // Schluessel gefunden, Wert auslesen
        while ( (++i < n) && sizeof(lines[i])) {
          // Mehrzeilige Werte mit newline verketten
          if (multiline) {
            val += "\n";
          }
          val += lines[i];
          multiline = 1;
        }
        m += ([key:val]);
        val = "";
      }
      i++;
    }
  }
  return m;
}
private varargs int isFile(string fn, string path) {
  if (stringp(path) && sizeof(path))
    fn = path+"/"+fn;
  return (file_size(fn) >= 0);
}

private varargs mixed readGroupDesc(string id) {
  mixed m;
  string fn;
  fn = MAT_DIR+"/groups/"+id;
  if (file_size(fn) > 0) {
    mapping parts;
    string desc;
    parts = getDescParts(read_file(fn));
    m = ([P_NAME:parts["Name"],
          P_MEMBERS:({})]);
    if (member(parts,"Beschreibung"))
      m += ([P_DESCRIPTION:parts["Beschreibung"]]);
    if (parts["Gruppenid"] != id)
      LOG_WARN(sprintf("Unstimmigkeit Gruppenid bei '%s'\n", id));
  } else {
    LOG_ERROR(sprintf("Kann Gruppenbeschreibung %s nicht laden\n", fn));
  }
  return m;
}

private mapping convMatId(string s) {
  mapping m;
  string* parts;
  parts = explode(s, "\"");
  if (sizeof(parts)) {
    int ende;
    ende = strstr(parts[0]," ")-1;
    if (ende < 0)
      ende = sizeof(parts[0]);
    m = ([P_ID:parts[0][0..ende]]);
    if (sizeof(parts) > 1)
      m += ([P_DEFSTR:parts[1]]);
  }
  return m;
}

private string* convMatNames(string s) {
  string* names = filter(explode(s, "\""), function int (string x) { 
                            return sizeof(x)>1;
                          });
  if (sizeof(names)<1)
    names=0;
  else {
    if (sizeof(names)<2)
      names+=({names[0]+"s"});
    if (sizeof(names)<3)
      names+=({names[0]});
    if (sizeof(names)<4)
      names+=({names[0]});
  }
  return names;
}

private int convMatGender(string s) {
  int gender;
  s = lowerstring(s);
  // Ein Buchstabe reicht zur Bestimmung. Wenn nur weiblich|female
  // bzw. maennlich|male verwendet wird. Dabei ist dann allerdings die
  // Reihenfolge der Auswertung wichtig, damit das m bei MALE nicht mehr bei
  // female passt.
  if (sizeof(regexp( ({s}), "f|w"))) {
    gender = FEMALE;
  } else if (sizeof(regexp( ({s}), "m"))) {
    gender = MALE;
  } else {
    gender = NEUTER;
  }
  return gender;
}
private string convMatDesc(string s) {
  if (sizeof(regexp( ({s}), "- nicht vorhanden -"))) {
    s = 0;
  } else {
    // Mehrzeilige Beschreibungen zu einer Zeile zusammenfassen
    s = implode(explode(s, "\n"), " ");
  }
  return s;
}
private void addRecocLine(string s, mixed* r) {
  // Die weitere Bewertung der Schwierigkeit kann erst vorgenommen werden,
  // wenn alle Materialien bekannt sind und passiert spaeter. Zuerst werden
  // nur die Elemente des Arrays konvertiert und eingetragen
  string mat;
  int val;
  if (sscanf(s, "%s:%d", mat, val)) {
    r += ({mat,val});
  } else if (sscanf(s, "%d", val)) {
    r += ({val});
  } else {
    r += ({s});
  }
}
private mixed convMatRec(string s) {
  mixed difficulties;
  if (sizeof(regexp( ({s}), "- keine Einschraenkung -"))) {
    difficulties = 0;
  } else {
    difficulties = ({});
    // Jede Zeile enthaelt eine Bedingung
    map(explode(s, "\n"), #'addRecocLine, &difficulties);
  }
  return difficulties;
}
private void addGroupLine(string s, mapping g) {
  // Die weitere Bewertung der Zugehoerigkeit passiert spaeter.
  string grp;
  int val;
  if (sscanf(s, "%s:%d", grp, val)) {
    g += ([grp:val]);
  } else {
    g += ([grp:100]);
  }
}
private mapping convMatGroups(string s) {
  mapping groups;
  if (!sizeof(regexp( ({s}), "- keine -"))) {
    groups = ([]);
    // Jede Zeile enthaelt eine Bedingung
    map(explode(s, "\n"), #'addGroupLine, groups);
  }
  return groups;
}
private mapping convMaterialDesc(string id, mapping desc) {
  /* Struktur Materialmapping:
     P_GENDER,
     P_NAME:({name_nom, name_gen, name_dativ, name_akkusativ}),
     (P_RECOC:({mat1,faehigkeit1,mat2,faehigkeit2,...}),)
     (P_DEFSTR: bei bedarf),
     P_DESCRIPTION,
     (grupp1:anteil1,
     gruppe2:anteil2,
     ...)
  */
  mapping m;
  mixed val, val2;
  m = ([]);
  // Der string fuer das #define zuerst:
  val = convMatId(desc["Materialid"]);
  if (mappingp(val)) {
    if (val[P_ID] != id)
      LOG_WARN(sprintf("Unstimmigkeit Materialid bei '%s':%O\n", id, val[P_ID]));
    if (member(val, P_DEFSTR)) {
      m += ([P_DEFSTR:val[P_DEFSTR]]);
    } else {
      // Wenn kein String fuers #define angegeben wurde, dann direkt ID verwenden
      //m += ([P_DEFSTR:lowerstring(id)[4..]]);
    }
  }
  // Die Namen
  if (val = convMatNames(desc["Name"])) {
    m += ([P_NAME:val]);
  } else {
    MDESC_WARN(id, "keine Namen");
    m += ([P_NAME:({"", "", "", ""})]);
  }
  // Das Geschlecht, standard ist NEUTER
  m += ([P_GENDER:convMatGender(desc["Geschlecht"]) ]);
  // Die Beschreibung
  val = convMatDesc(desc["Beschreibung"]);
  if (sizeof(val)) {
    m += ([P_DESCRIPTION:val]);
  } else {
    MDESC_WARN(id, "keine Beschreibung");
  }
  // Die Erkennbarkeit
  val = convMatRec(desc["Erkennbarkeit"]);
  if (sizeof(val)) {
    m += ([P_RECOC:val]);
  }
  // und zum Schluss die Gruppenzugehoerigkeit
  val = convMatGroups(desc["Gruppenzugehoerigkeit"]);
  if (mappingp(val) && sizeof(val)) {
    m += ([P_MG_FRACTIONS:val]);
  }
  return m;
}
private varargs mixed readMaterialDesc(string id) {
  mixed m;
  string fn;
  fn = MAT_DIR+"/materials/"+id;
  if (file_size(fn) > 0) {
    mapping parts;
    string desc;
    parts = getDescParts(read_file(fn));
    m = convMaterialDesc(id, parts);
  } else {
    LOG_ERROR(sprintf("MDB:Kann Materialbeschreibung %s nicht laden\n", fn));
  }
  return m;
}

public int GetUpdateTicks() {
  return updateTicks;
}

private void scanFinished() {
  isScanning = 0;
  initialized = 1;
  // Mappings umkopieren
  materials = new_materials;
  material_groups = new_material_groups;
  // Letzter Schritt: Mapping mit alten Schluesseln anlegen
  old_mat_keys = mkmapping(map(m_indices(materials), #'matKey2Defstr, materials),
                           m_indices(materials));
  // Generieren der Doku und des Materialheaders
  GenHeaderFile();
  GenMatList();
  GenMatGroupList();
  // Savefile schreiben
  save_object(SAVEFILE);
}

public int IsScanning() {
  return isScanning;
}

private varargs void doScanMaterials(string* mats, int i, int step) {
  int ticks, start;
  string matid;
  start = get_eval_cost();
  if (step < 2) {
    while ( (i < sizeof(mats)) &&
            ((start - get_eval_cost()) < query_limits()[LIMIT_EVAL]/3 ) ) {
      matid = mats[i];
      switch (step) {
      case 0:
        // Erster Schritt: Einlesen der Dateien
        new_materials[matid] = readMaterialDesc(matid);
        break;
      case 1:
        // Zweiter Schritt: Bearbeiten der Erkennung und Gruppenzugehoerigkeit
        updateGroupMembers(new_material_groups, matid, new_materials[matid]);
        break;
      default:
        break;
      }
      i++;
    }
  }
  if (i < sizeof(mats)) {
    catch(raise_error(sprintf("MaterialDB: Initialisierung noch nicht beendet,"
                              " fehlende Materialbeschreibungen moeglich"
                              " (Phase %d:%d/%d)\n",
                              step, i, sizeof(mats)));publish);
    call_out(#'doScanMaterials, 2, mats, i, step);
  } else {
    // Zweite Stufe ausloesen oder beenden
    if (step < 1) {
      if ((start - get_eval_cost()) < query_limits()[LIMIT_EVAL]/2 )
          doScanMaterials(mats, 0, step+1);
      else
          call_out(#'doScanMaterials, 2, mats, 0, step+1);
    }
    else
      scanFinished();
  }
  updateTicks += start - get_eval_cost();
}

private mapping ScanGroups() {
  mapping groups;
  string* grpfiles;
  groups = ([]);
  grpfiles = filter(get_dir(MAT_DIR+"/groups/MATGROUP_*"),
                          #'isFile, MAT_DIR+"/groups");
  groups = mkmapping(grpfiles, map(grpfiles, #'readGroupDesc, 1));
  return groups;
}

private void ScanMaterials() {
  string *matfiles;
  matfiles = filter(get_dir(MAT_DIR+"/materials/MAT_*"),
                          #'isFile, MAT_DIR+"/materials");
  doScanMaterials(matfiles);
}

void Update() {
  int start;
  updateTicks = 0;
  start = get_eval_cost();
  if (!isScanning) {
    if (sizeof(get_dir(MAT_DIR))) {
      isScanning = 1;
      new_material_groups = ScanGroups();
      new_materials = ([]);
      updateTicks = start - get_eval_cost();
      ScanMaterials();
    } else {
      LOG_ERROR("Kann Materialverzeichnis nicht finden, keine Materialien angelegt!\n");
    }
  }
}
