Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Erlscripten lambdaelim #1

Open
wants to merge 30 commits into
base: erlscripten-master
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
30 commits
Select commit Hold shift + click to select a range
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
9 changes: 9 additions & 0 deletions CONTRIBUTORS.md
Original file line number Diff line number Diff line change
Expand Up @@ -21,6 +21,7 @@ If you would prefer to use different terms, please use the section below instead
| [@andyarvanitis](https://github.com/andyarvanitis) | Andy Arvanitis | [MIT license](http://opensource.org/licenses/MIT) |
| [@anthok88](https://github.com/anthok88) | anthoq88 | MIT license |
| [@ardumont](https://github.com/ardumont) | Antoine R. Dumont | [MIT license](http://opensource.org/licenses/MIT) |
| [@arrowd](https://github.com/arrowd) | Gleb Popov | [MIT license](http://opensource.org/licenses/MIT) |
| [@aspidites](https://github.com/aspidites) | Edwin Marshall | [MIT license](http://opensource.org/licenses/MIT) |
| [@bagl](https://github.com/bagl) | Petr Vapenka | [MIT license](http://opensource.org/licenses/MIT) |
| [@balajirrao](https://github.com/balajirrao) | Balaji Rao | MIT license |
Expand Down Expand Up @@ -50,6 +51,7 @@ If you would prefer to use different terms, please use the section below instead
| [@fehrenbach](https://github.com/fehrenbach) | Stefan Fehrenbach | [MIT license](http://opensource.org/licenses/MIT) |
| [@felixSchl](https://github.com/felixSchl) | Felix Schlitter | [MIT license](http://opensource.org/licenses/MIT) |
| [@FrigoEU](https://github.com/FrigoEU) | Simon Van Casteren | [MIT license](http://opensource.org/licenses/MIT) |
| [@fsoikin](https://github.com/fsoikin) | Fyodor Soikin | [MIT license](http://opensource.org/licenses/MIT) |
| [@garyb](https://github.com/garyb) | Gary Burgess | [MIT license](http://opensource.org/licenses/MIT) |
| [@hdgarrood](https://github.com/hdgarrood) | Harry Garrood | [MIT license](http://opensource.org/licenses/MIT) |
| [@houli](https://github.com/houli) | Eoin Houlihan | [MIT license](http://opensource.org/licenses/MIT) |
Expand All @@ -67,6 +69,7 @@ If you would prefer to use different terms, please use the section below instead
| [@legrostdg](https://github.com/legrostdg) | Félix Sipma | [MIT license](http://opensource.org/licenses/MIT) |
| [@LiamGoodacre](https://github.com/LiamGoodacre) | Liam Goodacre | [MIT license](http://opensource.org/licenses/MIT) |
| [@lukerandall](https://github.com/lukerandall) | Luke Randall | [MIT license](http://opensource.org/licenses/MIT) |
| [@lunaris](https://github.com/lunaris) | Will Jones | [MIT license](http://opensource.org/licenses/MIT) |
| [@matthewleon](https://github.com/matthewleon) | Matthew Leon | [MIT license](http://opensource.org/licenses/MIT) |
| [@mcoffin](https://github.com/mcoffin) | Matt Coffin | [MIT license](http://opensource.org/licenses/MIT) |
| [@mhcurylo](https://github.com/mhcurylo) | Mateusz Curylo | [MIT license](http://opensource.org/licenses/MIT) |
Expand All @@ -75,6 +78,7 @@ If you would prefer to use different terms, please use the section below instead
| [@mgmeier](https://github.com/mgmeier) | Michael Gilliland | [MIT license](http://opensource.org/licenses/MIT) |
| [@michaelficarra](https://github.com/michaelficarra) | Michael Ficarra | [MIT license](http://opensource.org/licenses/MIT) |
| [@MichaelXavier](https://github.com/MichaelXavier) | Michael Xavier | MIT license |
| [@milesfrain](https://github.com/milesfrain) | Miles Frain | [MIT license](http://opensource.org/licenses/MIT) |
| [@mjgpy3](https://github.com/mjgpy3) | Michael Gilliland | [MIT license](http://opensource.org/licenses/MIT) |
| [@mpietrzak](https://github.com/mpietrzak) | Maciej Pietrzak | [MIT license](http://opensource.org/licenses/MIT) |
| [@mrhania](https://github.com/mrhania) | Łukasz Hanuszczak | [MIT license](http://opensource.org/licenses/MIT) |
Expand Down Expand Up @@ -137,13 +141,17 @@ If you would prefer to use different terms, please use the section below instead
| [@marcosh](https://github.com/marcosh) | Marco Perone | [MIT license](http://opensource.org/licenses/MIT) |
| [@matthew-hilty](https://github.com/matthew-hilty) | Matthew Hilty | [MIT license](http://opensource.org/licenses/MIT) |
| [@woody88](https://github.com/woody88) | Woodson Delhia | [MIT license](http://opensource.org/licenses/MIT) |
| [@mhmdanas](https://github.com/mhmdanas) | Mohammed Anas | [MIT license](http://opensource.org/licenses/MIT) |
| [@kl0tl](https://github.com/kl0tl) | Cyril Sobierajewicz | [MIT license](http://opensource.org/licenses/MIT) |
| [@gorbak25](https://github.com/gorbak25) | Grzegorz Uriasz | [MIT license](http://opensource.org/licenses/MIT) |

### Contributors using Modified Terms

| Username | Name | Terms |
| :------- | :--- | :------ |
| [@charleso](https://github.com/charleso) | Charles O'Farrell | My existing contributions to the PureScript compiler and all future contributions to the PureScript compiler until further notice, are Copyright Charles O'Farrell, and are licensed to the owners and users of the PureScript compiler project under the terms of the [MIT license](http://opensource.org/licenses/MIT). |
| [@chrissmoak](https://github.com/chrissmoak) | Chris Smoak | My existing contributions to the PureScript compiler and all future contributions to the PureScript compiler until further notice, are Copyright Chris Smoak, and are licensed to the owners and users of the PureScript compiler project under the terms of the [MIT license](http://opensource.org/licenses/MIT). |
| [@citizengabe](https://github.com/citizengabe) | Gabe Johnson | All contributions I have or will make using the @citizengabe GitHub account are during employment at [CitizenNet Inc.](#companies) who owns the copyright. All of my existing or future contributions made using the @gabejohnson GitHub account are personal contributions and subject to the terms specified [above](#contributors-using-standard-terms). |
| [@dylex](https://github.com/dylex) | Dylan Simon | My existing and all future contributions to the PureScript compiler until further notice are Copyright Dylan Simon, and are licensed to the owners and users of the PureScript compiler project under the terms of the [MIT license](http://opensource.org/licenses/MIT). |
| [@leighman](http://github.com/leighman) | Jack Leigh | My existing contributions and all future contributions until further notice are Copyright Jack Leigh, and are licensed to the owners and users of the PureScript compiler project under the terms of the [MIT license](http://opensource.org/licenses/MIT). |
| [@nagisa](https://github.com/nagisa) | nagisa | I hereby release my [only contribution](https://github.com/purescript/purescript/commit/80287a5d0de619862d3b4cda9c1ee276d18fdcd8) into public domain. |
Expand All @@ -153,5 +161,6 @@ If you would prefer to use different terms, please use the section below instead

| Username | Company | Terms |
| :------- | :--- | :------ |
| [@citizennet](https://github.com/citizennet) | CitizenNet Inc. | Our existing contributions to the PureScript compiler and all future contributions to the PureScript compiler until further notice, are Copyright CitizenNet Inc., and are licensed to the owners and users of the PureScript compiler project under the terms of the [MIT license](http://opensource.org/licenses/MIT). - [@dbenyamin-cn](https://github.com/dbenyamin-cn) |
| [@slamdata](https://github.com/slamdata) | SlamData, Inc. | Speaking on behalf of SlamData for SlamData employees, our existing contributions and all future contributions to the PureScript compiler are, until further notice, Copyright SlamData Inc., and are licensed to the owners and users of the PureScript compiler project under the terms of the [MIT license](http://opensource.org/licenses/MIT). - @jdegoes |
| [@qfpl](https://github.com/qfpl) | qfpl @ Data61 / CSIRO | Our existing contributions to the PureScript compiler and all future contributions to the PureScript compiler until further notice, are Copyright Data61 / CSIRO, and are licensed to the owners and users of the PureScript compiler project under the terms of the [MIT license](http://opensource.org/licenses/MIT). - [@lightandlight](https://github.com/lightandlight) |
4 changes: 2 additions & 2 deletions package.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -102,7 +102,7 @@ build-tools:

library:
source-dirs: src
ghc-options: -Wall -O2
ghc-options: -Wall -O3 -optc-O3
other-modules: Paths_purescript
default-extensions:
- ConstraintKinds
Expand Down Expand Up @@ -131,7 +131,7 @@ executables:
purs:
main: Main.hs
source-dirs: app
ghc-options: -Wall -O2 -fno-warn-unused-do-bind -threaded -rtsopts -with-rtsopts=-N
ghc-options: -Wall -O3 -optc-O3 -fno-warn-unused-do-bind -threaded -rtsopts -with-rtsopts=-N
other-modules:
- Command.Bundle
- Command.Compile
Expand Down
3 changes: 3 additions & 0 deletions src/Control/Monad/Supply/Class.hs
Original file line number Diff line number Diff line change
Expand Up @@ -34,3 +34,6 @@ instance (Monoid w, MonadSupply m) => MonadSupply (WriterT w m)

freshName :: MonadSupply m => m Text
freshName = fmap (("$" <> ) . pack . show) fresh

freshNameHint :: MonadSupply m => Text -> m Text
freshNameHint hint = fmap ((("$" <> hint) <> ) . pack . show) fresh
3 changes: 1 addition & 2 deletions src/Language/PureScript/AST/Declarations.hs
Original file line number Diff line number Diff line change
@@ -1,6 +1,5 @@
{-# LANGUAGE DeriveGeneric #-}
{-# LANGUAGE TemplateHaskell #-}
{-# LANGUAGE DeriveFoldable #-}
{-# LANGUAGE DeriveTraversable #-}
{-# LANGUAGE DeriveAnyClass #-}

Expand Down Expand Up @@ -34,7 +33,7 @@ import Language.PureScript.Kinds
import Language.PureScript.TypeClassDictionaries
import Language.PureScript.Comments
import Language.PureScript.Environment
import qualified Language.PureScript.Bundle as Bundle
import qualified Language.PureScript.Bundle.Types as Bundle
import qualified Language.PureScript.Constants as C
import qualified Language.PureScript.CST.Errors as CST

Expand Down
1 change: 1 addition & 0 deletions src/Language/PureScript/AST/Literals.hs
Original file line number Diff line number Diff line change
@@ -1,3 +1,4 @@
{-# LANGUAGE Strict #-}
-- |
-- The core functional representation for literal values.
--
Expand Down
1 change: 1 addition & 0 deletions src/Language/PureScript/AST/Operators.hs
Original file line number Diff line number Diff line change
@@ -1,3 +1,4 @@
{-# LANGUAGE Strict #-}
{-# LANGUAGE DeriveGeneric #-}
-- |
-- Operators fixity and associativity
Expand Down
67 changes: 34 additions & 33 deletions src/Language/PureScript/AST/Traversals.hs
Original file line number Diff line number Diff line change
@@ -1,3 +1,4 @@
{-# LANGUAGE Strict #-}
-- |
-- AST traversal helpers
--
Expand All @@ -8,7 +9,7 @@ import Prelude.Compat
import Control.Monad

import Data.Foldable (fold)
import Data.List (mapAccumL)
import Data.List (mapAccumL, foldl')
import Data.Maybe (mapMaybe)
import qualified Data.List.NonEmpty as NEL
import qualified Data.Map as M
Expand Down Expand Up @@ -273,11 +274,11 @@ everythingOnValues (<>.) f g h i j = (f', g', h', i', j')
where

f' :: Declaration -> r
f' d@(DataBindingGroupDeclaration ds) = foldl (<>.) (f d) (fmap f' ds)
f' d@(ValueDeclaration vd) = foldl (<>.) (f d) (fmap h' (valdeclBinders vd) ++ concatMap (\(GuardedExpr grd v) -> fmap k' grd ++ [g' v]) (valdeclExpression vd))
f' d@(BindingGroupDeclaration ds) = foldl (<>.) (f d) (fmap (\(_, _, val) -> g' val) ds)
f' d@(TypeClassDeclaration _ _ _ _ _ ds) = foldl (<>.) (f d) (fmap f' ds)
f' d@(TypeInstanceDeclaration _ _ _ _ _ _ _ (ExplicitInstance ds)) = foldl (<>.) (f d) (fmap f' ds)
f' d@(DataBindingGroupDeclaration ds) = foldl' (<>.) (f d) (fmap f' ds)
f' d@(ValueDeclaration vd) = foldl' (<>.) (f d) (fmap h' (valdeclBinders vd) ++ concatMap (\(GuardedExpr grd v) -> fmap k' grd ++ [g' v]) (valdeclExpression vd))
f' d@(BindingGroupDeclaration ds) = foldl' (<>.) (f d) (fmap (\(_, _, val) -> g' val) ds)
f' d@(TypeClassDeclaration _ _ _ _ _ ds) = foldl' (<>.) (f d) (fmap f' ds)
f' d@(TypeInstanceDeclaration _ _ _ _ _ _ _ (ExplicitInstance ds)) = foldl' (<>.) (f d) (fmap f' ds)
f' d@(BoundValueDeclaration _ b expr) = f d <>. h' b <>. g' expr
f' d = f d

Expand All @@ -288,23 +289,23 @@ everythingOnValues (<>.) f g h i j = (f', g', h', i', j')
g' v@(Parens v1) = g v <>. g' v1
g' v@(TypeClassDictionaryConstructorApp _ v1) = g v <>. g' v1
g' v@(Accessor _ v1) = g v <>. g' v1
g' v@(ObjectUpdate obj vs) = foldl (<>.) (g v <>. g' obj) (fmap (g' . snd) vs)
g' v@(ObjectUpdateNested obj vs) = foldl (<>.) (g v <>. g' obj) (fmap g' vs)
g' v@(ObjectUpdate obj vs) = foldl' (<>.) (g v <>. g' obj) (fmap (g' . snd) vs)
g' v@(ObjectUpdateNested obj vs) = foldl' (<>.) (g v <>. g' obj) (fmap g' vs)
g' v@(Abs b v1) = g v <>. h' b <>. g' v1
g' v@(App v1 v2) = g v <>. g' v1 <>. g' v2
g' v@(Unused v1) = g v <>. g' v1
g' v@(IfThenElse v1 v2 v3) = g v <>. g' v1 <>. g' v2 <>. g' v3
g' v@(Case vs alts) = foldl (<>.) (foldl (<>.) (g v) (fmap g' vs)) (fmap i' alts)
g' v@(Case vs alts) = foldl' (<>.) (foldl' (<>.) (g v) (fmap g' vs)) (fmap i' alts)
g' v@(TypedValue _ v1 _) = g v <>. g' v1
g' v@(Let _ ds v1) = foldl (<>.) (g v) (fmap f' ds) <>. g' v1
g' v@(Do _ es) = foldl (<>.) (g v) (fmap j' es)
g' v@(Ado _ es v1) = foldl (<>.) (g v) (fmap j' es) <>. g' v1
g' v@(Let _ ds v1) = foldl' (<>.) (g v) (fmap f' ds) <>. g' v1
g' v@(Do _ es) = foldl' (<>.) (g v) (fmap j' es)
g' v@(Ado _ es v1) = foldl' (<>.) (g v) (fmap j' es) <>. g' v1
g' v@(PositionedValue _ _ v1) = g v <>. g' v1
g' v = g v

h' :: Binder -> r
h' b@(LiteralBinder _ l) = lit (h b) h' l
h' b@(ConstructorBinder _ _ bs) = foldl (<>.) (h b) (fmap h' bs)
h' b@(ConstructorBinder _ _ bs) = foldl' (<>.) (h b) (fmap h' bs)
h' b@(BinaryNoParensBinder b1 b2 b3) = h b <>. h' b1 <>. h' b2 <>. h' b3
h' b@(ParensInBinder b1) = h b <>. h' b1
h' b@(NamedBinder _ _ b1) = h b <>. h' b1
Expand All @@ -313,18 +314,18 @@ everythingOnValues (<>.) f g h i j = (f', g', h', i', j')
h' b = h b

lit :: r -> (a -> r) -> Literal a -> r
lit r go (ArrayLiteral as) = foldl (<>.) r (fmap go as)
lit r go (ObjectLiteral as) = foldl (<>.) r (fmap (go . snd) as)
lit r go (ArrayLiteral as) = foldl' (<>.) r (fmap go as)
lit r go (ObjectLiteral as) = foldl' (<>.) r (fmap (go . snd) as)
lit r _ _ = r

i' :: CaseAlternative -> r
i' ca@(CaseAlternative bs gs) =
foldl (<>.) (i ca) (fmap h' bs ++ concatMap (\(GuardedExpr grd val) -> fmap k' grd ++ [g' val]) gs)
foldl' (<>.) (i ca) (fmap h' bs ++ concatMap (\(GuardedExpr grd val) -> fmap k' grd ++ [g' val]) gs)

j' :: DoNotationElement -> r
j' e@(DoNotationValue v) = j e <>. g' v
j' e@(DoNotationBind b v) = j e <>. h' b <>. g' v
j' e@(DoNotationLet ds) = foldl (<>.) (j e) (fmap f' ds)
j' e@(DoNotationLet ds) = foldl' (<>.) (j e) (fmap f' ds)
j' e@(PositionedDoNotationElement _ _ e1) = j e <>. j' e1

k' :: Guard -> r
Expand Down Expand Up @@ -353,11 +354,11 @@ everythingWithContextOnValues s0 r0 (<>.) f g h i j = (f'' s0, g'' s0, h'' s0, i
f'' s d = let (s', r) = f s d in r <>. f' s' d

f' :: s -> Declaration -> r
f' s (DataBindingGroupDeclaration ds) = foldl (<>.) r0 (fmap (f'' s) ds)
f' s (ValueDeclaration vd) = foldl (<>.) r0 (fmap (h'' s) (valdeclBinders vd) ++ concatMap (\(GuardedExpr grd v) -> fmap (k' s) grd ++ [g'' s v]) (valdeclExpression vd))
f' s (BindingGroupDeclaration ds) = foldl (<>.) r0 (fmap (\(_, _, val) -> g'' s val) ds)
f' s (TypeClassDeclaration _ _ _ _ _ ds) = foldl (<>.) r0 (fmap (f'' s) ds)
f' s (TypeInstanceDeclaration _ _ _ _ _ _ _ (ExplicitInstance ds)) = foldl (<>.) r0 (fmap (f'' s) ds)
f' s (DataBindingGroupDeclaration ds) = foldl' (<>.) r0 (fmap (f'' s) ds)
f' s (ValueDeclaration vd) = foldl' (<>.) r0 (fmap (h'' s) (valdeclBinders vd) ++ concatMap (\(GuardedExpr grd v) -> fmap (k' s) grd ++ [g'' s v]) (valdeclExpression vd))
f' s (BindingGroupDeclaration ds) = foldl' (<>.) r0 (fmap (\(_, _, val) -> g'' s val) ds)
f' s (TypeClassDeclaration _ _ _ _ _ ds) = foldl' (<>.) r0 (fmap (f'' s) ds)
f' s (TypeInstanceDeclaration _ _ _ _ _ _ _ (ExplicitInstance ds)) = foldl' (<>.) r0 (fmap (f'' s) ds)
f' _ _ = r0

g'' :: s -> Expr -> r
Expand All @@ -370,17 +371,17 @@ everythingWithContextOnValues s0 r0 (<>.) f g h i j = (f'' s0, g'' s0, h'' s0, i
g' s (Parens v1) = g'' s v1
g' s (TypeClassDictionaryConstructorApp _ v1) = g'' s v1
g' s (Accessor _ v1) = g'' s v1
g' s (ObjectUpdate obj vs) = foldl (<>.) (g'' s obj) (fmap (g'' s . snd) vs)
g' s (ObjectUpdateNested obj vs) = foldl (<>.) (g'' s obj) (fmap (g'' s) vs)
g' s (ObjectUpdate obj vs) = foldl' (<>.) (g'' s obj) (fmap (g'' s . snd) vs)
g' s (ObjectUpdateNested obj vs) = foldl' (<>.) (g'' s obj) (fmap (g'' s) vs)
g' s (Abs binder v1) = h'' s binder <>. g'' s v1
g' s (App v1 v2) = g'' s v1 <>. g'' s v2
g' s (Unused v) = g'' s v
g' s (IfThenElse v1 v2 v3) = g'' s v1 <>. g'' s v2 <>. g'' s v3
g' s (Case vs alts) = foldl (<>.) (foldl (<>.) r0 (fmap (g'' s) vs)) (fmap (i'' s) alts)
g' s (Case vs alts) = foldl' (<>.) (foldl' (<>.) r0 (fmap (g'' s) vs)) (fmap (i'' s) alts)
g' s (TypedValue _ v1 _) = g'' s v1
g' s (Let _ ds v1) = foldl (<>.) r0 (fmap (f'' s) ds) <>. g'' s v1
g' s (Do _ es) = foldl (<>.) r0 (fmap (j'' s) es)
g' s (Ado _ es v1) = foldl (<>.) r0 (fmap (j'' s) es) <>. g'' s v1
g' s (Let _ ds v1) = foldl' (<>.) r0 (fmap (f'' s) ds) <>. g'' s v1
g' s (Do _ es) = foldl' (<>.) r0 (fmap (j'' s) es)
g' s (Ado _ es v1) = foldl' (<>.) r0 (fmap (j'' s) es) <>. g'' s v1
g' s (PositionedValue _ _ v1) = g'' s v1
g' _ _ = r0

Expand All @@ -389,7 +390,7 @@ everythingWithContextOnValues s0 r0 (<>.) f g h i j = (f'' s0, g'' s0, h'' s0, i

h' :: s -> Binder -> r
h' s (LiteralBinder _ l) = lit h'' s l
h' s (ConstructorBinder _ _ bs) = foldl (<>.) r0 (fmap (h'' s) bs)
h' s (ConstructorBinder _ _ bs) = foldl' (<>.) r0 (fmap (h'' s) bs)
h' s (BinaryNoParensBinder b1 b2 b3) = h'' s b1 <>. h'' s b2 <>. h'' s b3
h' s (ParensInBinder b) = h'' s b
h' s (NamedBinder _ _ b1) = h'' s b1
Expand All @@ -398,23 +399,23 @@ everythingWithContextOnValues s0 r0 (<>.) f g h i j = (f'' s0, g'' s0, h'' s0, i
h' _ _ = r0

lit :: (s -> a -> r) -> s -> Literal a -> r
lit go s (ArrayLiteral as) = foldl (<>.) r0 (fmap (go s) as)
lit go s (ObjectLiteral as) = foldl (<>.) r0 (fmap (go s . snd) as)
lit go s (ArrayLiteral as) = foldl' (<>.) r0 (fmap (go s) as)
lit go s (ObjectLiteral as) = foldl' (<>.) r0 (fmap (go s . snd) as)
lit _ _ _ = r0

i'' :: s -> CaseAlternative -> r
i'' s ca = let (s', r) = i s ca in r <>. i' s' ca

i' :: s -> CaseAlternative -> r
i' s (CaseAlternative bs gs) = foldl (<>.) r0 (fmap (h'' s) bs ++ concatMap (\(GuardedExpr grd val) -> fmap (k' s) grd ++ [g'' s val]) gs)
i' s (CaseAlternative bs gs) = foldl' (<>.) r0 (fmap (h'' s) bs ++ concatMap (\(GuardedExpr grd val) -> fmap (k' s) grd ++ [g'' s val]) gs)

j'' :: s -> DoNotationElement -> r
j'' s e = let (s', r) = j s e in r <>. j' s' e

j' :: s -> DoNotationElement -> r
j' s (DoNotationValue v) = g'' s v
j' s (DoNotationBind b v) = h'' s b <>. g'' s v
j' s (DoNotationLet ds) = foldl (<>.) r0 (fmap (f'' s) ds)
j' s (DoNotationLet ds) = foldl' (<>.) r0 (fmap (f'' s) ds)
j' s (PositionedDoNotationElement _ _ e1) = j'' s e1

k' :: s -> Guard -> r
Expand Down
Loading