1 #include "Debug.h"
2 #include "LoadSaveData.h"
3 #include "LoadSaveObjectType.h"
4 #include "LoadSaveSoldierType.h"
5 #include "Overhead.h"
6 #include "Tactical_Save.h"
7 #include "Types.h"
8
9 #include <string_theory/string>
10
11 #include <algorithm>
12 #include <stdexcept>
13
MercChecksum(SOLDIERTYPE const & s)14 static UINT32 MercChecksum(SOLDIERTYPE const& s)
15 {
16 UINT32 sum = 1;
17
18 sum += 1 + s.bLife;
19 sum *= 1 + s.bLifeMax;
20 sum += 1 + s.bAgility;
21 sum *= 1 + s.bDexterity;
22 sum += 1 + s.bStrength;
23 sum *= 1 + s.bMarksmanship;
24 sum += 1 + s.bMedical;
25 sum *= 1 + s.bMechanical;
26 sum += 1 + s.bExplosive;
27 sum *= 1 + s.bExpLevel;
28 sum += 1 + s.ubProfile;
29
30 CFOR_EACH_SOLDIER_INV_SLOT(i, s)
31 {
32 sum += i->usItem;
33 sum += i->ubNumberOfObjects;
34 }
35
36 return sum;
37 }
38
39
ExtractSoldierType(const BYTE * const data,SOLDIERTYPE * const s,bool stracLinuxFormat,UINT32 uiSavedGameVersion)40 void ExtractSoldierType(const BYTE* const data, SOLDIERTYPE* const s, bool stracLinuxFormat, UINT32 uiSavedGameVersion)
41 {
42 UINT16 usPathingData[ MAX_PATH_LIST_SIZE ];
43 UINT16 usPathDataSize;
44 UINT16 usPathIndex;
45
46 *s = SOLDIERTYPE{};
47
48 DataReader d{data};
49 EXTR_U8(d, s->ubID)
50 EXTR_SKIP(d, 1)
51 EXTR_U8(d, s->ubBodyType)
52 EXTR_I8(d, s->bActionPoints)
53 EXTR_I8(d, s->bInitialActionPoints)
54 EXTR_SKIP(d, 3)
55 EXTR_U32(d, s->uiStatusFlags)
56 FOR_EACH_SOLDIER_INV_SLOT(i, *s)
57 {
58 ExtractObject(d, i);
59 }
60 EXTR_PTR(d, s->pTempObject)
61 EXTR_PTR(d, s->pKeyRing)
62 EXTR_I8(d, s->bOldLife)
63 EXTR_U8(d, s->bInSector)
64 EXTR_I8(d, s->bFlashPortraitFrame)
65 EXTR_SKIP(d, 1)
66 EXTR_I16(d, s->sFractLife)
67 EXTR_I8(d, s->bBleeding)
68 EXTR_I8(d, s->bBreath)
69 EXTR_I8(d, s->bBreathMax)
70 EXTR_I8(d, s->bStealthMode)
71 EXTR_I16(d, s->sBreathRed)
72 EXTR_BOOL(d, s->fDelayedMovement)
73 EXTR_SKIP(d, 1);
74 EXTR_U8(d, s->ubWaitActionToDo)
75 EXTR_SKIP(d, 1)
76 EXTR_I8(d, s->ubInsertionDirection)
77 EXTR_SKIP(d, 1)
78 EXTR_SOLDIER(d, s->opponent)
79 EXTR_I8(d, s->bLastRenderVisibleValue)
80 EXTR_SKIP(d, 1)
81 EXTR_U8(d, s->ubAttackingHand)
82 EXTR_SKIP(d, 2)
83 EXTR_I16(d, s->sWeightCarriedAtTurnStart)
84 if(stracLinuxFormat)
85 {
86 EXTR_SKIP(d, 2)
87 s->name = d.readUTF32(SOLDIERTYPE_NAME_LENGTH);
88 }
89 else
90 {
91 s->name = d.readUTF16(SOLDIERTYPE_NAME_LENGTH);
92 }
93 EXTR_I8(d, s->bVisible)
94 EXTR_I8(d, s->bActive)
95 EXTR_I8(d, s->bTeam)
96 EXTR_U8(d, s->ubGroupID)
97 EXTR_BOOL(d, s->fBetweenSectors)
98 EXTR_U8(d, s->ubMovementNoiseHeard)
99 if(stracLinuxFormat)
100 {
101 EXTR_SKIP(d, 2)
102 }
103 EXTR_FLOAT(d, s->dXPos)
104 EXTR_FLOAT(d, s->dYPos)
105 EXTR_SKIP(d, 8)
106 EXTR_I16(d, s->sInitialGridNo)
107 EXTR_I16(d, s->sGridNo)
108 EXTR_I8(d, s->bDirection)
109 EXTR_SKIP(d, 1)
110 EXTR_I16(d, s->sHeightAdjustment)
111 EXTR_I16(d, s->sDesiredHeight)
112 EXTR_I16(d, s->sTempNewGridNo)
113 EXTR_SKIP(d, 2)
114 EXTR_I8(d, s->bOverTerrainType)
115 EXTR_SKIP(d, 1)
116 EXTR_I8(d, s->bCollapsed)
117 EXTR_I8(d, s->bBreathCollapsed)
118 EXTR_U8(d, s->ubDesiredHeight)
119 EXTR_SKIP(d, 1)
120 EXTR_U16(d, s->usPendingAnimation)
121 EXTR_U8(d, s->ubPendingStanceChange)
122 EXTR_SKIP(d, 1)
123 EXTR_U16(d, s->usAnimState)
124 EXTR_BOOL(d, s->fNoAPToFinishMove)
125 EXTR_BOOL(d, s->fPausedMove)
126 EXTR_BOOL(d, s->fUIdeadMerc)
127 EXTR_SKIP(d, 1)
128 EXTR_BOOL(d, s->fUICloseMerc)
129 EXTR_SKIP(d, 5)
130 EXTR_I32(d, s->UpdateCounter)
131 EXTR_I32(d, s->DamageCounter)
132 EXTR_SKIP_I32(d)
133 EXTR_SKIP(d, 4)
134 EXTR_I32(d, s->AICounter)
135 EXTR_I32(d, s->FadeCounter)
136 EXTR_U8(d, s->ubSkillTrait1)
137 EXTR_U8(d, s->ubSkillTrait2)
138 EXTR_SKIP(d, 6)
139 EXTR_I8(d, s->bDexterity)
140 EXTR_I8(d, s->bWisdom)
141 EXTR_SKIP_I16(d)
142 EXTR_SOLDIER(d, s->attacker)
143 EXTR_SOLDIER(d, s->previous_attacker)
144 EXTR_BOOL(d, s->fTurnInProgress)
145 EXTR_BOOL(d, s->fIntendedTarget)
146 EXTR_BOOL(d, s->fPauseAllAnimation)
147 EXTR_I8(d, s->bExpLevel)
148 EXTR_I16(d, s->sInsertionGridNo)
149 EXTR_BOOL(d, s->fContinueMoveAfterStanceChange)
150 EXTR_SKIP(d, 15)
151 EXTR_I8(d, s->bLife)
152 EXTR_U8(d, s->bSide)
153 EXTR_SKIP(d, 1)
154 EXTR_I8(d, s->bNewOppCnt)
155 EXTR_SKIP(d, 2)
156 EXTR_U16(d, s->usAniCode)
157 EXTR_U16(d, s->usAniFrame)
158 EXTR_I16(d, s->sAniDelay)
159 EXTR_I8(d, s->bAgility)
160 EXTR_SKIP(d, 1)
161 EXTR_I16(d, s->sDelayedMovementCauseGridNo)
162 EXTR_I16(d, s->sReservedMovementGridNo)
163 EXTR_I8(d, s->bStrength)
164 EXTR_SKIP(d, 1)
165 EXTR_I16(d, s->sTargetGridNo)
166 EXTR_I8(d, s->bTargetLevel)
167 EXTR_I8(d, s->bTargetCubeLevel)
168 EXTR_I16(d, s->sLastTarget)
169 EXTR_I8(d, s->bTilesMoved)
170 EXTR_I8(d, s->bLeadership)
171 EXTR_FLOAT(d, s->dNextBleed)
172 EXTR_BOOL(d, s->fWarnedAboutBleeding)
173 EXTR_BOOL(d, s->fDyingComment)
174 EXTR_U8(d, s->ubTilesMovedPerRTBreathUpdate)
175 EXTR_SKIP(d, 1)
176 EXTR_U16(d, s->usLastMovementAnimPerRTBreathUpdate)
177 EXTR_BOOL(d, s->fTurningToShoot)
178 EXTR_SKIP(d, 1)
179 EXTR_BOOL(d, s->fTurningUntilDone)
180 EXTR_BOOL(d, s->fGettingHit)
181 EXTR_BOOL(d, s->fInNonintAnim)
182 EXTR_BOOL(d, s->fFlashLocator)
183 EXTR_I16(d, s->sLocatorFrame)
184 EXTR_BOOL(d, s->fShowLocator)
185 EXTR_BOOL(d, s->fFlashPortrait)
186 EXTR_I8(d, s->bMechanical)
187 EXTR_I8(d, s->bLifeMax)
188 EXTR_SKIP(d, 6)
189 s->HeadPal = d.readUTF8(PaletteRepID_LENGTH, ST::substitute_invalid);
190 s->PantsPal = d.readUTF8(PaletteRepID_LENGTH, ST::substitute_invalid);
191 s->VestPal = d.readUTF8(PaletteRepID_LENGTH, ST::substitute_invalid);
192 s->SkinPal = d.readUTF8(PaletteRepID_LENGTH, ST::substitute_invalid);
193 EXTR_SKIP(d, 328)
194 EXTR_I8(d, s->bMedical)
195 EXTR_BOOL(d, s->fBeginFade)
196 EXTR_U8(d, s->ubFadeLevel)
197 EXTR_U8(d, s->ubServiceCount)
198 EXTR_SOLDIER(d, s->service_partner)
199 EXTR_I8(d, s->bMarksmanship)
200 EXTR_I8(d, s->bExplosive)
201 EXTR_SKIP(d, 1)
202 EXTR_PTR(d, s->pThrowParams)
203 EXTR_BOOL(d, s->fTurningFromPronePosition)
204 EXTR_I8(d, s->bReverse)
205 EXTR_SKIP(d, 2)
206 EXTR_PTR(d, s->pLevelNode)
207 EXTR_SKIP(d, 8)
208 EXTR_I8(d, s->bDesiredDirection)
209 EXTR_SKIP(d, 1)
210 EXTR_I16(d, s->sDestXPos)
211 EXTR_I16(d, s->sDestYPos)
212 EXTR_SKIP(d, 2)
213 EXTR_I16(d, s->sDestination)
214 EXTR_I16(d, s->sFinalDestination)
215 EXTR_I8(d, s->bLevel)
216 EXTR_SKIP(d, 3)
217
218 // pathing info takes up 16 bit in the savegame but 8 bit in the engine
219 EXTR_U16A(d, usPathingData, lengthof(usPathingData))
220 EXTR_U16(d, usPathDataSize)
221 EXTR_U16(d, usPathIndex)
222 for (UINT8 i = 0; i < usPathDataSize && i < MAX_PATH_LIST_SIZE; i++) {
223 s->ubPathingData[i] = (UINT8)usPathingData[i];
224 }
225 s->ubPathDataSize = (UINT8)usPathDataSize;
226 s->ubPathIndex = (UINT8)usPathIndex;
227
228 EXTR_I16(d, s->sBlackList)
229 EXTR_I8(d, s->bAimTime)
230 EXTR_I8(d, s->bShownAimTime)
231 EXTR_I8(d, s->bPathStored)
232 EXTR_I8(d, s->bHasKeys)
233 EXTR_SKIP(d, 18)
234 EXTR_U8(d, s->ubStrategicInsertionCode)
235 EXTR_SKIP(d, 1)
236 EXTR_U16(d, s->usStrategicInsertionData)
237 EXTR_SKIP(d, 8)
238 EXTR_I8(d, s->bMuzFlashCount)
239 EXTR_SKIP(d, 1)
240 EXTR_I16(d, s->sX)
241 EXTR_I16(d, s->sY)
242 EXTR_U16(d, s->usOldAniState)
243 EXTR_I16(d, s->sOldAniCode)
244 EXTR_I8(d, s->bBulletsLeft)
245 EXTR_U8(d, s->ubSuppressionPoints)
246 EXTR_U32(d, s->uiTimeOfLastRandomAction)
247 EXTR_SKIP(d, 2)
248 EXTR_I8A(d, s->bOppList, lengthof(s->bOppList))
249 EXTR_I8(d, s->bLastAction)
250 EXTR_I8(d, s->bAction)
251 EXTR_U16(d, s->usActionData)
252 EXTR_I8(d, s->bNextAction)
253 EXTR_SKIP(d, 1)
254 EXTR_U16(d, s->usNextActionData)
255 EXTR_I8(d, s->bActionInProgress)
256 EXTR_I8(d, s->bAlertStatus)
257 EXTR_I8(d, s->bOppCnt)
258 EXTR_I8(d, s->bNeutral)
259 EXTR_I8(d, s->bNewSituation)
260 EXTR_I8(d, s->bNextTargetLevel)
261 EXTR_I8(d, s->bOrders)
262 EXTR_I8(d, s->bAttitude)
263 EXTR_I8(d, s->bUnderFire)
264 EXTR_I8(d, s->bShock)
265 EXTR_SKIP(d, 1)
266 EXTR_I8(d, s->bBypassToGreen)
267 EXTR_SKIP(d, 1)
268 EXTR_I8(d, s->bDominantDir)
269 EXTR_I8(d, s->bPatrolCnt)
270 EXTR_I8(d, s->bNextPatrolPnt)
271 EXTR_I16A(d, s->usPatrolGrid, lengthof(s->usPatrolGrid))
272 EXTR_I16(d, s->sNoiseGridno)
273 EXTR_U8(d, s->ubNoiseVolume)
274 EXTR_I8(d, s->bLastAttackHit)
275 EXTR_SOLDIER(d, s->xrayed_by)
276 EXTR_SKIP(d, 1)
277 EXTR_FLOAT(d, s->dHeightAdjustment)
278 EXTR_I8(d, s->bMorale)
279 EXTR_I8(d, s->bTeamMoraleMod)
280 EXTR_I8(d, s->bTacticalMoraleMod)
281 EXTR_I8(d, s->bStrategicMoraleMod)
282 EXTR_I8(d, s->bAIMorale)
283 EXTR_U8(d, s->ubPendingAction)
284 EXTR_U8(d, s->ubPendingActionAnimCount)
285 EXTR_SKIP(d, 1)
286 EXTR_U32(d, s->uiPendingActionData1)
287 EXTR_I16(d, s->sPendingActionData2)
288 EXTR_I8(d, s->bPendingActionData3)
289 EXTR_I8(d, s->ubDoorHandleCode)
290 EXTR_U32(d, s->uiPendingActionData4)
291 EXTR_I8(d, s->bInterruptDuelPts)
292 EXTR_I8(d, s->bPassedLastInterrupt)
293 EXTR_I8(d, s->bIntStartAPs)
294 EXTR_I8(d, s->bMoved)
295 EXTR_I8(d, s->bHunting)
296 EXTR_SKIP(d, 1)
297 EXTR_U8(d, s->ubCaller)
298 EXTR_SKIP(d, 1)
299 EXTR_I16(d, s->sCallerGridNo)
300 EXTR_U8(d, s->bCallPriority)
301 EXTR_I8(d, s->bCallActedUpon)
302 EXTR_I8(d, s->bFrenzied)
303 EXTR_I8(d, s->bNormalSmell)
304 EXTR_I8(d, s->bMonsterSmell)
305 EXTR_I8(d, s->bMobility)
306 EXTR_SKIP(d, 1)
307 EXTR_I8(d, s->fAIFlags)
308 EXTR_BOOL(d, s->fDontChargeReadyAPs)
309 EXTR_SKIP(d, 1)
310 EXTR_U16(d, s->usAnimSurface)
311 EXTR_U16(d, s->sZLevel)
312 EXTR_BOOL(d, s->fPrevInWater)
313 EXTR_BOOL(d, s->fGoBackToAimAfterHit)
314 EXTR_I16(d, s->sWalkToAttackGridNo)
315 EXTR_I16(d, s->sWalkToAttackWalkToCost)
316 EXTR_SKIP(d, 7)
317 EXTR_BOOL(d, s->fForceShade)
318 EXTR_SKIP(d, 2)
319 EXTR_PTR(d, s->pForcedShade)
320 EXTR_I8(d, s->bDisplayDamageCount)
321 EXTR_I8(d, s->fDisplayDamage)
322 EXTR_I16(d, s->sDamage)
323 EXTR_I16(d, s->sDamageX)
324 EXTR_I16(d, s->sDamageY)
325 EXTR_SKIP(d, 1)
326 EXTR_I8(d, s->bDoBurst)
327 EXTR_I16(d, s->usUIMovementMode)
328 EXTR_SKIP(d, 1)
329 EXTR_BOOL(d, s->fUIMovementFast)
330 EXTR_SKIP(d, 2)
331 EXTR_I32(d, s->BlinkSelCounter)
332 EXTR_I32(d, s->PortraitFlashCounter)
333 EXTR_BOOL(d, s->fDeadSoundPlayed)
334 EXTR_U8(d, s->ubProfile)
335 EXTR_U8(d, s->ubQuoteRecord)
336 EXTR_U8(d, s->ubQuoteActionID)
337 EXTR_U8(d, s->ubBattleSoundID)
338 EXTR_BOOL(d, s->fClosePanel)
339 EXTR_BOOL(d, s->fClosePanelToDie)
340 EXTR_U8(d, s->ubClosePanelFrame)
341 EXTR_BOOL(d, s->fDeadPanel)
342 EXTR_U8(d, s->ubDeadPanelFrame)
343 EXTR_SKIP(d, 2)
344 EXTR_I16(d, s->sPanelFaceX)
345 EXTR_I16(d, s->sPanelFaceY)
346 EXTR_I8(d, s->bNumHitsThisTurn)
347 EXTR_SKIP(d, 1)
348 EXTR_U16(d, s->usQuoteSaidFlags)
349 EXTR_I8(d, s->fCloseCall)
350 EXTR_I8(d, s->bLastSkillCheck)
351 EXTR_I8(d, s->ubSkillCheckAttempts)
352 EXTR_SKIP(d, 1)
353 EXTR_I8(d, s->bStartFallDir)
354 EXTR_I8(d, s->fTryingToFall)
355 EXTR_U8(d, s->ubPendingDirection)
356 EXTR_SKIP(d, 1)
357 EXTR_U32(d, s->uiAnimSubFlags)
358 EXTR_U8(d, s->bAimShotLocation)
359 EXTR_U8(d, s->ubHitLocation)
360 EXTR_SKIP(d, 16)
361 EXTR_I16A(d, s->sSpreadLocations, lengthof(s->sSpreadLocations))
362 EXTR_BOOL(d, s->fDoSpread)
363 EXTR_SKIP(d, 1)
364 EXTR_I16(d, s->sStartGridNo)
365 EXTR_I16(d, s->sEndGridNo)
366 EXTR_I16(d, s->sForcastGridno)
367 EXTR_I16(d, s->sZLevelOverride)
368 EXTR_I8(d, s->bMovedPriorToInterrupt)
369 EXTR_SKIP(d, 3)
370 EXTR_I32(d, s->iEndofContractTime)
371 EXTR_I32(d, s->iStartContractTime)
372 EXTR_I32(d, s->iTotalContractLength)
373 EXTR_I32(d, s->iNextActionSpecialData)
374 EXTR_U8(d, s->ubWhatKindOfMercAmI)
375 EXTR_I8(d, s->bAssignment)
376 EXTR_SKIP(d, 1)
377 EXTR_BOOL(d, s->fForcedToStayAwake)
378 EXTR_I8(d, s->bTrainStat)
379 EXTR_SKIP(d, 1)
380 EXTR_I16(d, s->sSectorX)
381 EXTR_I16(d, s->sSectorY)
382 EXTR_I8(d, s->bSectorZ)
383 EXTR_SKIP(d, 1)
384 EXTR_I32(d, s->iVehicleId)
385 EXTR_PTR(d, s->pMercPath)
386 EXTR_U8(d, s->fHitByGasFlags)
387 EXTR_SKIP(d, 1)
388 EXTR_U16(d, s->usMedicalDeposit)
389 EXTR_U16(d, s->usLifeInsurance)
390 EXTR_SKIP(d, 26)
391 EXTR_I32(d, s->iStartOfInsuranceContract)
392 EXTR_U32(d, s->uiLastAssignmentChangeMin)
393 EXTR_I32(d, s->iTotalLengthOfInsuranceContract)
394 EXTR_U8(d, s->ubSoldierClass)
395 EXTR_U8(d, s->ubAPsLostToSuppression)
396 EXTR_BOOL(d, s->fChangingStanceDueToSuppression)
397 EXTR_SOLDIER(d, s->suppressor)
398 EXTR_SKIP(d, 4)
399 EXTR_U8(d, s->ubCivilianGroup)
400 EXTR_SKIP(d, 3)
401 EXTR_U32(d, s->uiChangeLevelTime)
402 EXTR_U32(d, s->uiChangeHealthTime)
403 EXTR_U32(d, s->uiChangeStrengthTime)
404 EXTR_U32(d, s->uiChangeDexterityTime)
405 EXTR_U32(d, s->uiChangeAgilityTime)
406 EXTR_U32(d, s->uiChangeWisdomTime)
407 EXTR_U32(d, s->uiChangeLeadershipTime)
408 EXTR_U32(d, s->uiChangeMarksmanshipTime)
409 EXTR_U32(d, s->uiChangeExplosivesTime)
410 EXTR_U32(d, s->uiChangeMedicalTime)
411 EXTR_U32(d, s->uiChangeMechanicalTime)
412 EXTR_U32(d, s->uiUniqueSoldierIdValue)
413 EXTR_I8(d, s->bBeingAttackedCount)
414 EXTR_I8A(d, s->bNewItemCount, lengthof(s->bNewItemCount))
415 EXTR_I8A(d, s->bNewItemCycleCount, lengthof(s->bNewItemCycleCount))
416 EXTR_BOOL(d, s->fCheckForNewlyAddedItems)
417 EXTR_I8(d, s->bEndDoorOpenCode)
418 EXTR_U8(d, s->ubScheduleID)
419 EXTR_I16(d, s->sEndDoorOpenCodeData)
420 EXTR_I32(d, s->NextTileCounter)
421 EXTR_BOOL(d, s->fBlockedByAnotherMerc)
422 EXTR_I8(d, s->bBlockedByAnotherMercDirection)
423 EXTR_U16(d, s->usAttackingWeapon)
424 EXTR_I8(d, s->bWeaponMode)
425 EXTR_SOLDIER(d, s->target)
426 EXTR_I8(d, s->bAIScheduleProgress)
427 EXTR_SKIP(d, 1)
428 EXTR_I16(d, s->sOffWorldGridNo)
429 EXTR_SKIP(d, 2)
430 EXTR_PTR(d, s->pAniTile)
431 EXTR_I8(d, s->bCamo)
432 EXTR_SKIP(d, 1)
433 EXTR_I16(d, s->sAbsoluteFinalDestination)
434 EXTR_U8(d, s->ubHiResDirection)
435 EXTR_SKIP(d, 1)
436 EXTR_U8(d, s->ubLastFootPrintSound)
437 EXTR_I8(d, s->bVehicleID)
438 EXTR_I8(d, s->fPastXDest)
439 EXTR_I8(d, s->fPastYDest)
440 EXTR_I8(d, s->bMovementDirection)
441 EXTR_SKIP(d, 1)
442 EXTR_I16(d, s->sOldGridNo)
443 EXTR_U16(d, s->usDontUpdateNewGridNoOnMoveAnimChange)
444 EXTR_I16(d, s->sBoundingBoxWidth)
445 EXTR_I16(d, s->sBoundingBoxHeight)
446 EXTR_I16(d, s->sBoundingBoxOffsetX)
447 EXTR_I16(d, s->sBoundingBoxOffsetY)
448 EXTR_U32(d, s->uiTimeSameBattleSndDone)
449 EXTR_I8(d, s->bOldBattleSnd)
450 EXTR_SKIP(d, 1)
451 EXTR_BOOL(d, s->fContractPriceHasIncreased)
452 EXTR_SKIP(d, 1)
453 EXTR_U32(d, s->uiBurstSoundID)
454 EXTR_BOOL(d, s->fFixingSAMSite)
455 EXTR_BOOL(d, s->fFixingRobot)
456 EXTR_I8(d, s->bSlotItemTakenFrom)
457 EXTR_BOOL(d, s->fSignedAnotherContract)
458 EXTR_SOLDIER(d, s->auto_bandaging_medic)
459 EXTR_BOOL(d, s->fDontChargeTurningAPs)
460 EXTR_SOLDIER(d, s->robot_remote_holder)
461 EXTR_SKIP(d, 1)
462 EXTR_U32(d, s->uiTimeOfLastContractUpdate)
463 EXTR_I8(d, s->bTypeOfLastContract)
464 EXTR_I8(d, s->bTurnsCollapsed)
465 EXTR_I8(d, s->bSleepDrugCounter)
466 EXTR_U8(d, s->ubMilitiaKills)
467 EXTR_I8A(d, s->bFutureDrugEffect, lengthof(s->bFutureDrugEffect))
468 EXTR_I8A(d, s->bDrugEffectRate, lengthof(s->bDrugEffectRate))
469 EXTR_I8A(d, s->bDrugEffect, lengthof(s->bDrugEffect))
470 EXTR_I8A(d, s->bDrugSideEffectRate, lengthof(s->bDrugSideEffectRate))
471 EXTR_I8A(d, s->bDrugSideEffect, lengthof(s->bDrugSideEffect))
472 EXTR_SKIP(d, 2)
473 EXTR_I8(d, s->bBlindedCounter)
474 EXTR_BOOL(d, s->fMercCollapsedFlag)
475 EXTR_BOOL(d, s->fDoneAssignmentAndNothingToDoFlag)
476 EXTR_BOOL(d, s->fMercAsleep)
477 EXTR_BOOL(d, s->fDontChargeAPsForStanceChange)
478 EXTR_SKIP(d, 2)
479 EXTR_U8(d, s->ubTurnsUntilCanSayHeardNoise)
480 EXTR_U16(d, s->usQuoteSaidExtFlags)
481 EXTR_U16(d, s->sContPathLocation)
482 EXTR_I8(d, s->bGoodContPath)
483 EXTR_SKIP(d, 1)
484 EXTR_I8(d, s->bNoiseLevel)
485 EXTR_I8(d, s->bRegenerationCounter)
486 EXTR_I8(d, s->bRegenBoostersUsedToday)
487 EXTR_I8(d, s->bNumPelletsHitBy)
488 EXTR_I16(d, s->sSkillCheckGridNo)
489 EXTR_U8(d, s->ubLastEnemyCycledID)
490 EXTR_U8(d, s->ubPrevSectorID)
491 EXTR_U8(d, s->ubNumTilesMovesSinceLastForget)
492 EXTR_I8(d, s->bTurningIncrement)
493 EXTR_U32(d, s->uiBattleSoundID)
494 EXTR_BOOL(d, s->fSoldierWasMoving)
495 EXTR_BOOL(d, s->fSayAmmoQuotePending)
496 EXTR_U16(d, s->usValueGoneUp)
497 EXTR_U8(d, s->ubNumLocateCycles)
498 EXTR_U8(d, s->ubDelayedMovementFlags)
499 EXTR_BOOL(d, s->fMuzzleFlash)
500 EXTR_SOLDIER(d, s->CTGTTarget)
501 EXTR_I32(d, s->PanelAnimateCounter)
502 UINT32 checksum;
503 EXTR_U32(d, checksum)
504 EXTR_I8(d, s->bCurrentCivQuote)
505 EXTR_I8(d, s->bCurrentCivQuoteDelta)
506 EXTR_U8(d, s->ubMiscSoldierFlags)
507 EXTR_U8(d, s->ubReasonCantFinishMove)
508 EXTR_I16(d, s->sLocationOfFadeStart)
509 EXTR_U8(d, s->bUseExitGridForReentryDirection)
510 EXTR_SKIP(d, 1)
511 EXTR_U32(d, s->uiTimeSinceLastSpoke)
512 EXTR_U8(d, s->ubContractRenewalQuoteCode)
513 EXTR_SKIP(d, 1)
514 EXTR_I16(d, s->sPreTraversalGridNo)
515 EXTR_U32(d, s->uiXRayActivatedTime)
516 EXTR_I8(d, s->bTurningFromUI)
517 EXTR_I8(d, s->bPendingActionData5)
518 EXTR_I8(d, s->bDelayedStrategicMoraleMod)
519 EXTR_U8(d, s->ubDoorOpeningNoise)
520 EXTR_SKIP(d, 4)
521 EXTR_U8(d, s->ubLeaveHistoryCode)
522 EXTR_BOOL(d, s->fDontUnsetLastTargetFromTurn)
523 EXTR_I8(d, s->bOverrideMoveSpeed)
524 EXTR_BOOL(d, s->fUseMoverrideMoveSpeed)
525 EXTR_U32(d, s->uiTimeSoldierWillArrive)
526 EXTR_SKIP(d, 1)
527 EXTR_BOOL(d, s->fUseLandingZoneForArrival)
528 EXTR_BOOL(d, s->fFallClockwise)
529 EXTR_I8(d, s->bVehicleUnderRepairID)
530 EXTR_I32(d, s->iTimeCanSignElsewhere)
531 EXTR_I8(d, s->bHospitalPriceModifier)
532 EXTR_SKIP(d, 3)
533 EXTR_U32(d, s->uiStartTimeOfInsuranceContract)
534 EXTR_BOOL(d, s->fRTInNonintAnim)
535 EXTR_BOOL(d, s->fDoingExternalDeath)
536 EXTR_I8(d, s->bCorpseQuoteTolerance)
537 EXTR_SKIP(d, 1)
538 EXTR_I32(d, s->iPositionSndID)
539 EXTR_U32(d, s->uiTuringSoundID)
540 EXTR_U8(d, s->ubLastDamageReason)
541 EXTR_BOOL(d, s->fComplainedThatTired)
542 EXTR_I16A(d, s->sLastTwoLocations, lengthof(s->sLastTwoLocations))
543 EXTR_SKIP(d, 2)
544 EXTR_I32(d, s->uiTimeSinceLastBleedGrunt)
545 EXTR_SOLDIER(d, s->next_to_previous_attacker)
546 EXTR_SKIP(d, 39)
547 if(stracLinuxFormat)
548 {
549 Assert(d.getConsumed() == 2352);
550 }
551 else
552 {
553 Assert(d.getConsumed() == 2328);
554 }
555
556 if (checksum != MercChecksum(*s))
557 {
558 throw std::runtime_error("soldier checksum mismatch");
559 }
560 }
561
562
InjectSoldierType(BYTE * const data,const SOLDIERTYPE * const s)563 void InjectSoldierType(BYTE* const data, const SOLDIERTYPE* const s)
564 {
565 UINT16 usPathingData[ MAX_PATH_LIST_SIZE ];
566 UINT16 usPathDataSize;
567 UINT16 usPathIndex;
568
569 DataWriter d{data};
570 INJ_U8(d, s->ubID)
571 INJ_SKIP(d, 1)
572 INJ_U8(d, s->ubBodyType)
573 INJ_I8(d, s->bActionPoints)
574 INJ_I8(d, s->bInitialActionPoints)
575 INJ_SKIP(d, 3)
576 INJ_U32(d, s->uiStatusFlags)
577 CFOR_EACH_SOLDIER_INV_SLOT(i, *s)
578 {
579 InjectObject(d, i);
580 }
581 INJ_PTR(d, s->pTempObject)
582 INJ_PTR(d, s->pKeyRing)
583 INJ_I8(d, s->bOldLife)
584 INJ_U8(d, s->bInSector)
585 INJ_I8(d, s->bFlashPortraitFrame)
586 INJ_SKIP(d, 1)
587 INJ_I16(d, s->sFractLife)
588 INJ_I8(d, s->bBleeding)
589 INJ_I8(d, s->bBreath)
590 INJ_I8(d, s->bBreathMax)
591 INJ_I8(d, s->bStealthMode)
592 INJ_I16(d, s->sBreathRed)
593 INJ_BOOL(d, s->fDelayedMovement)
594 INJ_SKIP(d, 1)
595 INJ_U8(d, s->ubWaitActionToDo)
596 INJ_SKIP(d, 1)
597 INJ_I8(d, s->ubInsertionDirection)
598 INJ_SKIP(d, 1)
599 INJ_SOLDIER(d, s->opponent)
600 INJ_I8(d, s->bLastRenderVisibleValue)
601 INJ_SKIP(d, 1)
602 INJ_U8(d, s->ubAttackingHand)
603 INJ_SKIP(d, 2)
604 INJ_I16(d, s->sWeightCarriedAtTurnStart)
605 d.writeUTF16(s->name, SOLDIERTYPE_NAME_LENGTH);
606 INJ_I8(d, s->bVisible)
607 INJ_I8(d, s->bActive)
608 INJ_I8(d, s->bTeam)
609 INJ_U8(d, s->ubGroupID)
610 INJ_BOOL(d, s->fBetweenSectors)
611 INJ_U8(d, s->ubMovementNoiseHeard)
612 INJ_FLOAT(d, s->dXPos)
613 INJ_FLOAT(d, s->dYPos)
614 INJ_SKIP(d, 8)
615 INJ_I16(d, s->sInitialGridNo)
616 INJ_I16(d, s->sGridNo)
617 INJ_I8(d, s->bDirection)
618 INJ_SKIP(d, 1)
619 INJ_I16(d, s->sHeightAdjustment)
620 INJ_I16(d, s->sDesiredHeight)
621 INJ_I16(d, s->sTempNewGridNo)
622 INJ_SKIP(d, 2)
623 INJ_I8(d, s->bOverTerrainType)
624 INJ_SKIP(d, 1)
625 INJ_I8(d, s->bCollapsed)
626 INJ_I8(d, s->bBreathCollapsed)
627 INJ_U8(d, s->ubDesiredHeight)
628 INJ_SKIP(d, 1)
629 INJ_U16(d, s->usPendingAnimation)
630 INJ_U8(d, s->ubPendingStanceChange)
631 INJ_SKIP(d, 1)
632 INJ_U16(d, s->usAnimState)
633 INJ_BOOL(d, s->fNoAPToFinishMove)
634 INJ_BOOL(d, s->fPausedMove)
635 INJ_BOOL(d, s->fUIdeadMerc)
636 INJ_SKIP(d, 1)
637 INJ_BOOL(d, s->fUICloseMerc)
638 INJ_SKIP(d, 5)
639 INJ_I32(d, s->UpdateCounter)
640 INJ_I32(d, s->DamageCounter)
641 INJ_SKIP_I32(d)
642 INJ_SKIP(d, 4)
643 INJ_I32(d, s->AICounter)
644 INJ_I32(d, s->FadeCounter)
645 INJ_U8(d, s->ubSkillTrait1)
646 INJ_U8(d, s->ubSkillTrait2)
647 INJ_SKIP(d, 6)
648 INJ_I8(d, s->bDexterity)
649 INJ_I8(d, s->bWisdom)
650 INJ_SKIP_I16(d)
651 INJ_SOLDIER(d, s->attacker)
652 INJ_SOLDIER(d, s->previous_attacker)
653 INJ_BOOL(d, s->fTurnInProgress)
654 INJ_BOOL(d, s->fIntendedTarget)
655 INJ_BOOL(d, s->fPauseAllAnimation)
656 INJ_I8(d, s->bExpLevel)
657 INJ_I16(d, s->sInsertionGridNo)
658 INJ_BOOL(d, s->fContinueMoveAfterStanceChange)
659 INJ_SKIP(d, 15)
660 INJ_I8(d, s->bLife)
661 INJ_U8(d, s->bSide)
662 INJ_SKIP(d, 1)
663 INJ_I8(d, s->bNewOppCnt)
664 INJ_SKIP(d, 2)
665 INJ_U16(d, s->usAniCode)
666 INJ_U16(d, s->usAniFrame)
667 INJ_I16(d, s->sAniDelay)
668 INJ_I8(d, s->bAgility)
669 INJ_SKIP(d, 1)
670 INJ_I16(d, s->sDelayedMovementCauseGridNo)
671 INJ_I16(d, s->sReservedMovementGridNo)
672 INJ_I8(d, s->bStrength)
673 INJ_SKIP(d, 1)
674 INJ_I16(d, s->sTargetGridNo)
675 INJ_I8(d, s->bTargetLevel)
676 INJ_I8(d, s->bTargetCubeLevel)
677 INJ_I16(d, s->sLastTarget)
678 INJ_I8(d, s->bTilesMoved)
679 INJ_I8(d, s->bLeadership)
680 INJ_FLOAT(d, s->dNextBleed)
681 INJ_BOOL(d, s->fWarnedAboutBleeding)
682 INJ_BOOL(d, s->fDyingComment)
683 INJ_U8(d, s->ubTilesMovedPerRTBreathUpdate)
684 INJ_SKIP(d, 1)
685 INJ_U16(d, s->usLastMovementAnimPerRTBreathUpdate)
686 INJ_BOOL(d, s->fTurningToShoot)
687 INJ_SKIP(d, 1)
688 INJ_BOOL(d, s->fTurningUntilDone)
689 INJ_BOOL(d, s->fGettingHit)
690 INJ_BOOL(d, s->fInNonintAnim)
691 INJ_BOOL(d, s->fFlashLocator)
692 INJ_I16(d, s->sLocatorFrame)
693 INJ_BOOL(d, s->fShowLocator)
694 INJ_BOOL(d, s->fFlashPortrait)
695 INJ_I8(d, s->bMechanical)
696 INJ_I8(d, s->bLifeMax)
697 INJ_SKIP(d, 6)
698 d.writeUTF8(s->HeadPal, PaletteRepID_LENGTH);
699 d.writeUTF8(s->PantsPal, PaletteRepID_LENGTH);
700 d.writeUTF8(s->VestPal, PaletteRepID_LENGTH);
701 d.writeUTF8(s->SkinPal, PaletteRepID_LENGTH);
702 INJ_SKIP(d, 328)
703 INJ_I8(d, s->bMedical)
704 INJ_BOOL(d, s->fBeginFade)
705 INJ_U8(d, s->ubFadeLevel)
706 INJ_U8(d, s->ubServiceCount)
707 INJ_SOLDIER(d, s->service_partner)
708 INJ_I8(d, s->bMarksmanship)
709 INJ_I8(d, s->bExplosive)
710 INJ_SKIP(d, 1)
711 INJ_PTR(d, s->pThrowParams)
712 INJ_BOOL(d, s->fTurningFromPronePosition)
713 INJ_I8(d, s->bReverse)
714 INJ_SKIP(d, 2)
715 INJ_PTR(d, s->pLevelNode)
716 INJ_SKIP(d, 8)
717 INJ_I8(d, s->bDesiredDirection)
718 INJ_SKIP(d, 1)
719 INJ_I16(d, s->sDestXPos)
720 INJ_I16(d, s->sDestYPos)
721 INJ_SKIP(d, 2)
722 INJ_I16(d, s->sDestination)
723 INJ_I16(d, s->sFinalDestination)
724 INJ_I8(d, s->bLevel)
725 INJ_SKIP(d, 3)
726
727 // pathing info takes up 16 bit in the savegame but 8 bit in the engine
728 usPathDataSize = s->ubPathDataSize > MAX_PATH_LIST_SIZE ? (UINT16)MAX_PATH_LIST_SIZE : (UINT16)s->ubPathDataSize;
729 usPathIndex = (UINT16)s->ubPathIndex;
730 std::fill_n(usPathingData, MAX_PATH_LIST_SIZE, 0);
731 for (UINT8 i = 0; i < usPathDataSize; i++) {
732 usPathingData[i] = (UINT16)s->ubPathingData[i];
733 }
734 INJ_U16A(d, usPathingData, lengthof(usPathingData))
735 INJ_U16(d, usPathDataSize)
736 INJ_U16(d, usPathIndex)
737
738 INJ_I16(d, s->sBlackList)
739 INJ_I8(d, s->bAimTime)
740 INJ_I8(d, s->bShownAimTime)
741 INJ_I8(d, s->bPathStored)
742 INJ_I8(d, s->bHasKeys)
743 INJ_SKIP(d, 18)
744 INJ_U8(d, s->ubStrategicInsertionCode)
745 INJ_SKIP(d, 1)
746 INJ_U16(d, s->usStrategicInsertionData)
747 INJ_SKIP(d, 8)
748 INJ_I8(d, s->bMuzFlashCount)
749 INJ_SKIP(d, 1)
750 INJ_I16(d, s->sX)
751 INJ_I16(d, s->sY)
752 INJ_U16(d, s->usOldAniState)
753 INJ_I16(d, s->sOldAniCode)
754 INJ_I8(d, s->bBulletsLeft)
755 INJ_U8(d, s->ubSuppressionPoints)
756 INJ_U32(d, s->uiTimeOfLastRandomAction)
757 INJ_SKIP(d, 2)
758 INJ_I8A(d, s->bOppList, lengthof(s->bOppList))
759 INJ_I8(d, s->bLastAction)
760 INJ_I8(d, s->bAction)
761 INJ_U16(d, s->usActionData)
762 INJ_I8(d, s->bNextAction)
763 INJ_SKIP(d, 1)
764 INJ_U16(d, s->usNextActionData)
765 INJ_I8(d, s->bActionInProgress)
766 INJ_I8(d, s->bAlertStatus)
767 INJ_I8(d, s->bOppCnt)
768 INJ_I8(d, s->bNeutral)
769 INJ_I8(d, s->bNewSituation)
770 INJ_I8(d, s->bNextTargetLevel)
771 INJ_I8(d, s->bOrders)
772 INJ_I8(d, s->bAttitude)
773 INJ_I8(d, s->bUnderFire)
774 INJ_I8(d, s->bShock)
775 INJ_SKIP(d, 1)
776 INJ_I8(d, s->bBypassToGreen)
777 INJ_SKIP(d, 1)
778 INJ_I8(d, s->bDominantDir)
779 INJ_I8(d, s->bPatrolCnt)
780 INJ_I8(d, s->bNextPatrolPnt)
781 INJ_I16A(d, s->usPatrolGrid, lengthof(s->usPatrolGrid))
782 INJ_I16(d, s->sNoiseGridno)
783 INJ_U8(d, s->ubNoiseVolume)
784 INJ_I8(d, s->bLastAttackHit)
785 INJ_SOLDIER(d, s->xrayed_by)
786 INJ_SKIP(d, 1)
787 INJ_FLOAT(d, s->dHeightAdjustment)
788 INJ_I8(d, s->bMorale)
789 INJ_I8(d, s->bTeamMoraleMod)
790 INJ_I8(d, s->bTacticalMoraleMod)
791 INJ_I8(d, s->bStrategicMoraleMod)
792 INJ_I8(d, s->bAIMorale)
793 INJ_U8(d, s->ubPendingAction)
794 INJ_U8(d, s->ubPendingActionAnimCount)
795 INJ_SKIP(d, 1)
796 INJ_U32(d, s->uiPendingActionData1)
797 INJ_I16(d, s->sPendingActionData2)
798 INJ_I8(d, s->bPendingActionData3)
799 INJ_I8(d, s->ubDoorHandleCode)
800 INJ_U32(d, s->uiPendingActionData4)
801 INJ_I8(d, s->bInterruptDuelPts)
802 INJ_I8(d, s->bPassedLastInterrupt)
803 INJ_I8(d, s->bIntStartAPs)
804 INJ_I8(d, s->bMoved)
805 INJ_I8(d, s->bHunting)
806 INJ_SKIP(d, 1)
807 INJ_U8(d, s->ubCaller)
808 INJ_SKIP(d, 1)
809 INJ_I16(d, s->sCallerGridNo)
810 INJ_U8(d, s->bCallPriority)
811 INJ_I8(d, s->bCallActedUpon)
812 INJ_I8(d, s->bFrenzied)
813 INJ_I8(d, s->bNormalSmell)
814 INJ_I8(d, s->bMonsterSmell)
815 INJ_I8(d, s->bMobility)
816 INJ_SKIP(d, 1)
817 INJ_I8(d, s->fAIFlags)
818 INJ_BOOL(d, s->fDontChargeReadyAPs)
819 INJ_SKIP(d, 1)
820 INJ_U16(d, s->usAnimSurface)
821 INJ_U16(d, s->sZLevel)
822 INJ_BOOL(d, s->fPrevInWater)
823 INJ_BOOL(d, s->fGoBackToAimAfterHit)
824 INJ_I16(d, s->sWalkToAttackGridNo)
825 INJ_I16(d, s->sWalkToAttackWalkToCost)
826 INJ_SKIP(d, 7)
827 INJ_BOOL(d, s->fForceShade)
828 INJ_SKIP(d, 2)
829 INJ_PTR(d, s->pForcedShade)
830 INJ_I8(d, s->bDisplayDamageCount)
831 INJ_I8(d, s->fDisplayDamage)
832 INJ_I16(d, s->sDamage)
833 INJ_I16(d, s->sDamageX)
834 INJ_I16(d, s->sDamageY)
835 INJ_SKIP(d, 1)
836 INJ_I8(d, s->bDoBurst)
837 INJ_I16(d, s->usUIMovementMode)
838 INJ_SKIP(d, 1)
839 INJ_BOOL(d, s->fUIMovementFast)
840 INJ_SKIP(d, 2)
841 INJ_I32(d, s->BlinkSelCounter)
842 INJ_I32(d, s->PortraitFlashCounter)
843 INJ_BOOL(d, s->fDeadSoundPlayed)
844 INJ_U8(d, s->ubProfile)
845 INJ_U8(d, s->ubQuoteRecord)
846 INJ_U8(d, s->ubQuoteActionID)
847 INJ_U8(d, s->ubBattleSoundID)
848 INJ_BOOL(d, s->fClosePanel)
849 INJ_BOOL(d, s->fClosePanelToDie)
850 INJ_U8(d, s->ubClosePanelFrame)
851 INJ_BOOL(d, s->fDeadPanel)
852 INJ_U8(d, s->ubDeadPanelFrame)
853 INJ_SKIP(d, 2)
854 INJ_I16(d, s->sPanelFaceX)
855 INJ_I16(d, s->sPanelFaceY)
856 INJ_I8(d, s->bNumHitsThisTurn)
857 INJ_SKIP(d, 1)
858 INJ_U16(d, s->usQuoteSaidFlags)
859 INJ_I8(d, s->fCloseCall)
860 INJ_I8(d, s->bLastSkillCheck)
861 INJ_I8(d, s->ubSkillCheckAttempts)
862 INJ_SKIP(d, 1)
863 INJ_I8(d, s->bStartFallDir)
864 INJ_I8(d, s->fTryingToFall)
865 INJ_U8(d, s->ubPendingDirection)
866 INJ_SKIP(d, 1)
867 INJ_U32(d, s->uiAnimSubFlags)
868 INJ_U8(d, s->bAimShotLocation)
869 INJ_U8(d, s->ubHitLocation)
870 INJ_SKIP(d, 16)
871 INJ_I16A(d, s->sSpreadLocations, lengthof(s->sSpreadLocations))
872 INJ_BOOL(d, s->fDoSpread)
873 INJ_SKIP(d, 1)
874 INJ_I16(d, s->sStartGridNo)
875 INJ_I16(d, s->sEndGridNo)
876 INJ_I16(d, s->sForcastGridno)
877 INJ_I16(d, s->sZLevelOverride)
878 INJ_I8(d, s->bMovedPriorToInterrupt)
879 INJ_SKIP(d, 3)
880 INJ_I32(d, s->iEndofContractTime)
881 INJ_I32(d, s->iStartContractTime)
882 INJ_I32(d, s->iTotalContractLength)
883 INJ_I32(d, s->iNextActionSpecialData)
884 INJ_U8(d, s->ubWhatKindOfMercAmI)
885 INJ_I8(d, s->bAssignment)
886 INJ_SKIP(d, 1)
887 INJ_BOOL(d, s->fForcedToStayAwake)
888 INJ_I8(d, s->bTrainStat)
889 INJ_SKIP(d, 1)
890 INJ_I16(d, s->sSectorX)
891 INJ_I16(d, s->sSectorY)
892 INJ_I8(d, s->bSectorZ)
893 INJ_SKIP(d, 1)
894 INJ_I32(d, s->iVehicleId)
895 INJ_PTR(d, s->pMercPath)
896 INJ_U8(d, s->fHitByGasFlags)
897 INJ_SKIP(d, 1)
898 INJ_U16(d, s->usMedicalDeposit)
899 INJ_U16(d, s->usLifeInsurance)
900 INJ_SKIP(d, 26)
901 INJ_I32(d, s->iStartOfInsuranceContract)
902 INJ_U32(d, s->uiLastAssignmentChangeMin)
903 INJ_I32(d, s->iTotalLengthOfInsuranceContract)
904 INJ_U8(d, s->ubSoldierClass)
905 INJ_U8(d, s->ubAPsLostToSuppression)
906 INJ_BOOL(d, s->fChangingStanceDueToSuppression)
907 INJ_SOLDIER(d, s->suppressor)
908 INJ_SKIP(d, 4)
909 INJ_U8(d, s->ubCivilianGroup)
910 INJ_SKIP(d, 3)
911 INJ_U32(d, s->uiChangeLevelTime)
912 INJ_U32(d, s->uiChangeHealthTime)
913 INJ_U32(d, s->uiChangeStrengthTime)
914 INJ_U32(d, s->uiChangeDexterityTime)
915 INJ_U32(d, s->uiChangeAgilityTime)
916 INJ_U32(d, s->uiChangeWisdomTime)
917 INJ_U32(d, s->uiChangeLeadershipTime)
918 INJ_U32(d, s->uiChangeMarksmanshipTime)
919 INJ_U32(d, s->uiChangeExplosivesTime)
920 INJ_U32(d, s->uiChangeMedicalTime)
921 INJ_U32(d, s->uiChangeMechanicalTime)
922 INJ_U32(d, s->uiUniqueSoldierIdValue)
923 INJ_I8(d, s->bBeingAttackedCount)
924 INJ_I8A(d, s->bNewItemCount, lengthof(s->bNewItemCount))
925 INJ_I8A(d, s->bNewItemCycleCount, lengthof(s->bNewItemCycleCount))
926 INJ_BOOL(d, s->fCheckForNewlyAddedItems)
927 INJ_I8(d, s->bEndDoorOpenCode)
928 INJ_U8(d, s->ubScheduleID)
929 INJ_I16(d, s->sEndDoorOpenCodeData)
930 INJ_I32(d, s->NextTileCounter)
931 INJ_BOOL(d, s->fBlockedByAnotherMerc)
932 INJ_I8(d, s->bBlockedByAnotherMercDirection)
933 INJ_U16(d, s->usAttackingWeapon)
934 INJ_I8(d, s->bWeaponMode)
935 INJ_SOLDIER(d, s->target)
936 INJ_I8(d, s->bAIScheduleProgress)
937 INJ_SKIP(d, 1)
938 INJ_I16(d, s->sOffWorldGridNo)
939 INJ_SKIP(d, 2)
940 INJ_PTR(d, s->pAniTile)
941 INJ_I8(d, s->bCamo)
942 INJ_SKIP(d, 1)
943 INJ_I16(d, s->sAbsoluteFinalDestination)
944 INJ_U8(d, s->ubHiResDirection)
945 INJ_SKIP(d, 1)
946 INJ_U8(d, s->ubLastFootPrintSound)
947 INJ_I8(d, s->bVehicleID)
948 INJ_I8(d, s->fPastXDest)
949 INJ_I8(d, s->fPastYDest)
950 INJ_I8(d, s->bMovementDirection)
951 INJ_SKIP(d, 1)
952 INJ_I16(d, s->sOldGridNo)
953 INJ_U16(d, s->usDontUpdateNewGridNoOnMoveAnimChange)
954 INJ_I16(d, s->sBoundingBoxWidth)
955 INJ_I16(d, s->sBoundingBoxHeight)
956 INJ_I16(d, s->sBoundingBoxOffsetX)
957 INJ_I16(d, s->sBoundingBoxOffsetY)
958 INJ_U32(d, s->uiTimeSameBattleSndDone)
959 INJ_I8(d, s->bOldBattleSnd)
960 INJ_SKIP(d, 1)
961 INJ_BOOL(d, s->fContractPriceHasIncreased)
962 INJ_SKIP(d, 1)
963 INJ_U32(d, s->uiBurstSoundID)
964 INJ_BOOL(d, s->fFixingSAMSite)
965 INJ_BOOL(d, s->fFixingRobot)
966 INJ_I8(d, s->bSlotItemTakenFrom)
967 INJ_BOOL(d, s->fSignedAnotherContract)
968 INJ_SOLDIER(d, s->auto_bandaging_medic)
969 INJ_BOOL(d, s->fDontChargeTurningAPs)
970 INJ_SOLDIER(d, s->robot_remote_holder)
971 INJ_SKIP(d, 1)
972 INJ_U32(d, s->uiTimeOfLastContractUpdate)
973 INJ_I8(d, s->bTypeOfLastContract)
974 INJ_I8(d, s->bTurnsCollapsed)
975 INJ_I8(d, s->bSleepDrugCounter)
976 INJ_U8(d, s->ubMilitiaKills)
977 INJ_I8A(d, s->bFutureDrugEffect, lengthof(s->bFutureDrugEffect))
978 INJ_I8A(d, s->bDrugEffectRate, lengthof(s->bDrugEffectRate))
979 INJ_I8A(d, s->bDrugEffect, lengthof(s->bDrugEffect))
980 INJ_I8A(d, s->bDrugSideEffectRate, lengthof(s->bDrugSideEffectRate))
981 INJ_I8A(d, s->bDrugSideEffect, lengthof(s->bDrugSideEffect))
982 INJ_SKIP(d, 2)
983 INJ_I8(d, s->bBlindedCounter)
984 INJ_BOOL(d, s->fMercCollapsedFlag)
985 INJ_BOOL(d, s->fDoneAssignmentAndNothingToDoFlag)
986 INJ_BOOL(d, s->fMercAsleep)
987 INJ_BOOL(d, s->fDontChargeAPsForStanceChange)
988 INJ_SKIP(d, 2)
989 INJ_U8(d, s->ubTurnsUntilCanSayHeardNoise)
990 INJ_U16(d, s->usQuoteSaidExtFlags)
991 INJ_U16(d, s->sContPathLocation)
992 INJ_I8(d, s->bGoodContPath)
993 INJ_SKIP(d, 1)
994 INJ_I8(d, s->bNoiseLevel)
995 INJ_I8(d, s->bRegenerationCounter)
996 INJ_I8(d, s->bRegenBoostersUsedToday)
997 INJ_I8(d, s->bNumPelletsHitBy)
998 INJ_I16(d, s->sSkillCheckGridNo)
999 INJ_U8(d, s->ubLastEnemyCycledID)
1000 INJ_U8(d, s->ubPrevSectorID)
1001 INJ_U8(d, s->ubNumTilesMovesSinceLastForget)
1002 INJ_I8(d, s->bTurningIncrement)
1003 INJ_U32(d, s->uiBattleSoundID)
1004 INJ_BOOL(d, s->fSoldierWasMoving)
1005 INJ_BOOL(d, s->fSayAmmoQuotePending)
1006 INJ_U16(d, s->usValueGoneUp)
1007 INJ_U8(d, s->ubNumLocateCycles)
1008 INJ_U8(d, s->ubDelayedMovementFlags)
1009 INJ_BOOL(d, s->fMuzzleFlash)
1010 INJ_SOLDIER(d, s->CTGTTarget)
1011 INJ_I32(d, s->PanelAnimateCounter)
1012 UINT32 const checksum = MercChecksum(*s);
1013 INJ_U32(d, checksum)
1014 INJ_I8(d, s->bCurrentCivQuote)
1015 INJ_I8(d, s->bCurrentCivQuoteDelta)
1016 INJ_U8(d, s->ubMiscSoldierFlags)
1017 INJ_U8(d, s->ubReasonCantFinishMove)
1018 INJ_I16(d, s->sLocationOfFadeStart)
1019 INJ_U8(d, s->bUseExitGridForReentryDirection)
1020 INJ_SKIP(d, 1)
1021 INJ_U32(d, s->uiTimeSinceLastSpoke)
1022 INJ_U8(d, s->ubContractRenewalQuoteCode)
1023 INJ_SKIP(d, 1)
1024 INJ_I16(d, s->sPreTraversalGridNo)
1025 INJ_U32(d, s->uiXRayActivatedTime)
1026 INJ_I8(d, s->bTurningFromUI)
1027 INJ_I8(d, s->bPendingActionData5)
1028 INJ_I8(d, s->bDelayedStrategicMoraleMod)
1029 INJ_U8(d, s->ubDoorOpeningNoise)
1030 INJ_SKIP(d, 4)
1031 INJ_U8(d, s->ubLeaveHistoryCode)
1032 INJ_BOOL(d, s->fDontUnsetLastTargetFromTurn)
1033 INJ_I8(d, s->bOverrideMoveSpeed)
1034 INJ_BOOL(d, s->fUseMoverrideMoveSpeed)
1035 INJ_U32(d, s->uiTimeSoldierWillArrive)
1036 INJ_SKIP(d, 1)
1037 INJ_BOOL(d, s->fUseLandingZoneForArrival)
1038 INJ_BOOL(d, s->fFallClockwise)
1039 INJ_I8(d, s->bVehicleUnderRepairID)
1040 INJ_I32(d, s->iTimeCanSignElsewhere)
1041 INJ_I8(d, s->bHospitalPriceModifier)
1042 INJ_SKIP(d, 3)
1043 INJ_U32(d, s->uiStartTimeOfInsuranceContract)
1044 INJ_BOOL(d, s->fRTInNonintAnim)
1045 INJ_BOOL(d, s->fDoingExternalDeath)
1046 INJ_I8(d, s->bCorpseQuoteTolerance)
1047 INJ_SKIP(d, 1)
1048 INJ_I32(d, s->iPositionSndID)
1049 INJ_U32(d, s->uiTuringSoundID)
1050 INJ_U8(d, s->ubLastDamageReason)
1051 INJ_BOOL(d, s->fComplainedThatTired)
1052 INJ_I16A(d, s->sLastTwoLocations, lengthof(s->sLastTwoLocations))
1053 INJ_SKIP(d, 2)
1054 INJ_I32(d, s->uiTimeSinceLastBleedGrunt)
1055 INJ_SOLDIER(d, s->next_to_previous_attacker)
1056 INJ_SKIP(d, 39)
1057 Assert(d.getConsumed() == 2328);
1058 }
1059