Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Describe the relocations that LLVM is currently using. #7

Merged
merged 6 commits into from
Mar 13, 2017

Conversation

sunfishcode
Copy link
Member

Because we want to be able to write C++ global addresses into the data section,
we can't count on using a get_global to read the value of an imported global to
get the C++ global address. In view of that, and the fact that it's also simpler
to write addresses directly into the code section than use an actual get_global,
drop the get_globals altogether. This results in several changes to the
relocations.

And, add an addend field to C++ global address relocations. I think this ends
up making sense because it makes sense for the addend to be signed, but some of
the relocations apply to fields which are unsigned, so storing the addend in them
is awkward.

LLVM isn't quite finished implementing the stack pointer part of this, and as I wrote this up, I also realized that it's missing support for relocating type indices in call_indirect instructions, however I'm posting it now so that we can start talking about the other parts.

Because we want to be able to write C++ global addresses into the data section,
we can't count on using a get_global to read the value of an imported global to
get the C++ global address. In view of that, and the fact that it's also simpler
to write addresses directly into the code section than use an actual get_global,
drop the get_globals altogether. This results in several changes to the
relocations.

And, add an addend field to C++ global address relocations. I think this ends
up making sense because it makes sense for the addend to be signed, but some of
the relocations apply to fields which are unsigned, so storing the addend in them
is awkward.
Copy link
Member

@sbc100 sbc100 left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

lgtm % comments.

Thanks for working on this. This approach makes sense to me.

Linking.md Outdated
instruction.
- `4 / R_WEBASSEMBLY_GLOBAL_ADDR_SLEB` - a global index encoded as a 5-byte
[varint32]. Used for the immediate argument of a `i32.const` instruction,
e.g. taking the address of a function.
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

taking the address of a global?

Linking.md Outdated
[uint32].
- `3 / R_WEBASSEMBLY_GLOBAL_ADDR_LEB` - a global index encoded as a 5-byte
[varuint32]. Used for the immediate argument of a `load` or `store`
instruction.
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

e.g. reading/writing to a global?

Linking.md Outdated
5-byte [varint32]. Used to refer to the immediate argument of a `i32.const`
instruction, e.g. taking the address of a function.
- `2 / R_WEBASSEMBLY_TABLE_INDEX_I32` - a function table index encoded as a
[uint32].
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I guess this is for function addresses stored in the data segment? perhaps mention that?

Add explanations for the relocations that didn't have them, and fix copypasta.
Linking.md Outdated
i32 global initialized to "STACKTOP" in the "env" module. During linking, only
one of these globals is kept, and it remains the first global. This is a
simple convention which allows code to reference global `0` without needing to
be rewritten.
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

What about the fact that any imported globals come first in the index space of globals? Are we relying on the fact that there will be no imported globals in the final linked executable?

@sbc100
Copy link
Member

sbc100 commented Mar 13, 2017

Can/should we land this now? I'd like to update wabt to support these changes.

This eliminates some ambiguity; this isn't a relocation for an address
of a C++ global, not to be confused with a wasm global.
For example, for the stack pointer global.
@sunfishcode
Copy link
Member Author

I'm still working on the stack pointer issue, but we can merge it now and continue to iterate if that works for you.

This is currently used to identify a stack pointer.
@sbc100
Copy link
Member

sbc100 commented Mar 13, 2017

Yes, lets merge this now and iterate. lgtm

@sbc100
Copy link
Member

sbc100 commented Mar 13, 2017

Can you explain how and why the linker would make use of the new R_WEBASSEMBLY_STACK_POINTER? Is it so that the stack point of each object can be merged into a single global in the output?

@sunfishcode
Copy link
Member Author

Merging, as discussed above. We'll continue to iterate.

Yes, the purpose of R_WEBASSEMBLY_STACK_POINTER is so that the stack pointers of each object can be merged. I'm open to other ideas too.

@sunfishcode sunfishcode merged commit 4a4d7f5 into master Mar 13, 2017
@sunfishcode sunfishcode deleted the llvm-relocs branch March 13, 2017 23:17
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

2 participants