Hi! I'm trying to assemble a flat binary with nasm. I've added some constant data after the code, which i was planning on using as a data segment.
However, nasm seems to be persistent in creating labels with an offset from the (absolute) start of the code. So when i try to access the data with ds:label, it fails for obvious reasons.
So, i'm wondering if there's any way to tell nasm to create the labels (or access them?) with a offset relative to a certain section.
I tried the SEG operator, but that doesn't work with flat binaries. The WRT i'm having huge problems with, so if someone could point me in the right direction that would be awesome.
nasm: Labels relative to a section/segment
-
- Posts: 4
- Joined: Tue Dec 07, 2010 3:15 pm
Re: nasm: Labels relative to a section/segment
Why don't you just load the same value into DS as in CS?
-
- Posts: 4
- Joined: Tue Dec 07, 2010 3:15 pm
Re: nasm: Labels relative to a section/segment
Thanks, i actually didn't think of that.berkus wrote:You could use (label - section_start) for addressing.
I was however looking for less tedious solution, so i won't have to write that everytime i need to access my data.
Because i like to keep code and data separated.Hobbes wrote:Why don't you just load the same value into DS as in CS?
Re: nasm: Labels relative to a section/segment
I'm a little confused as to exactly what you are trying here. I assume you are programming in rmode? You do realize that in rmode, your address registers are only 16 bits? So you can only hardcode an absolute address that's below 64K? Is your data section loaded below 64K? Have you tried using an ORG 0 statement? If you are doing anything else, then what berkus suggested is really your only hope. You don't have to do it on every access. You only have to do it once, and store it in a register.
Re: nasm: Labels relative to a section/segment
You could use a macro.llamaswithhats wrote:I was however looking for less tedious solution, so i won't have to write that everytime i need to access my data.
Code: Select all
%define FOO(bar) ((bar) - section_start)
mov ax, [FOO(label)]
-
- Posts: 4
- Joined: Tue Dec 07, 2010 3:15 pm
Re: nasm: Labels relative to a section/segment
I'm actually in the process of transitioning to pmode.bewing wrote:I'm a little confused as to exactly what you are trying here. I assume you are programming in rmode? You do realize that in rmode, your address registers are only 16 bits? So you can only hardcode an absolute address that's below 64K? Is your data section loaded below 64K? Have you tried using an ORG 0 statement? If you are doing anything else, then what berkus suggested is really your only hope. You don't have to do it on every access. You only have to do it once, and store it in a register.
Which was the reason for wanting to separate data and code.
I just wanted to see if there was a way to keep my data section's labels without to much hassle.
I apologize for being a bit cryptic.
Re: nasm: Labels relative to a section/segment
Hi,
For the "binary" output format, the default can be entirely overridden with "section" directives. In the NASM manual "Section 7.1.3; Multisection Support for the bin Format" has a (less than thorough) description of the capabilities. For an example, I have a macro that generates headers, etc for my own executable file format, which sets up sections like this:
As you can see, it's similar to a linker script, even though it is NASM code (for the "binary" output file format).
Basically, in all cases (regardless of whether you're using a linker or the binary output format) the starting address of each section can be controlled; and it would be entirely possible to modify the ".data" section or create your own ".myDS" section; so that the beginning of the section is 0x00000000 and offsets to labels within the section are relative to 0x00000000.
However, I guess I should also point out that for each section there's 2 similar things - the starting offset of the section within the executable file, and the starting address of the section in virtual memory. For the "binary" output file format there are no headers or anything, so if there isn't a simple relationship between the starting offset of the section within the executable file and the starting address of the section in virtual memory, then you'd need to cope with it yourself (e.g. create your own header, so that your loader can figure out which pieces of the file end up at which virtual addresses). For my own executable file format I don't need to do this (the virtual address for a section is the offset in the file plus a fixed constant), but I still have fields in the header that describes where the "executable" area ends, where the "read only" area ends, etc (so that the program loader can setup page attributes appropriately).
Cheers,
Brendan
This isn't technically correct. The labels are an offset from the beginning of the section. For most output file formats the starting address of each section is determined by the linker. For the "binary" output format (where there is no linker) the default behaviour is for sections to follow each other. For example, if ".text" starts at the address 0x8000000 and is 0x00009000 bytes then the ".data" section will begin at the address 0x80009000, and a label that is at offset 0x00000246 in the ".data" section will end up at the address 0x80009246.llamaswithhats wrote:However, nasm seems to be persistent in creating labels with an offset from the (absolute) start of the code.
For the "binary" output format, the default can be entirely overridden with "section" directives. In the NASM manual "Section 7.1.3; Multisection Support for the bin Format" has a (less than thorough) description of the capabilities. For an example, I have a macro that generates headers, etc for my own executable file format, which sets up sections like this:
Code: Select all
SECTION .header progbits start=FILE_START
SECTION .strings progbits follows=.header align=%2
SECTION .text progbits follows=.strings align=%2
SECTION .rodata progbits follows=.text align=%2
SECTION .data progbits follows=.rodata align=%2
SECTION .bss nobits follows=.data align=%2
Basically, in all cases (regardless of whether you're using a linker or the binary output format) the starting address of each section can be controlled; and it would be entirely possible to modify the ".data" section or create your own ".myDS" section; so that the beginning of the section is 0x00000000 and offsets to labels within the section are relative to 0x00000000.
However, I guess I should also point out that for each section there's 2 similar things - the starting offset of the section within the executable file, and the starting address of the section in virtual memory. For the "binary" output file format there are no headers or anything, so if there isn't a simple relationship between the starting offset of the section within the executable file and the starting address of the section in virtual memory, then you'd need to cope with it yourself (e.g. create your own header, so that your loader can figure out which pieces of the file end up at which virtual addresses). For my own executable file format I don't need to do this (the virtual address for a section is the offset in the file plus a fixed constant), but I still have fields in the header that describes where the "executable" area ends, where the "read only" area ends, etc (so that the program loader can setup page attributes appropriately).
Cheers,
Brendan
For all things; perfection is, and will always remain, impossible to achieve in practice. However; by striving for perfection we create things that are as perfect as practically possible. Let the pursuit of perfection be our guide.
-
- Posts: 4
- Joined: Tue Dec 07, 2010 3:15 pm
Re: nasm: Labels relative to a section/segment
Awesome! Thank you good sir.
I was wondering how to use those strange directives (vstart, start, progbits..) and your example made it perfectly clear!
For future reference:
will make sure that the offsets of all labels created in that section will be relative to 0.
I was wondering how to use those strange directives (vstart, start, progbits..) and your example made it perfectly clear!
For future reference:
Code: Select all
section .foo vstart=0