Themabewertung:
  • 4 Bewertung(en) - 3.5 im Durchschnitt
  • 1
  • 2
  • 3
  • 4
  • 5
Reverse Engineering der NLT II
(18.11.2025, 11:47)NewProggie schrieb: CMake hatte ich vor ein paar Wochen schon hinzugefügt (in meinem Fork). Wurde aber nicht upstream gemerged bisher.

wenn der SDL port mal läuft wird es schnell relevant - auch so Auto-Builds (Linux,Win,Mac) auf github oder Coverity integration etc.
Zitieren
(18.11.2025, 11:57)llm schrieb:
(18.11.2025, 11:47)NewProggie schrieb: CMake hatte ich vor ein paar Wochen schon hinzugefügt (in meinem Fork). Wurde aber nicht upstream gemerged bisher.

wenn der SDL port mal läuft wird es schnell relevant - auch so Auto-Builds (Linux,Win,Mac) auf github oder Coverity integration etc.

CI mit Auto-Builds und Linter Checks hab ich ebenfalls vor ein paar Wochen schon hinzugefügt :-)
Zitieren
(18.11.2025, 11:59)NewProggie schrieb: -Builds und Linter Checks hab ich ebenfalls vor ein paar Wochen schon hinzugefügt :-)

aber nur für gen, oder? musst mal deinen Branch auf schick updaten
Zitieren
(18.11.2025, 10:47)HenneNWH schrieb: Danke, Danke!



Von übermäßigem gebranche halten ich nicht soviel: "Branchen ist einfach, das Zusammenführen ist eher das Problem."



Das Verzeichnis schick ist jetzt der Hauptbranch des Projektes!

Schade. Aber ich sehe das; es wäre einiges an Aufwand, die binär äquivalente DOS-Version weiter nachzuziehen und zu pflegen.

(18.11.2025, 10:47)HenneNWH schrieb: Kleine Info zu den Charakterbildern und dem Import nach Schweif:

Hab gerade einen das Bild eines Schick-Helden per Hexeditor modifiziert und den Spielstand in Schweif importiert.

Der Held bekommt dann automatisch ein Gesicht zugeordnet, welches man in Schweif per Auswahl ändern kann.

D.h. es ist für Schick möglich eigene Icons zu benutzen.

Somit ist der Wunsch von Obi-Wahn praktisch umsetzbar, aber nur auf Schick begrenzt.


In Schick liegt das Heldenbild (32x32 Pixel/Bits) eben noch im Spielstand. Ab Schweif gibt es lediglich einen Index in eine vordefinierte Auswahl an Bildern.

Diese vordefinierten Bilder ließen sich übrigens auch relativ simpel (automatisiert per Skript) im Spielarchiv verändern -- ggf. sogar hin zu dem, was man im Schick-Spielstand eigens kreiert hatte. Nur sind die Paletten von Schick und Schweif leider nicht kompatibel; es gibt zwar ab Schweif mehr Farben, aber die alten gibt es nicht mehr 1:1. (Schweif und Riva sind identisch.) Ich habe gerade mal testweise die Charakterporträts von Schick (von denen es nicht mehr alle in Schweif gibt) automatisiert in die Palette von Schweif überführt (nearest-color / ΔE*76), und es sieht, bis auf eine subjektiv leichte Verdunkelung hier und da, eigentlich bei allen Porträts ganz passabel aus.

Vielleicht baue ich die Idee bei Gelegenheit zu einem kleinen Modding-Tool aus, um die alten (oder eigenen) Charakterporträts nach Schweif / Riva zu übertragen.
Zitieren
(18.11.2025, 19:18)cmfrydos schrieb: In Schick liegt das Heldenbild (32x32 Pixel/Bits) eben noch im Spielstand. Ab Schweif gibt es lediglich einen Index in eine vordefinierte Auswahl an Bildern.

Diese vordefinierten Bilder ließen sich übrigens auch relativ simpel (automatisiert per Skript) im Spielarchiv verändern -- ggf. sogar hin zu dem, was man im Schick-Spielstand eigens kreiert hatte. Nur sind die Paletten von Schick und Schweif leider nicht kompatibel; es gibt zwar ab Schweif mehr Farben, aber die alten gibt es nicht mehr 1:1. (Schweif und Riva sind identisch.) Ich habe gerade mal testweise die Charakterporträts von Schick (von denen es nicht mehr alle in Schweif gibt) automatisiert in die Palette von Schweif überführt (nearest-color / ΔE*76), und es sieht, bis auf eine subjektiv leichte Verdunkelung hier und da, eigentlich bei allen Porträts ganz passabel aus.

