Skip to content

Commit

Permalink
Address problem tighter to nameof usage.
Browse files Browse the repository at this point in the history
  • Loading branch information
nojaf committed Jan 18, 2024
1 parent fb4e72e commit d8ffb9d
Showing 1 changed file with 43 additions and 6 deletions.
49 changes: 43 additions & 6 deletions src/Compiler/Driver/GraphChecking/FileContentMapping.fs
Original file line number Diff line number Diff line change
Expand Up @@ -307,9 +307,27 @@ let visitSynTypeConstraint (tc: SynTypeConstraint) : FileContentEntry list =
| SynTypeConstraint.WhereTyparIsEnum(typeArgs = typeArgs) -> List.collect visitSynType typeArgs
| SynTypeConstraint.WhereTyparIsDelegate(typeArgs = typeArgs) -> List.collect visitSynType typeArgs

/// Special case of `nameof Module` type of expression
let (|NameofExpr|_|) (e: SynExpr) =
let rec stripParen (e: SynExpr) =
match e with
| SynExpr.Paren(expr = expr) -> stripParen expr
| _ -> e

match e with
| SynExpr.App(flag = ExprAtomicFlag.NonAtomic; isInfix = false; funcExpr = SynExpr.Ident nameofIdent; argExpr = moduleNameExpr) ->
if nameofIdent.idText <> "nameof" then
None
else
match stripParen moduleNameExpr with
| SynExpr.Ident moduleNameIdent -> Some moduleNameIdent
| _ -> None
| _ -> None

let visitSynExpr (e: SynExpr) : FileContentEntry list =
let rec visit (e: SynExpr) (continuation: FileContentEntry list -> FileContentEntry list) : FileContentEntry list =
match e with
| NameofExpr moduleNameIdent -> continuation [ visitIdentAsPotentialModuleName moduleNameIdent ]
| SynExpr.Const _ -> continuation []
| SynExpr.Paren(expr = expr) -> visit expr continuation
| SynExpr.Quote(operator = operator; quotedExpr = quotedExpr) ->
Expand Down Expand Up @@ -394,8 +412,8 @@ let visitSynExpr (e: SynExpr) : FileContentEntry list =
| SynExpr.IfThenElse(ifExpr = ifExpr; thenExpr = thenExpr; elseExpr = elseExpr) ->
let continuations = List.map visit (ifExpr :: thenExpr :: Option.toList elseExpr)
Continuation.concatenate continuations continuation
| SynExpr.Typar _ -> continuation []
| SynExpr.Ident ident -> continuation [ visitIdentAsPotentialModuleName ident ]
| SynExpr.Typar _
| SynExpr.Ident _ -> continuation []
| SynExpr.LongIdent(longDotId = longDotId) -> continuation (visitSynLongIdent longDotId)
| SynExpr.LongIdentSet(longDotId, expr, _) -> visit expr (fun nodes -> visitSynLongIdent longDotId @ nodes |> continuation)
| SynExpr.DotGet(expr = expr; longDotId = longDotId) ->
Expand Down Expand Up @@ -522,9 +540,32 @@ let visitSynExpr (e: SynExpr) : FileContentEntry list =

visit e id

/// Special case of `| nameof Module ->` type of pattern
let (|NameofPat|_|) (pat: SynPat) =
let rec stripPats p =
match p with
| SynPat.Paren(pat = pat) -> stripPats pat
| _ -> p

match pat with
| SynPat.LongIdent(longDotId = SynLongIdent(id = [ nameofIdent ]); typarDecls = None; argPats = SynArgPats.Pats [ moduleNamePat ]) ->
if nameofIdent.idText <> "nameof" then
None
else
match stripPats moduleNamePat with
| SynPat.LongIdent(
longDotId = SynLongIdent.SynLongIdent(id = [ moduleNameIdent ]; dotRanges = []; trivia = [ None ])
extraId = None
typarDecls = None
argPats = SynArgPats.Pats []
accessibility = None) -> Some moduleNameIdent
| _ -> None
| _ -> None

let visitPat (p: SynPat) : FileContentEntry list =
let rec visit (p: SynPat) (continuation: FileContentEntry list -> FileContentEntry list) : FileContentEntry list =
match p with
| NameofPat moduleNameIdent -> continuation [ visitIdentAsPotentialModuleName moduleNameIdent ]
| SynPat.Paren(pat = pat) -> visit pat continuation
| SynPat.Typed(pat = pat; targetType = t) -> visit pat (fun nodes -> nodes @ visitSynType t)
| SynPat.Const _ -> continuation []
Expand All @@ -543,10 +584,6 @@ let visitPat (p: SynPat) : FileContentEntry list =
| SynPat.As(lhsPat, rhsPat, _) ->
let continuations = List.map visit [ lhsPat; rhsPat ]
Continuation.concatenate continuations continuation
// Special case of `| nameof Module ->` type of pattern
// We check for `Module` below
| SynPat.LongIdent(longDotId = SynLongIdent(id = [ moduleNameIdent ]); typarDecls = None; argPats = SynArgPats.Pats []) ->
continuation [ visitIdentAsPotentialModuleName moduleNameIdent ]
| SynPat.LongIdent(longDotId = longDotId; typarDecls = typarDecls; argPats = argPats) ->
continuation
[
Expand Down

0 comments on commit d8ffb9d

Please sign in to comment.