2019-08-23 23:24:04 +00:00
|
|
|
#include "DataSpec/DNACommon/FSM2.hpp"
|
|
|
|
|
|
|
|
#include "DataSpec/DNACommon/PAK.hpp"
|
|
|
|
|
|
|
|
#include <athena/FileWriter.hpp>
|
2016-04-11 05:13:16 +00:00
|
|
|
#include <athena/Global.hpp>
|
|
|
|
#include <athena/IStreamWriter.hpp>
|
|
|
|
|
2019-08-23 23:24:04 +00:00
|
|
|
#include <logvisor/logvisor.hpp>
|
2016-04-11 05:13:16 +00:00
|
|
|
|
2018-12-08 05:30:43 +00:00
|
|
|
namespace DataSpec::DNAFSM2 {
|
2021-04-10 08:42:06 +00:00
|
|
|
logvisor::Module LogDNAFSM2("DataSpec::DNAFSM2");
|
2016-04-11 05:13:16 +00:00
|
|
|
|
|
|
|
template <class IDType>
|
2018-02-22 07:24:51 +00:00
|
|
|
template <class Op>
|
2018-12-08 05:30:43 +00:00
|
|
|
void FSM2<IDType>::Enumerate(typename Op::StreamT& s) {
|
2019-08-27 03:02:31 +00:00
|
|
|
Do<Op>(athena::io::PropId{"header"}, header, s);
|
2018-12-08 05:30:43 +00:00
|
|
|
if (header.magic != SBIG('FSM2')) {
|
2020-04-11 22:51:39 +00:00
|
|
|
LogDNAFSM2.report(logvisor::Fatal, FMT_STRING("Invalid FSM2 magic '{}' expected 'FSM2'"), header.magic);
|
2018-12-08 05:30:43 +00:00
|
|
|
return;
|
|
|
|
}
|
2016-04-11 05:13:16 +00:00
|
|
|
|
2018-12-08 05:30:43 +00:00
|
|
|
if (header.version == 1) {
|
|
|
|
if (!detail)
|
|
|
|
detail.reset(new FSMV1);
|
2019-08-27 03:02:31 +00:00
|
|
|
Do<Op>(athena::io::PropId{"detail"}, static_cast<FSMV1&>(*detail), s);
|
2018-12-08 05:30:43 +00:00
|
|
|
} else if (header.version == 2) {
|
|
|
|
if (!detail)
|
|
|
|
detail.reset(new FSMV2);
|
2019-08-27 03:02:31 +00:00
|
|
|
Do<Op>(athena::io::PropId{"detail"}, static_cast<FSMV2&>(*detail), s);
|
2018-12-08 05:30:43 +00:00
|
|
|
} else {
|
2020-04-11 22:51:39 +00:00
|
|
|
LogDNAFSM2.report(logvisor::Fatal, FMT_STRING("Invalid FSM2 version '{}'"), header.version);
|
2018-12-08 05:30:43 +00:00
|
|
|
return;
|
|
|
|
}
|
2016-04-11 05:13:16 +00:00
|
|
|
}
|
|
|
|
|
2018-02-22 07:24:51 +00:00
|
|
|
AT_SPECIALIZE_DNA(FSM2<UniqueID32>)
|
|
|
|
AT_SPECIALIZE_DNA(FSM2<UniqueID64>)
|
2016-04-11 05:13:16 +00:00
|
|
|
|
2018-02-22 07:24:51 +00:00
|
|
|
template <>
|
2019-10-01 07:38:03 +00:00
|
|
|
std::string_view FSM2<UniqueID32>::DNAType() {
|
2021-04-10 08:42:06 +00:00
|
|
|
return "FSM2<UniqueID32>"sv;
|
2018-12-08 05:30:43 +00:00
|
|
|
}
|
2016-04-11 05:13:16 +00:00
|
|
|
|
2018-02-22 07:24:51 +00:00
|
|
|
template <>
|
2019-10-01 07:38:03 +00:00
|
|
|
std::string_view FSM2<UniqueID64>::DNAType() {
|
2021-04-10 08:42:06 +00:00
|
|
|
return "FSM2<UniqueID64>"sv;
|
2018-12-08 05:30:43 +00:00
|
|
|
}
|
2016-04-11 05:13:16 +00:00
|
|
|
|
|
|
|
template struct FSM2<UniqueID32>;
|
|
|
|
template struct FSM2<UniqueID64>;
|
|
|
|
|
|
|
|
template <class IDType>
|
2018-12-08 05:30:43 +00:00
|
|
|
bool ExtractFSM2(PAKEntryReadStream& rs, const hecl::ProjectPath& outPath) {
|
|
|
|
athena::io::FileWriter writer(outPath.getAbsolutePath());
|
|
|
|
if (writer.isOpen()) {
|
|
|
|
FSM2<IDType> fsm2;
|
|
|
|
fsm2.read(rs);
|
|
|
|
athena::io::ToYAMLStream(fsm2, writer);
|
|
|
|
return true;
|
|
|
|
}
|
|
|
|
return false;
|
2016-04-11 05:13:16 +00:00
|
|
|
}
|
|
|
|
template bool ExtractFSM2<UniqueID32>(PAKEntryReadStream& rs, const hecl::ProjectPath& outPath);
|
|
|
|
template bool ExtractFSM2<UniqueID64>(PAKEntryReadStream& rs, const hecl::ProjectPath& outPath);
|
|
|
|
|
|
|
|
template <class IDType>
|
2018-12-08 05:30:43 +00:00
|
|
|
bool WriteFSM2(const FSM2<IDType>& fsm2, const hecl::ProjectPath& outPath) {
|
|
|
|
athena::io::FileWriter w(outPath.getAbsolutePath(), true, false);
|
|
|
|
if (w.hasError())
|
|
|
|
return false;
|
|
|
|
fsm2.write(w);
|
|
|
|
int64_t rem = w.position() % 32;
|
|
|
|
if (rem)
|
|
|
|
for (int64_t i = 0; i < 32 - rem; ++i)
|
|
|
|
w.writeUByte(0xff);
|
|
|
|
return true;
|
2016-04-11 05:13:16 +00:00
|
|
|
}
|
|
|
|
template bool WriteFSM2<UniqueID32>(const FSM2<UniqueID32>& fsm2, const hecl::ProjectPath& outPath);
|
|
|
|
template bool WriteFSM2<UniqueID64>(const FSM2<UniqueID64>& fsm2, const hecl::ProjectPath& outPath);
|
|
|
|
|
2018-12-08 05:30:43 +00:00
|
|
|
} // namespace DataSpec::DNAFSM2
|