GameBalance Items*.gam Files
This section discusses the "\GameBalance\Items*.gam" file in the "CoreData.mpq" file. MPQ Patches to this file are located in the "base" subdirectory of the Diablo 3 "MPQs" directory. Please see the MPQs section for general MPQ information and basic information about how GameBalance (*.gam) files are encoded.
Item Structure
In Beta version 8815, this structure size was increased to 0x5F0 (up from 0x5D0 since patch 7728). A new DWord was also added after "cLvl"; the values also look like some kind of level. It's hard to know which levels correspond to what. The "unknown10A" array was increased by one DWord. These unknown structures are used when items are populated in-memory. The "unknown14" area at the end of the structure is now 7 DWords.
In Beta version 7728, this structure size was increased to 0x5D0 (up from 0x5B0 since patch 7318). The extra 0x20 bytes were added at the end. Also, weapons no longer have ModCodes that alter the min/max damage range; instead this capability has been moved to two new float values located at offsets 0x328 and 0x32C.
This Item structure is used for all the items (weapons, armor, potions, etc). The same structure is used for items of all rarities (common, magic, etc).
| struct Item | // sizeof 0x5F0 | ||
| { | |||
| 0x000 | DWord unknown1; | // always 0x00000000 | |
| 0x000 | DWord itemName[256]; | // non-NLS key name of the item | |
| 0x104 | DWord actorId; | // Actor MPQ Id | |
| 0x108 | DWord itemTypeHash; | // hash of the ItemType | |
| 0x10C | DWord unknown2; | // possibly related to Act level | |
| 0x110 | DWord unknown3; | // ??? | |
| 0x114 | DWord iLevel; | // item level | |
| 0x118 | DWord unknown4; | // ??? | |
| 0x11C | DWord unknown5; | // ??? | |
| 0x120 | DWord numRandomAffixes; | // number of random affixes | |
| 0x124 | DWord numSockets; | // number of sockets the item can have | |
| 0x128 | DWord stackSize; | // stack size | |
| 0x12C | DWord goldPrice; | // gold buy price (sell price is 15% of buy) | |
| 0x130 | DWord unknown6; | // related to level? | |
| 0x134 | DWord cLevel; | // character level required to use the item | |
| 0x138 | DWord unknown15; | // related to level? | |
| 0x13C | DWord durabilityMin; | // min durability | |
| 0x140 | DWord durabilityMax; | // max durability (offset from min) | |
| 0x144 | DWord baseItemHash; | // hash of the base item | |
| 0x148 | DWord setItemBonuses; | // set item bonuses | |
| 0x14C | DWord salvageCommon; | // salvage common TreasureClass | |
| 0x150 | DWord salvageMagic; | // salvage magic TreasureClass | |
| 0x154 | DWord salvageRare; | // salvage rare TreasureClass | |
| 0x158 | DWord rareGroupPrefixId; | // MPQ Id of RareNameStrings_Prefix_*.stl file | |
| 0x15C | DWord rareGroupSuffixId; | // MPQ Id of RareNameStrings_Suffix_*.stl file | |
| 0x160 | DWord unknown7[26]; | // ??? | |
| 0x1C8 | float minDamage; | // weapon min damage | |
| 0x1CC | float maxDamage; | // weapon max damage (offset from min) | |
| 0x1D0 | DWord unknown8[21]; | // ??? | |
| 0x224 | float minArmor; | // min armor | |
| 0x228 | float maxArmor; | // max armor (offset from min) | |
| 0x22C | DWord unknown9[42]; | // ??? | |
| 0x2D4 | float weaponSpeed; | // weapon speed | |
| 0x2D8 | DWord unknown10[21]; | // ??? | |
| 0x32C | float minDamageMod; | // weapon min damage modifier | |
| 0x330 | float maxDamageMod; | // weapon max damage modifier (offset from min) | |
| 0x334 | DWord unknown10A[26]; | // ??? | |
| 0x39C | DWord unknown11; | // ??? | |
| 0x3A0 | DWord unknown12[18]; | // ??? | |
| 0x3E8 | ModCode mods[16]; | // see ModCode structure below | |
| 0x568 | DWord itemQuality; | // -1: invalid, 3: magic, 6: rare, 9: lgd. | |
| 0x56C | DWord teaches1; | // recipe hash (in Recipes*.gam) | |
| 0x570 | DWord teaches2; | // recipe hash (in Recipes*.gam) | |
| 0x574 | DWord teaches3; | // recipe hash (in Recipes*.gam) | |
| 0x578 | DWord teaches4; | // recipe hash (in Recipes*.gam) | |
| 0x57C | DWord teaches5; | // recipe hash (in Recipes*.gam) | |
| 0x580 | DWord teaches6; | // recipe hash (in Recipes*.gam) | |
| 0x584 | DWord teaches7; | // recipe hash (in Recipes*.gam) | |
| 0x588 | DWord unknown13[3]; | // 0x00000000 (added in Beta 7728) | |
| 0x594 | DWord enchants; | // recipe hash (in ItemEnhancements.gam) | |
| 0x598 | DWord affixGroupHash[6]; | // hash of the Affix Group | |
| 0x5B0 | DWord affixLevel[6]; | // level of the Affix | |
| 0x5C8 | DWord gemType; | // gem type: 1=Amethyst, 2=Emerald, 3=Ruby, 4=Topaz | |
| 0x5CC | DWord craftingMatTier; | // crafting material tier | |
| 0x5D0 | DWord craftingMatRarity; | // crafting material rarity | |
| 0x5D4 | DWord unknown14[7]; | // always 0x00000000 | |
| } |
ModCode Structure
The ModCode (sometimes called Attribute) structure is shown below. The NLS (enUS) string descriptions for the various ModCodes can be found here. Unfortunately, I have not found a mapping between the non-NLS string keys (e.g., "Attack_Rating") and the ModCode ids.
| struct ModCode | // sizeof 0x18 | |
| { | ||
| 0x00 | DWord modCode; | // modCode (id) |
| 0x04 | DWord modParam1; | // param used for elemental dmg and resists |
| 0x08 | DWord modParam2; | // param |
| 0x0C | DWord modParam3; | // param |
| 0x10 | DWord varDataOffset; | // variable data offset (from the start of the data section) |
| 0x14 | DWord varDataLength; | // variable data length |
| } |
Please see the Affixes and ModCodes for more information on Affixes and ModCodes.
Please see the ModCode Variable Data section for information on decoding the variable data.
The "itemQuality" value is only set for crafting plans and some special items (e.g., "StoneOfRecall").
The "affixGroupHash" and "affixLevel" arrays are only used for Unique items in the client game files. If this same structure is used at runtime, I expect that all items with affixes (e.g., magical and rares) will have these values populated accordingly. Note that rare items can have at most 6 affixes, as was the case in Diablo 2.
The value at 0x160 (part of unknown7[26]) is only used for three items:
- TownPortalStone: 0x00400000
- ScrollIdentify: 0x01000000
- ChaosShardCorrupted: 0x02000000
All of the other unknown values listed above have a value of either 0x00000000 or 0xFFFFFFFF. Rather than storing these values individually, I am storing only their crc32 value to be able to detect changes between versions.
The "teaches" value is the hash of the Recipe from the Recipes*.gam files Blacksmith, Jeweler, and Mystic training-only). Prior to patch 7728, there was only a single value for this. In patch 7728, this was changed to 7 values to accommodate "set" recipes that allow for the creation of all items in the set.
The "enchants" value was moved to offset 0x58C in Patch 7728. This value is the hash of the recipe from the ItemEnhancements.gam files (Mystic non-training).
Please check out the String Hashing section for more details on Diablo 3 hashing.
