[llvm] [GOFF] Refactor writing GOFF records (PR #93855)
Kevin P. Neal via llvm-commits
llvm-commits at lists.llvm.org
Thu Jun 27 07:18:34 PDT 2024
================
@@ -185,81 +158,71 @@ class GOFFState {
yaml::ErrorHandler ErrHandler)
: GW(OS), Doc(Doc), ErrHandler(ErrHandler), HasError(false) {}
- ~GOFFState() { GW.finalize(); }
-
bool writeObject();
public:
static bool writeGOFF(raw_ostream &OS, GOFFYAML::Object &Doc,
yaml::ErrorHandler ErrHandler);
private:
- GOFFOstream GW;
+ GOFFOStream GW;
GOFFYAML::Object &Doc;
yaml::ErrorHandler ErrHandler;
bool HasError;
};
-void GOFFState::writeHeader(GOFFYAML::FileHeader &FileHdr) {
- SmallString<16> CCSIDName;
- if (std::error_code EC =
- ConverterEBCDIC::convertToEBCDIC(FileHdr.CharacterSetName, CCSIDName))
- reportError("Conversion error on " + FileHdr.CharacterSetName);
- if (CCSIDName.size() > 16) {
- reportError("CharacterSetName too long");
- CCSIDName.resize(16);
- }
- SmallString<16> LangProd;
- if (std::error_code EC = ConverterEBCDIC::convertToEBCDIC(
- FileHdr.LanguageProductIdentifier, LangProd))
- reportError("Conversion error on " + FileHdr.LanguageProductIdentifier);
- if (LangProd.size() > 16) {
- reportError("LanguageProductIdentifier too long");
- LangProd.resize(16);
- }
-
- GW.makeNewRecord(GOFF::RT_HDR, GOFF::PayloadLength);
- GW << binaryBe(FileHdr.TargetEnvironment) // TargetEnvironment
- << binaryBe(FileHdr.TargetOperatingSystem) // TargetOperatingSystem
- << zeros(2) // Reserved
- << binaryBe(FileHdr.CCSID) // CCSID
- << CCSIDName // CharacterSetName
- << zeros(16 - CCSIDName.size()) // Fill bytes
- << LangProd // LanguageProductIdentifier
- << zeros(16 - LangProd.size()) // Fill bytes
- << binaryBe(FileHdr.ArchitectureLevel); // ArchitectureLevel
- // The module propties are optional. Figure out if we need to write them.
- uint16_t ModPropLen = 0;
- if (FileHdr.TargetSoftwareEnvironment)
- ModPropLen = 3;
- else if (FileHdr.InternalCCSID)
- ModPropLen = 2;
- if (ModPropLen) {
- GW << binaryBe(ModPropLen) << zeros(6);
- if (ModPropLen >= 2)
- GW << binaryBe(FileHdr.InternalCCSID ? *FileHdr.InternalCCSID : 0);
- if (ModPropLen >= 3)
- GW << binaryBe(FileHdr.TargetSoftwareEnvironment
- ? *FileHdr.TargetSoftwareEnvironment
- : 0);
- }
+void GOFFState::writeHeader(const GOFFYAML::ModuleHeader &ModHdr) {
+ // See
+ // https://www.ibm.com/docs/en/zos/3.1.0?topic=formats-module-header-record.
+ GW.newRecord(GOFF::RT_HDR);
+ LogicalRecord LR(GW);
+ LR << zeros(45) // Reserved.
+ << binaryBe(ModHdr.ArchitectureLevel) // The architecture level.
+ << binaryBe(ModHdr.PropertiesLength) // Length of module properties.
+ << zeros(6); // Reserved.
+ if (ModHdr.Properties)
+ LR << *ModHdr.Properties; // Module properties.
}
-void GOFFState::writeEnd() {
- GW.makeNewRecord(GOFF::RT_END, GOFF::PayloadLength);
- GW << binaryBe(uint8_t(0)) // No entry point
- << binaryBe(uint8_t(0)) // No AMODE
- << zeros(3) // Reserved
- << binaryBe(GW.logicalRecords());
- // No entry point yet. Automatically fill remaining space with zero bytes.
- GW.finalize();
+void GOFFState::writeEnd(const GOFFYAML::EndOfModule &EndMod) {
+ // See https://www.ibm.com/docs/en/zos/3.1.0?topic=formats-end-module-record.
+ SmallString<16> EntryName;
+ if (std::error_code EC =
+ ConverterEBCDIC::convertToEBCDIC(EndMod.EntryName, EntryName))
+ reportError("failed to convert '" + EndMod.EntryName + "' to EBCDIC 1047");
+
+ GW.newRecord(GOFF::RT_END);
+ LogicalRecord LR(GW);
+ LR << binaryBe(uint8_t(EndMod.Flags)) // The flags.
+ << binaryBe(uint8_t(EndMod.AMODE)) // The addressing mode.
+ << zeros(3) // Reserved.
+ << binaryBe(EndMod.RecordCount) // The record count.
----------------
kpneal wrote:
Correct, fields that are missing are filled with zero bytes in GOFF. A count of zero means the record count is unspecified.
https://github.com/llvm/llvm-project/pull/93855
More information about the llvm-commits
mailing list