Vielleicht baue ich die Idee bei Gelegenheit zu einem kleinen Modding-Tool aus, um die alten (oder eigenen) Charakterporträts nach Schweif / Riva zu übertragen.

Kannst du das mal zeigen? (Screenshots)
Zitieren
(18.11.2025, 20:34)NewProggie schrieb: Kannst du das mal zeigen? (Screenshots)

Hatte sogar schon was vorbereitet, aber dann aus urheberrechtlichen Gründen zurückgerudert. 
Hier eine Variante davon, in der quasi nur 2/3 * 2/3 der Charakterporträts gezeigt werden (um hier keine originalen Spieldateien zu teilen). Achtung, dadurch wirken die Porträts etwas entstellt, da Pixel fehlen. Sollte einem dennoch eine Idee der Farbverfälschung geben.

Links jeweils das Original (skaliert) aus Schick, rechts, wie es mit der Palette aus Stern/Riva aussehen würde:
   

Bzw. hier das ermittelte Mapping zwischen den Paletten (links Schick, rechts Sternenschweif). Man sieht, dass vor allem dunklere Brauntöne problematisch sind:

   
Zitieren
Hier noch mein aktueller Kenntnisstand zum Gegenstandszähler (hero.num_filled_inv_slots). Die Sache scheint ähnlich gelagert zu sein wie bei den von Henne recht treffend benannten Placebo-Zaubern: Der Zähler wird fleißig aktualisiert, wenn auch nicht immer ganz korrekt. Aber ausgelesen wird der Zähler nur an sehr wenigen Stellen, und die Wirkung hält sich arg in Grenzen:
  • In der Funktion sell_screen wird zweimal auf num_filled_inv_slots==0 getestet. Der Effekt dürfte sein, dass der Verkaufsbildschirm vorzeitig geschlossen wird, weil der Held dann ja keine Gegenstände hat. Das dürfte zu vernachlässigen sein, und außerdem wird in der Funktion auch nochmal "zu Fuß" nachgezählt, wie viele Gegenstände der Held hat.
  • In der Funktion give_new_item_to_hero wird hero->num_filled_inv_slots < NR_HERO_INVENTORY_SLOTS abgefragt, um nachzuschauen, ob überhaupt ein Inventarslot frei ist. Das ist (wie schon weiter oben angesprochen) ziemlich schwach, weil dabei die Inventarslots am Körper mit einbezogen werden, obwohl der Gegenstand im Rucksack landen muss. Danach wird ohnehin mit einer Schleife nach einem freien Slot im Rucksack gesucht, d.h. die Bedingung kann ohne negative Auswirkungen rausgenommen werden.

Eine gewisse Gefahr geht allerdings davon aus, dass der Zähler manchmal falsch aktualisiert wird, womit er potentiell jeden denkbaren Wert annehmen kann. U.u. wird also ein Verkaufsbildschirm zu Unrecht vorzeitig beendet. Oder ein Held bekommt einen neuen Gegenstand nicht, obwohl er durchaus Platz dafür gehabt hätte.

Fazit: Eigentlich braucht man den Zähler num_filled_inv_slots nicht, aber er macht potentiell Ärger.
Die beste Lösung wäre wohl, das Ding in der "cleanen" Neuprogrammierung einfach abzuklemmen (und für den Schweif-Import den Wert am Ende einmal korrekt rauszuzählen).
Zitieren
Es gibt wieder Neuigkeiten:

   

Schick ist nach ein paar kleinen Änderungen in der Lage zumindest das unanimierte Bild aus dem Tempel anzuzeigen.
Das kompiliert mit GCC und Clang und die Binäräquivalenz konnte noch aufrecht erhalten werden.
Zitieren
(19.11.2025, 17:21)HenneNWH schrieb: Das kompiliert mit GCC und Clang

MSVC cl.exe mag den code auch noch und erzeugt das selbe Bild unter Windows 11

   

btw deine swap32 geht ein wenig kompakter :)

