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

Add support for const operands and options to global_asm! #84107

Merged
merged 7 commits into from
May 14, 2021

Conversation

Amanieu
Copy link
Member

@Amanieu Amanieu commented Apr 11, 2021

On x86, the default syntax is also switched to Intel to match asm!.

Currently global_asm! only supports const operands and the att_syntax option. In the future, sym operands will also be supported. However there is no plan to support any of the other operand types or options since they don't make sense in the context of global_asm!.

r? @nagisa

@rust-highfive
Copy link
Collaborator

Some changes occured to rustc_codegen_cranelift

cc @bjorn3

@rust-highfive rust-highfive added the S-waiting-on-review Status: Awaiting review from the assignee but also interested parties. label Apr 11, 2021
@rust-log-analyzer

This comment has been minimized.

@bors
Copy link
Contributor

bors commented Apr 12, 2021

☔ The latest upstream changes (presumably #84112) made this pull request unmergeable. Please resolve the merge conflicts.

@rust-log-analyzer

This comment has been minimized.

@Amanieu
Copy link
Member Author

Amanieu commented Apr 21, 2021

This is now ready for review.

@nagisa
Copy link
Member

nagisa commented Apr 21, 2021

I do have this on my list and meant to get through this last weekend, but was busy with more pressing business throughout it, so didn't really have an opportunity to spend any time reviewing.

@Amanieu
Copy link
Member Author

Amanieu commented Apr 21, 2021

There's quite a few changes, but a large part of it is making ItemKind::GlobalAsm(asm) and ExprKind::InlineAsm(asm) both contain the same {ast,hir}::InlineAsm type. The main difference between the two is that global_asm! is currently only allowed to hold const (and in the future sym) operands, and only supports the att_syntax option.

If you don't think that is appropriate then I can change ItemKind::GlobalAsm to use its own separate AST/HIR representation.

@rust-log-analyzer

This comment has been minimized.

Copy link
Member

@nagisa nagisa left a comment

Choose a reason for hiding this comment

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

Welp, that took way longer than I expected it would.

See comments inline. No major issues other than the one with the collector.

r=me once comments are acknowledged/resolved.

compiler/rustc_ast/src/ast.rs Show resolved Hide resolved
ty::IntTy::I128 => (value as i128).to_string(),
ty::IntTy::Isize => unreachable!(),
},
ty::Float(ty::FloatTy::F32) => f32::from_bits(value as u32).to_string(),
Copy link
Member

Choose a reason for hiding this comment

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

Is it intended that this uses a decimal representation of the float as opposed to writing out a hex value representing the encoding of the float? I don't recall seeing any other way to represent floats in assembly than their hex encoding.

I'm worried mostly that encoding a float here could lead to double-rounding resembling issues – we had some of those in the past where the Rust's formatting algorithm used to produce very slightly different results than those produced by C, but both still "correct". Encoding the bits representation of the float would make me much more comfortable with this.

Copy link
Member

Choose a reason for hiding this comment

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

That said it seems preexisting… so 🤷

Copy link
Member Author

Choose a reason for hiding this comment

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

