diff options
author | Alexandru Macovei <[email protected]> | 2021-03-30 21:06:57 +0100 |
---|---|---|
committer | Alexandru Macovei <[email protected]> | 2021-04-06 14:01:31 +0100 |
commit | fb1f544e2479addd5957688e297ea04ddf0cf249 (patch) | |
tree | cad7e5fce89b5b42d46ea5c9fe6f5bc12ed7c03e | |
parent | 4bc8a018302d53951ae855ba57d07095a16ef182 (diff) |
Use Box'es to reduce size of hir_def::expr::Expr from 128 to 72 bytes (on 64bit systems)
Rationale: only a minority of variants used almost half the size.
By keeping large members (especially in Option) behind a box
the memory cost is only payed when the large variants are needed.
This reduces the size Vec<Expr> needs to allocate.
-rw-r--r-- | crates/hir_def/src/body/lower.rs | 16 | ||||
-rw-r--r-- | crates/hir_def/src/expr.rs | 8 | ||||
-rw-r--r-- | crates/hir_ty/src/infer/expr.rs | 10 |
3 files changed, 22 insertions, 12 deletions
diff --git a/crates/hir_def/src/body/lower.rs b/crates/hir_def/src/body/lower.rs index 63e89a1f4..73e7aee33 100644 --- a/crates/hir_def/src/body/lower.rs +++ b/crates/hir_def/src/body/lower.rs | |||
@@ -322,8 +322,10 @@ impl ExprCollector<'_> { | |||
322 | Vec::new() | 322 | Vec::new() |
323 | }; | 323 | }; |
324 | let method_name = e.name_ref().map(|nr| nr.as_name()).unwrap_or_else(Name::missing); | 324 | let method_name = e.name_ref().map(|nr| nr.as_name()).unwrap_or_else(Name::missing); |
325 | let generic_args = | 325 | let generic_args = e |
326 | e.generic_arg_list().and_then(|it| GenericArgs::from_ast(&self.ctx(), it)); | 326 | .generic_arg_list() |
327 | .and_then(|it| GenericArgs::from_ast(&self.ctx(), it)) | ||
328 | .map(Box::new); | ||
327 | self.alloc_expr( | 329 | self.alloc_expr( |
328 | Expr::MethodCall { receiver, method_name, args, generic_args }, | 330 | Expr::MethodCall { receiver, method_name, args, generic_args }, |
329 | syntax_ptr, | 331 | syntax_ptr, |
@@ -385,7 +387,7 @@ impl ExprCollector<'_> { | |||
385 | self.alloc_expr(Expr::Yield { expr }, syntax_ptr) | 387 | self.alloc_expr(Expr::Yield { expr }, syntax_ptr) |
386 | } | 388 | } |
387 | ast::Expr::RecordExpr(e) => { | 389 | ast::Expr::RecordExpr(e) => { |
388 | let path = e.path().and_then(|path| self.expander.parse_path(path)); | 390 | let path = e.path().and_then(|path| self.expander.parse_path(path)).map(Box::new); |
389 | let record_lit = if let Some(nfl) = e.record_expr_field_list() { | 391 | let record_lit = if let Some(nfl) = e.record_expr_field_list() { |
390 | let fields = nfl | 392 | let fields = nfl |
391 | .fields() | 393 | .fields() |
@@ -430,7 +432,7 @@ impl ExprCollector<'_> { | |||
430 | } | 432 | } |
431 | ast::Expr::CastExpr(e) => { | 433 | ast::Expr::CastExpr(e) => { |
432 | let expr = self.collect_expr_opt(e.expr()); | 434 | let expr = self.collect_expr_opt(e.expr()); |
433 | let type_ref = TypeRef::from_ast_opt(&self.ctx(), e.ty()); | 435 | let type_ref = Box::new(TypeRef::from_ast_opt(&self.ctx(), e.ty())); |
434 | self.alloc_expr(Expr::Cast { expr, type_ref }, syntax_ptr) | 436 | self.alloc_expr(Expr::Cast { expr, type_ref }, syntax_ptr) |
435 | } | 437 | } |
436 | ast::Expr::RefExpr(e) => { | 438 | ast::Expr::RefExpr(e) => { |
@@ -469,8 +471,10 @@ impl ExprCollector<'_> { | |||
469 | arg_types.push(type_ref); | 471 | arg_types.push(type_ref); |
470 | } | 472 | } |
471 | } | 473 | } |
472 | let ret_type = | 474 | let ret_type = e |
473 | e.ret_type().and_then(|r| r.ty()).map(|it| TypeRef::from_ast(&self.ctx(), it)); | 475 | .ret_type() |
476 | .and_then(|r| r.ty()) | ||
477 | .map(|it| Box::new(TypeRef::from_ast(&self.ctx(), it))); | ||
474 | let body = self.collect_expr_opt(e.body()); | 478 | let body = self.collect_expr_opt(e.body()); |
475 | self.alloc_expr(Expr::Lambda { args, arg_types, ret_type, body }, syntax_ptr) | 479 | self.alloc_expr(Expr::Lambda { args, arg_types, ret_type, body }, syntax_ptr) |
476 | } | 480 | } |
diff --git a/crates/hir_def/src/expr.rs b/crates/hir_def/src/expr.rs index 6c7376fad..ba00b9609 100644 --- a/crates/hir_def/src/expr.rs +++ b/crates/hir_def/src/expr.rs | |||
@@ -86,7 +86,7 @@ pub enum Expr { | |||
86 | receiver: ExprId, | 86 | receiver: ExprId, |
87 | method_name: Name, | 87 | method_name: Name, |
88 | args: Vec<ExprId>, | 88 | args: Vec<ExprId>, |
89 | generic_args: Option<GenericArgs>, | 89 | generic_args: Option<Box<GenericArgs>>, |
90 | }, | 90 | }, |
91 | Match { | 91 | Match { |
92 | expr: ExprId, | 92 | expr: ExprId, |
@@ -106,7 +106,7 @@ pub enum Expr { | |||
106 | expr: Option<ExprId>, | 106 | expr: Option<ExprId>, |
107 | }, | 107 | }, |
108 | RecordLit { | 108 | RecordLit { |
109 | path: Option<Path>, | 109 | path: Option<Box<Path>>, |
110 | fields: Vec<RecordLitField>, | 110 | fields: Vec<RecordLitField>, |
111 | spread: Option<ExprId>, | 111 | spread: Option<ExprId>, |
112 | }, | 112 | }, |
@@ -131,7 +131,7 @@ pub enum Expr { | |||
131 | }, | 131 | }, |
132 | Cast { | 132 | Cast { |
133 | expr: ExprId, | 133 | expr: ExprId, |
134 | type_ref: TypeRef, | 134 | type_ref: Box<TypeRef>, |
135 | }, | 135 | }, |
136 | Ref { | 136 | Ref { |
137 | expr: ExprId, | 137 | expr: ExprId, |
@@ -162,7 +162,7 @@ pub enum Expr { | |||
162 | Lambda { | 162 | Lambda { |
163 | args: Vec<PatId>, | 163 | args: Vec<PatId>, |
164 | arg_types: Vec<Option<TypeRef>>, | 164 | arg_types: Vec<Option<TypeRef>>, |
165 | ret_type: Option<TypeRef>, | 165 | ret_type: Option<Box<TypeRef>>, |
166 | body: ExprId, | 166 | body: ExprId, |
167 | }, | 167 | }, |
168 | Tuple { | 168 | Tuple { |
diff --git a/crates/hir_ty/src/infer/expr.rs b/crates/hir_ty/src/infer/expr.rs index ff564106b..2fcc7c549 100644 --- a/crates/hir_ty/src/infer/expr.rs +++ b/crates/hir_ty/src/infer/expr.rs | |||
@@ -317,7 +317,13 @@ impl<'a> InferenceContext<'a> { | |||
317 | self.normalize_associated_types_in(ret_ty) | 317 | self.normalize_associated_types_in(ret_ty) |
318 | } | 318 | } |
319 | Expr::MethodCall { receiver, args, method_name, generic_args } => self | 319 | Expr::MethodCall { receiver, args, method_name, generic_args } => self |
320 | .infer_method_call(tgt_expr, *receiver, &args, &method_name, generic_args.as_ref()), | 320 | .infer_method_call( |
321 | tgt_expr, | ||
322 | *receiver, | ||
323 | &args, | ||
324 | &method_name, | ||
325 | generic_args.as_deref(), | ||
326 | ), | ||
321 | Expr::Match { expr, arms } => { | 327 | Expr::Match { expr, arms } => { |
322 | let input_ty = self.infer_expr(*expr, &Expectation::none()); | 328 | let input_ty = self.infer_expr(*expr, &Expectation::none()); |
323 | 329 | ||
@@ -398,7 +404,7 @@ impl<'a> InferenceContext<'a> { | |||
398 | TyKind::Never.intern(&Interner) | 404 | TyKind::Never.intern(&Interner) |
399 | } | 405 | } |
400 | Expr::RecordLit { path, fields, spread } => { | 406 | Expr::RecordLit { path, fields, spread } => { |
401 | let (ty, def_id) = self.resolve_variant(path.as_ref()); | 407 | let (ty, def_id) = self.resolve_variant(path.as_deref()); |
402 | if let Some(variant) = def_id { | 408 | if let Some(variant) = def_id { |
403 | self.write_variant_resolution(tgt_expr.into(), variant); | 409 | self.write_variant_resolution(tgt_expr.into(), variant); |
404 | } | 410 | } |