Home / Database versions and battlesets
Database versions and battlesets
Which generations of the database file the editor reads, which one it writes, which battleset a database is for, and how to write one into a battleset file.
Reading every generation
The database file format has changed over the life of the game. It carries a structure version, 1 to 6, which the editor works out from the file itself. It reads all six. The last line of the Overview says which one you have open.
| Version | Where you meet it | What the editor does |
|---|---|---|
| 1 | The classic battlesets of the 1990s and early 2000s, whose database
lives inside the battleset's own .res. |
Converts it to the current record layout as it reads it, so every screen works on it unchanged. |
| 2 to 4 | Older commondb.res builds, up to 2020. |
Opens and edits it as it is, and converts it to the version you export when you write it. |
| 5 | Every commondb.res since 2021. |
Opens and edits it as it is. |
| 6 | Game builds from HC 2023.007 on. | Opens and edits it as it is. |
A classic battleset's own database
To work on the database of a classic battleset, use File →
Open… on the battleset's .res itself (for example
GIUK.RES). Each battleset converts to its own database, one per
battleset, with nothing merged between them, so every id stays what the
battleset made it. A few things do not carry over, because the old format had
no room for them or the game ignored them:
- An old record's serial byte, whose meaning is unknown, is dropped.
- RCS and source level come across as zero. The game assigns both itself for these battlesets, so the stored value never mattered (see the battleset target below).
- The very earliest battlesets have no magazine reload times at all, so each magazine gets 60 seconds, and no victory types, so every record gets type 0 and the names table is empty. Nothing is invented to fill the gap.
- Reload times stay in seconds, which is what those battlesets used.
The converted database lands with its target set to that battleset, embedded, before the commondb era. A file that fits none of the old layouts is refused with a message rather than guessed at.
What each structure version changes
The editor tells the versions apart by the size of the string
tables in the file (the names for countries, ship types, aircraft types
and so on). Nothing else in the file says which generation it is, and the number
stored after the BBFT marker at the start of a file does not: that
number stamps the tool that wrote the file (see
Container quirks).
| Version | String tables | What it changes |
|---|---|---|
| 1 | 1,340 bytes | Small tables: 24 countries, 40 ship types, 16 aircraft types. Names are short (18 to 26 characters, against 48 later). Records carry no disk id: a record is known by its position in its annex. Two sub-generations exist (see Quirks of the original battlesets). |
| 2 | 6,976 bytes | Ids, 48-character names, and tables mostly of 128 entries. A record’s Country is one byte, so at most 128 countries. Runway names are not in the database at all (see Runway names). |
| 3 | 37,696 bytes | Country becomes four bytes in ships, subs, aircraft and bases, and the country table grows to 1,024 entries of up to 32 bytes. Records do not change size. |
| 4 | 41,920 bytes | The ship type table grows from 128 entries of 8 bytes to 256 of 12. The aircraft type and aircraft short-type tables grow from 128 to 256 entries. |
| 5 | 46,016 bytes | Adds RunwayString, 128 runway names the database now holds itself. |
| 6 | 47,680 bytes | Adds BroadVicType, 128 victory-type names of 13 bytes each, to the string tables. Versions 2 to 5 keep the same 128 names in a separate resource. A version 6 file still carries that resource, but only as a placeholder: the game reads the names from the string tables. The game reads version 6 from HC 2023.007. |
The editor reads all six and writes 5 or 6 (see below). Opening a version 2, 3 or 4 database and exporting it converts it: the one-byte country becomes four bytes, the string tables grow to the exported version's size with every entry at the same index, and the runway names are supplied (see below). A version 1 database is converted as it is read.
Runway names
Before version 5 the game has eight runway names built in, numbered 0 to 7, and the database does not hold them. From version 5 the database holds its own list (RunwayString, room for 128), and the Runway of a ship, aircraft or base is an index into it. In a version 5 or 6 database a Runway value above 7 is valid, provided its name slot is filled; in versions 2 to 4 only the built-in eight exist. The editor labels Runway from the database’s own list from version 5 on, and from the built-in eight before that. Converting an older database to version 5 or 6 fills the list with the eight names and leaves the rest empty.
Four weapon slots or eight
A loadout (Y1) or a multi-mount (Z2) holds a number of weapon slots: eight in current databases, and four in the database of the 2003-era builds. The record is the same size either way. Which one a file uses is not decided by its structure version: both 4-slot and 8-slot databases exist at version 2, and nothing in the file says which. The editor works it out from the weapons the slots name, and falls back to eight unless four fits decisively. When it opens a database as four-slot, it says so on import, in the change history and on the export check, and writing it out widens it to eight.
Writing: version 6, or version 5
The editor writes only the current format. Export .res… writes version 6 by default. Settings → Database exports → Structure version also offers 5:
- 6 — HC 2023.007 and later (default). The victory-type names live in the string tables, where the game has read them since 2023.007. You edit them under Strings → BroadVicType.
- 5 — also loads in older game builds. The victory-type names live in their own resource, which every game build reads. You edit them under Strings → VicTypes.
Either way the Victory type of a ship, sub, aircraft or base is a dropdown listing each named type as “index — name”; a value that has no name shows as “N (no name)” and is kept as it is. Rename a type in Strings and the dropdown follows. Each rename is in History and can be reverted.
Pick 5 if anyone you share the database with plays on a build older than 2023.007, which may not accept a version 6 file. Both carry exactly the same records. A database opened at version 2, 3 or 4 is converted to the version chosen here when you export; nothing is ever written back at versions 1 to 4. The choice applies to Export into battleset… too.
Battleset numbers and eras
Every battleset has a number, and the number decides what the target means for the database. The editor groups the numbers into eras:
| Battlesets | Number | Where its database lives | Resource header | Reload time | RCS and source level |
|---|---|---|---|---|---|
| The original four: GIUK, NACV, MEDC, IOPG, and the original USNI | 1 to 4 (USNI is 1) | Inside the battleset | 5 bytes | Seconds | Assigned by the game |
| HDS1 to HDSC | 6 to 17 | Inside the battleset | 5 bytes | Seconds | Assigned by the game |
| HDSD to HDSG | 18 to 21 | Inside the battleset | 5 bytes | Seconds | Assigned by the game |
| HDSH to HDSK | 22 to 25 | commondb.res |
5 bytes | Minutes | Read by the game |
| BSBuilder numbering starts here: HDSL to HDSU, then BSB036 and up | 26 and up | commondb.res, or inside the battleset when its
DBinBS setting is on |
7 bytes | Minutes | Read by the game |
| The USNI demo sets, GIUKUSNI and WPACUSNI | 120 and up | Inside the battleset | 7 bytes | Minutes | Read by the game |
commondb.res itself |
none | It is the database | 7 bytes | Minutes | Read by the game |
So 22 is the line. Below it a battleset carries its own database, with reload times in seconds and RCS and source level that the game works out itself. From it up the database is the shared one (or, for the USNI sets and for BSBuilder battlesets that ask for it, still inside the battleset), with reload times in minutes and ratings the game reads. What the editor does about this is under The battleset target. The ratings’ ranges are in the limits reference, and what Check does with them is in the Check reference.
The number a battleset stores about itself
A battleset file carries its own battleset number, but it cannot be trusted: HDSD to HDSG store 1 to 4, HDSH stores 1, and the original USNI says 1 in every copy (it is GIUK’s number, and it carries GIUK’s database). The editor therefore goes by the file name. A name it knows gives the number directly; an unfamiliar name is asked about (see The battleset target).
Quirks of the original battlesets
Helicopters on Helo Pad mounts
In the original four battlesets (1 to 4), a ship carries its helicopter on a Helo Pad mount, a mount whose weapon is the aircraft itself. When the target is battleset 1 to 4, Check and the export accept an aircraft record as a mount’s weapon, but only a helicopter: a fixed-wing aircraft there is still a fault. With any other target, an aircraft on a mount is reported like any other bad reference. If a database has Helo Pad mounts but its target is not set to 1 to 4, set it in Change target… first.
The earliest releases
- The earliest releases have no victory types and no
magazine reload times at all, and their resources are packed with an
older compression (the kind Unix
compressmakes) that the later ones do not use. The editor reads it. - In a version 1 file the resource that later holds the database version stamp is never one (in the earliest sets it holds music), so a fresh stamp is made on conversion.
- The text of the platform descriptions is over 64 KB in every original battleset examined, more than their five-byte headers can state. The editor recovers the true size when it reads them.
Two sub-generations of version 1
Version 1 comes in two sub-generations that share the same string tables, so the string-table size cannot tell them apart. The editor tells them apart by the size of the ship, aircraft and base records, and refuses a file where those disagree. The later sub-generation has:
- a victory-type byte in ships, subs, aircraft and bases, and the victory-type names;
- a per-record serial byte in those four, of unknown meaning;
- more mount slots: 20 on a ship (the earlier has 17) and 10 on a sub (the earlier has 5);
- a reload time in each magazine entry.
The victory-type names of HDSD to HDSG could not be established with confidence: the table they carry does not describe their records, so the editor keeps the names that read as text, and you should check them.
What else does not carry over from version 1
Beyond what is listed under A classic battleset’s own database, a conversion also:
- drops the padding bytes that only kept old records aligned, and a loadout’s old plane link (which was not kept up to date; the aircraft’s own loadout list says which loadouts it has);
- sets RCS and source level to 0, because the game assigns its own;
- cuts radar and sonar names at the 16th character, dropping the class code that followed it;
- gives each record the id its position implies, so the references that already pointed at positions still point at the right records;
- looks up country, ship type, aircraft type and loadout mission by name in the converted tables rather than copying the index, because those tables are numbered differently in version 1.
A file that holds only database resources but has version 1’s small string tables is refused: version 1 only ever lived inside a battleset.
The battleset target
Two facts about a database are written nowhere in its bytes, and both change
what the editor must do: which battleset reads it, and
where it lives, in commondb.res or inside a
battleset's own file. The editor keeps them together as the database's
target, saves it in the project file,
and shows it on the Overview under Target, below the
contents table, with what it means.
The battleset number matters for two things:
- A magazine's reload time is in minutes for battleset 22 and higher, and in seconds below that. Magazine rows label it (min) or (s) to match.
- RCS and source level are read by the game for battleset 22 and higher. Below 22 the game assigns them itself, whatever is stored. The editor keeps the values and says on those fields that the game assigns them, and Check's advisory rating family does not run. A source level the game cannot hold is a warning there, where it is not used, and blocks the export only for battleset 22 and higher.
A commondb.res counts as the commondb era (minutes, RCS and
source level live). A battleset file you open takes its number from its file
name. If the name is not one the editor recognises (a renamed copy, say), it
asks which battleset the file is, with the kind already chosen from the file
itself: a battleset carrying its own database behind the old 5-byte resource
headers is a classic set below 22, and anything else is 22 or higher. That
answer only says how to read the reload times already in the file; nothing is
converted. Decide later leaves it for Change target….
A project file saved before this existed opens as a commondb database.
Change target…
The Overview's Change target… button opens a small dialog with three choices: a commondb database (saved under any file name, such as HCDB-052354.res; reload time in minutes), a battleset below 22, embedded (reload time in seconds), and a battleset 22 or higher, embedded (minutes), plus the battleset number for the last two. Before anything happens it says what would change:
- Seconds to minutes (retargeting from below 22 to 22 or higher, or to a commondb database): reload times convert, rounding up, and a reload of 0 becomes 1 minute. The dialog says how many magazine rows change. RCS and source level become live, so Check will report any that are out of range.
- Minutes to seconds (the other way): reload times are multiplied by 60. A reload of 5 minutes or more does not fit the one-byte field, so it is capped at 255 seconds, and the dialog counts the rows that will be capped. RCS and source level are kept but ignored by the game.
- Within one era: only the target changes. Reload times, RCS and source level are left alone.
One entry goes in Change history for the whole change, and one Undo takes it all back, every reload time exactly as it was, capped rows included. Undo refuses if the target or those rows have been changed again since.
Export into battleset…
A database that belongs inside a battleset is not what a plain
commondb.res is for: the game reads it from the battleset's file.
File → Export into battleset… writes it there. (If
the target is a battleset, File → Export .res… asks
first whether you meant this instead.) It runs the same checks as
Export .res…, then asks for two files:
The battleset to start from
Choose the battleset's
.res. It is only read.A new file to save
The name offered is the battleset's own with
-hcpeadded, beside it. It must be a new file: the editor will not write over the battleset it started from.
Only the database part of the battleset is replaced: the annexes, the magazines, the string tables, the platform descriptions and hull names with their indexes, the database version stamp and the victory-type names. Everything else in it (maps, scenarios, music, messages) is copied across byte for byte, and the battleset's own header size is kept. When it finishes, a dialog lists what it did, and says so if it had to:
- add the prefix that names the structure version, on a classic battleset that had none;
- extend the table of resources;
- leave a database part empty because this database holds nothing for it,
so the game will look for it in
commondb.res; - switch a battleset built with BSBuilder over to reading its database
from itself rather than from
commondb.res; - warn that a part is too large for the old five-byte resource header to describe, so the game may not read it.
The result is written at the structure version Settings picks, version 6 unless you chose 5. It is logged as an export, with a note saying which battleset it went into.
Container quirks
A .res file is a container of numbered resources. A few details
of it differ between battlesets and between generations of the database:
- Five-byte and seven-byte resource headers. Every
resource begins with a header. Classic battlesets use the older 5-byte
header, whose size field is 16 bits wide; the newer files use a 7-byte
header. The game picks the header size by file name:
commondb,GIUKUSNI,WPACUSNIandHDSLtoHDSUare 7-byte, and every other classic name is 5-byte. When the editor writes into a BSBuilder battleset (BSBand a number), it uses 7-byte headers too. The era table lists each battleset’s. - The 5-byte header cannot describe a resource over 65,535 bytes. That matters when a modern database goes into a classic battleset: a real ship or aircraft annex is usually larger than that. The editor has no compressor, so it cannot shrink them, and Export into battleset… warns about each such resource rather than hiding it. Whether the game reads such a file is to be confirmed in the game.
- The
BBFTprefix. Some files begin with the lettersBBFTand a number; the oldest battlesets and the 2003-era files do not. The number stamps the tool that wrote the file and does not follow the structure version. The editor keeps whatever a file had, and Export into battleset… adds the prefix, with the version it writes, to a classic battleset that had none, which is also to be confirmed in the game. - The version stamp. The resource that names the database (its flavor) and when it was built comes in a 36-byte and a 40-byte form. Which one a file has depends on the tool that built it, not on the structure version; the editor writes back the size it read.
- Compressed resources. Older files compress some resources. The editor reads them, and writes every resource uncompressed, so such a database gets larger when exported; the export check says when that happens. Whether a 2003-era game build loads an uncompressed file has not been confirmed.