summaryrefslogtreecommitdiff
path: root/src/Data/Tox/Relay.hs
blob: e35f49f0d0948aa5cf1a6480bafa14c5eafe2344 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
{-# LANGUAGE DeriveDataTypeable #-}
module Data.Tox.Relay where

import Data.ByteString
import Data.Data
import Data.Serialize
import Data.Word

import Crypto.Tox
import Network.Tox.Onion.Transport
import Network.Tox.NodeId (key2id,id2key)

data RelayPacket
    = RoutingRequest PublicKey
    | RoutingResponse Word8 PublicKey
    | ConnectNotification Word8
    | DisconnectNotification Word8
    | RelayPing Word64
    | RelayPong Word64
    | OOBSend PublicKey ByteString
    | OOBRecv PublicKey ByteString
    | OnionPacket (OnionRequest N0)
    | OnionPacketResponse (OnionResponse N1)
    -- 0x0A through 0x0F reserved for future use.
    | RelayData Word8 ByteString -- Word8 is a connection id.  Encoded as number 16 to 255.
 deriving (Eq,Ord,Show,Data)

packetNumber :: RelayPacket -> Word8
packetNumber (RelayData conid _) = conid -- 0 to 15 not allowed.
packetNumber rp                  = fromIntegral $ pred $ constrIndex $ toConstr rp

instance Serialize RelayPacket where

    get = do
        pktid <- getWord8
        case pktid of
            0 -> RoutingRequest <$> (id2key <$> get)
            1 -> RoutingResponse <$> getWord8 <*> (id2key <$> get)
            2 -> ConnectNotification <$> getWord8
            3 -> DisconnectNotification <$> getWord8
            4 -> RelayPing <$> getWord64be
            5 -> RelayPong <$> getWord64be
            6 -> OOBSend <$> (id2key <$> get) <*> (remaining >>= getBytes)
            7 -> OOBRecv <$> (id2key <$> get) <*> (remaining >>= getBytes)
            8 -> OnionPacket <$> get
            9 -> OnionPacketResponse <$> get
            conid -> RelayData conid <$> (remaining >>= getBytes)

    put rp = do
        putWord8 $ packetNumber rp
        case rp of
            RoutingRequest k             -> put (key2id k)
            RoutingResponse rpid k       -> putWord8 rpid >> put (key2id k)
            ConnectNotification conid    -> putWord8 conid
            DisconnectNotification conid -> putWord8 conid
            RelayPing pingid             -> putWord64be pingid
            RelayPong pingid             -> putWord64be pingid
            OOBSend k bs                 -> put (key2id k) >> putByteString bs
            OOBRecv k bs                 -> put (key2id k) >> putByteString bs
            OnionPacket query            -> put query
            OnionPacketResponse answer   -> put answer
            RelayData _ bs               -> putByteString bs