diff options
author | bors[bot] <bors[bot]@users.noreply.github.com> | 2019-01-14 20:58:20 +0000 |
---|---|---|
committer | bors[bot] <bors[bot]@users.noreply.github.com> | 2019-01-14 20:58:20 +0000 |
commit | e8e82ce032f8678929b015e6f70ac060bb2cf94c (patch) | |
tree | 9fb158e9f7115bb70cf2b8623b70710c55497ed4 /crates/ra_hir/src/expr.rs | |
parent | 784ff638e549a27503b719e5c2f0009b40d25364 (diff) | |
parent | 37ba237e6686d94783d1f025d23823ad7c0cb0c8 (diff) |
Merge #485
485: Add type inference for a bunch of primitives r=flodiebold a=marcusklaas
This PR adds inference for `&str`, `&[u8]`, `char`, `bool`, floats and integers. For floats and integers it uses type variables to infer the exact type, i.e. `u32`, from context when it's not annotated explicitly.
I'm not quite happy with the implementation yet, but I think it mostly works now.
Co-authored-by: Marcus Klaas de Vries <[email protected]>
Diffstat (limited to 'crates/ra_hir/src/expr.rs')
-rw-r--r-- | crates/ra_hir/src/expr.rs | 56 |
1 files changed, 54 insertions, 2 deletions
diff --git a/crates/ra_hir/src/expr.rs b/crates/ra_hir/src/expr.rs index f0936e9f3..5081466a2 100644 --- a/crates/ra_hir/src/expr.rs +++ b/crates/ra_hir/src/expr.rs | |||
@@ -5,9 +5,12 @@ use rustc_hash::FxHashMap; | |||
5 | 5 | ||
6 | use ra_arena::{Arena, RawId, impl_arena_id, map::ArenaMap}; | 6 | use ra_arena::{Arena, RawId, impl_arena_id, map::ArenaMap}; |
7 | use ra_db::{LocalSyntaxPtr, Cancelable}; | 7 | use ra_db::{LocalSyntaxPtr, Cancelable}; |
8 | use ra_syntax::ast::{self, AstNode, LoopBodyOwner, ArgListOwner, NameOwner}; | 8 | use ra_syntax::{ |
9 | ast::{self, AstNode, LoopBodyOwner, ArgListOwner, NameOwner, LiteralFlavor} | ||
10 | }; | ||
9 | 11 | ||
10 | use crate::{Path, type_ref::{Mutability, TypeRef}, Name, HirDatabase, DefId, Def, name::AsName}; | 12 | use crate::{Path, type_ref::{Mutability, TypeRef}, Name, HirDatabase, DefId, Def, name::AsName}; |
13 | use crate::ty::primitive::{UintTy, UncertainIntTy, UncertainFloatTy}; | ||
11 | 14 | ||
12 | #[derive(Debug, Clone, Copy, PartialEq, Eq, PartialOrd, Ord, Hash)] | 15 | #[derive(Debug, Clone, Copy, PartialEq, Eq, PartialOrd, Ord, Hash)] |
13 | pub struct ExprId(RawId); | 16 | pub struct ExprId(RawId); |
@@ -104,6 +107,16 @@ impl BodySyntaxMapping { | |||
104 | } | 107 | } |
105 | 108 | ||
106 | #[derive(Debug, Clone, Eq, PartialEq)] | 109 | #[derive(Debug, Clone, Eq, PartialEq)] |
110 | pub enum Literal { | ||
111 | String(String), | ||
112 | ByteString(Vec<u8>), | ||
113 | Char(char), | ||
114 | Bool(bool), | ||
115 | Int(u64, UncertainIntTy), | ||
116 | Float(u64, UncertainFloatTy), // FIXME: f64 is not Eq | ||
117 | } | ||
118 | |||
119 | #[derive(Debug, Clone, Eq, PartialEq)] | ||
107 | pub enum Expr { | 120 | pub enum Expr { |
108 | /// This is produced if syntax tree does not have a required expression piece. | 121 | /// This is produced if syntax tree does not have a required expression piece. |
109 | Missing, | 122 | Missing, |
@@ -186,6 +199,7 @@ pub enum Expr { | |||
186 | Tuple { | 199 | Tuple { |
187 | exprs: Vec<ExprId>, | 200 | exprs: Vec<ExprId>, |
188 | }, | 201 | }, |
202 | Literal(Literal), | ||
189 | } | 203 | } |
190 | 204 | ||
191 | pub use ra_syntax::ast::PrefixOp as UnaryOp; | 205 | pub use ra_syntax::ast::PrefixOp as UnaryOp; |
@@ -305,6 +319,7 @@ impl Expr { | |||
305 | f(*expr); | 319 | f(*expr); |
306 | } | 320 | } |
307 | } | 321 | } |
322 | Expr::Literal(_) => {} | ||
308 | } | 323 | } |
309 | } | 324 | } |
310 | } | 325 | } |
@@ -633,13 +648,50 @@ impl ExprCollector { | |||
633 | let exprs = e.exprs().map(|expr| self.collect_expr(expr)).collect(); | 648 | let exprs = e.exprs().map(|expr| self.collect_expr(expr)).collect(); |
634 | self.alloc_expr(Expr::Tuple { exprs }, syntax_ptr) | 649 | self.alloc_expr(Expr::Tuple { exprs }, syntax_ptr) |
635 | } | 650 | } |
651 | ast::ExprKind::Literal(e) => { | ||
652 | let child = if let Some(child) = e.literal_expr() { | ||
653 | child | ||
654 | } else { | ||
655 | return self.alloc_expr(Expr::Missing, syntax_ptr); | ||
656 | }; | ||
657 | |||
658 | let lit = match child.flavor() { | ||
659 | LiteralFlavor::IntNumber { suffix } => { | ||
660 | let known_name = suffix | ||
661 | .map(|s| Name::new(s)) | ||
662 | .and_then(|name| UncertainIntTy::from_name(&name)); | ||
663 | |||
664 | Literal::Int( | ||
665 | Default::default(), | ||
666 | known_name.unwrap_or(UncertainIntTy::Unknown), | ||
667 | ) | ||
668 | } | ||
669 | LiteralFlavor::FloatNumber { suffix } => { | ||
670 | let known_name = suffix | ||
671 | .map(|s| Name::new(s)) | ||
672 | .and_then(|name| UncertainFloatTy::from_name(&name)); | ||
673 | |||
674 | Literal::Float( | ||
675 | Default::default(), | ||
676 | known_name.unwrap_or(UncertainFloatTy::Unknown), | ||
677 | ) | ||
678 | } | ||
679 | LiteralFlavor::ByteString => Literal::ByteString(Default::default()), | ||
680 | LiteralFlavor::String => Literal::String(Default::default()), | ||
681 | LiteralFlavor::Byte => { | ||
682 | Literal::Int(Default::default(), UncertainIntTy::Unsigned(UintTy::U8)) | ||
683 | } | ||
684 | LiteralFlavor::Bool => Literal::Bool(Default::default()), | ||
685 | LiteralFlavor::Char => Literal::Char(Default::default()), | ||
686 | }; | ||
687 | self.alloc_expr(Expr::Literal(lit), syntax_ptr) | ||
688 | } | ||
636 | 689 | ||
637 | // TODO implement HIR for these: | 690 | // TODO implement HIR for these: |
638 | ast::ExprKind::Label(_e) => self.alloc_expr(Expr::Missing, syntax_ptr), | 691 | ast::ExprKind::Label(_e) => self.alloc_expr(Expr::Missing, syntax_ptr), |
639 | ast::ExprKind::IndexExpr(_e) => self.alloc_expr(Expr::Missing, syntax_ptr), | 692 | ast::ExprKind::IndexExpr(_e) => self.alloc_expr(Expr::Missing, syntax_ptr), |
640 | ast::ExprKind::ArrayExpr(_e) => self.alloc_expr(Expr::Missing, syntax_ptr), | 693 | ast::ExprKind::ArrayExpr(_e) => self.alloc_expr(Expr::Missing, syntax_ptr), |
641 | ast::ExprKind::RangeExpr(_e) => self.alloc_expr(Expr::Missing, syntax_ptr), | 694 | ast::ExprKind::RangeExpr(_e) => self.alloc_expr(Expr::Missing, syntax_ptr), |
642 | ast::ExprKind::Literal(_e) => self.alloc_expr(Expr::Missing, syntax_ptr), | ||
643 | } | 695 | } |
644 | } | 696 | } |
645 | 697 | ||