// Code generated by kaitai-struct-compiler from a .ksy source file. DO NOT EDIT.
import (
"github.com/kaitai-io/kaitai_struct_go_runtime/kaitai"
"io"
"bytes"
)
/**
* The data format of Macintosh resource forks,
* used on Classic Mac OS and Mac OS X/macOS to store additional structured data along with a file's main data (the data fork).
* The kinds of data stored in resource forks include:
*
* * Document resources:
* images, sounds, etc. used by a document
* * Application resources:
* graphics, GUI layouts, localizable strings,
* and even code used by an application, a library, or system files
* * Common metadata:
* custom icons and version metadata that could be displayed by the Finder
* * Application-specific metadata:
* because resource forks follow a common format,
* other applications can store new metadata in them,
* even if the original application does not recognize or understand it
*
* Macintosh file systems (MFS, HFS, HFS+, APFS) support resource forks natively,
* which allows storing resources along with any file.
* Non-Macintosh file systems and protocols have little or no support for resource forks,
* so the resource fork data must be stored in some other way when using such file systems or protocols.
* Various file formats and tools exist for this purpose,
* such as BinHex, MacBinary, AppleSingle, AppleDouble, or QuickTime RezWack.
* In some cases,
* resource forks are stored as plain data in separate files with a .rsrc extension,
* even on Mac systems that natively support resource forks.
*
* On modern Mac OS X/macOS systems,
* resource forks are used far less commonly than on classic Mac OS systems,
* because of compatibility issues with other systems and historical limitations in the format.
* Modern macOS APIs and libraries do not use resource forks,
* and the legacy Carbon API that still used them has been deprecated since OS X 10.8.
* Despite this,
* even current macOS systems still use resource forks for certain purposes,
* such as custom file icons.
* @see Inside Macintosh, More Macintosh Toolbox, Resource Manager, Resource Manager Reference, Resource File Format
* @see Inside Macintosh, Volume I, The Resource Manager, Format of a Resource File
* @see Source
* @see Source
*/
type ResourceFork struct {
Header *ResourceFork_FileHeader
SystemData []byte
ApplicationData []byte
_io *kaitai.Stream
_root *ResourceFork
_parent interface{}
_raw_dataBlocksWithIo []byte
_raw_resourceMap []byte
_f_dataBlocksWithIo bool
dataBlocksWithIo *BytesWithIo
_f_dataBlocks bool
dataBlocks []byte
_f_resourceMap bool
resourceMap *ResourceFork_ResourceMap
}
func NewResourceFork() *ResourceFork {
return &ResourceFork{
}
}
func (this *ResourceFork) Read(io *kaitai.Stream, parent interface{}, root *ResourceFork) (err error) {
this._io = io
this._parent = parent
this._root = root
tmp1 := NewResourceFork_FileHeader()
err = tmp1.Read(this._io, this, this._root)
if err != nil {
return err
}
this.Header = tmp1
tmp2, err := this._io.ReadBytes(int(112))
if err != nil {
return err
}
tmp2 = tmp2
this.SystemData = tmp2
tmp3, err := this._io.ReadBytes(int(128))
if err != nil {
return err
}
tmp3 = tmp3
this.ApplicationData = tmp3
return err
}
/**
* Use `data_blocks` instead,
* unless you need access to this instance's `_io`.
*/
func (this *ResourceFork) DataBlocksWithIo() (v *BytesWithIo, err error) {
if (this._f_dataBlocksWithIo) {
return this.dataBlocksWithIo, nil
}
_pos, err := this._io.Pos()
if err != nil {
return nil, err
}
_, err = this._io.Seek(int64(this.Header.OfsDataBlocks), io.SeekStart)
if err != nil {
return nil, err
}
tmp4, err := this._io.ReadBytes(int(this.Header.LenDataBlocks))
if err != nil {
return nil, err
}
tmp4 = tmp4
this._raw_dataBlocksWithIo = tmp4
_io__raw_dataBlocksWithIo := kaitai.NewStream(bytes.NewReader(this._raw_dataBlocksWithIo))
tmp5 := NewBytesWithIo()
err = tmp5.Read(_io__raw_dataBlocksWithIo, this, nil)
if err != nil {
return nil, err
}
this.dataBlocksWithIo = tmp5
_, err = this._io.Seek(_pos, io.SeekStart)
if err != nil {
return nil, err
}
this._f_dataBlocksWithIo = true
this._f_dataBlocksWithIo = true
return this.dataBlocksWithIo, nil
}
/**
* Storage area for the data blocks of all resources.
*
* These data blocks are not required to appear in any particular order,
* and there may be unused space between and around them.
*
* In practice,
* the data blocks in newly created resource files are usually contiguous.
* When existing resources are shortened,
* the Mac OS resource manager leaves unused space where the now removed resource data was,
* as this is quicker than moving the following resource data into the newly freed space.
* Such unused space may be cleaned up later when the resource manager "compacts" the resource file,
* which happens when resources are removed entirely,
* or when resources are added or grown so that more space is needed in the data area.
*/
func (this *ResourceFork) DataBlocks() (v []byte, err error) {
if (this._f_dataBlocks) {
return this.dataBlocks, nil
}
tmp6, err := this.DataBlocksWithIo()
if err != nil {
return nil, err
}
this.dataBlocks = []byte(tmp6.Data)
this._f_dataBlocks = true
return this.dataBlocks, nil
}
/**
* The resource file's resource map.
*/
func (this *ResourceFork) ResourceMap() (v *ResourceFork_ResourceMap, err error) {
if (this._f_resourceMap) {
return this.resourceMap, nil
}
_pos, err := this._io.Pos()
if err != nil {
return nil, err
}
_, err = this._io.Seek(int64(this.Header.OfsResourceMap), io.SeekStart)
if err != nil {
return nil, err
}
tmp7, err := this._io.ReadBytes(int(this.Header.LenResourceMap))
if err != nil {
return nil, err
}
tmp7 = tmp7
this._raw_resourceMap = tmp7
_io__raw_resourceMap := kaitai.NewStream(bytes.NewReader(this._raw_resourceMap))
tmp8 := NewResourceFork_ResourceMap()
err = tmp8.Read(_io__raw_resourceMap, this, this._root)
if err != nil {
return nil, err
}
this.resourceMap = tmp8
_, err = this._io.Seek(_pos, io.SeekStart)
if err != nil {
return nil, err
}
this._f_resourceMap = true
this._f_resourceMap = true
return this.resourceMap, nil
}
/**
* The resource file's header information.
*/
/**
* System-reserved data area.
* This field can generally be ignored when reading and writing.
*
* This field is used by the Classic Mac OS Finder as temporary storage space.
* It usually contains parts of the file metadata (name, type/creator code, etc.).
* Any existing data in this field is ignored and overwritten.
*
* In resource files written by Mac OS X,
* this field is set to all zero bytes.
*/
/**
* Application-specific data area.
* This field can generally be ignored when reading and writing.
*
* According to early revisions of Inside Macintosh,
* this field is "available for application data".
* In practice, it is almost never used for this purpose,
* and usually contains only junk data.
*
* In resource files written by Mac OS X,
* this field is set to all zero bytes.
*/
/**
* Resource file header,
* containing the offsets and lengths of the resource data area and resource map.
*/
type ResourceFork_FileHeader struct {
OfsDataBlocks uint32
OfsResourceMap uint32
LenDataBlocks uint32
LenResourceMap uint32
_io *kaitai.Stream
_root *ResourceFork
_parent interface{}
}
func NewResourceFork_FileHeader() *ResourceFork_FileHeader {
return &ResourceFork_FileHeader{
}
}
func (this *ResourceFork_FileHeader) Read(io *kaitai.Stream, parent interface{}, root *ResourceFork) (err error) {
this._io = io
this._parent = parent
this._root = root
tmp9, err := this._io.ReadU4be()
if err != nil {
return err
}
this.OfsDataBlocks = uint32(tmp9)
tmp10, err := this._io.ReadU4be()
if err != nil {
return err
}
this.OfsResourceMap = uint32(tmp10)
tmp11, err := this._io.ReadU4be()
if err != nil {
return err
}
this.LenDataBlocks = uint32(tmp11)
tmp12, err := this._io.ReadU4be()
if err != nil {
return err
}
this.LenResourceMap = uint32(tmp12)
return err
}
/**
* Offset of the resource data area,
* from the start of the resource file.
*
* In practice,
* this should always be `256`,
* i. e. the resource data area should directly follow the application-specific data area.
*/
/**
* Offset of the resource map,
* from the start of the resource file.
*
* In practice,
* this should always be `ofs_data_blocks + len_data_blocks`,
* i. e. the resource map should directly follow the resource data area.
*/
/**
* Length of the resource data area.
*/
/**
* Length of the resource map.
*
* In practice,
* this should always be `_root._io.size - ofs_resource_map`,
* i. e. the resource map should extend to the end of the resource file.
*/
/**
* A resource data block,
* as stored in the resource data area.
*
* Each data block stores the data contained in a resource,
* along with its length.
*/
type ResourceFork_DataBlock struct {
LenData uint32
Data []byte
_io *kaitai.Stream
_root *ResourceFork
_parent *ResourceFork_ResourceMap_TypeListAndReferenceLists_ReferenceList_Reference
}
func NewResourceFork_DataBlock() *ResourceFork_DataBlock {
return &ResourceFork_DataBlock{
}
}
func (this *ResourceFork_DataBlock) Read(io *kaitai.Stream, parent *ResourceFork_ResourceMap_TypeListAndReferenceLists_ReferenceList_Reference, root *ResourceFork) (err error) {
this._io = io
this._parent = parent
this._root = root
tmp13, err := this._io.ReadU4be()
if err != nil {
return err
}
this.LenData = uint32(tmp13)
tmp14, err := this._io.ReadBytes(int(this.LenData))
if err != nil {
return err
}
tmp14 = tmp14
this.Data = tmp14
return err
}
/**
* The length of the resource data stored in this block.
*/
/**
* The data stored in this block.
*/
/**
* Resource map,
* containing information about the resources in the file and where they are located in the data area.
*/
type ResourceFork_ResourceMap struct {
ReservedFileHeaderCopy *ResourceFork_FileHeader
ReservedNextResourceMapHandle uint32
ReservedFileReferenceNumber uint16
FileAttributes *ResourceFork_ResourceMap_FileAttributes
OfsTypeList uint16
OfsNames uint16
_io *kaitai.Stream
_root *ResourceFork
_parent *ResourceFork
_raw_FileAttributes []byte
_raw_typeListAndReferenceLists []byte
_raw_namesWithIo []byte
_f_typeListAndReferenceLists bool
typeListAndReferenceLists *ResourceFork_ResourceMap_TypeListAndReferenceLists
_f_namesWithIo bool
namesWithIo *BytesWithIo
_f_names bool
names []byte
}
func NewResourceFork_ResourceMap() *ResourceFork_ResourceMap {
return &ResourceFork_ResourceMap{
}
}
func (this *ResourceFork_ResourceMap) Read(io *kaitai.Stream, parent *ResourceFork, root *ResourceFork) (err error) {
this._io = io
this._parent = parent
this._root = root
tmp15 := NewResourceFork_FileHeader()
err = tmp15.Read(this._io, this, this._root)
if err != nil {
return err
}
this.ReservedFileHeaderCopy = tmp15
tmp16, err := this._io.ReadU4be()
if err != nil {
return err
}
this.ReservedNextResourceMapHandle = uint32(tmp16)
tmp17, err := this._io.ReadU2be()
if err != nil {
return err
}
this.ReservedFileReferenceNumber = uint16(tmp17)
tmp18, err := this._io.ReadBytes(int(2))
if err != nil {
return err
}
tmp18 = tmp18
this._raw_FileAttributes = tmp18
_io__raw_FileAttributes := kaitai.NewStream(bytes.NewReader(this._raw_FileAttributes))
tmp19 := NewResourceFork_ResourceMap_FileAttributes()
err = tmp19.Read(_io__raw_FileAttributes, this, this._root)
if err != nil {
return err
}
this.FileAttributes = tmp19
tmp20, err := this._io.ReadU2be()
if err != nil {
return err
}
this.OfsTypeList = uint16(tmp20)
tmp21, err := this._io.ReadU2be()
if err != nil {
return err
}
this.OfsNames = uint16(tmp21)
return err
}
/**
* The resource map's resource type list, followed by the resource reference list area.
*/
func (this *ResourceFork_ResourceMap) TypeListAndReferenceLists() (v *ResourceFork_ResourceMap_TypeListAndReferenceLists, err error) {
if (this._f_typeListAndReferenceLists) {
return this.typeListAndReferenceLists, nil
}
_pos, err := this._io.Pos()
if err != nil {
return nil, err
}
_, err = this._io.Seek(int64(this.OfsTypeList), io.SeekStart)
if err != nil {
return nil, err
}
tmp22, err := this._io.ReadBytes(int((this.OfsNames - this.OfsTypeList)))
if err != nil {
return nil, err
}
tmp22 = tmp22
this._raw_typeListAndReferenceLists = tmp22
_io__raw_typeListAndReferenceLists := kaitai.NewStream(bytes.NewReader(this._raw_typeListAndReferenceLists))
tmp23 := NewResourceFork_ResourceMap_TypeListAndReferenceLists()
err = tmp23.Read(_io__raw_typeListAndReferenceLists, this, this._root)
if err != nil {
return nil, err
}
this.typeListAndReferenceLists = tmp23
_, err = this._io.Seek(_pos, io.SeekStart)
if err != nil {
return nil, err
}
this._f_typeListAndReferenceLists = true
this._f_typeListAndReferenceLists = true
return this.typeListAndReferenceLists, nil
}
/**
* Use `names` instead,
* unless you need access to this instance's `_io`.
*/
func (this *ResourceFork_ResourceMap) NamesWithIo() (v *BytesWithIo, err error) {
if (this._f_namesWithIo) {
return this.namesWithIo, nil
}
_pos, err := this._io.Pos()
if err != nil {
return nil, err
}
_, err = this._io.Seek(int64(this.OfsNames), io.SeekStart)
if err != nil {
return nil, err
}
tmp24, err := this._io.ReadBytesFull()
if err != nil {
return nil, err
}
tmp24 = tmp24
this._raw_namesWithIo = tmp24
_io__raw_namesWithIo := kaitai.NewStream(bytes.NewReader(this._raw_namesWithIo))
tmp25 := NewBytesWithIo()
err = tmp25.Read(_io__raw_namesWithIo, this, nil)
if err != nil {
return nil, err
}
this.namesWithIo = tmp25
_, err = this._io.Seek(_pos, io.SeekStart)
if err != nil {
return nil, err
}
this._f_namesWithIo = true
this._f_namesWithIo = true
return this.namesWithIo, nil
}
/**
* Storage area for the names of all resources.
*/
func (this *ResourceFork_ResourceMap) Names() (v []byte, err error) {
if (this._f_names) {
return this.names, nil
}
tmp26, err := this.NamesWithIo()
if err != nil {
return nil, err
}
this.names = []byte(tmp26.Data)
this._f_names = true
return this.names, nil
}
/**
* Reserved space for a copy of the resource file header.
*/
/**
* Reserved space for a handle to the next loaded resource map in memory.
*/
/**
* Reserved space for the resource file's file reference number.
*/
/**
* The resource file's attributes.
*/
/**
* Offset of the resource type list,
* from the start of the resource map.
*
* In practice,
* this should always be `sizeof`,
* i. e. the resource type list should directly follow the resource map.
*/
/**
* Offset of the resource name area,
* from the start of the resource map.
*/
/**
* A resource file's attributes,
* as stored in the resource map.
*
* These attributes are sometimes also referred to as resource map attributes,
* because of where they are stored in the file.
*/
type ResourceFork_ResourceMap_FileAttributes struct {
ResourcesLocked bool
Reserved0 uint64
PrinterDriverMultifinderCompatible bool
NoWriteChanges bool
NeedsCompact bool
MapNeedsWrite bool
Reserved1 uint64
_io *kaitai.Stream
_root *ResourceFork
_parent *ResourceFork_ResourceMap
_f_asInt bool
asInt uint16
}
func NewResourceFork_ResourceMap_FileAttributes() *ResourceFork_ResourceMap_FileAttributes {
return &ResourceFork_ResourceMap_FileAttributes{
}
}
func (this *ResourceFork_ResourceMap_FileAttributes) Read(io *kaitai.Stream, parent *ResourceFork_ResourceMap, root *ResourceFork) (err error) {
this._io = io
this._parent = parent
this._root = root
tmp27, err := this._io.ReadBitsIntBe(1)
if err != nil {
return err
}
this.ResourcesLocked = tmp27 != 0
tmp28, err := this._io.ReadBitsIntBe(6)
if err != nil {
return err
}
this.Reserved0 = tmp28
tmp29, err := this._io.ReadBitsIntBe(1)
if err != nil {
return err
}
this.PrinterDriverMultifinderCompatible = tmp29 != 0
tmp30, err := this._io.ReadBitsIntBe(1)
if err != nil {
return err
}
this.NoWriteChanges = tmp30 != 0
tmp31, err := this._io.ReadBitsIntBe(1)
if err != nil {
return err
}
this.NeedsCompact = tmp31 != 0
tmp32, err := this._io.ReadBitsIntBe(1)
if err != nil {
return err
}
this.MapNeedsWrite = tmp32 != 0
tmp33, err := this._io.ReadBitsIntBe(5)
if err != nil {
return err
}
this.Reserved1 = tmp33
return err
}
/**
* The attributes as a packed integer,
* as they are stored in the file.
*/
func (this *ResourceFork_ResourceMap_FileAttributes) AsInt() (v uint16, err error) {
if (this._f_asInt) {
return this.asInt, nil
}
_pos, err := this._io.Pos()
if err != nil {
return 0, err
}
_, err = this._io.Seek(int64(0), io.SeekStart)
if err != nil {
return 0, err
}
tmp34, err := this._io.ReadU2be()
if err != nil {
return 0, err
}
this.asInt = tmp34
_, err = this._io.Seek(_pos, io.SeekStart)
if err != nil {
return 0, err
}
this._f_asInt = true
this._f_asInt = true
return this.asInt, nil
}
/**
* TODO What does this attribute actually do,
* and how is it different from `read_only`?
*
* This attribute is undocumented and not defined in ,
* but ResEdit has a checkbox called "Resources Locked" for this attribute.
*/
/**
* These attributes have no known usage or meaning and should always be zero.
*/
/**
* Indicates that this printer driver is compatible with MultiFinder,
* i. e. can be used simultaneously by multiple applications.
* This attribute is only meant to be set on printer driver resource forks.
*
* This attribute is not documented in Inside Macintosh and is not defined in .
* It is documented in technote PR510,
* and ResEdit has a checkbox called "Printer Driver MultiFinder Compatible" for this attribute.
* @see Apple Technical Note PR510 - Printer Driver Q&As, section '"Printer driver is MultiFinder compatible" bit'
*/
/**
* Indicates that the Resource Manager should not write any changes from memory into the resource file.
* Any modification operations requested by the application will return successfully,
* but will not actually update the resource file.
*
* TODO Is this attribute supposed to be set on disk or only in memory?
*/
/**
* Indicates that the resource file should be compacted the next time it is written by the Resource Manager.
* This attribute is only meant to be set in memory;
* it is cleared when the resource file is written to disk.
*
* This attribute is mainly used internally by the Resource Manager,
* but may also be set manually by the application.
*/
/**
* Indicates that the resource map has been changed in memory and should be written to the resource file on the next update.
* This attribute is only meant to be set in memory;
* it is cleared when the resource file is written to disk.
*
* This attribute is mainly used internally by the Resource Manager,
* but may also be set manually by the application.
*/
/**
* These attributes have no known usage or meaning and should always be zero.
*/
/**
* Resource type list and storage area for resource reference lists in the resource map.
*
* The two parts are combined into a single type here for technical reasons:
* the start of the resource reference list area is not stored explicitly in the file,
* instead it always starts directly after the resource type list.
* The simplest way to implement this is by placing both types into a single `seq`.
*/
type ResourceFork_ResourceMap_TypeListAndReferenceLists struct {
TypeList *ResourceFork_ResourceMap_TypeListAndReferenceLists_TypeList
ReferenceLists []byte
_io *kaitai.Stream
_root *ResourceFork
_parent *ResourceFork_ResourceMap
}
func NewResourceFork_ResourceMap_TypeListAndReferenceLists() *ResourceFork_ResourceMap_TypeListAndReferenceLists {
return &ResourceFork_ResourceMap_TypeListAndReferenceLists{
}
}
func (this *ResourceFork_ResourceMap_TypeListAndReferenceLists) Read(io *kaitai.Stream, parent *ResourceFork_ResourceMap, root *ResourceFork) (err error) {
this._io = io
this._parent = parent
this._root = root
tmp35 := NewResourceFork_ResourceMap_TypeListAndReferenceLists_TypeList()
err = tmp35.Read(this._io, this, this._root)
if err != nil {
return err
}
this.TypeList = tmp35
tmp36, err := this._io.ReadBytesFull()
if err != nil {
return err
}
tmp36 = tmp36
this.ReferenceLists = tmp36
return err
}
/**
* The resource map's resource type list.
*/
/**
* Storage area for the resource map's resource reference lists.
*
* According to Inside Macintosh,
* the reference lists are stored contiguously,
* in the same order as their corresponding resource type list entries.
*/
/**
* Resource type list in the resource map.
*/
type ResourceFork_ResourceMap_TypeListAndReferenceLists_TypeList struct {
NumTypesM1 uint16
Entries []*ResourceFork_ResourceMap_TypeListAndReferenceLists_TypeList_TypeListEntry
_io *kaitai.Stream
_root *ResourceFork
_parent *ResourceFork_ResourceMap_TypeListAndReferenceLists
_f_numTypes bool
numTypes int
}
func NewResourceFork_ResourceMap_TypeListAndReferenceLists_TypeList() *ResourceFork_ResourceMap_TypeListAndReferenceLists_TypeList {
return &ResourceFork_ResourceMap_TypeListAndReferenceLists_TypeList{
}
}
func (this *ResourceFork_ResourceMap_TypeListAndReferenceLists_TypeList) Read(io *kaitai.Stream, parent *ResourceFork_ResourceMap_TypeListAndReferenceLists, root *ResourceFork) (err error) {
this._io = io
this._parent = parent
this._root = root
tmp37, err := this._io.ReadU2be()
if err != nil {
return err
}
this.NumTypesM1 = uint16(tmp37)
tmp38, err := this.NumTypes()
if err != nil {
return err
}
for i := 0; i < int(tmp38); i++ {
_ = i
tmp39 := NewResourceFork_ResourceMap_TypeListAndReferenceLists_TypeList_TypeListEntry()
err = tmp39.Read(this._io, this, this._root)
if err != nil {
return err
}
this.Entries = append(this.Entries, tmp39)
}
return err
}
/**
* The number of resource types in this list.
*/
func (this *ResourceFork_ResourceMap_TypeListAndReferenceLists_TypeList) NumTypes() (v int, err error) {
if (this._f_numTypes) {
return this.numTypes, nil
}
tmp40 := (this.NumTypesM1 + 1) % 65536
if tmp40 < 0 {
tmp40 += 65536
}
this.numTypes = int(tmp40)
this._f_numTypes = true
return this.numTypes, nil
}
/**
* The number of resource types in this list,
* minus one.
*
* If the resource list is empty,
* the value of this field is `0xffff`,
* i. e. `-1` truncated to a 16-bit unsigned integer.
*/
/**
* Entries in the resource type list.
*/
/**
* A single entry in the resource type list.
*
* Each entry corresponds to exactly one resource reference list.
*/
type ResourceFork_ResourceMap_TypeListAndReferenceLists_TypeList_TypeListEntry struct {
Type []byte
NumReferencesM1 uint16
OfsReferenceList uint16
_io *kaitai.Stream
_root *ResourceFork
_parent *ResourceFork_ResourceMap_TypeListAndReferenceLists_TypeList
_f_numReferences bool
numReferences int
_f_referenceList bool
referenceList *ResourceFork_ResourceMap_TypeListAndReferenceLists_ReferenceList
}
func NewResourceFork_ResourceMap_TypeListAndReferenceLists_TypeList_TypeListEntry() *ResourceFork_ResourceMap_TypeListAndReferenceLists_TypeList_TypeListEntry {
return &ResourceFork_ResourceMap_TypeListAndReferenceLists_TypeList_TypeListEntry{
}
}
func (this *ResourceFork_ResourceMap_TypeListAndReferenceLists_TypeList_TypeListEntry) Read(io *kaitai.Stream, parent *ResourceFork_ResourceMap_TypeListAndReferenceLists_TypeList, root *ResourceFork) (err error) {
this._io = io
this._parent = parent
this._root = root
tmp41, err := this._io.ReadBytes(int(4))
if err != nil {
return err
}
tmp41 = tmp41
this.Type = tmp41
tmp42, err := this._io.ReadU2be()
if err != nil {
return err
}
this.NumReferencesM1 = uint16(tmp42)
tmp43, err := this._io.ReadU2be()
if err != nil {
return err
}
this.OfsReferenceList = uint16(tmp43)
return err
}
/**
* The number of resources in the reference list for this type.
*/
func (this *ResourceFork_ResourceMap_TypeListAndReferenceLists_TypeList_TypeListEntry) NumReferences() (v int, err error) {
if (this._f_numReferences) {
return this.numReferences, nil
}
tmp44 := (this.NumReferencesM1 + 1) % 65536
if tmp44 < 0 {
tmp44 += 65536
}
this.numReferences = int(tmp44)
this._f_numReferences = true
return this.numReferences, nil
}
/**
* The resource reference list for this resource type.
*/
func (this *ResourceFork_ResourceMap_TypeListAndReferenceLists_TypeList_TypeListEntry) ReferenceList() (v *ResourceFork_ResourceMap_TypeListAndReferenceLists_ReferenceList, err error) {
if (this._f_referenceList) {
return this.referenceList, nil
}
thisIo := this._parent._parent._io
_pos, err := thisIo.Pos()
if err != nil {
return nil, err
}
_, err = thisIo.Seek(int64(this.OfsReferenceList), io.SeekStart)
if err != nil {
return nil, err
}
tmp46, err := this.NumReferences()
if err != nil {
return nil, err
}
tmp45 := NewResourceFork_ResourceMap_TypeListAndReferenceLists_ReferenceList(tmp46)
err = tmp45.Read(thisIo, this, this._root)
if err != nil {
return nil, err
}
this.referenceList = tmp45
_, err = thisIo.Seek(_pos, io.SeekStart)
if err != nil {
return nil, err
}
this._f_referenceList = true
this._f_referenceList = true
return this.referenceList, nil
}
/**
* The four-character type code of the resources in the reference list.
*/
/**
* The number of resources in the reference list for this type,
* minus one.
*
* Empty reference lists should never exist.
*/
/**
* Offset of the resource reference list for this resource type,
* from the start of the resource type list.
*
* Although the offset is relative to the start of the type list,
* it should never point into the type list itself,
* but into the reference list storage area that directly follows it.
* That is,
* it should always be at least `_parent._sizeof`.
*/
/**
* A resource reference list,
* as stored in the reference list area.
*
* Each reference list has exactly one matching entry in the resource type list,
* and describes all resources of a single type in the file.
*/
type ResourceFork_ResourceMap_TypeListAndReferenceLists_ReferenceList struct {
References []*ResourceFork_ResourceMap_TypeListAndReferenceLists_ReferenceList_Reference
NumReferences uint16
_io *kaitai.Stream
_root *ResourceFork
_parent *ResourceFork_ResourceMap_TypeListAndReferenceLists_TypeList_TypeListEntry
}
func NewResourceFork_ResourceMap_TypeListAndReferenceLists_ReferenceList(numReferences uint16) *ResourceFork_ResourceMap_TypeListAndReferenceLists_ReferenceList {
return &ResourceFork_ResourceMap_TypeListAndReferenceLists_ReferenceList{
NumReferences: numReferences,
}
}
func (this *ResourceFork_ResourceMap_TypeListAndReferenceLists_ReferenceList) Read(io *kaitai.Stream, parent *ResourceFork_ResourceMap_TypeListAndReferenceLists_TypeList_TypeListEntry, root *ResourceFork) (err error) {
this._io = io
this._parent = parent
this._root = root
for i := 0; i < int(this.NumReferences); i++ {
_ = i
tmp47 := NewResourceFork_ResourceMap_TypeListAndReferenceLists_ReferenceList_Reference()
err = tmp47.Read(this._io, this, this._root)
if err != nil {
return err
}
this.References = append(this.References, tmp47)
}
return err
}
/**
* The resource references in this reference list.
*/
/**
* A single resource reference in a resource reference list.
*/
type ResourceFork_ResourceMap_TypeListAndReferenceLists_ReferenceList_Reference struct {
Id int16
OfsName uint16
Attributes *ResourceFork_ResourceMap_TypeListAndReferenceLists_ReferenceList_Reference_Attributes
OfsDataBlock uint64
ReservedHandle uint32
_io *kaitai.Stream
_root *ResourceFork
_parent *ResourceFork_ResourceMap_TypeListAndReferenceLists_ReferenceList
_raw_Attributes []byte
_f_name bool
name *ResourceFork_ResourceMap_Name
_f_dataBlock bool
dataBlock *ResourceFork_DataBlock
}
func NewResourceFork_ResourceMap_TypeListAndReferenceLists_ReferenceList_Reference() *ResourceFork_ResourceMap_TypeListAndReferenceLists_ReferenceList_Reference {
return &ResourceFork_ResourceMap_TypeListAndReferenceLists_ReferenceList_Reference{
}
}
func (this *ResourceFork_ResourceMap_TypeListAndReferenceLists_ReferenceList_Reference) Read(io *kaitai.Stream, parent *ResourceFork_ResourceMap_TypeListAndReferenceLists_ReferenceList, root *ResourceFork) (err error) {
this._io = io
this._parent = parent
this._root = root
tmp48, err := this._io.ReadS2be()
if err != nil {
return err
}
this.Id = int16(tmp48)
tmp49, err := this._io.ReadU2be()
if err != nil {
return err
}
this.OfsName = uint16(tmp49)
tmp50, err := this._io.ReadBytes(int(1))
if err != nil {
return err
}
tmp50 = tmp50
this._raw_Attributes = tmp50
_io__raw_Attributes := kaitai.NewStream(bytes.NewReader(this._raw_Attributes))
tmp51 := NewResourceFork_ResourceMap_TypeListAndReferenceLists_ReferenceList_Reference_Attributes()
err = tmp51.Read(_io__raw_Attributes, this, this._root)
if err != nil {
return err
}
this.Attributes = tmp51
tmp52, err := this._io.ReadBitsIntBe(24)
if err != nil {
return err
}
this.OfsDataBlock = tmp52
this._io.AlignToByte()
tmp53, err := this._io.ReadU4be()
if err != nil {
return err
}
this.ReservedHandle = uint32(tmp53)
return err
}
/**
* The name (if any) of the resource described by this reference.
*/
func (this *ResourceFork_ResourceMap_TypeListAndReferenceLists_ReferenceList_Reference) Name() (v *ResourceFork_ResourceMap_Name, err error) {
if (this._f_name) {
return this.name, nil
}
if (this.OfsName != 65535) {
tmp54, err := this._root.ResourceMap()
if err != nil {
return nil, err
}
tmp55, err := tmp54.NamesWithIo()
if err != nil {
return nil, err
}
thisIo := tmp55._io
_pos, err := thisIo.Pos()
if err != nil {
return nil, err
}
_, err = thisIo.Seek(int64(this.OfsName), io.SeekStart)
if err != nil {
return nil, err
}
tmp56 := NewResourceFork_ResourceMap_Name()
err = tmp56.Read(thisIo, this, this._root)
if err != nil {
return nil, err
}
this.name = tmp56
_, err = thisIo.Seek(_pos, io.SeekStart)
if err != nil {
return nil, err
}
this._f_name = true
}
this._f_name = true
return this.name, nil
}
/**
* The data block containing the data for the resource described by this reference.
*/
func (this *ResourceFork_ResourceMap_TypeListAndReferenceLists_ReferenceList_Reference) DataBlock() (v *ResourceFork_DataBlock, err error) {
if (this._f_dataBlock) {
return this.dataBlock, nil
}
tmp57, err := this._root.DataBlocksWithIo()
if err != nil {
return nil, err
}
thisIo := tmp57._io
_pos, err := thisIo.Pos()
if err != nil {
return nil, err
}
_, err = thisIo.Seek(int64(this.OfsDataBlock), io.SeekStart)
if err != nil {
return nil, err
}
tmp58 := NewResourceFork_DataBlock()
err = tmp58.Read(thisIo, this, this._root)
if err != nil {
return nil, err
}
this.dataBlock = tmp58
_, err = thisIo.Seek(_pos, io.SeekStart)
if err != nil {
return nil, err
}
this._f_dataBlock = true
this._f_dataBlock = true
return this.dataBlock, nil
}
/**
* ID of the resource described by this reference.
*/
/**
* Offset of the name for the resource described by this reference,
* from the start of the resource name area.
*
* If the resource has no name,
* the value of this field is `0xffff`
* i. e. `-1` truncated to a 16-bit unsigned integer.
*/
/**
* Attributes of the resource described by this reference.
*/
/**
* Offset of the data block for the resource described by this reference,
* from the start of the resource data area.
*/
/**
* Reserved space for the resource's handle in memory.
*/
/**
* A resource's attributes,
* as stored in a resource reference.
*/
type ResourceFork_ResourceMap_TypeListAndReferenceLists_ReferenceList_Reference_Attributes struct {
SystemReference bool
LoadIntoSystemHeap bool
Purgeable bool
Locked bool
Protected bool
Preload bool
NeedsWrite bool
Compressed bool
_io *kaitai.Stream
_root *ResourceFork
_parent *ResourceFork_ResourceMap_TypeListAndReferenceLists_ReferenceList_Reference
_f_asInt bool
asInt uint8
}
func NewResourceFork_ResourceMap_TypeListAndReferenceLists_ReferenceList_Reference_Attributes() *ResourceFork_ResourceMap_TypeListAndReferenceLists_ReferenceList_Reference_Attributes {
return &ResourceFork_ResourceMap_TypeListAndReferenceLists_ReferenceList_Reference_Attributes{
}
}
func (this *ResourceFork_ResourceMap_TypeListAndReferenceLists_ReferenceList_Reference_Attributes) Read(io *kaitai.Stream, parent *ResourceFork_ResourceMap_TypeListAndReferenceLists_ReferenceList_Reference, root *ResourceFork) (err error) {
this._io = io
this._parent = parent
this._root = root
tmp59, err := this._io.ReadBitsIntBe(1)
if err != nil {
return err
}
this.SystemReference = tmp59 != 0
tmp60, err := this._io.ReadBitsIntBe(1)
if err != nil {
return err
}
this.LoadIntoSystemHeap = tmp60 != 0
tmp61, err := this._io.ReadBitsIntBe(1)
if err != nil {
return err
}
this.Purgeable = tmp61 != 0
tmp62, err := this._io.ReadBitsIntBe(1)
if err != nil {
return err
}
this.Locked = tmp62 != 0
tmp63, err := this._io.ReadBitsIntBe(1)
if err != nil {
return err
}
this.Protected = tmp63 != 0
tmp64, err := this._io.ReadBitsIntBe(1)
if err != nil {
return err
}
this.Preload = tmp64 != 0
tmp65, err := this._io.ReadBitsIntBe(1)
if err != nil {
return err
}
this.NeedsWrite = tmp65 != 0
tmp66, err := this._io.ReadBitsIntBe(1)
if err != nil {
return err
}
this.Compressed = tmp66 != 0
return err
}
/**
* The attributes as a packed integer,
* as they are stored in the file.
*/
func (this *ResourceFork_ResourceMap_TypeListAndReferenceLists_ReferenceList_Reference_Attributes) AsInt() (v uint8, err error) {
if (this._f_asInt) {
return this.asInt, nil
}
_pos, err := this._io.Pos()
if err != nil {
return 0, err
}
_, err = this._io.Seek(int64(0), io.SeekStart)
if err != nil {
return 0, err
}
tmp67, err := this._io.ReadU1()
if err != nil {
return 0, err
}
this.asInt = tmp67
_, err = this._io.Seek(_pos, io.SeekStart)
if err != nil {
return 0, err
}
this._f_asInt = true
this._f_asInt = true
return this.asInt, nil
}
/**
* Indicates that this resource reference is a system reference rather than a regular local reference.
* This attribute is nearly undocumented.
* For all practical purposes,
* it should be considered reserved and should always be zero.
*
* This attribute was last documented in the Promotional Edition of Inside Macintosh,
* in the Resource Manager chapter,
* on pages 37-41,
* in a "System References" section that calls itself "of historical interest only".
* The final versions of Inside Macintosh only mention this attribute as "reserved for use by the Resource Manager".
* contains a `resSysRefBit` constant,
* but no corresponding `resSysRef` constant like for all other resource attributes.
*
* According to the Inside Macintosh Promotional Edition,
* a system reference was effectively an alias pointing to a resource stored in the system file,
* possibly with a different ID and name (but not type) than the system reference.
* If this attribute is set,
* `ofs_data_block` is ignored and should be zero,
* and `reserved_handle` contains
* (in its high and low two bytes, respectively)
* the ID and name offset of the real system resource that this system reference points to.
*
* TODO Do any publicly available Mac OS versions support system references,
* and do any real files/applications use them?
* So far the answer seems to be no,
* but I would like to be proven wrong!
*/
/**
* Indicates that this resource should be loaded into the system heap if possible,
* rather than the application heap.
*
* This attribute is only meant to be used by Mac OS itself,
* for System and Finder resources,
* and not by normal applications.
*
* This attribute may be set both in memory and on disk,
* but it only has any meaning while the resource file is loaded into memory.
*/
/**
* Indicates that this resource's data should be purgeable by the Mac OS Memory Manager.
* This allows the resource data to be purged from memory if space is needed on the heap.
* Purged resources can later be reloaded from disk if their data is needed again.
*
* If the `locked` attribute is set,
* this attribute has no effect
* (i. e. locked resources are never purgeable).
*
* This attribute may be set both in memory and on disk,
* but it only has any meaning while the resource file is loaded into memory.
*/
/**
* Indicates that this resource's data should be locked to the Mac OS Memory Manager.
* This prevents the resource data from being moved when the heap is compacted.
*
* This attribute may be set both in memory and on disk,
* but it only has any meaning while the resource file is loaded into memory.
*/
/**
* Indicates that this resource should be protected (i. e. unmodifiable) in memory.
* This prevents the application from using the Resource Manager to change the resource's data or metadata,
* or delete it.
* The only exception are the resource's attributes,
* which can always be changed,
* even for protected resources.
* This allows protected resources to be unprotected again by the application.
*
* This attribute may be set both in memory and on disk,
* but it only has any meaning while the resource file is loaded into memory.
*/
/**
* Indicates that this resource's data should be immediately loaded into memory when the resource file is opened.
*
* This attribute may be set both in memory and on disk,
* but it only has any meaning when the resource file is first opened.
*/
/**
* Indicates that this resource's data has been changed in memory and should be written to the resource file on the next update.
* This attribute is only meant to be set in memory;
* it is cleared when the resource file is written to disk.
*
* This attribute is used internally by the Resource Manager and should not be set manually by the application.
*/
/**
* Indicates that this resource's data is compressed.
* Compressed resource data is decompressed transparently by the Resource Manager when reading.
*
* For a detailed description of the structure of compressed resources as they are stored in the file,
* see the compressed_resource.ksy spec.
*/
/**
* A resource name,
* as stored in the resource name storage area in the resource map.
*
* The resource names are not required to appear in any particular order.
* There may be unused space between and around resource names,
* but in practice they are often contiguous.
*/
type ResourceFork_ResourceMap_Name struct {
LenValue uint8
Value []byte
_io *kaitai.Stream
_root *ResourceFork
_parent *ResourceFork_ResourceMap_TypeListAndReferenceLists_ReferenceList_Reference
}
func NewResourceFork_ResourceMap_Name() *ResourceFork_ResourceMap_Name {
return &ResourceFork_ResourceMap_Name{
}
}
func (this *ResourceFork_ResourceMap_Name) Read(io *kaitai.Stream, parent *ResourceFork_ResourceMap_TypeListAndReferenceLists_ReferenceList_Reference, root *ResourceFork) (err error) {
this._io = io
this._parent = parent
this._root = root
tmp68, err := this._io.ReadU1()
if err != nil {
return err
}
this.LenValue = tmp68
tmp69, err := this._io.ReadBytes(int(this.LenValue))
if err != nil {
return err
}
tmp69 = tmp69
this.Value = tmp69
return err
}
/**
* The length of the resource name, in bytes.
*/
/**
* The resource name.
*
* This field is exposed as a byte array,
* because there is no universal encoding for resource names.
* Most Classic Mac software does not deal with encodings explicitly and instead assumes that all strings,
* including resource names,
* use the system encoding,
* which varies depending on the system language.
* This means that resource names can use different encodings depending on what system language they were created with.
*
* Many resource names are plain ASCII,
* meaning that the encoding often does not matter
* (because all Mac OS encodings are ASCII-compatible).
* For non-ASCII resource names,
* the most common encoding is perhaps MacRoman
* (used for English and other Western languages),
* but other encodings are also sometimes used,
* especially for software in non-Western languages.
*
* There is no requirement that all names in a single resource file use the same encoding.
* For example,
* localized software may have some (but not all) of its resource names translated.
* For non-Western languages,
* this can lead to some resource names using MacRoman,
* and others using a different encoding.
*/