I'm actually considering getting rid of float constants and only supporting integers. It would work better with typeck too.

};
let value = scalar.assert_bits(ty_and_layout.size);
match ty_and_layout.ty.kind() {
ty::Uint(_) => value.to_string(),
Copy link
Member

Choose a reason for hiding this comment

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

Hm, so I have questions about this. Many architectures have separate instructions that sign-extend or zero-extend the constant operands from, say, 12-bits to the register bit width. Do i recall correctly that otherwise the assembler implementations don't particularly care about whether the constant is represented as a wrapped signed integer or a unsigned integer, as far as it is in range of the maximum bit width for the instruction?

This is probably the correct implementation regardless, but it seems like it could result in some weird action at a distance behaviour.

Copy link
Member Author

Choose a reason for hiding this comment

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

Our job in rustc is to emit the given constant as a string. The actual interpretation of that string is up to the assembler and is not our problem.

The most sensible way of handling this is to format based on the original type of the value, just like format! does.

Copy link
Member

Choose a reason for hiding this comment

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

The problem is exactly in how different pieces of software interpret the same decimal float string. There's very often a difference between different interpretations. Outputting the float as a hexadecimal bit representation avoids this issue entirely and the only party in control of what float ends up being encoded in the binary is Rust. Which sounds like an improvement to me.

compiler/rustc_mir/src/monomorphize/collector.rs Outdated Show resolved Hide resolved
global_asm!("{}", const 0);
global_asm!("{}", const 0i32);
global_asm!("{}", const 0f32);
global_asm!("{}", const 0 as *mut u8);
Copy link
Member

Choose a reason for hiding this comment

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

Allowing pointers may be useful for e.g. embedded use-cases where people might want to refer to e.g. peripherals.

Copy link
Member Author

Choose a reason for hiding this comment

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

There is a separate sym operand type for this which inserts a symbol name. It is not supported in global_asm! yet but will be in the future.

Copy link
Member

Choose a reason for hiding this comment

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

Ah, I meant something different. Like

const GPIOA: *const u32 = 0x8000_4200;

and then users trying to use that pointer as-is. Symbol isn't quite usable here because placing the symbol in the right place would require linker shenanigans people don't generally love all that much.

src/test/ui/asm/bad-arch.stderr Outdated Show resolved Hide resolved
@nagisa nagisa added S-waiting-on-author Status: This is awaiting some action (such as code changes or more information) from the author. and removed S-waiting-on-review Status: Awaiting review from the assignee but also interested parties. labels Apr 24, 2021
@bors
Copy link
Contributor

bors commented Apr 27, 2021

☔ The latest upstream changes (presumably #77246) made this pull request unmergeable. Please resolve the merge conflicts.

@nagisa
Copy link
Member

nagisa commented May 1, 2021

@bors r+ rollup=never but also see the comments. I think those could still be something for a future improvement.

@bors
Copy link
Contributor

bors commented May 1, 2021

📌 Commit 59479edc12a54054c6e3a00d4fb80b79fa257bb9 has been approved by nagisa

@bors bors added S-waiting-on-bors Status: Waiting on bors to run and complete tests. Bors will change the label on completion. and removed S-waiting-on-author Status: This is awaiting some action (such as code changes or more information) from the author. labels May 1, 2021
@bors
Copy link
Contributor

bors commented May 1, 2021

⌛ Testing commit 59479edc12a54054c6e3a00d4fb80b79fa257bb9 with merge 4def5812b498a6b2c87604c9f3bd7868bb01018a...

@rust-log-analyzer

This comment has been minimized.

@bors bors added S-waiting-on-review Status: Awaiting review from the assignee but also interested parties. and removed S-waiting-on-bors Status: Waiting on bors to run and complete tests. Bors will change the label on completion. labels May 8, 2021
@Amanieu
Copy link
Member Author

Amanieu commented May 13, 2021

@bors r=nagisa

@bors
Copy link
Contributor

bors commented May 13, 2021

📌 Commit d9cf2ce has been approved by nagisa

@bors bors added S-waiting-on-bors Status: Waiting on bors to run and complete tests. Bors will change the label on completion. and removed S-waiting-on-review Status: Awaiting review from the assignee but also interested parties. labels May 13, 2021
@rust-log-analyzer

This comment has been minimized.

@Amanieu
Copy link
Member Author

Amanieu commented May 13, 2021

@bors r=nagisa

@bors
Copy link
Contributor

bors commented May 13, 2021

📌 Commit a7ed6a5 has been approved by nagisa

@bors
Copy link
Contributor

bors commented May 13, 2021

⌛ Testing commit a7ed6a5 with merge 17f30e5...

@bors
Copy link
Contributor

bors commented May 14, 2021

☀️ Test successful - checks-actions
Approved by: nagisa
Pushing 17f30e5 to master...

@pnkfelix
Copy link
Member

Performance triage indicates that this PR introduced a 1.4% regression when fully compiling html5ever-opt.

I don't think any performance hit was expected. However, it also seems like this may be just noise.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
merged-by-bors This PR was explicitly merged by bors. S-waiting-on-bors Status: Waiting on bors to run and complete tests. Bors will change the label on completion.
Projects
None yet
Development

Successfully merging this pull request may close these issues.

9 participants