Summary
Morrowind mod and save files use the same basic format of records and subrecords.
- Dave Humphrey wrote a fairly detailed description of the file structure: Format of Morrowind's ESM Plug-In File.
- The most up to date encoding of the file structure can be found in ESTemplate.ini file for Enchanted Editor. It is also packaged with Wrye Mash.
- Jim Adam has an older, but more readable version of the Morrowind File Format, but it does not address save game records.
- The author of Enchanted Editor offers a tutorial for interpreting the morrowind file format.
Notes
Following is a collection of rough notes on file format records and subrecords.
- Organization is by Record, then subrecord, the subrecord notes.
PGRD (Path Grid)
(Follows a CELL record)
-
- 4 bytes String = "PGRD"
- 4 bytes long = size of record (excluding 16 bytes of header)
- 4 bytes unknown (useless?)
- 4 bytes unknown (useless?)
- DATA
- 4 bytes String = "DATA"
- 4 bytes long = size of sub-record (excluding 8 bytes of header)
- 4 bytes (signed) Int = Cell's X co-ordinates (for exteriors ... for interiors == 0)
- 4 bytes (signed) Int = Cell's Y co-ordinates (for exteriors ... for interiors == 0)
- 2 bytes unknown
- 2 bytes short = (? multiple of ?)total number of number of points in the path grid.
- NAME
- 4 bytes String = "NAME"
- 4 bytes long = size of record (excluding 8 bytes of header)
- (variable) bytes String = Cell Name. The string length is equal to the sub-record's size (listed above). The string is terminated with an unrecognized character (maybe used to put an asterisk(*) for mods.
- PGRP (Path Grid Points)
-
- 4 bytes String = "PGRP"
- 4 bytes long = size of sub-record (excluding 8 bytes of header)
--- Repeating structure for each point in cell's pathgrid ----
-
- 4 bytes long = X-Position of point
- 4 bytes long = Y-Position of point
- 4 bytes long = Z-Position of point
- 4 bytes unknown (possibly flag for coloring\user-placed vs auto-generated)
<---------------------------->
-
-
- The positions for Path Grid Points are whole numbers (long) and not floating point numbers, unlike the positions of objects in the CELL records.
-
- PGRC (Path Grid Edges\Links)
-
- 4 bytes String = "PGRP"
- 4 bytes long = size of sub-record (excluding 8 bytes of header)
--- Repeating structure for each link in cell's pathgrid ----
-
- 4 bytes long = index of point (0 stands for the first point in the above (PGRP) structure 1 for the next and so on. A typical structure for 3 inter-linked points (triangle) would be 1,2,0,2,1,2 which means that 1 is joined to 2, 2 is joined to 0, 0 is joined to 2,two is joined to 1, 1 is joined to 2).
<---------------------------->
CELL
- CNAM (Cell Name)
- Used after a MVRF
- MPDT (Map Data: x,y,z floats) [ESS]
- MPNT (Map Note, String) [ESS]
- MVRF (Move Reference) [ESS,ESP]
- Signifies that the reference has been moved to another cell.
- If moved to an interior cell is followed by CNAM. (And other times? I forget.)
- Found frequently in ESS files as creatures and NPCS move (or are moved) from their original.
- Can also be found (very rarely) in an esp if the esp moves a reference from a master file.
- NAM8 (Visibility Map) [ESS]
- NAM0 (Normal Objects Count, Long) [ESM,ESP]
- ESM/ESPs only.
- Corresponds to __TEMP_REFS___ line
- Count of non "reference persists" objects in cell
- Appears between "persistent" and non-"persistent" objects
- ZNAM (Disabled: 1 byte) [ESS?]
- Probably presence is enough.
- Byte always == 0?
INFO
- NAME: NOT zero terminated!
- BNAM: NOT zero terminated!
NPCC (NPC Contents)
- NPDT
- Bytes 0-1: Base disposition
- Bytes 2-3: Flag? values: {0,2,4,8,10,14}
- Bytes 4-8: Index number
- SLCS (script variable ?)
- WIDX (Wear index: index of items within the list that are worn)
- But why 8 bytes???
- XCHG (Charge? float)
- XIDX (Subindex of NPCO, precedes greater detail)
- XHLT (Health)
- Format (integer or float) depends on type of item.
- XSOL (Soul gem contained creature, zero terminated string creature id)
SCPT (Global Script)
- SCHD (Script Header)
- SLCS (?: 3 ints?)
- Always present?
- SLFD (Float Data: 4 bytes x num of floats)
- SLSD (Short Data 2 bytes x num of shorts)
- RNAM (Reference)
- Reference object for global script. Same format as CELL.FRMR.