diff --git a/fsharp/ygosim/src/Board.fs b/fsharp/ygosim/src/Board.fs
index d84800f..a07f5ff 100644
--- a/fsharp/ygosim/src/Board.fs
+++ b/fsharp/ygosim/src/Board.fs
@@ -7,8 +7,8 @@ module Side =
 
     type Side<'s> =
         { field: CardInstance<'s> option
-          monsters: CardInstance<'s> list
-          spells: CardInstance<'s> list
+          monsters: CardInstance<'s> option list
+          spells: CardInstance<'s> option list
           graveyard: CardInstance<'s> list
           deck: CardInstance<'s> list }
 
@@ -19,10 +19,12 @@ module Side =
         let inline graveyard f side = f side.graveyard <&> fun v -> { side with graveyard = v }
         let inline deck f side = f side.deck <&> fun v -> { side with deck = v }
 
-    let emptySide =
+    let emptyRow _ = List.init 5 <| fun _ -> None
+
+    let emptySide _ =
         { field = None
-          monsters = []
-          spells = []
+          monsters = emptyRow()
+          spells = emptyRow()
           graveyard = []
           deck = [] }
 
@@ -41,7 +43,8 @@ module Player =
           side: Side<'s>
           hand: CardInstance<'s> list
           state: PlayerState
-          id: int }
+          id: int
+          lastNormalSummon: int }
 
     module Player =
         let inline lifePoints f player = f player.lifePoints <&> fun v -> { player with lifePoints = v }
@@ -49,15 +52,18 @@ module Player =
         let inline hand f player = f player.hand <&> fun v -> { player with hand = v }
         let inline state f player = f player.state <&> fun v -> { player with state = v }
         let inline _id f player = f player.id <&> fun v -> { player with id = v }
+        let inline lastNormalSummon f player =
+            f player.lastNormalSummon <&> fun v -> { player with lastNormalSummon = v }
 
         let inline deck f player = (side << Side.deck) f player
 
     let initialPlayer lp id =
         { lifePoints = lp
-          side = emptySide
+          side = emptySide()
           hand = []
           state = InGame
-          id = id }
+          id = id
+          lastNormalSummon = -1 }
 
 module Turn =
     type Phase =
@@ -82,6 +88,7 @@ module Board =
     open Card
     open Player
 
+
     type Player = Player.Player<Board>
 
     and Board =
@@ -103,6 +110,7 @@ module Board =
         let inline currentPlayerState f board = (currentPlayer << Player.state) f board
         let inline currentPlayerDeck f board = (currentPlayer << Player.deck) f board
         let inline currentPlayerHand f board = (currentPlayer << Player.hand) f board
+        let inline currentPlayerLastNormalSummon f board = (currentPlayer << Player.lastNormalSummon) f board
 
         let inline firstPlayer f board = (players << _1) f board
         let inline secondPlayer f board = (players << _2) f board
@@ -121,24 +129,73 @@ module Board =
         { players = (initialPlayer 8000 0, initialPlayer 8000 1)
           moment = 0, Draw }
 
-module Game =
-    open Turn
+module Client =
     open Player
+    open Turn
+    open Card.Card
     open Board
 
     type Log =
         | CardToHand of string
         | NewPhase of Phase
         | StateChanged of PlayerState * PlayerState
+        | ChooseZone of int list
 
     type Client = Log -> int
 
+    let rec chooseZone client free =
+        let freeIndices = List.mapi (fun i _ -> i) free
+        let command = ChooseZone freeIndices
+        let result = client command
+
+        if List.contains result freeIndices then free.[result]
+        else chooseZone client free
+
+module Zone =
+    open Player
+    open Side
+
+    let freeMonsterZones player = List.filter Option.isNone player.side.monsters
+    let freeMonsterZoneCount player = List.length <| freeMonsterZones player
+    let hasFreeMonsterZones player count = freeMonsterZoneCount player >= count
+    let hasFreeMonsterZone player = hasFreeMonsterZones player 1
+
+module Summon =
+    open Board
+    open Zone
+    open Client
+
+    module Normal =
+        let canNormalSummon board =
+            hasFreeMonsterZone <| board ^. Board.currentPlayer
+            && board ^. Board.currentPlayerLastNormalSummon < board ^. Board.turn
+
+        let performNormalSummon client board =
+            let free = freeMonsterZones <| board ^. Board.currentPlayer
+
+            printfn "%A" free
+
+            let zone = chooseZone client free
+
+            printfn "%A" zone
+
+            let turn = board ^. Board.turn
+
+            board |> Board.currentPlayerLastNormalSummon .-> turn
+
+
+module Game =
+    open Turn
+    open Player
+    open Board
+    open Summon.Normal
+    open Client
+
     let isCurrentPlayer (board: Board) (player: Player) = (board ^. Board.currentPlayerId) = player.id
 
     let canDrawCard (board: Board) (player: Player) =
         isCurrentPlayer board player && board ^. Board.phase = Draw && board ^. Board.turn <> 0
 
-
     let draw (board: Board) =
         match board ^. Board.currentPlayerDeck with
         | [] -> board |> Board.currentPlayerState .-> Lost "deckout"
@@ -151,11 +208,18 @@ module Game =
 
     let toDeckBottom (card: CardInstance) (player: Player) = over Player.deck (fun d -> card :: d) player
 
+    let handleMainPhase client board =
+        printfn "%b" <| canNormalSummon board
+        if canNormalSummon board then performNormalSummon client board
+        else board
+
     let processPhase client board =
         match board ^. Board.phase with
         | Draw ->
             if canDrawCard board <| board ^. Board.currentPlayer then draw board
             else board
+        | Main1 -> handleMainPhase client board
+        | Main2 -> handleMainPhase client board
         | _ -> board
 
     let switchPhases (client: Client) board =
diff --git a/fsharp/ygosim/src/Card.fs b/fsharp/ygosim/src/Card.fs
index 960d898..29dbaad 100644
--- a/fsharp/ygosim/src/Card.fs
+++ b/fsharp/ygosim/src/Card.fs
@@ -16,6 +16,7 @@ module Effect =
     type EffectType =
         | Trigger
         | Ignition
+        | Maintanence
 
     type Effect<'s> =
         { cost: Action<'s>
@@ -125,7 +126,6 @@ module Card =
         let inline baseCard f card = _1 f card
         let inline cardDetails f card = _2 f card
 
-    // TODO: actually make this do what its supposed to
     type CardInstance<'s> = Card<'s>
 
 module Decklist =
diff --git a/fsharp/ygosim/src/Program.fs b/fsharp/ygosim/src/Program.fs
index daa7aa1..28ab318 100644
--- a/fsharp/ygosim/src/Program.fs
+++ b/fsharp/ygosim/src/Program.fs
@@ -3,6 +3,7 @@
     open Board.Player
     open Board.Board
     open Board.Game
+    open Board.Client
     open Card
 
     let printState state = 
@@ -21,10 +22,15 @@
             | StateChanged (s1, s2) -> 
                 printfn "Player 1: %s" <| printState s1
                 printfn "Player 2: %s" <| printState s2
-            | NewPhase phase -> printfn "New phse: %A" phase
-            | _ -> printfn "Something unkown happened"
-
-            0
+                0
+            | NewPhase phase -> 
+                printfn "New phse: %A" phase
+                0
+            | ChooseZone free -> 
+                List.head free
+            | _ -> 
+                printfn "Something unkown happened" 
+                0
 
         game board client