Code:
inline uint32_t swap32(uint32_t v) {
    return (v >> 24) |
          ((v >> 8) & 0x0000FF00u) |
          ((v << 8) & 0x00FF0000u) |
          (v << 24);
}
Zitieren
Das ist richtig. Meine Funktion hat den Vorteil, dass sie mathematisch beweisbar ist.
Hier mal ein kleiner Brute-Force-Test um sich ein Urteil über die Qualität der Compileroptimierung zu bilden.

Code:
#include <stdio.h>
#include <stdint.h>

static inline uint32_t swap32_llm(uint32_t v) {
    return (v >> 24) |
          ((v >> 8) & 0x0000FF00u) |
          ((v << 8) & 0x00FF0000u) |
          (v << 24);
}

static inline uint32_t swap32_hen(uint32_t v) {
  unsigned char tmp[4] = { 0 };
  uint32_t retval = 0L;

  tmp[0] = (v >> 0) & 0xff;
  tmp[1] = (v >> 8) & 0xff;
  tmp[2] = (v >> 16) & 0xff;
  tmp[3] = (v >> 24) & 0xff;

  retval |= tmp[0];
  retval <<= 8L;
  retval |= tmp[1];
  retval <<= 8L;
  retval |= tmp[2];
  retval <<= 8L;
  retval |= tmp[3];

  return retval;
}

int main() {

  for (uint32_t i = 0; i < 0xffffffff; i++) {
    if (i != swap32_llm(swap32_llm(i))) {
      printf("FEHLER\n");
    }
  }
}

Meine Version (-O0, -O1, -O2)
GCC: 94s, 10s, 10s
Clang: 113s, 0s, 0s

Deine Version (-O0, -O1, -O2)
GCC: 29s, 0s, 0s
Clang: 28s, 9s, 0s

Die Werte vom MSVC würden mich hier mal interessieren.
P.S.: Wenn es weniger als 1s dauer Optimiert der Compiler die Schleife in der main()-Funktion weg.
Zitieren
(19.11.2025, 19:40)HenneNWH schrieb: Das ist richtig. Meine Funktion hat den Vorteil, dass sie mathematisch beweisbar ist.


Jetzt muss ich auch mal den Klugscheißer anschalten. :D

Man beweist Aussagen, nicht Funktionen. Vermutlich meinst du die zugehörige Korrektheitsaussage, also dass die angegebene Funktion wirklich immer das tut, was wir von ihr erwarten (sie spiegelt die Positionen der vier Bytes). Dies ist aber für beide Fälle beweisbar, schon allein, weil es nur endlich viele mögliche Eingabe-Bitmuster gibt, die man schlimmstenfalls alle durchprobieren kann. Und in beiden Fällen geht es natürlich auch direkt.
Zitieren
(19.11.2025, 20:30)siebenstreich schrieb:
(19.11.2025, 19:40)HenneNWH schrieb: Das ist richtig. Meine Funktion hat den Vorteil, dass sie mathematisch beweisbar ist.


Jetzt muss ich auch mal den Klugscheißer anschalten.  :D

Man beweist Aussagen, nicht Funktionen. Vermutlich meinst du die Aussage, dass die angegebene Funktion das tut, was die sie soll, also dass sie die Bytes entsprechend vertauscht. Diese Aussage ist aber für beide Fälle beweisbar, schon allein, weil es nur endlich viele mögliche Eingabe-Bitmuster gibt, die man schlimmstenfalls alle durchprobieren kann. Und in beiden Fällen geht es natürlich auch direkt.

Und ganz praktisch gesprochen, macht so ein Quatsch in einem Rollenspiel auch keinen Sinn oder Unterschied. HPC ist ein wichtiges Werkzeug, aber man muss auch den Kontext sehen (können).
Zitieren
In erster Linie muss es zuverlässig funktionieren.
Die Originalimplementierung dieser Funktion hat mit GCC/Clang falsche Werte geliefert.
Auch der BCC hat mit eingeschaltener Optimierung nicht korrekten Code erzeugt.
Korrektheitsbeweise sind sehr praktisch.

Was genau möchtest du mir/ uns damit mitteilen?
Zitieren
(19.11.2025, 22:09)HenneNWH schrieb: Was genau möchtest du mir/ uns damit mitteilen?

