Five restype numbers in internal/erf disagree with upstream #64

Closed
opened 2026-07-27 19:00:31 +00:00 by archvillainette · 1 comment
Owner

Five entries in internal/erf/erf.go's restype table disagree with upstream neverwinter.nim's restype.nim. Found while researching restype handling for NWSync emit (#57); none are in the current asset corpus, so nothing is broken in shipped content today, but they are wrong for HAK writing in general — HAKResourceTypeForExtension packs arbitrary source files (internal/pipeline/build.go:870, internal/topdata/top_package.go:441).

ext Crucible upstream what Crucible's number actually means upstream
gff 2039 (erf.go:100,167) 2037 (restype.nim:75) 2039 = bte
ltr 2067 (erf.go:120,186) 2036 (restype.nim:74) 2067 = bak
jpg 2076 (erf.go:124,190) 2081 (restype.nim:119) 2076 = tml
mdb 2070 (erf.go:121,187) not registered 2070 = xbc
dfa 2045 (erf.go:104,170) 2045 is dft (restype.nim:83) number right, name is a typo

So a .jpg packed into a HAK by Crucible today is written with restype 2076, which the game reads as tml.

Root cause of why this was never caught: the init() at erf.go:202-212 is meant to keep extensionTypes and typeExtensions consistent, but it only panics when a number is missing from the reverse map — its if canonicalExt == ext { continue } branch does nothing when the two maps disagree. Fixing the guard is probably worth more than fixing the five values.

Separately, Crucible registers six extensions upstream does not have at all — lyt 3000, vis 3001, mdx 3008, wlk 3020, xml 3021, gr2 4003 (erf.go:128-133). Those are deliberate local additions, not bugs, but they are why upstream conformance for NWSync emit mirrors upstream's table rather than this one.

Five entries in `internal/erf/erf.go`'s restype table disagree with upstream `neverwinter.nim`'s `restype.nim`. Found while researching restype handling for NWSync emit (#57); none are in the current asset corpus, so nothing is broken in shipped content today, but they are wrong for HAK writing in general — `HAKResourceTypeForExtension` packs arbitrary source files (`internal/pipeline/build.go:870`, `internal/topdata/top_package.go:441`). | ext | Crucible | upstream | what Crucible's number actually means upstream | |---|---|---|---| | `gff` | 2039 (`erf.go:100,167`) | 2037 (`restype.nim:75`) | 2039 = `bte` | | `ltr` | 2067 (`erf.go:120,186`) | 2036 (`restype.nim:74`) | 2067 = `bak` | | `jpg` | 2076 (`erf.go:124,190`) | 2081 (`restype.nim:119`) | 2076 = `tml` | | `mdb` | 2070 (`erf.go:121,187`) | not registered | 2070 = `xbc` | | `dfa` | 2045 (`erf.go:104,170`) | 2045 is `dft` (`restype.nim:83`) | number right, name is a typo | So a `.jpg` packed into a HAK by Crucible today is written with restype 2076, which the game reads as `tml`. Root cause of why this was never caught: the `init()` at `erf.go:202-212` is meant to keep `extensionTypes` and `typeExtensions` consistent, but it only panics when a number is missing from the reverse map — its `if canonicalExt == ext { continue }` branch does nothing when the two maps disagree. Fixing the guard is probably worth more than fixing the five values. Separately, Crucible registers six extensions upstream does not have at all — `lyt` 3000, `vis` 3001, `mdx` 3008, `wlk` 3020, `xml` 3021, `gr2` 4003 (`erf.go:128-133`). Those are deliberate local additions, not bugs, but they are why upstream conformance for NWSync emit mirrors upstream's table rather than this one.
Author
Owner

Correction to one premise in the description, found while fixing this in #69.

The issue says the six extensions upstream does not have — lyt 3000, vis 3001, mdx 3008, wlk 3020, xml 3021, gr2 4003 — "are deliberate local additions, not bugs". That holds for three of them. The other three are NWN2 formats, the same class of problem as mdb.

Checked against xoreos src/aurora/types.h, which covers every Aurora game and so keeps the games' tables apart:

ext Crucible had xoreos verdict
lyt 3000 3000, room layout real, NWN1/EE — deliberate, kept
vis 3001 3001, room visibilities real, NWN1/EE — deliberate, kept
mdx 3008 3008, model mesh data real, NWN1/EE — deliberate, kept
gr2 4003 4003, in the NWN2 block (MDB2 4000, MDA2 4001, SPT2 4002, GR2 4003, PWC 4008) NWN2 (Granny) — removed
wlk 3020 20004, "Found in NWN2's ZIP files" NWN2, number invented — removed
xml 3021 20003, same NWN2 ZIP section NWN2, number invented — removed

The 20000+ range sits above kFileTypeMAXArchive, under the heading "Entries for files not found in archives with numerical type IDs". So wlk and xml have no archive restype in any Aurora game: 0x0BCC and 0x0BCD were made up, and they sit in a band Aurora does use elsewhere (3022 FSM, 3023 ART).

NWN:EE already covers those jobs with formats in the table: wok/pwk/dwk for walkmeshes, and EE's own UI XML loads from ui/ovr rather than from a HAK by restype — consistent with upstream neverwinter.nim (Niv being a Beamdog dev) registering no xml number.

lyt/vis/mdx are genuinely deliberate as the description says: real Aurora archive types NWN1 ships in its own data/*.bif, same numbers in xoreos. Upstream's table just does not list them.

Also a small amendment on mdb and the corpus. The description says none of these are in the current asset corpus, which is true of the shipped content, but there are nine .mdb files in _contentpool/!GunsPackage/Weapons/ — a downloaded NWN2 package, the files starting with the literal magic bytes NWN2. They confirm the diagnosis rather than complicate it: NWN:EE cannot use them at any restype. mdb was dropped rather than renumbered, since upstream gives 2070 to xbc and there is no correct NWN:EE number to move it to.

Net effect in #69: four extensions removed (mdb, gr2, wlk, xml) instead of one, plus the five number fixes. .mdb/.gr2/.wlk/.xml sources now fail the build with "unsupported extension" instead of packing into a HAK under a number the game misreads.

Correction to one premise in the description, found while fixing this in #69. The issue says the six extensions upstream does not have — `lyt` 3000, `vis` 3001, `mdx` 3008, `wlk` 3020, `xml` 3021, `gr2` 4003 — "are deliberate local additions, not bugs". That holds for three of them. The other three are NWN2 formats, the same class of problem as `mdb`. Checked against [xoreos `src/aurora/types.h`](https://github.com/xoreos/xoreos/blob/master/src/aurora/types.h), which covers every Aurora game and so keeps the games' tables apart: | ext | Crucible had | xoreos | verdict | |-----|--------------|--------|---------| | lyt | 3000 | 3000, room layout | real, NWN1/EE — deliberate, kept | | vis | 3001 | 3001, room visibilities | real, NWN1/EE — deliberate, kept | | mdx | 3008 | 3008, model mesh data | real, NWN1/EE — deliberate, kept | | gr2 | 4003 | 4003, in the NWN2 block (MDB2 4000, MDA2 4001, SPT2 4002, GR2 4003, PWC 4008) | NWN2 (Granny) — removed | | wlk | 3020 | **20004**, "Found in NWN2's ZIP files" | NWN2, number invented — removed | | xml | 3021 | **20003**, same NWN2 ZIP section | NWN2, number invented — removed | The 20000+ range sits above `kFileTypeMAXArchive`, under the heading "Entries for files not found in archives with numerical type IDs". So `wlk` and `xml` have no archive restype in *any* Aurora game: 0x0BCC and 0x0BCD were made up, and they sit in a band Aurora does use elsewhere (3022 FSM, 3023 ART). NWN:EE already covers those jobs with formats in the table: `wok`/`pwk`/`dwk` for walkmeshes, and EE's own UI XML loads from `ui`/`ovr` rather than from a HAK by restype — consistent with upstream neverwinter.nim (Niv being a Beamdog dev) registering no `xml` number. `lyt`/`vis`/`mdx` are genuinely deliberate as the description says: real Aurora archive types NWN1 ships in its own `data/*.bif`, same numbers in xoreos. Upstream's table just does not list them. Also a small amendment on `mdb` and the corpus. The description says none of these are in the current asset corpus, which is true of the shipped content, but there are nine `.mdb` files in `_contentpool/!GunsPackage/Weapons/` — a downloaded **NWN2** package, the files starting with the literal magic bytes `NWN2`. They confirm the diagnosis rather than complicate it: NWN:EE cannot use them at any restype. `mdb` was dropped rather than renumbered, since upstream gives 2070 to `xbc` and there is no correct NWN:EE number to move it to. Net effect in #69: four extensions removed (`mdb`, `gr2`, `wlk`, `xml`) instead of one, plus the five number fixes. `.mdb`/`.gr2`/`.wlk`/`.xml` sources now fail the build with "unsupported extension" instead of packing into a HAK under a number the game misreads.
Sign in to join this conversation.
1 Participants
Notifications
Due Date
No due date set.
Dependencies

No dependencies set.

Reference: ShadowsOverWestgate/sow-tools#64