summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorjoe <joe@jerkface.net>2017-08-31 15:42:27 -0400
committerjoe <joe@jerkface.net>2017-08-31 15:42:49 -0400
commiteba3cdcc646211cc152c16d0813cc7e9b1c3111b (patch)
treee90c45a86d11b16da4eee5f21bb8ee618d7d94d6
parenta6b55a29ff656f105ca79c7d4f060920a37c7c70 (diff)
Separated module OnionTransport from ToxTransport.
-rw-r--r--DHTTransport.hs18
-rw-r--r--OnionTransport.hs196
-rw-r--r--ToxCrypto.hs11
-rw-r--r--ToxTransport.hs194
4 files changed, 226 insertions, 193 deletions
diff --git a/DHTTransport.hs b/DHTTransport.hs
index 6b3af2fc..3de276f1 100644
--- a/DHTTransport.hs
+++ b/DHTTransport.hs
@@ -1,8 +1,10 @@
1{-# LANGUAGE GeneralizedNewtypeDeriving #-} 1{-# LANGUAGE GeneralizedNewtypeDeriving #-}
2{-# LANGUAGE KindSignatures #-} 2{-# LANGUAGE KindSignatures #-}
3{-# LANGUAGE LambdaCase #-}
3module DHTTransport 4module DHTTransport
4 ( parseDHTAddr 5 ( parseDHTAddr
5 , encodeDHTAddr 6 , encodeDHTAddr
7 , forwardDHTRequests
6 , module ToxAddress 8 , module ToxAddress
7 , DHTMessage(..) 9 , DHTMessage(..)
8 , Ping 10 , Ping
@@ -16,6 +18,7 @@ module DHTTransport
16 18
17import ToxAddress 19import ToxAddress
18import ToxCrypto 20import ToxCrypto
21import Network.QueryResponse
19 22
20import Control.Arrow 23import Control.Arrow
21import qualified Data.ByteString as B 24import qualified Data.ByteString as B
@@ -24,6 +27,8 @@ import Data.Serialize as S (Get, Serialize, get, put, runGet)
24import Data.Word 27import Data.Word
25import Network.Socket 28import Network.Socket
26 29
30type DHTTransport = Transport String NodeInfo (DHTMessage Encrypted8)
31type HandleHi a = Maybe (Either String (DHTMessage Encrypted8, NodeInfo)) -> IO a
27 32
28 33
29data DHTMessage (f :: * -> *) 34data DHTMessage (f :: * -> *)
@@ -175,3 +180,16 @@ data CookieData = CookieData -- 16 (mac)
175 180
176instance Sized CookieRequest where 181instance Sized CookieRequest where
177 size = ConstSize 64 -- 32 byte key + 32 byte padding 182 size = ConstSize 64 -- 32 byte key + 32 byte padding
183
184forwardDHTRequests :: TransportCrypto -> (PublicKey -> IO (Maybe NodeInfo)) -> DHTTransport -> DHTTransport
185forwardDHTRequests crypto closeLookup dht = dht { awaitMessage = await' }
186 where
187 await' :: HandleHi a -> IO a
188 await' pass = awaitMessage dht $ \case
189 Just (Right (m@(DHTDHTRequest target payload),src)) | target /= transportPublic crypto
190 -> do mni <- closeLookup target
191 -- Forward the message if the target is in our close list.
192 forM_ mni $ \ni -> sendMessage dht ni m
193 await' pass
194 m -> pass m
195
diff --git a/OnionTransport.hs b/OnionTransport.hs
new file mode 100644
index 00000000..804c444e
--- /dev/null
+++ b/OnionTransport.hs
@@ -0,0 +1,196 @@
1{-# LANGUAGE DataKinds #-}
2{-# LANGUAGE GADTs #-}
3{-# LANGUAGE GeneralizedNewtypeDeriving #-}
4{-# LANGUAGE KindSignatures #-}
5{-# LANGUAGE LambdaCase #-}
6{-# LANGUAGE ScopedTypeVariables #-}
7{-# LANGUAGE TupleSections #-}
8{-# LANGUAGE TypeOperators #-}
9module OnionTransport
10 ( parseOnionAddr
11 , encodeOnionAddr
12 , forwardOnions
13 , OnionToOwner(..)
14 , OnionMessage(..)
15 , DataToRoute(..)
16 , AnnounceResponse(..)
17 , AnnounceRequest(..)
18 , Forwarding(..)
19 , ReturnPath(..)
20 , OnionRequest(..)
21 , OnionResponse(..)
22 , Addressed(..)
23 , UDPTransport
24 ) where
25
26import Network.QueryResponse
27import ToxCrypto
28import DHTTransport (NodeInfo(..),NodeId(..),SendNodes,nodeInfo)
29
30import Control.Arrow
31import qualified Data.ByteString as B
32 ;import Data.ByteString (ByteString)
33import Data.Serialize as S (Get, Put, Serialize, get, put, runGet)
34import Data.Typeable
35import Data.Word
36import GHC.TypeLits
37import Network.Socket
38
39type HandleLo a = Maybe (Either String (ByteString, SockAddr)) -> IO a
40
41type UDPTransport = Transport String SockAddr ByteString
42
43
44getOnionAssym :: Get (Assym (Encrypted DataToRoute))
45getOnionAssym = _todo
46
47data OnionMessage (f :: * -> *)
48 = OnionAnnounce (Assym (f (AnnounceRequest,Nonce8)))
49 | OnionAnnounceResponse Nonce8 Nonce24 (f AnnounceResponse)
50 | OnionToRoute PublicKey (Assym (f DataToRoute)) -- destination key, aliased Assym
51 | OnionToRouteResponse (Assym (f DataToRoute))
52
53data OnionToOwner = OnionToOwner NodeInfo (ReturnPath 3)
54 | OnionToMe SockAddr -- SockAddr is immediate peer in route
55
56
57onionToOwner assym ret3 saddr = do
58 ni <- nodeInfo (NodeId $ senderKey assym) saddr
59 return $ OnionToOwner ni ret3
60-- data CookieAddress = WithoutCookie NodeInfo | CookieAddress Cookie SockAddr
61
62
63onion bs saddr getf = do (f,(assym,ret3)) <- runGet ((,) <$> getf <*> getOnionRequest) bs
64 oaddr <- onionToOwner assym ret3 saddr
65 return (f assym, oaddr)
66
67
68parseOnionAddr :: (ByteString, SockAddr) -> Either (OnionMessage Encrypted,OnionToOwner) (ByteString,SockAddr)
69parseOnionAddr (msg,saddr)
70 | Just (typ,bs) <- B.uncons msg
71 , let right = Right (msg,saddr)
72 query = either (const right) Left
73 response = either (const right) (Left . (, OnionToMe saddr))
74 = case typ of
75 0x83 -> query $ onion bs saddr (pure OnionAnnounce) -- Announce Request
76 0x85 -> query $ onion bs saddr (OnionToRoute <$> getPublicKey) -- Onion Data Request
77 0x84 -> response $ runGet (OnionAnnounceResponse <$> get <*> get <*> get) bs -- Announce Response
78 0x86 -> response $ runGet (OnionToRouteResponse <$> getOnionAssym) bs -- Onion Data Response
79 _ -> right
80
81encodeOnionAddr :: (OnionMessage Encrypted,OnionToOwner) -> (ByteString, SockAddr)
82encodeOnionAddr = _todo
83
84forwardOnions :: TransportCrypto -> UDPTransport -> UDPTransport -- HandleHi a -> IO a -> HandleLo a
85forwardOnions crypto udp = udp { awaitMessage = await' }
86 where
87 -- forMe :: HandleHi
88 -- forThem :: handleLo
89 await' :: HandleLo a -> IO a
90 await' forThem = awaitMessage udp $ \case
91 m@(Just (Right (bs,saddr))) -> case B.head bs of
92 0x80 -> forward forThem bs $ handleOnionRequest (Proxy :: Proxy 0) crypto saddr (forThem m)
93 0x81 -> forward forThem bs $ handleOnionRequest (Proxy :: Proxy 1) crypto saddr (forThem m)
94 0x82 -> forward forThem bs $ handleOnionRequest (Proxy :: Proxy 2) crypto saddr (forThem m)
95 0x8c -> forward forThem bs $ handleOnionResponse (Proxy :: Proxy 3) crypto saddr (forThem m)
96 0x8d -> forward forThem bs $ handleOnionResponse (Proxy :: Proxy 2) crypto saddr (forThem m)
97 0x8e -> forward forThem bs $ handleOnionResponse (Proxy :: Proxy 1) crypto saddr (forThem m)
98 _ -> forThem m
99 m -> forThem m
100
101forward :: forall c b b1.
102 Serialize b =>
103 (Maybe (Either String b1) -> c) -> ByteString -> (b -> c) -> c
104forward forMe bs f = either (forMe . Just . Left) f $ decode $ B.tail bs
105
106-- n = 0, 1, 2
107data OnionRequest (n :: Nat) = OnionRequest
108 { onionNonce :: Nonce24
109 , onionForward :: Forwarding (3 - n) (OnionMessage Encrypted)
110 , pathFromOwner :: ReturnPath n
111 }
112
113instance Serialize (OnionRequest n) where { get = _todo; put = _todo }
114instance Serialize (OnionResponse n) where { get = _todo; put = _todo }
115
116-- n = 1, 2, 3
117-- Attributed (Encrypted (
118
119data OnionResponse (n :: Nat) = OnionResponse
120 { pathToOwner :: ReturnPath n
121 , msgToOwner :: OnionMessage Encrypted
122 }
123
124data Addressed a = Addressed { sockAddr :: SockAddr, unaddressed :: a }
125
126data ReturnPath (n :: Nat) where
127 NoReturnPath :: ReturnPath 0
128 ReturnPath :: Nonce24 -> Encrypted (Addressed (ReturnPath n)) -> ReturnPath (n + 1)
129
130-- instance KnownNat n => Serialize (ReturnPath n) where
131-- -- Size: 59 = 1(family) + 16(ip) + 2(port) +16(mac) + 24(nonce)
132-- get = ReturnPath <$> getBytes ( 59 * (fromIntegral $ natVal $ Proxy @n) )
133-- put (ReturnPath bs) = putByteString bs
134
135
136data Forwarding (n :: Nat) msg where
137 NotForwarded :: msg -> Forwarding 0 msg
138 Forwarding :: Assym (Encrypted (Addressed (Forwarding n msg))) -> Forwarding (n + 1) msg
139
140handleOnionRequest :: KnownNat n => proxy n -> TransportCrypto -> SockAddr -> IO a -> OnionRequest n -> IO a
141handleOnionRequest = _todo
142
143handleOnionResponse :: KnownNat n => proxy n -> TransportCrypto -> SockAddr -> IO a -> OnionResponse n -> IO a
144handleOnionResponse = _todo
145
146data AnnounceRequest = AnnounceRequest
147 { announcePingId :: Nonce32 -- Ping ID
148 , announceSeeking :: NodeId -- Public key we are searching for
149 , announceKey :: NodeId -- Public key that we want those sending back data packets to use
150 }
151
152instance S.Serialize AnnounceRequest where
153 get = AnnounceRequest <$> S.get <*> S.get <*> S.get
154 put (AnnounceRequest p s k) = S.put (p,s,k)
155
156getOnionRequest :: Get (Assym (Encrypted msg), ReturnPath 3)
157getOnionRequest = _todo
158
159data KeyRecord = NotStored Nonce32
160 | SendBackKey PublicKey
161 | Acknowledged Nonce32
162
163getPublicKey :: Get PublicKey
164getPublicKey = _todo
165
166putPublicKey :: PublicKey -> Put
167putPublicKey = _todo
168
169instance S.Serialize KeyRecord where
170 get = do
171 is_stored <- S.get :: S.Get Word8
172 case is_stored of
173 1 -> SendBackKey <$> getPublicKey
174 2 -> Acknowledged <$> S.get
175 _ -> NotStored <$> S.get
176 put (NotStored n32) = S.put (0 :: Word8) >> S.put n32
177 put (SendBackKey key) = S.put (1 :: Word8) >> putPublicKey key
178 put (Acknowledged n32) = S.put (2 :: Word8) >> S.put n32
179
180data AnnounceResponse = AnnounceResponse
181 { is_stored :: KeyRecord
182 , announceNodes :: SendNodes
183 }
184
185instance Sized AnnounceResponse where
186 size = VarSize $ \AnnounceResponse {} -> _todo
187
188instance S.Serialize AnnounceResponse where
189 get = AnnounceResponse <$> S.get <*> S.get
190 put (AnnounceResponse st ns) = S.put st >> S.put ns
191
192data DataToRoute = DataToRoute
193 { dataFromKey :: PublicKey
194 , dataToRoute :: Encrypted (Word8,ByteString)
195 }
196
diff --git a/ToxCrypto.hs b/ToxCrypto.hs
index 6f0fcf1a..4a8de635 100644
--- a/ToxCrypto.hs
+++ b/ToxCrypto.hs
@@ -6,6 +6,8 @@ module ToxCrypto
6 ( PublicKey 6 ( PublicKey
7 , publicKey 7 , publicKey
8 , SecretKey 8 , SecretKey
9 , SymmetricKey(..)
10 , TransportCrypto(..)
9 , Encrypted 11 , Encrypted
10 , Encrypted8 12 , Encrypted8
11 , Assym(..) 13 , Assym(..)
@@ -44,6 +46,7 @@ import Foreign.Ptr
44import Foreign.Storable 46import Foreign.Storable
45import System.Endian 47import System.Endian
46import qualified Data.ByteString.Internal 48import qualified Data.ByteString.Internal
49import Control.Concurrent.STM
47 50
48-- | A 16-byte mac and an arbitrary-length encrypted stream. 51-- | A 16-byte mac and an arbitrary-length encrypted stream.
49newtype Encrypted a = Encrypted ByteString 52newtype Encrypted a = Encrypted ByteString
@@ -226,3 +229,11 @@ data Assym a = Assym
226 , assymData :: a 229 , assymData :: a
227 } 230 }
228 231
232newtype SymmetricKey = SymmetricKey ByteString
233
234data TransportCrypto = TransportCrypto
235 { transportSecret :: SecretKey
236 , transportPublic :: PublicKey
237 , transportSymmetric :: STM SymmetricKey
238 }
239
diff --git a/ToxTransport.hs b/ToxTransport.hs
index 3e442d49..62081df5 100644
--- a/ToxTransport.hs
+++ b/ToxTransport.hs
@@ -9,24 +9,8 @@
9module ToxTransport 9module ToxTransport
10 ( toxTransport 10 ( toxTransport
11 11
12 , TransportCrypto(..)
13 , SymmetricKey(..)
14 , Encrypted8(..) 12 , Encrypted8(..)
15 13
16 , UDPTransport
17
18 -- OnionTransport
19 , OnionToOwner(..)
20 , OnionMessage(..)
21 , DataToRoute(..)
22 , AnnounceResponse(..)
23 , AnnounceRequest(..)
24 , Forwarding(..)
25 , ReturnPath(..)
26 , OnionRequest(..)
27 , OnionResponse(..)
28 , Addressed(..)
29
30 -- CryptoTransport 14 -- CryptoTransport
31 , NetCrypto(..) 15 , NetCrypto(..)
32 , CryptoData(..) 16 , CryptoData(..)
@@ -40,6 +24,7 @@ module ToxTransport
40import Network.QueryResponse 24import Network.QueryResponse
41import ToxCrypto 25import ToxCrypto
42import DHTTransport 26import DHTTransport
27import OnionTransport
43 28
44import Control.Applicative 29import Control.Applicative
45import Control.Arrow 30import Control.Arrow
@@ -56,17 +41,6 @@ import Data.Word
56import GHC.TypeLits 41import GHC.TypeLits
57import Network.Socket 42import Network.Socket
58 43
59newtype SymmetricKey = SymmetricKey ByteString
60
61data TransportCrypto = TransportCrypto
62 { transportSecret :: SecretKey
63 , transportPublic :: PublicKey
64 , transportSymmetric :: STM SymmetricKey
65 }
66
67type UDPTransport = Transport String SockAddr ByteString
68type DHTTransport = Transport String NodeInfo (DHTMessage Encrypted8)
69
70toxTransport :: 44toxTransport ::
71 TransportCrypto 45 TransportCrypto
72 -> (PublicKey -> IO (Maybe NodeInfo)) 46 -> (PublicKey -> IO (Maybe NodeInfo))
@@ -84,50 +58,8 @@ toxTransport crypto closeLookup udp = do
84 ) 58 )
85 59
86 60
87type HandleHi a = Maybe (Either String (DHTMessage Encrypted8, NodeInfo)) -> IO a
88type HandleLo a = Maybe (Either String (ByteString, SockAddr)) -> IO a
89
90-- instance (Sized a, Sized b) => Sized (a,b) where size = _todo 61-- instance (Sized a, Sized b) => Sized (a,b) where size = _todo
91 62
92getOnionAssym :: Get (Assym (Encrypted DataToRoute))
93getOnionAssym = _todo
94
95
96data OnionMessage (f :: * -> *)
97 = OnionAnnounce (Assym (f (AnnounceRequest,Nonce8)))
98 | OnionAnnounceResponse Nonce8 Nonce24 (f AnnounceResponse)
99 | OnionToRoute PublicKey (Assym (f DataToRoute)) -- destination key, aliased Assym
100 | OnionToRouteResponse (Assym (f DataToRoute))
101
102data OnionToOwner = OnionToOwner NodeInfo (ReturnPath 3)
103 | OnionToMe SockAddr -- SockAddr is immediate peer in route
104
105onionToOwner assym ret3 saddr = do
106 ni <- nodeInfo (NodeId $ senderKey assym) saddr
107 return $ OnionToOwner ni ret3
108
109onion bs saddr getf = do (f,(assym,ret3)) <- runGet ((,) <$> getf <*> getOnionRequest) bs
110 oaddr <- onionToOwner assym ret3 saddr
111 return (f assym, oaddr)
112
113parseOnionAddr :: (ByteString, SockAddr) -> Either (OnionMessage Encrypted,OnionToOwner) (ByteString,SockAddr)
114parseOnionAddr (msg,saddr)
115 | Just (typ,bs) <- B.uncons msg
116 , let right = Right (msg,saddr)
117 query = either (const right) Left
118 response = either (const right) (Left . (, OnionToMe saddr))
119 = case typ of
120 0x83 -> query $ onion bs saddr (pure OnionAnnounce) -- Announce Request
121 0x85 -> query $ onion bs saddr (OnionToRoute <$> getPublicKey) -- Onion Data Request
122 0x84 -> response $ runGet (OnionAnnounceResponse <$> get <*> get <*> get) bs -- Announce Response
123 0x86 -> response $ runGet (OnionToRouteResponse <$> getOnionAssym) bs -- Onion Data Response
124 _ -> right
125
126encodeOnionAddr :: (OnionMessage Encrypted,OnionToOwner) -> (ByteString, SockAddr)
127encodeOnionAddr = _todo
128
129
130-- data CookieAddress = WithoutCookie NodeInfo | CookieAddress Cookie SockAddr
131 63
132data NetCrypto 64data NetCrypto
133 = NetHandshake (Handshake Encrypted) 65 = NetHandshake (Handshake Encrypted)
@@ -260,129 +192,5 @@ data CryptoMessage -- First byte indicates data
260-- `0x8d` Onion Response 2 -return 192-- `0x8d` Onion Response 2 -return
261-- `0x8e` Onion Response 1 -return 193-- `0x8e` Onion Response 1 -return
262 194
263forwardOnions :: TransportCrypto -> UDPTransport -> UDPTransport -- HandleHi a -> IO a -> HandleLo a
264forwardOnions crypto udp = udp { awaitMessage = await' }
265 where
266 -- forMe :: HandleHi
267 -- forThem :: handleLo
268 await' :: HandleLo a -> IO a
269 await' forThem = awaitMessage udp $ \case
270 m@(Just (Right (bs,saddr))) -> case B.head bs of
271 0x80 -> forward forThem bs $ handleOnionRequest (Proxy :: Proxy 0) crypto saddr (forThem m)
272 0x81 -> forward forThem bs $ handleOnionRequest (Proxy :: Proxy 1) crypto saddr (forThem m)
273 0x82 -> forward forThem bs $ handleOnionRequest (Proxy :: Proxy 2) crypto saddr (forThem m)
274 0x8c -> forward forThem bs $ handleOnionResponse (Proxy :: Proxy 3) crypto saddr (forThem m)
275 0x8d -> forward forThem bs $ handleOnionResponse (Proxy :: Proxy 2) crypto saddr (forThem m)
276 0x8e -> forward forThem bs $ handleOnionResponse (Proxy :: Proxy 1) crypto saddr (forThem m)
277 _ -> forThem m
278 m -> forThem m
279
280forward :: forall c b b1.
281 Serialize b =>
282 (Maybe (Either String b1) -> c) -> ByteString -> (b -> c) -> c
283forward forMe bs f = either (forMe . Just . Left) f $ decode $ B.tail bs
284
285
286forwardDHTRequests :: TransportCrypto -> (PublicKey -> IO (Maybe NodeInfo)) -> DHTTransport -> DHTTransport
287forwardDHTRequests crypto closeLookup dht = dht { awaitMessage = await' }
288 where
289 await' :: HandleHi a -> IO a
290 await' pass = awaitMessage dht $ \case
291 Just (Right (m@(DHTDHTRequest target payload),src)) | target /= transportPublic crypto
292 -> do mni <- closeLookup target
293 -- Forward the message if the target is in our close list.
294 forM_ mni $ \ni -> sendMessage dht ni m
295 await' pass
296 m -> pass m
297
298
299-- n = 0, 1, 2
300data OnionRequest (n :: Nat) = OnionRequest
301 { onionNonce :: Nonce24
302 , onionForward :: Forwarding (3 - n) (OnionMessage Encrypted)
303 , pathFromOwner :: ReturnPath n
304 }
305
306instance Serialize (OnionRequest n) where { get = _todo; put = _todo }
307instance Serialize (OnionResponse n) where { get = _todo; put = _todo }
308 195
309-- n = 1, 2, 3
310-- Attributed (Encrypted (
311 196
312data OnionResponse (n :: Nat) = OnionResponse
313 { pathToOwner :: ReturnPath n
314 , msgToOwner :: OnionMessage Encrypted
315 }
316
317data Addressed a = Addressed { sockAddr :: SockAddr, unaddressed :: a }
318
319data ReturnPath (n :: Nat) where
320 NoReturnPath :: ReturnPath 0
321 ReturnPath :: Nonce24 -> Encrypted (Addressed (ReturnPath n)) -> ReturnPath (n + 1)
322
323-- instance KnownNat n => Serialize (ReturnPath n) where
324-- -- Size: 59 = 1(family) + 16(ip) + 2(port) +16(mac) + 24(nonce)
325-- get = ReturnPath <$> getBytes ( 59 * (fromIntegral $ natVal $ Proxy @n) )
326-- put (ReturnPath bs) = putByteString bs
327
328
329data Forwarding (n :: Nat) msg where
330 NotForwarded :: msg -> Forwarding 0 msg
331 Forwarding :: Assym (Encrypted (Addressed (Forwarding n msg))) -> Forwarding (n + 1) msg
332
333handleOnionRequest :: KnownNat n => proxy n -> TransportCrypto -> SockAddr -> IO a -> OnionRequest n -> IO a
334handleOnionRequest = _todo
335
336handleOnionResponse :: KnownNat n => proxy n -> TransportCrypto -> SockAddr -> IO a -> OnionResponse n -> IO a
337handleOnionResponse = _todo
338
339data AnnounceRequest = AnnounceRequest
340 { announcePingId :: Nonce32 -- Ping ID
341 , announceSeeking :: NodeId -- Public key we are searching for
342 , announceKey :: NodeId -- Public key that we want those sending back data packets to use
343 }
344
345instance S.Serialize AnnounceRequest where
346 get = AnnounceRequest <$> S.get <*> S.get <*> S.get
347 put (AnnounceRequest p s k) = S.put (p,s,k)
348
349getOnionRequest :: Get (Assym (Encrypted msg), ReturnPath 3)
350getOnionRequest = _todo
351
352data KeyRecord = NotStored Nonce32
353 | SendBackKey PublicKey
354 | Acknowledged Nonce32
355
356getPublicKey :: Get PublicKey
357getPublicKey = _todo
358
359putPublicKey :: PublicKey -> Put
360putPublicKey = _todo
361
362instance S.Serialize KeyRecord where
363 get = do
364 is_stored <- S.get :: S.Get Word8
365 case is_stored of
366 1 -> SendBackKey <$> getPublicKey
367 2 -> Acknowledged <$> S.get
368 _ -> NotStored <$> S.get
369 put (NotStored n32) = S.put (0 :: Word8) >> S.put n32
370 put (SendBackKey key) = S.put (1 :: Word8) >> putPublicKey key
371 put (Acknowledged n32) = S.put (2 :: Word8) >> S.put n32
372
373data AnnounceResponse = AnnounceResponse
374 { is_stored :: KeyRecord
375 , announceNodes :: SendNodes
376 }
377
378instance Sized AnnounceResponse where
379 size = VarSize $ \AnnounceResponse {} -> _todo
380
381instance S.Serialize AnnounceResponse where
382 get = AnnounceResponse <$> S.get <*> S.get
383 put (AnnounceResponse st ns) = S.put st >> S.put ns
384
385data DataToRoute = DataToRoute
386 { dataFromKey :: PublicKey
387 , dataToRoute :: Encrypted (Word8,ByteString)
388 }