ohne die Info von dir mit "Die Originalimplementierung dieser Funktion hat mit GCC/Clang falsche Werte geliefert." war einfach nicht klar warum dich diese kleine Routine so interessiert - jetzt sind NewProggie und ich im Bilde :)

d.h. du hast das für 32/64bit gefixt aber weils im BCC eh ohne Optimierung gebaut wurde hatte der Fehler in der DOS Exe nie Auswirkungen?

zu deinem Benchmark

Code:
Meine Version (-O0, -O1, -O2)
GCC: 94s, 10s, 10s
Clang: 113s, 0s, 0s

Deine Version (-O0, -O1, -O2)
GCC: 29s, 0s, 0s
Clang: 28s, 9s, 0s

die Zahlen kommen mir komisch vor - speziell gcc -02 und clang -01 - der clang (21.1.5) und der gcc (15.2.1) schmeissen bei mir mit -O2 schon den kompletten Code raus und machen nur return 0;
siehe: https://gcc.godbolt.org/z/a6GssaaT1

und für clang(ab -O1)/gcc(ab -O2) ist der code unserer beiden bei Funktionen 100% identisch (der MSVC 2022 reduziert meine Funktion auch auf bswap bei /O2) - nur der Benchmark-Code ist anders optimiert
https://gcc.godbolt.org/z/8rqvY9bjh
Code:
swap32_llm(unsigned int):
        mov    eax, edi
        bswap  eax
        ret

swap32_hen(unsigned int):
        mov    eax, edi
        bswap  eax
        ret

main:
        xor    eax, eax
        ret

damit "wissen" der gcc und clang das dein if nie anschlagen wird, also kann man alles weg optimieren

bei sowas musst du meist Sondervariable mit einfügen - damit der Optimizer die Finger still hält - UND den Assembler-Code anschauen

eher sowas wie

Code:
int main() {
  int x = 0;

  for (uint32_t i = 0; i < 0xffffffff; i++) {
    x += swap32_llm(i);
  }

  return x;
}

aber da beiden Funktionen identisch sind nach der Code-Generierung macht hier Benchmarking nicht so viel Sinn weil man dann nur den Benchmark-Code benchmarkt

und du solltest deinen gcc/clang mal updaten :)

der aktuelle MSVC 2022 schafft es nur meine Routine in den einfach swap zu wandeln - deine Routine bleibt etwas umfangreicher
https://gcc.godbolt.org/z/bW8vxc3Wz

aber VS2022 schafft es auch nicht mit dem einfachen swap (also dem wissen darum) auf return 0 zu optimieren
was man aber auf keinen Fall als gcc/clang machen immer den bessere Code interpretieren sollte - die Final-Optimierung bei solchen Dead-Ends ist beim gcc/clang einfach besser - aber haben nicht immer Auswirkung auf echte Software

manchmal rasten auch die Optimizer vom gcc/clang aus (hab da schon genug Bug Reports eingestellt oder Diskussionen) gehabt wo der sich ergebende Code auch nicht mehr so fein war

Entscheident sind die richtigen Werkzeuge(VTune unter Windows/Linux, gcc.godbolt.org sind die Welt-Favoriten)/Strategien zum Benchmarking, aktuelle Kompiler und keine ausgeprägte "so war das mal" Denke
Es ändert sich in den letzten 10 Jahren erstaunlich viel, erstaunlich schnell als das Erfahrungswerte nicht einer deutlichen Auffrischung benötigen - das gilt für jeden Entwickler :)

aber es zeigt auf jeden Fall wie gut die Optimizer arbeiten können
Zitieren
HPC? High Performance Code? Hilbert-Proof-Calculus?  ;)  

Naja, ich bin auch überzeugt, dass llm's swap32 leicht beweisbar korrekt ist: 
Jeder Term der bitweisen Veroderung beeinflusst genau 8 Bits, und es sind jeweils die richtigen für den Big↔Little-Endian-Swap.
Durch die Kompaktheit lässt sich die Funktion auch gut lesen.

Aber eigentlich will man hier ja doch, dass der Compiler am Ende wieder ein bswap im Assembler erzeugt, oder?
__builtin_bswap32 (GCC/Clang) bzw. _byteswap_ulong (MSVC) dürften daher die schnellste und, im Gegensatz zu Inline-Asm, plattformunabhängigere Variante sein.

