The result of decompressing the contents of the dir stream object is almost as incomprehensible as the compressed data.
It consists of a large number of records of which we want a grand total of two per module.
The records we are interested in are preceded by a large number of records we are not interested in. Most of these records have a length field so it is possible to ‘skip’ them, but some of them do not, so there is nothing for it but to brute force our way through to the ones we want.
The top-level method
func parse() -> [VBAModule]?
{
informationRecord()
projectReferences()
return modules()
}
is reasonably tidy, the others just consist of a lot of calls to a variety of methods for reading the different types of record, for example
private func informationRecord()
{
readRecord(0x01)
readRecord(0x02)
readRecord(0x14)
readRecord(0x03)
readRecord(0x04)
readRecordTwo(0x05)
readRecordTwo(0x06)
readRecord(0x07)
readRecord(0x08)
readRecordThree(0x09)
readRecordTwo(0x0c)
}
The end result should be an array of containing one or more instances of VBAModule
.
struct VBAModule
{
let streamName : String
let offset : UInt32
}
A VBAModule
is simply two pieces of information
-
the name of the stream object that contains the module’s compressed source, and
-
the offset within the stream object at which the compressed data starts.
Copyright (c) 2014 By Simon Lewis. All Rights Reserved.
Unauthorized use and/or duplication of this material without express and written permission from this blog’s author and owner Simon Lewis is strictly prohibited.
Excerpts and links may be used, provided that full and clear credit is given to Simon Lewis and justanapplication.wordpress.com with appropriate and specific direction to the original content.
Leave a Reply