Insert builtin#asm into asm! expansion
This commit is contained in:
parent
15048304e3
commit
3431d586e5
@ -30,8 +30,8 @@ use crate::{
|
||||
expander::Expander,
|
||||
hir::{
|
||||
dummy_expr_id, Array, Binding, BindingAnnotation, BindingId, BindingProblems, CaptureBy,
|
||||
ClosureKind, Expr, ExprId, Label, LabelId, Literal, LiteralOrConst, MatchArm, Movability,
|
||||
OffsetOf, Pat, PatId, RecordFieldPat, RecordLitField, Statement,
|
||||
ClosureKind, Expr, ExprId, InlineAsm, Label, LabelId, Literal, LiteralOrConst, MatchArm,
|
||||
Movability, OffsetOf, Pat, PatId, RecordFieldPat, RecordLitField, Statement,
|
||||
},
|
||||
item_scope::BuiltinShadowMode,
|
||||
lang_item::LangItem,
|
||||
@ -648,7 +648,10 @@ impl ExprCollector<'_> {
|
||||
}
|
||||
}
|
||||
ast::Expr::UnderscoreExpr(_) => self.alloc_expr(Expr::Underscore, syntax_ptr),
|
||||
ast::Expr::AsmExpr(_) => self.missing_expr(),
|
||||
ast::Expr::AsmExpr(e) => {
|
||||
let expr = Expr::InlineAsm(InlineAsm { e: self.collect_expr_opt(e.expr()) });
|
||||
self.alloc_expr(expr, syntax_ptr)
|
||||
}
|
||||
ast::Expr::OffsetOfExpr(e) => {
|
||||
let container = Interned::new(TypeRef::from_ast_opt(&self.ctx(), e.ty()));
|
||||
let fields = e.fields().map(|it| it.as_name()).collect();
|
||||
|
@ -155,8 +155,9 @@ impl Printer<'_> {
|
||||
match expr {
|
||||
Expr::Missing => w!(self, "<EFBFBD>"),
|
||||
Expr::Underscore => w!(self, "_"),
|
||||
Expr::InlineAsm(_) => w!(self, "builtin#asm(_)"),
|
||||
Expr::OffsetOf(offset_of) => {
|
||||
w!(self, "builtin#offset_of!(");
|
||||
w!(self, "builtin#offset_of(");
|
||||
self.print_type_ref(&offset_of.container);
|
||||
w!(
|
||||
self,
|
||||
|
@ -282,6 +282,7 @@ pub enum Expr {
|
||||
Literal(Literal),
|
||||
Underscore,
|
||||
OffsetOf(OffsetOf),
|
||||
InlineAsm(InlineAsm),
|
||||
}
|
||||
|
||||
#[derive(Debug, Clone, PartialEq, Eq)]
|
||||
@ -290,6 +291,11 @@ pub struct OffsetOf {
|
||||
pub fields: Box<[Name]>,
|
||||
}
|
||||
|
||||
#[derive(Debug, Clone, PartialEq, Eq)]
|
||||
pub struct InlineAsm {
|
||||
pub e: ExprId,
|
||||
}
|
||||
|
||||
#[derive(Debug, Clone, Copy, PartialEq, Eq)]
|
||||
pub enum ClosureKind {
|
||||
Closure,
|
||||
@ -349,6 +355,7 @@ impl Expr {
|
||||
match self {
|
||||
Expr::Missing => {}
|
||||
Expr::Path(_) | Expr::OffsetOf(_) => {}
|
||||
Expr::InlineAsm(e) => f(e.e),
|
||||
Expr::If { condition, then_branch, else_branch } => {
|
||||
f(*condition);
|
||||
f(*then_branch);
|
||||
|
@ -453,6 +453,7 @@ impl InferenceContext<'_> {
|
||||
fn walk_expr_without_adjust(&mut self, tgt_expr: ExprId) {
|
||||
match &self.body[tgt_expr] {
|
||||
Expr::OffsetOf(_) => (),
|
||||
Expr::InlineAsm(e) => self.walk_expr_without_adjust(e.e),
|
||||
Expr::If { condition, then_branch, else_branch } => {
|
||||
self.consume_expr(*condition);
|
||||
self.consume_expr(*then_branch);
|
||||
|
@ -844,6 +844,10 @@ impl InferenceContext<'_> {
|
||||
expected
|
||||
}
|
||||
Expr::OffsetOf(_) => TyKind::Scalar(Scalar::Uint(UintTy::Usize)).intern(Interner),
|
||||
Expr::InlineAsm(it) => {
|
||||
self.infer_expr_no_expect(it.e);
|
||||
self.result.standard_types.unit.clone()
|
||||
}
|
||||
};
|
||||
// use a new type variable if we got unknown here
|
||||
let ty = self.insert_type_vars_shallow(ty);
|
||||
|
@ -35,6 +35,7 @@ impl InferenceContext<'_> {
|
||||
fn infer_mut_expr_without_adjust(&mut self, tgt_expr: ExprId, mutability: Mutability) {
|
||||
match &self.body[tgt_expr] {
|
||||
Expr::Missing => (),
|
||||
Expr::InlineAsm(e) => self.infer_mut_expr_without_adjust(e.e, Mutability::Not),
|
||||
Expr::OffsetOf(_) => (),
|
||||
&Expr::If { condition, then_branch, else_branch } => {
|
||||
self.infer_mut_expr(condition, Mutability::Not);
|
||||
|
@ -373,6 +373,9 @@ impl<'ctx> MirLowerCtx<'ctx> {
|
||||
Expr::OffsetOf(_) => {
|
||||
not_supported!("builtin#offset_of")
|
||||
}
|
||||
Expr::InlineAsm(_) => {
|
||||
not_supported!("builtin#asm")
|
||||
}
|
||||
Expr::Missing => {
|
||||
if let DefWithBodyId::FunctionId(f) = self.owner {
|
||||
let assoc = f.lookup(self.db.upcast());
|
||||
|
@ -176,7 +176,15 @@ pre { color: #DCDCCC; background: #3F3F3F; font-size: 22px; padd
|
||||
<span class="macro">assert</span><span class="macro_bang">!</span><span class="parenthesis macro">(</span><span class="bool_literal macro">true</span><span class="comma macro">,</span> <span class="string_literal macro">"</span><span class="format_specifier">{</span><span class="format_specifier">}</span><span class="string_literal macro">"</span><span class="comma macro">,</span> <span class="numeric_literal macro">1</span><span class="parenthesis macro">)</span><span class="semicolon">;</span>
|
||||
<span class="macro">assert</span><span class="macro_bang">!</span><span class="parenthesis macro">(</span><span class="bool_literal macro">true</span><span class="comma macro">,</span> <span class="string_literal macro">"</span><span class="format_specifier">{</span><span class="format_specifier">}</span><span class="string_literal macro"> asdasd"</span><span class="comma macro">,</span> <span class="numeric_literal macro">1</span><span class="parenthesis macro">)</span><span class="semicolon">;</span>
|
||||
<span class="macro">toho</span><span class="macro_bang">!</span><span class="parenthesis macro">(</span><span class="string_literal macro">"</span><span class="format_specifier">{</span><span class="format_specifier">}</span><span class="string_literal macro">fmt"</span><span class="comma macro">,</span> <span class="numeric_literal macro">0</span><span class="parenthesis macro">)</span><span class="semicolon">;</span>
|
||||
<span class="macro unsafe">asm</span><span class="macro_bang">!</span><span class="parenthesis macro">(</span><span class="string_literal macro">"mov eax, </span><span class="format_specifier">{</span><span class="numeric_literal">0</span><span class="format_specifier">}</span><span class="string_literal macro">"</span><span class="parenthesis macro">)</span><span class="semicolon">;</span>
|
||||
<span class="keyword">let</span> <span class="variable declaration">i</span><span class="colon">:</span> <span class="builtin_type">u64</span> <span class="operator">=</span> <span class="numeric_literal">3</span><span class="semicolon">;</span>
|
||||
<span class="keyword">let</span> <span class="variable declaration">o</span><span class="colon">:</span> <span class="builtin_type">u64</span><span class="semicolon">;</span>
|
||||
<span class="macro unsafe">asm</span><span class="macro_bang">!</span><span class="parenthesis macro">(</span>
|
||||
<span class="string_literal macro">"mov </span><span class="format_specifier">{</span><span class="numeric_literal">0</span><span class="format_specifier">}</span><span class="string_literal macro">, </span><span class="format_specifier">{</span><span class="numeric_literal">1</span><span class="format_specifier">}</span><span class="string_literal macro">"</span><span class="comma macro">,</span>
|
||||
<span class="string_literal macro">"add </span><span class="format_specifier">{</span><span class="numeric_literal">0</span><span class="format_specifier">}</span><span class="string_literal macro">, 5"</span><span class="comma macro">,</span>
|
||||
<span class="none macro">out</span><span class="parenthesis macro">(</span><span class="none macro">reg</span><span class="parenthesis macro">)</span> <span class="none macro">o</span><span class="comma macro">,</span>
|
||||
<span class="keyword control macro">in</span><span class="parenthesis macro">(</span><span class="none macro">reg</span><span class="parenthesis macro">)</span> <span class="none macro">i</span><span class="comma macro">,</span>
|
||||
<span class="parenthesis macro">)</span><span class="semicolon">;</span>
|
||||
|
||||
<span class="macro">format_args</span><span class="macro_bang">!</span><span class="parenthesis macro">(</span><span class="none macro">concat</span><span class="punctuation macro">!</span><span class="parenthesis macro">(</span><span class="string_literal macro">"</span><span class="format_specifier">{</span><span class="format_specifier">}</span><span class="string_literal macro">"</span><span class="parenthesis macro">)</span><span class="comma macro">,</span> <span class="string_literal macro">"{}"</span><span class="parenthesis macro">)</span><span class="semicolon">;</span>
|
||||
<span class="macro">format_args</span><span class="macro_bang">!</span><span class="parenthesis macro">(</span><span class="string_literal macro">"</span><span class="format_specifier">{</span><span class="format_specifier">}</span><span class="string_literal macro"> </span><span class="format_specifier">{</span><span class="format_specifier">}</span><span class="string_literal macro"> </span><span class="format_specifier">{</span><span class="format_specifier">}</span><span class="string_literal macro"> </span><span class="format_specifier">{</span><span class="format_specifier">}</span><span class="string_literal macro"> </span><span class="format_specifier">{</span><span class="format_specifier">}</span><span class="string_literal macro"> </span><span class="format_specifier">{</span><span class="format_specifier">}</span><span class="string_literal macro">"</span><span class="comma macro">,</span> <span class="variable macro reference">backslash</span><span class="comma macro">,</span> <span class="none macro">format_args</span><span class="punctuation macro">!</span><span class="parenthesis macro">(</span><span class="string_literal macro">"</span><span class="format_specifier">{</span><span class="format_specifier">}</span><span class="string_literal macro">"</span><span class="comma macro">,</span> <span class="numeric_literal macro">0</span><span class="parenthesis macro">)</span><span class="comma macro">,</span> <span class="unresolved_reference macro">foo</span><span class="comma macro">,</span> <span class="string_literal macro">"bar"</span><span class="comma macro">,</span> <span class="none macro">toho</span><span class="punctuation macro">!</span><span class="parenthesis macro">(</span><span class="parenthesis macro">)</span><span class="comma macro">,</span> <span class="variable macro reference">backslash</span><span class="parenthesis macro">)</span><span class="semicolon">;</span>
|
||||
<span class="brace">}</span></code></pre>
|
@ -254,6 +254,7 @@ fn builtin_expr(p: &mut Parser<'_>) -> Option<CompletedMarker> {
|
||||
} else if p.at_contextual_kw(T![asm]) {
|
||||
p.bump_remap(T![asm]);
|
||||
p.expect(T!['(']);
|
||||
// FIXME: We just put expression here so highlighting kind of keeps working
|
||||
expr(p);
|
||||
p.expect(T![')']);
|
||||
Some(m.complete(p, ASM_EXPR))
|
||||
|
@ -0,0 +1,62 @@
|
||||
SOURCE_FILE
|
||||
FN
|
||||
FN_KW "fn"
|
||||
WHITESPACE " "
|
||||
NAME
|
||||
IDENT "foo"
|
||||
PARAM_LIST
|
||||
L_PAREN "("
|
||||
R_PAREN ")"
|
||||
WHITESPACE " "
|
||||
BLOCK_EXPR
|
||||
STMT_LIST
|
||||
L_CURLY "{"
|
||||
WHITESPACE "\n "
|
||||
EXPR_STMT
|
||||
ASM_EXPR
|
||||
BUILTIN_KW "builtin"
|
||||
POUND "#"
|
||||
ASM_KW "asm"
|
||||
L_PAREN "("
|
||||
LITERAL
|
||||
INT_NUMBER "0"
|
||||
R_PAREN ")"
|
||||
SEMICOLON ";"
|
||||
WHITESPACE "\n "
|
||||
EXPR_STMT
|
||||
FORMAT_ARGS_EXPR
|
||||
BUILTIN_KW "builtin"
|
||||
POUND "#"
|
||||
FORMAT_ARGS_KW "format_args"
|
||||
L_PAREN "("
|
||||
LITERAL
|
||||
INT_NUMBER "0"
|
||||
R_PAREN ")"
|
||||
SEMICOLON ";"
|
||||
WHITESPACE "\n "
|
||||
EXPR_STMT
|
||||
OFFSET_OF_EXPR
|
||||
BUILTIN_KW "builtin"
|
||||
POUND "#"
|
||||
OFFSET_OF_KW "offset_of"
|
||||
L_PAREN "("
|
||||
PATH_TYPE
|
||||
PATH
|
||||
PATH_SEGMENT
|
||||
NAME_REF
|
||||
IDENT "Foo"
|
||||
COMMA ","
|
||||
WHITESPACE " "
|
||||
NAME_REF
|
||||
IDENT "bar"
|
||||
DOT "."
|
||||
NAME_REF
|
||||
IDENT "baz"
|
||||
DOT "."
|
||||
NAME_REF
|
||||
INT_NUMBER "0"
|
||||
R_PAREN ")"
|
||||
SEMICOLON ";"
|
||||
WHITESPACE "\n"
|
||||
R_CURLY "}"
|
||||
WHITESPACE "\n"
|
@ -0,0 +1,5 @@
|
||||
fn foo() {
|
||||
builtin#asm(0);
|
||||
builtin#format_args(0);
|
||||
builtin#offset_of(Foo, bar.baz.0);
|
||||
}
|
@ -379,7 +379,7 @@ OffsetOfExpr =
|
||||
Attr* 'builtin' '#' 'offset_of' '(' Type ',' fields:(NameRef ('.' NameRef)* ) ')'
|
||||
|
||||
AsmExpr =
|
||||
Attr* 'builtin' '#' 'asm' '(' ')'
|
||||
Attr* 'builtin' '#' 'asm' '(' Expr ')'
|
||||
|
||||
FormatArgsExpr =
|
||||
Attr* 'builtin' '#' 'format_args' '(' ')'
|
||||
|
@ -814,6 +814,7 @@ impl AsmExpr {
|
||||
pub fn pound_token(&self) -> Option<SyntaxToken> { support::token(&self.syntax, T![#]) }
|
||||
pub fn asm_token(&self) -> Option<SyntaxToken> { support::token(&self.syntax, T![asm]) }
|
||||
pub fn l_paren_token(&self) -> Option<SyntaxToken> { support::token(&self.syntax, T!['(']) }
|
||||
pub fn expr(&self) -> Option<Expr> { support::child(&self.syntax) }
|
||||
pub fn r_paren_token(&self) -> Option<SyntaxToken> { support::token(&self.syntax, T![')']) }
|
||||
}
|
||||
|
||||
|
Loading…
x
Reference in New Issue
Block a user