Der alte Code hatte gegen Strict-Aliasing (und Alignment) verstoßen, vermutlich daher undefiniertes Verhalten (bei höheren Optimierungsstufen):
Code:
int16_t a[2];
int32_t *ptr = (int32_t*)(&a[0]);

Edit: Ups, da war ich zu langsam, interessante Analyse llm!.
Zitieren
Zitat:vermutlich daher undefiniertes Verhalten (bei höheren Optimierungsstufen)

wäre interessant ob der "-fsanitize=undefined" das aufzeigt - ich denke ein Coverity hätte das auch bemängelt

update: "-fsanitize=undefined" zeigt da nix mit -O0 oder höher, hab einfach den Borland-Code - also die 3-4 Routinen kopiert - das Ergebnis ändert sich ständig aber sanitizer schlägt nicht an - kann aber auch an mir liegen

der neue TypeSanitizer "-fsanitize=type" findet was, ist aber auch noch sehr experimentell
https://clang.llvm.org/docs/TypeSanitizer.html

Code:
clang++ -fsanitize=type -fno-omit-frame-pointer -g -O0 test.cpp -o test

bekommt man für diesen Code (TypeSanitizer findings als Kommentar) folgende Ausgaben

Code:
#include <stdint.h>

static inline uint8_t readb(uint8_t *p)
{
   return ((uint8_t)*p);
}

static inline int16_t readws(uint8_t *p)
{
  return ((int16_t)(readb(p + 1) << 8) | (readb(p)));
}

uint16_t swap_u16(const uint16_t val)
{
  return (val << 8) | (val >> 8);
}

static inline int32_t readds(uint8_t *p)
{
  return ((int32_t)(readws(p + 2) << 16) | readws(p));
}

static inline uint32_t swap32_bor(uint32_t v){
  /*register*/ signed int tmp;
  int16_t a[2];
  int32_t *ptr = (int32_t*)(&a[0]);
  *ptr = readds((uint8_t*)&v);
  tmp = a[0];                  // <== TypeSanitizer: type-aliasing-violation on address
  a[0] = swap_u16(a[1]); // <== TypeSanitizer: type-aliasing-violation on address
  a[1] = swap_u16(tmp); // <== TypeSanitizer: type-aliasing-violation on address
  return readds((uint8_t*)ptr);
}

int main() {
  return swap32_bor(0x12345678);
}

Ausgabe

Code:
==13160==ERROR: TypeSanitizer: type-aliasing-violation on address 0x7ffe1e8763b4 (pc 0x5b2bbc0665f8 bp 0x7ffe1e876280 sp 0x7ffe1e876210 tid 13160)
READ of size 2 at 0x7ffe1e8763b4 with type short accesses an existing object of type int
    #0 0x5b2bbc0665f7 in swap32_bor(unsigned int) /home/linux/temp/swap32_speed/test.cpp:30:8

==13160==ERROR: TypeSanitizer: type-aliasing-violation on address 0x7ffe1e8763b6 (pc 0x5b2bbc06682f bp 0x7ffe1e876280 sp 0x7ffe1e876210 tid 13160)
READ of size 2 at 0x7ffe1e8763b6 with type short accesses part of an existing object of type int that starts at offset -2
    #0 0x5b2bbc06682e in swap32_bor(unsigned int) /home/linux/temp/swap32_speed/test.cpp:31:18

==13160==ERROR: TypeSanitizer: type-aliasing-violation on address 0x7ffe1e8763b4 (pc 0x5b2bbc066930 bp 0x7ffe1e876280 sp 0x7ffe1e876210 tid 13160)
WRITE of size 2 at 0x7ffe1e8763b4 with type short accesses an existing object of type int
    #0 0x5b2bbc06692f in swap32_bor(unsigned int) /home/linux/temp/swap32_speed/test.cpp:31:7

==13160==ERROR: TypeSanitizer: type-aliasing-violation on address 0x7ffe1e8763b6 (pc 0x5b2bbc066b68 bp 0x7ffe1e876280 sp 0x7ffe1e876210 tid 13160)
WRITE of size 2 at 0x7ffe1e8763b6 with type short accesses part of an existing object of type int that starts at offset -2
    #0 0x5b2bbc066b67 in swap32_bor(unsigned int) /home/linux/temp/swap32_speed/test.cpp:32:7

d.h. der TypeSanitizer kommt jetzt auch auf meine Liste also: -fsanitize=address, =thread, =undefined und =type :)

