From 39dbaf743abbbbd9ddc91cced6d942020d89dfa9 Mon Sep 17 00:00:00 2001 From: Alexander Gavrilov Date: Wed, 13 Feb 2013 13:54:49 +0400 Subject: [PATCH] Add a script to fix cloth stockpiles by patching memory objects. This patching needs to be done every time raws are reloaded. --- dfhack.init-example | 3 ++ scripts/fix/cloth-stockpile.lua | 80 +++++++++++++++++++++++++++++++++ 2 files changed, 83 insertions(+) create mode 100644 scripts/fix/cloth-stockpile.lua diff --git a/dfhack.init-example b/dfhack.init-example index 1a5aee48f..ddf93de16 100644 --- a/dfhack.init-example +++ b/dfhack.init-example @@ -144,6 +144,9 @@ tweak military-training # write the correct season to gamelog on world load soundsense-season +# patch the material objects in memory to fix cloth stockpiles +fix/cloth-stockpile enable + ####################################################### # Apply binary patches at runtime # # # diff --git a/scripts/fix/cloth-stockpile.lua b/scripts/fix/cloth-stockpile.lua new file mode 100644 index 000000000..7da5d583c --- /dev/null +++ b/scripts/fix/cloth-stockpile.lua @@ -0,0 +1,80 @@ +-- Fixes cloth/thread stockpiles by correcting material object data. + +local raws = df.global.world.raws +local organic_types = raws.mat_table.organic_types +local organic_indexes = raws.mat_table.organic_indexes + +local function verify(category,idx,vtype,vidx) + if idx == -1 then + -- Purely for reporting reasons + return true + end + local tvec = organic_types[category] + if idx < 0 or idx >= #tvec or tvec[idx] ~= vtype then + return false + end + return organic_indexes[category][idx] == vidx +end + +local patched_cnt = 0 +local mat_cnt = 0 + +function patch_material(mat,mat_type,mat_index) + local idxarr = mat.food_mat_index + + -- These refer to fish/eggs, i.e. castes and not materials + idxarr[1] = -1 + idxarr[2] = -1 + idxarr[3] = -1 + + for i = 0,#idxarr-1 do + if not verify(i,idxarr[i],mat_type,mat_index) then + idxarr[i] = -1 + patched_cnt = patched_cnt+1 + end + end + + mat_cnt = mat_cnt + 1 +end + +function patch_materials() + patched_cnt = 0 + mat_cnt = 0 + + print('Fixing cloth stockpile handling (bug 5739)...') + + for i,v in ipairs(raws.inorganics) do + patch_material(v.material, 0, i) + end + + for i,v in ipairs(raws.creatures.all) do + for j,m in ipairs(v.material) do + patch_material(m, 19+j, i) + end + end + + for i,v in ipairs(raws.plants.all) do + for j,m in ipairs(v.material) do + patch_material(m, 419+j, i) + end + end + + print('Patched '..patched_cnt..' bad references in '..mat_cnt..' materials.') +end + +local args = {...} + +if args[1] == 'enable' then + dfhack.onStateChange[_ENV] = function(sc) + if sc == SC_WORLD_LOADED then + patch_materials() + end + end + if dfhack.isWorldLoaded() then + patch_materials() + end +elseif args[1] == 'disable' then + dfhack.onStateChange[_ENV] = nil +else + patch_materials() +end