aboutsummaryrefslogtreecommitdiff
path: root/crates/ra_ide/src/syntax_highlighting.rs
diff options
context:
space:
mode:
Diffstat (limited to 'crates/ra_ide/src/syntax_highlighting.rs')
-rw-r--r--crates/ra_ide/src/syntax_highlighting.rs89
1 files changed, 69 insertions, 20 deletions
diff --git a/crates/ra_ide/src/syntax_highlighting.rs b/crates/ra_ide/src/syntax_highlighting.rs
index 6b7874460..c10e15db8 100644
--- a/crates/ra_ide/src/syntax_highlighting.rs
+++ b/crates/ra_ide/src/syntax_highlighting.rs
@@ -497,9 +497,9 @@ fn highlight_element(
497 match name_kind { 497 match name_kind {
498 Some(NameClass::ExternCrate(_)) => HighlightTag::Module.into(), 498 Some(NameClass::ExternCrate(_)) => HighlightTag::Module.into(),
499 Some(NameClass::Definition(def)) => { 499 Some(NameClass::Definition(def)) => {
500 highlight_name(db, def, false) | HighlightModifier::Definition 500 highlight_name(sema, db, def, None, false) | HighlightModifier::Definition
501 } 501 }
502 Some(NameClass::ConstReference(def)) => highlight_name(db, def, false), 502 Some(NameClass::ConstReference(def)) => highlight_name(sema, db, def, None, false),
503 Some(NameClass::FieldShorthand { field, .. }) => { 503 Some(NameClass::FieldShorthand { field, .. }) => {
504 let mut h = HighlightTag::Field.into(); 504 let mut h = HighlightTag::Field.into();
505 if let Definition::Field(field) = field { 505 if let Definition::Field(field) = field {
@@ -532,7 +532,7 @@ fn highlight_element(
532 binding_hash = Some(calc_binding_hash(&name, *shadow_count)) 532 binding_hash = Some(calc_binding_hash(&name, *shadow_count))
533 } 533 }
534 }; 534 };
535 highlight_name(db, def, possibly_unsafe) 535 highlight_name(sema, db, def, Some(name_ref), possibly_unsafe)
536 } 536 }
537 NameRefClass::FieldShorthand { .. } => HighlightTag::Field.into(), 537 NameRefClass::FieldShorthand { .. } => HighlightTag::Field.into(),
538 }, 538 },
@@ -566,9 +566,20 @@ fn highlight_element(
566 } 566 }
567 } 567 }
568 p if p.is_punct() => match p { 568 p if p.is_punct() => match p {
569 T![::] | T![->] | T![=>] | T![&] | T![..] | T![=] | T![@] => { 569 T![&] => {
570 HighlightTag::Operator.into() 570 let h = HighlightTag::Operator.into();
571 let is_unsafe = element
572 .parent()
573 .and_then(ast::RefExpr::cast)
574 .map(|ref_expr| sema.is_unsafe_ref_expr(&ref_expr))
575 .unwrap_or(false);
576 if is_unsafe {
577 h | HighlightModifier::Unsafe
578 } else {
579 h
580 }
571 } 581 }
582 T![::] | T![->] | T![=>] | T![..] | T![=] | T![@] => HighlightTag::Operator.into(),
572 T![!] if element.parent().and_then(ast::MacroCall::cast).is_some() => { 583 T![!] if element.parent().and_then(ast::MacroCall::cast).is_some() => {
573 HighlightTag::Macro.into() 584 HighlightTag::Macro.into()
574 } 585 }
@@ -649,6 +660,18 @@ fn highlight_element(
649 HighlightTag::SelfKeyword.into() 660 HighlightTag::SelfKeyword.into()
650 } 661 }
651 } 662 }
663 T![ref] => element
664 .parent()
665 .and_then(ast::IdentPat::cast)
666 .and_then(|ident_pat| {
667 if sema.is_unsafe_ident_pat(&ident_pat) {
668 Some(HighlightModifier::Unsafe)
669 } else {
670 None
671 }
672 })
673 .map(|modifier| h | modifier)
674 .unwrap_or(h),
652 _ => h, 675 _ => h,
653 } 676 }
654 } 677 }
@@ -678,7 +701,13 @@ fn is_child_of_impl(element: &SyntaxElement) -> bool {
678 } 701 }
679} 702}
680 703
681fn highlight_name(db: &RootDatabase, def: Definition, possibly_unsafe: bool) -> Highlight { 704fn highlight_name(
705 sema: &Semantics<RootDatabase>,
706 db: &RootDatabase,
707 def: Definition,
708 name_ref: Option<ast::NameRef>,
709 possibly_unsafe: bool,
710) -> Highlight {
682 match def { 711 match def {
683 Definition::Macro(_) => HighlightTag::Macro, 712 Definition::Macro(_) => HighlightTag::Macro,
684 Definition::Field(field) => { 713 Definition::Field(field) => {
@@ -697,6 +726,15 @@ fn highlight_name(db: &RootDatabase, def: Definition, possibly_unsafe: bool) ->
697 let mut h = HighlightTag::Function.into(); 726 let mut h = HighlightTag::Function.into();
698 if func.is_unsafe(db) { 727 if func.is_unsafe(db) {
699 h |= HighlightModifier::Unsafe; 728 h |= HighlightModifier::Unsafe;
729 } else {
730 let is_unsafe = name_ref
731 .and_then(|name_ref| name_ref.syntax().parent())
732 .and_then(ast::MethodCallExpr::cast)
733 .map(|method_call_expr| sema.is_unsafe_method_call(method_call_expr))
734 .unwrap_or(false);
735 if is_unsafe {
736 h |= HighlightModifier::Unsafe;
737 }
700 } 738 }
701 return h; 739 return h;
702 } 740 }
@@ -768,8 +806,18 @@ fn highlight_name_ref_by_syntax(name: ast::NameRef, sema: &Semantics<RootDatabas
768 _ => return default.into(), 806 _ => return default.into(),
769 }; 807 };
770 808
771 let tag = match parent.kind() { 809 match parent.kind() {
772 METHOD_CALL_EXPR => HighlightTag::Function, 810 METHOD_CALL_EXPR => {
811 let mut h = Highlight::new(HighlightTag::Function);
812 let is_unsafe = ast::MethodCallExpr::cast(parent)
813 .map(|method_call_expr| sema.is_unsafe_method_call(method_call_expr))
814 .unwrap_or(false);
815 if is_unsafe {
816 h |= HighlightModifier::Unsafe;
817 }
818
819 h
820 }
773 FIELD_EXPR => { 821 FIELD_EXPR => {
774 let h = HighlightTag::Field; 822 let h = HighlightTag::Field;
775 let is_union = ast::FieldExpr::cast(parent) 823 let is_union = ast::FieldExpr::cast(parent)
@@ -782,7 +830,11 @@ fn highlight_name_ref_by_syntax(name: ast::NameRef, sema: &Semantics<RootDatabas
782 }) 830 })
783 }) 831 })
784 .unwrap_or(false); 832 .unwrap_or(false);
785 return if is_union { h | HighlightModifier::Unsafe } else { h.into() }; 833 if is_union {
834 h | HighlightModifier::Unsafe
835 } else {
836 h.into()
837 }
786 } 838 }
787 PATH_SEGMENT => { 839 PATH_SEGMENT => {
788 let path = match parent.parent().and_then(ast::Path::cast) { 840 let path = match parent.parent().and_then(ast::Path::cast) {
@@ -807,18 +859,15 @@ fn highlight_name_ref_by_syntax(name: ast::NameRef, sema: &Semantics<RootDatabas
807 }; 859 };
808 860
809 match parent.kind() { 861 match parent.kind() {
810 CALL_EXPR => HighlightTag::Function, 862 CALL_EXPR => HighlightTag::Function.into(),
811 _ => { 863 _ => if name.text().chars().next().unwrap_or_default().is_uppercase() {
812 if name.text().chars().next().unwrap_or_default().is_uppercase() { 864 HighlightTag::Struct.into()
813 HighlightTag::Struct 865 } else {
814 } else { 866 HighlightTag::Constant
815 HighlightTag::Constant
816 }
817 } 867 }
868 .into(),
818 } 869 }
819 } 870 }
820 _ => default, 871 _ => default.into(),
821 }; 872 }
822
823 tag.into()
824} 873}