leider ist der =memory so kompliziert zu nutzen wegen den 3rd-parties (aber Schick ist da ja angenehm bescheiden) - da bleibt aber noch der valgrind - auch wenn er 100x langsamer ist :(

die Sanitizer werden ständig verbessert oder es kommen neue hinzu - wenn man sicher gehen will sollte man die Kompiler immer schön aktuell halten - SUSE Tumbleweed/Fedora oder Arch-Linux sind da immer recht fix mit Update auf die neuen Releases
Zitieren
(20.11.2025, 05:59)llm schrieb: ohne die Info von dir mit "Die Originalimplementierung dieser Funktion hat mit GCC/Clang falsche Werte geliefert." war einfach nicht klar warum dich diese kleine Routine so interessiert :)

d.h. du hast das für 32/64bit gefixt aber weils im BCC eh ohne Optimierung gebaut wurde hatte der Fehler in der DOS Exe nie Auswirkungen?

zu deinem Benchmark

...

aber es zeigt auf jeden Fall wie gut die Optimizer arbeiten können

Ziel des Tests war herauszufinden wie gut die Compiler optimieren. Wenn die Schleife aus der main()-Funktion wegoptimiert wird, passt es.

Die Funktion swap_u32() ist mir im Charaktergenerator schon aufgefallen.
Damals hatte ich diese Idee für den Test. Gestern gab's dann auch einen echten Grund das zu fixen.
Performance steht da nicht im Vordergrund, dafür wird diese Funktion zu selten aufgerufen.

Hab am Wochenende auf Debian 13 aktualisiert: GCC 14.2.0, Clang 19.1.7 läuft hervorragend.


(20.11.2025, 06:19)cmfrydos schrieb: Aber eigentlich will man hier ja doch, dass der Compiler am Ende wieder ein bswap im Assembler erzeugt, oder?
__builtin_bswap32 (GCC/Clang) bzw. _byteswap_ulong (MSVC) dürften daher die schnellste und, im Gegensatz zu Inline-Asm, plattformunabhängigere Variante sein.

Nicht ganz. Mir geht es bei BrightEyes darum möglichst nah am Original zu bleiben und portablen und korrekten Code zu erzeugen.
Die builtins halte ich bei performancekritischer Software für das Mittel der Wahl, aber es zieht im Nachgang für mehrere Compiler Präprozessor-ifdef-Orgien nach sich.
Das muss nicht sein.

(20.11.2025, 06:26)llm schrieb: wäre interessant ob der "-fsanitize=undefined" das aufzeigt - ich denke ein Coverity hätte das auch bemängelt

Nur zur Info: Der Address-Sanitizer funktioniert bei mir mit GCC auf dem Raspi2 nicht. Da fehlen scheinbar hardwareseitig atomic_load/store und compare_exchange Instruktionen.
Zitieren
Ich hab eben rudimentären CMake Support für Schick hinzugefügt und Henne hat das auch schon upstream gemerged.
Daneben bin ich einmal die seg-Dateien durch und hätte folgenden Vorschlag für die Umbenennung der Dateien:

Code:
# Core Systems (seg001-seg011)
seg001 -> cdrom
seg002 -> misc
seg003 -> movement
seg004 -> graphics
seg005 -> fight_core
seg006 -> fight_base
seg007 -> random_dice
seg008 -> rasterlib
seg009 -> pp20_decompress
seg010 -> ems
seg011 -> sound_ail

# Game Data & Core Mechanics (seg024-seg032)
seg024 -> diary
seg025 -> locations
seg026 -> save_text
seg027 -> file_loader
seg028 -> resource_loader
seg029 -> playmask
seg030 -> talk_date
seg031 -> tavern_helpers
seg032 -> fight_helpers

# Fight System (seg033-seg050)
seg033 -> fight_menu
seg034 -> fight_system
seg035 -> fight_logic
seg036 -> fight_auto_hero
seg037 -> fight_enemy_attack
seg038 -> fight_actions
seg039 -> fight_mechanics
seg040 -> fight_scenarios
seg041 -> fight_control
seg042 -> fight_hero_action
seg043 -> fight_enemy_action
seg044 -> fight_anim_figures
seg045 -> fight_anim_effects
seg046 -> status_display
seg047 -> heroes_group
seg048 -> status_menu
seg049 -> group_mgmt
seg050 -> level_up

