mirror of https://github.com/OpenTTD/OpenTTD
Codechange: Support saveload of reference vectors.
This uses the same data format as reference lists, but for vectors, so allows data structures to be changed without affecting savegame format.pull/13127/head
parent
e7c63de55d
commit
177e2ebf80
|
@ -565,6 +565,7 @@ static uint8_t GetSavegameFileType(const SaveLoad &sld)
|
||||||
return IsSavegameVersionBefore(SLV_69) ? SLE_FILE_U16 : SLE_FILE_U32;
|
return IsSavegameVersionBefore(SLV_69) ? SLE_FILE_U16 : SLE_FILE_U32;
|
||||||
|
|
||||||
case SL_REFLIST:
|
case SL_REFLIST:
|
||||||
|
case SL_REFVECTOR:
|
||||||
return (IsSavegameVersionBefore(SLV_69) ? SLE_FILE_U16 : SLE_FILE_U32) | SLE_FILE_HAS_LENGTH_FIELD;
|
return (IsSavegameVersionBefore(SLV_69) ? SLE_FILE_U16 : SLE_FILE_U32) | SLE_FILE_HAS_LENGTH_FIELD;
|
||||||
|
|
||||||
case SL_SAVEBYTE:
|
case SL_SAVEBYTE:
|
||||||
|
@ -1352,6 +1353,33 @@ static void SlRefList(void *list, VarType conv)
|
||||||
SlStorageHelper<std::list, void *>::SlSaveLoad(list, conv, SL_REF);
|
SlStorageHelper<std::list, void *>::SlSaveLoad(list, conv, SL_REF);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Return the size in bytes of a vector.
|
||||||
|
* @param vector The std::vector to find the size of.
|
||||||
|
* @param conv VarType type of variable that is used for calculating the size.
|
||||||
|
*/
|
||||||
|
static size_t SlCalcRefVectorLen(const void *vector, VarType conv)
|
||||||
|
{
|
||||||
|
return SlStorageHelper<std::vector, void *>::SlCalcLen(vector, conv, SL_REF);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Save/Load a vector.
|
||||||
|
* @param vector The vector being manipulated.
|
||||||
|
* @param conv VarType type of variable that is used for calculating the size.
|
||||||
|
*/
|
||||||
|
static void SlRefVector(void *vector, VarType conv)
|
||||||
|
{
|
||||||
|
/* Automatically calculate the length? */
|
||||||
|
if (_sl.need_length != NL_NONE) {
|
||||||
|
SlSetLength(SlCalcRefVectorLen(vector, conv));
|
||||||
|
/* Determine length only? */
|
||||||
|
if (_sl.need_length == NL_CALCLENGTH) return;
|
||||||
|
}
|
||||||
|
|
||||||
|
SlStorageHelper<std::vector, void *>::SlSaveLoad(vector, conv, SL_REF);
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Return the size in bytes of a std::deque.
|
* Return the size in bytes of a std::deque.
|
||||||
* @param deque The std::deque to find the size of
|
* @param deque The std::deque to find the size of
|
||||||
|
@ -1530,6 +1558,7 @@ size_t SlCalcObjMemberLength(const void *object, const SaveLoad &sld)
|
||||||
case SL_REF: return SlCalcRefLen();
|
case SL_REF: return SlCalcRefLen();
|
||||||
case SL_ARR: return SlCalcArrayLen(sld.length, sld.conv);
|
case SL_ARR: return SlCalcArrayLen(sld.length, sld.conv);
|
||||||
case SL_REFLIST: return SlCalcRefListLen(GetVariableAddress(object, sld), sld.conv);
|
case SL_REFLIST: return SlCalcRefListLen(GetVariableAddress(object, sld), sld.conv);
|
||||||
|
case SL_REFVECTOR: return SlCalcRefVectorLen(GetVariableAddress(object, sld), sld.conv);
|
||||||
case SL_DEQUE: return SlCalcDequeLen(GetVariableAddress(object, sld), sld.conv);
|
case SL_DEQUE: return SlCalcDequeLen(GetVariableAddress(object, sld), sld.conv);
|
||||||
case SL_VECTOR: return SlCalcVectorLen(GetVariableAddress(object, sld), sld.conv);
|
case SL_VECTOR: return SlCalcVectorLen(GetVariableAddress(object, sld), sld.conv);
|
||||||
case SL_STDSTR: return SlCalcStdStringLen(GetVariableAddress(object, sld));
|
case SL_STDSTR: return SlCalcStdStringLen(GetVariableAddress(object, sld));
|
||||||
|
@ -1575,6 +1604,7 @@ static bool SlObjectMember(void *object, const SaveLoad &sld)
|
||||||
case SL_REF:
|
case SL_REF:
|
||||||
case SL_ARR:
|
case SL_ARR:
|
||||||
case SL_REFLIST:
|
case SL_REFLIST:
|
||||||
|
case SL_REFVECTOR:
|
||||||
case SL_DEQUE:
|
case SL_DEQUE:
|
||||||
case SL_VECTOR:
|
case SL_VECTOR:
|
||||||
case SL_STDSTR: {
|
case SL_STDSTR: {
|
||||||
|
@ -1585,6 +1615,7 @@ static bool SlObjectMember(void *object, const SaveLoad &sld)
|
||||||
case SL_REF: SlSaveLoadRef(ptr, conv); break;
|
case SL_REF: SlSaveLoadRef(ptr, conv); break;
|
||||||
case SL_ARR: SlArray(ptr, sld.length, conv); break;
|
case SL_ARR: SlArray(ptr, sld.length, conv); break;
|
||||||
case SL_REFLIST: SlRefList(ptr, conv); break;
|
case SL_REFLIST: SlRefList(ptr, conv); break;
|
||||||
|
case SL_REFVECTOR: SlRefVector(ptr, conv); break;
|
||||||
case SL_DEQUE: SlDeque(ptr, conv); break;
|
case SL_DEQUE: SlDeque(ptr, conv); break;
|
||||||
case SL_VECTOR: SlVector(ptr, conv); break;
|
case SL_VECTOR: SlVector(ptr, conv); break;
|
||||||
case SL_STDSTR: SlStdString(ptr, sld.conv); break;
|
case SL_STDSTR: SlStdString(ptr, sld.conv); break;
|
||||||
|
|
|
@ -705,6 +705,8 @@ enum SaveLoadType : uint8_t {
|
||||||
|
|
||||||
SL_SAVEBYTE = 10, ///< Save (but not load) a byte.
|
SL_SAVEBYTE = 10, ///< Save (but not load) a byte.
|
||||||
SL_NULL = 11, ///< Save null-bytes and load to nowhere.
|
SL_NULL = 11, ///< Save null-bytes and load to nowhere.
|
||||||
|
|
||||||
|
SL_REFVECTOR = 12, ///< Save/load a vector of #SL_REF elements.
|
||||||
};
|
};
|
||||||
|
|
||||||
typedef void *SaveLoadAddrProc(void *base, size_t extra);
|
typedef void *SaveLoadAddrProc(void *base, size_t extra);
|
||||||
|
@ -813,6 +815,7 @@ inline constexpr bool SlCheckVarSize(SaveLoadType cmd, VarType type, size_t leng
|
||||||
case SL_DEQUE: return sizeof(std::deque<void *>) == size;
|
case SL_DEQUE: return sizeof(std::deque<void *>) == size;
|
||||||
case SL_VECTOR: return sizeof(std::vector<void *>) == size;
|
case SL_VECTOR: return sizeof(std::vector<void *>) == size;
|
||||||
case SL_REFLIST: return sizeof(std::list<void *>) == size;
|
case SL_REFLIST: return sizeof(std::list<void *>) == size;
|
||||||
|
case SL_REFVECTOR: return sizeof(std::vector<void *>) == size;
|
||||||
case SL_SAVEBYTE: return true;
|
case SL_SAVEBYTE: return true;
|
||||||
default: NOT_REACHED();
|
default: NOT_REACHED();
|
||||||
}
|
}
|
||||||
|
@ -948,6 +951,16 @@ inline constexpr bool SlCheckVarSize(SaveLoadType cmd, VarType type, size_t leng
|
||||||
*/
|
*/
|
||||||
#define SLE_CONDREFLIST(base, variable, type, from, to) SLE_GENERAL(SL_REFLIST, base, variable, type, 0, from, to, 0)
|
#define SLE_CONDREFLIST(base, variable, type, from, to) SLE_GENERAL(SL_REFLIST, base, variable, type, 0, from, to, 0)
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Storage of a vector of #SL_REF elements in some savegame versions.
|
||||||
|
* @param base Name of the class or struct containing the vector.
|
||||||
|
* @param variable Name of the variable in the class or struct referenced by \a base.
|
||||||
|
* @param type Storage of the data in memory and in the savegame.
|
||||||
|
* @param from First savegame version that has the vector.
|
||||||
|
* @param to Last savegame version that has the vector.
|
||||||
|
*/
|
||||||
|
#define SLE_CONDREFVECTOR(base, variable, type, from, to) SLE_GENERAL(SL_REFVECTOR, base, variable, type, 0, from, to, 0)
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Storage of a vector of #SL_VAR elements in some savegame versions.
|
* Storage of a vector of #SL_VAR elements in some savegame versions.
|
||||||
* @param base Name of the class or struct containing the list.
|
* @param base Name of the class or struct containing the list.
|
||||||
|
@ -1047,6 +1060,14 @@ inline constexpr bool SlCheckVarSize(SaveLoadType cmd, VarType type, size_t leng
|
||||||
*/
|
*/
|
||||||
#define SLE_REFLIST(base, variable, type) SLE_CONDREFLIST(base, variable, type, SL_MIN_VERSION, SL_MAX_VERSION)
|
#define SLE_REFLIST(base, variable, type) SLE_CONDREFLIST(base, variable, type, SL_MIN_VERSION, SL_MAX_VERSION)
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Storage of a vector of #SL_REF elements in every savegame version.
|
||||||
|
* @param base Name of the class or struct containing the vector.
|
||||||
|
* @param variable Name of the variable in the class or struct referenced by \a base.
|
||||||
|
* @param type Storage of the data in memory and in the savegame.
|
||||||
|
*/
|
||||||
|
#define SLE_REFVECTOR(base, variable, type) SLE_CONDREFVECTOR(base, variable, type, SL_MIN_VERSION, SL_MAX_VERSION)
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Only write byte during saving; never read it during loading.
|
* Only write byte during saving; never read it during loading.
|
||||||
* When using SLE_SAVEBYTE you will have to read this byte before the table
|
* When using SLE_SAVEBYTE you will have to read this byte before the table
|
||||||
|
|
Loading…
Reference in New Issue