I have found conflicting information about the DOS .exe header fields specifying the image size. http://www.delorie.com/djgpp/doc/exe/ indicates that the first field (f2) should be image_size modulo 512, and the second field (f4) should be image_size divided by 512, rounded up. However other documentation specifies that f2 should be 512 if the image_size is divisible by 512. Some software use the formula f2 + f4 * 512
.
Thus if image_size is 2046 bytes, then this is correct: f2=510, f4=4.
So if the image_size is 2048 bytes, which are the correct values?
Is there some definitive documentation about this?
(Maybe I should look at what OpenWatcom produces and what FreeDOS and DOSBox use.)
This answer is based on observing the .exe output of OpenWatcom (owcc -bdos -mcmodel=s
) for the example image_size values in the question, and the .exe files in FreeDOS 1.2.
min_extra_paragraphs
(uint16 at offset 10) is the size of uninitialized data (.bss, and usually includes the stack) divided by 16, rounded up.bytes_in_last_block
(uint16 at offset 2) is (as generated by OpenWatcom) image_size modulo 512. Instead of the value 0, the value 512 can also be used.blocks_in_file
(uint16 at offset 4) is image_size divided by 512, rounded up.bytes_in_last_block
& 511) + blocks_in_file
* 512.bytes_in_last_block
? bytes_in_last_block
: 512) - 512) + blocks_in_file
* 512. This is equivalent to to the formula above for 0 <= bytes_in_last_block
<= 512. Larger values of bytes_in_last_block
are invalid, and should be reported as an error.blocks_in_file
* 512.bytes_in_last_block
, and loads (blocks_in_file
* 32) - header_paragraphs
bytes, which is equivalent to using image_size <= blocks_in_file
* 512.Examples:
bytes_in_last_block
=510, f4=blocks_in_file
=4.bytes_in_last_block
=0, f4=blocks_in_file
=4, and this is also correct: f2=bytes_in_last_block
=512, f4=blocks_in_file
=4.