# Locations & Environments (seg051-seg074)
seg051 -> wilderness_camp
seg052 -> area_camp
seg053 -> location_healer
seg054 -> location_inn
seg055 -> merchant_main
seg056 -> merchant_buy
seg057 -> merchant_sell
seg058 -> location_smith
seg059 -> tavern_main
seg060 -> tavern_talk
seg061 -> temple_main
seg062 -> temple_miracle
seg063 -> harbor_main
seg064 -> harbor_helper
seg065 -> special_anims
seg066 -> town_main
seg067 -> city_events
seg068 -> thorwal_buildings1
seg069 -> thorwal_buildings2
seg070 -> phexcaer_buildings1
seg071 -> phexcaer_buildings2
seg072 -> informer_script
seg073 -> tavern_gossip
seg074 -> automap

# Dungeon Systems (seg075-seg092)
seg075 -> dungeon_common1
seg076 -> dungeon_common2
seg077 -> dungeon_ship_death
seg078 -> dungeon_inn
seg079 -> dungeon_spider_cave
seg080 -> dungeon_wolf_cave
seg081 -> dungeon_cave2
seg082 -> dungeon_mageruin
seg083 -> dungeon_orc_lair
seg084 -> dungeon_main
seg085 -> dungeon_cave4
seg086 -> dungeon_pirate_cave
seg087 -> dungeon_thorwal1
seg088 -> dungeon_thorwal2
seg089 -> dungeon_ruined_castle
seg090 -> dungeon_oberorken_mine
seg091 -> dungeon_prem_mine
seg092 -> treasures

# Game Mechanics & Magic (seg093-seg122)
seg093 -> travel_mode1
seg094 -> travel_mode2
seg095 -> npcs
seg096 -> text_output
seg097 -> gui
seg098 -> magic_main
seg099 -> spells1
seg100 -> spells2
seg101 -> spells3
seg102 -> spells_monster
seg103 -> talents
seg104 -> alchemy_cure
seg105 -> inventory_main
seg106 -> inventory_misc
seg107 -> item_use
seg108 -> consume
seg109 -> travel_event1
seg110 -> travel_event2
seg111 -> travel_event3
seg112 -> travel_event4
seg113 -> travel_event5
seg114 -> travel_event6
seg115 -> travel_event7
seg116 -> travel_event8
seg117 -> travel_event9
seg118 -> travel_event10
seg119 -> disease_effect
seg120 -> game_init
seg121 -> poison_effect
seg122 -> dummy_location

Was meint ihr?
Zitieren
(20.11.2025, 14:46)NewProggie schrieb: Ich hab eben rudimentären CMake Support für Schick hinzugefügt 

Super!

warum nutzt du die alte Schreibweise in CMake mit den Include/Lib Pfaden

also warum nicht die neue(auch schon Jahre alte) Schreibweise wie in ngen? bei OpenMP machst du neu, bei SDL alter Style?

Code:
target_link_libraries(ngen PUBLIC SDL2::SDL2main)
target_link_libraries(ngen PUBLIC SDL2::SDL2)

und bitte auch die Header rein machen - sonst fehlen die in MSVC, QtCreator oder CLion - Bauen geht aber CMake stellt keinen Projektbezug her
Zitieren
(20.11.2025, 14:46)NewProggie schrieb: Ich hab eben rudimentären CMake Support für Schick hinzugefügt und Henne hat das auch schon upstream gemerged.
Daneben bin ich einmal die seg-Dateien durch und hätte folgenden Vorschlag für die Umbenennung der Dateien:

Was meint ihr?

Danke für die Arbeit. Das Umbenennen ist aktuell noch nicht vorgesehen, aber für die Zukunft geplant.
Siebenstreich und ich haben uns an die historische Struktur, die sich aus dem Rekonstruktionsprozess ergeben hat, gewöhnt.
Die bleibt vorerst so, da wir damit klarkommen. Ist ja auch mein Projekt.  :D

Prio haben aktuell, unter Beibehaltung der Binäräquivalenz des DOS-Binaries, Umbenennungen, die SDL2-Portierung und Fehlerbehebungen für 64-Bit Systeme. Alles andere muss warten.
Zitieren




Benutzer, die gerade dieses Thema anschauen: HenneNWH, 2 Gast/Gäste