RetroLinker
Linker for several 8-bit, 16-bit and 32-bit formats
Loading...
Searching...
No Matches
bwexp.h
1#ifndef BWEXP_H
2#define BWEXP_H
3
4#include "../common.h"
5#include "../dumper/dumper.h"
6#include "../linker/options.h"
7#include "../linker/segment_manager.h"
8#include "mzexe.h"
9
10namespace DOS16M
11{
15 class BWFormat : public virtual Linker::SegmentManager
16 {
17 public:
19 {
20 public:
21 Linker::Option<std::string> stub{"stub", "Filename for stub that gets prepended to executable"};
22
24 {
25 InitializeFields(stub);
26 }
27 };
28
29 void ReadFile(Linker::Reader& rd) override;
30
31 bool FormatSupportsSegmentation() const override;
32
33 bool FormatIs16bit() const override;
34
35 bool FormatIsProtectedMode() const override;
36
37 unsigned FormatAdditionalSectionFlags(std::string section_name) const override;
38
40 {
41 public:
42 enum access_type
43 {
44 TYPE_DATA = 0x92,
45 TYPE_CODE = 0x9A,
46 };
47 access_type access;
48
49 enum flag_type
50 {
51 FLAG_EMPTY = 0x2000,
52 FLAG_TRANSPARENT = 0x8000,
53 };
54 flag_type flags;
55
56 uint32_t address = 0;
57 uint32_t total_length;
58 uint32_t size = 0; // only used for reading
59
60 AbstractSegment(unsigned access = TYPE_DATA, unsigned flags = 0, uint32_t total_length = 0)
61 : access(access_type(access)), flags(flag_type(flags)), total_length(total_length)
62 {
63 }
64
65 virtual ~AbstractSegment();
66
70 uint32_t GetTotalSize();
71
75 virtual void SetTotalSize(uint32_t new_value);
76
80 virtual uint32_t GetSize(const BWFormat& bw) const = 0;
81
82 void ReadHeader(Linker::Reader& rd);
83
84 virtual void ReadContent(Linker::Reader& rd, BWFormat& bw) = 0;
85
89 virtual void WriteContent(Linker::Writer& wr, const BWFormat& bw) const = 0;
90
94 void Prepare(BWFormat& bw);
95
99 void WriteHeader(Linker::Writer& wr, const BWFormat& bw) const;
100
101 virtual void Dump(Dumper::Dumper& dump, const BWFormat& bw, offset_t file_offset, uint16_t selector_offset) const = 0;
102 };
103
105 {
106 public:
107 std::shared_ptr<Linker::Image> image;
108
109 explicit Segment()
110 : AbstractSegment(0, 0, 0), image(nullptr)
111 {
112 }
113
114 Segment(std::shared_ptr<Linker::Segment> segment, unsigned access = TYPE_DATA, unsigned flags = 0)
115 : AbstractSegment(access, flags, segment->TotalSize()), image(segment)
116 {
117 }
118
119 void SetTotalSize(uint32_t new_value) override;
120
121 uint32_t GetSize(const BWFormat& bw) const override;
122
123 void ReadContent(Linker::Reader& rd, BWFormat& bw) override;
124
125 void WriteContent(Linker::Writer& wr, const BWFormat& bw) const override;
126
127 void Dump(Dumper::Dumper& dump, const BWFormat& bw, offset_t file_offset, uint16_t selector_offset) const override;
128 };
129
131 {
132 public:
133 DummySegment(uint32_t total_length, unsigned access = TYPE_DATA, unsigned flags = 0)
134 : AbstractSegment(access, flags, total_length)
135 {
136 }
137
138 void SetTotalSize(uint32_t new_value) override;
139
140 uint32_t GetSize(const BWFormat& bw) const override;
141
142 void ReadContent(Linker::Reader& rd, BWFormat& bw) override;
143
144 void WriteContent(Linker::Writer& wr, const BWFormat& bw) const override;
145
146 void Dump(Dumper::Dumper& dump, const BWFormat& bw, offset_t file_offset, uint16_t selector_offset) const override;
147 };
148
150 {
151 public:
152 uint16_t index;
153
154 RelocationSegment(uint16_t index)
155 : AbstractSegment(TYPE_DATA), index(index)
156 {
157 }
158
162 void SetTotalSize(uint32_t new_value) override;
163
164 uint32_t GetSize(const BWFormat& bw) const override;
165
166 void ReadContent(Linker::Reader& rd, BWFormat& bw) override;
167
168 void WriteContent(Linker::Writer& wr, const BWFormat& bw) const override;
169
170 void Dump(Dumper::Dumper& dump, const BWFormat& bw, offset_t file_offset, uint16_t selector_offset) const override;
171 };
172
177 {
178 RelocationsNone,
179 RelocationsType1,
180 RelocationsType2,
181 };
182 relocations_type option_relocations = RelocationsType2;
183 bool option_force_relocations = true;
184
185 enum exp_flag_type
186 {
187 EXP_FLAG_RELOCATABLE = 0x0001,
188 };
189 exp_flag_type exp_flags = exp_flag_type(0);
190
191 enum option_type
192 {
193 OPTION_RELOCATIONS = 0x1000,
194 };
195 option_type options = option_type(0);
196
198 {
199 public:
200 uint16_t selector = 0;
201 // for RSI-1, this contains a single offset, for RSI-2, a list of all the offsets in a single relocation bundle
202 std::vector<uint16_t> offsets;
203 };
204
205 std::vector<Relocation> relocations_list;
206 std::map<uint16_t, std::set<uint16_t>> relocations_map;
207 uint16_t last_relocation_selector = 0; // only used during reading
208 uint16_t remaining_relocation_offsets = 0; // only used during reading
209 bool must_read_relocation_count = false; // only used during reading
210
211 offset_t MeasureRelocations() const;
212
213 std::shared_ptr<Linker::OptionCollector> GetOptions() override;
214
215 void SetOptions(std::map<std::string, std::string>& options) override;
216
217 offset_t file_size = 0;
218 offset_t min_extra = 0;
219 offset_t max_extra = 0;
220 uint16_t ss = 0, sp = 0, cs = 0, ip = 0, relocsel = 0;
221 uint16_t runtime_gdt_length = 0xFFFF;
222 uint16_t version = 0;
223 uint32_t next_header_offset = 0;
224 uint32_t debug_info_offset = 0; /* TODO: ??? */
225 uint16_t last_used_selector = 0;
226 uint16_t first_selector = 0x0080; /* TODO: make dynamic */
227 uint32_t private_xm = 0; /* TODO: make parameter */
228 uint16_t ext_reserve = 0; /* TODO: ??? */
229 uint16_t transparent_stack = 0; /* TODO: ??? */
230 uint32_t program_size = 0; /* TODO: ??? */
231 uint16_t gdt_size = 0;
232 uint8_t default_memory_strategy = 0; /* TODO: ??? */
233 uint16_t transfer_buffer_size = 0; /* TODO: ??? */
234 std::string exp_name; /* TODO: ??? */
235
236 mutable Microsoft::MZStubWriter stub;
237
238 std::vector<std::unique_ptr<AbstractSegment>> segments;
239 std::map<std::shared_ptr<Linker::Segment>, size_t> segment_indices;
240 int default_data = 0;
241
242 void OnNewSegment(std::shared_ptr<Linker::Segment> segment) override;
243
244 std::unique_ptr<Script::List> GetScript(Linker::Module& module);
245
246 void Link(Linker::Module& module);
247
248 size_t GetDefaultDataIndex();
249
250 void ProcessModule(Linker::Module& module) override;
251
252 void CalculateValues() override;
253
254 offset_t ImageSize() const override;
255
257 offset_t WriteFile(Linker::Writer& wr) const override;
258
259 void Dump(Dumper::Dumper& dump) const override;
260
262 std::string GetDefaultExtension(Linker::Module& module, std::string filename) const override;
263 };
264}
265
266#endif /* BWEXP_H */
virtual void WriteContent(Linker::Writer &wr, const BWFormat &bw) const =0
Produces the binary contents of the segment.
virtual uint32_t GetSize(const BWFormat &bw) const =0
Retrieves size of segment. Some subclasses might calculate this dynamically.
uint32_t GetTotalSize()
Retrieves the total size of the segment, including the bss.
Definition bwexp.cc:138
virtual void SetTotalSize(uint32_t new_value)
Modifies the total size of the segment, including the bss. Note that this is not guaranteed to work f...
Definition bwexp.cc:143
void Prepare(BWFormat &bw)
Sets up any values before it can be written to file.
Definition bwexp.cc:155
void WriteHeader(Linker::Writer &wr, const BWFormat &bw) const
Produces the GDT entry for the header.
Definition bwexp.cc:178
Definition bwexp.h:131
uint32_t GetSize(const BWFormat &bw) const override
Retrieves size of segment. Some subclasses might calculate this dynamically.
Definition bwexp.cc:251
void SetTotalSize(uint32_t new_value) override
Modifies the total size of the segment, including the bss. Note that this is not guaranteed to work f...
Definition bwexp.cc:246
void WriteContent(Linker::Writer &wr, const BWFormat &bw) const override
Produces the binary contents of the segment.
Definition bwexp.cc:260
uint32_t GetSize(const BWFormat &bw) const override
Retrieves size of segment. Some subclasses might calculate this dynamically.
Definition bwexp.cc:275
void SetTotalSize(uint32_t new_value) override
Invalid call, the size of a relocation segment is calculated dynamically and cannot be changed via a ...
Definition bwexp.cc:270
void WriteContent(Linker::Writer &wr, const BWFormat &bw) const override
Produces the binary contents of the segment.
Definition bwexp.cc:363
Definition bwexp.h:198
Definition bwexp.h:105
uint32_t GetSize(const BWFormat &bw) const override
Retrieves size of segment. Some subclasses might calculate this dynamically.
Definition bwexp.cc:198
void SetTotalSize(uint32_t new_value) override
Modifies the total size of the segment, including the bss. Note that this is not guaranteed to work f...
Definition bwexp.cc:187
void WriteContent(Linker::Writer &wr, const BWFormat &bw) const override
Produces the binary contents of the segment.
Definition bwexp.cc:211
Rational Systems DOS/16M "BW" .exp file.
Definition bwexp.h:16
std::string GetDefaultExtension(Linker::Module &module, std::string filename) const override
Appends a default extension to the filename.
Definition bwexp.cc:887
offset_t ImageSize() const override
Retrieves size of stored data.
Definition bwexp.cc:708
std::shared_ptr< Linker::OptionCollector > GetOptions() override
Returns object containing a sequence of option fields provided with the -S command line flag.
Definition bwexp.cc:468
void CalculateValues() override
Intermediate step between processing module and generating output file to set up headers and manageme...
Definition bwexp.cc:634
void SetOptions(std::map< std::string, std::string > &options) override
Passes command line parameters as settings over to format object.
Definition bwexp.cc:473
relocations_type
BW .exp files support two versions of relocations.
Definition bwexp.h:177
void Dump(Dumper::Dumper &dump) const override
Display file contents in a nice manner.
Definition bwexp.cc:768
bool FormatIsProtectedMode() const override
Whether the format is in protected mode or not (x86 only)
Definition bwexp.cc:117
bool FormatSupportsSegmentation() const override
Whether the format supports multiple segments.
Definition bwexp.cc:107
bool FormatIs16bit() const override
Whether the format is 16-bit or not.
Definition bwexp.cc:112
offset_t WriteFile(Linker::Writer &wr) const override
Stores data in memory to file.
Definition bwexp.cc:713
void ReadFile(Linker::Reader &rd) override
Loads file into memory.
Definition bwexp.cc:10
void ProcessModule(Linker::Module &module) override
Processes the module object and initializes format fields.
Definition bwexp.cc:553
An abstract interface that separates structure and presentation of the data inside a file.
Definition dumper.h:773
offset_t WriteFile(Writer &wr) const override=0
Stores data in memory to file.
Encodes an object module file as a collection of sections, symbols and relocations.
Definition module.h:24
Helper class that contains the options interpreted by the format.
Definition options.h:474
Documents and handles command line options.
Definition options.h:306
virtual std::string GetDefaultExtension(Module &module, std::string filename) const
Appends a default extension to the filename.
A helper class, encapsulating functionality needed to import binary data.
Definition reader.h:20
A helper class to collect sections into segments.
Definition segment_manager.h:32
A helper class, encapsulating functionality needed to export binary data.
Definition writer.h:15
Definition mzexe.h:305