summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--Mainline.hs53
1 files changed, 33 insertions, 20 deletions
diff --git a/Mainline.hs b/Mainline.hs
index 93393c40..ac870a43 100644
--- a/Mainline.hs
+++ b/Mainline.hs
@@ -144,11 +144,17 @@ hexdigit c = ('0' <= c && c <= '9') || ( 'a' <= c && c <= 'f') || ( 'A' <= c &&
144instance Read NodeInfo where 144instance Read NodeInfo where
145 readsPrec i = RP.readP_to_S $ do 145 readsPrec i = RP.readP_to_S $ do
146 RP.skipSpaces 146 RP.skipSpaces
147 let n = 40 147 let n = 40 -- characters in node id.
148 hexhash <- sequence $ replicate n (RP.satisfy hexdigit) 148 parseAddr = RP.between (RP.char '(') (RP.char ')') (RP.munch (/=')'))
149 RP.char '@' RP.+++ RP.satisfy isSpace 149 RP.+++ RP.munch (not . isSpace)
150 addrstr <- RP.between (RP.char '(') (RP.char ')') (RP.munch (/=')')) 150 nodeidAt = do hexhash <- sequence $ replicate n (RP.satisfy hexdigit)
151 RP.+++ RP.munch (not . isSpace) 151 RP.char '@' RP.+++ RP.satisfy isSpace
152 addrstr <- parseAddr
153 nid <- case Base16.decode $ Char8.pack hexhash of
154 (bs,_) | B.length bs==20 -> return (NodeId bs)
155 _ -> fail "Bad node id."
156 return (nid,addrstr)
157 (nid,addrstr) <- ( nodeidAt RP.+++ ( (zeroID,) <$> parseAddr) )
152 let raddr = do 158 let raddr = do
153 -- TODO: Support IPv6 159 -- TODO: Support IPv6
154 ipv4 <- RP.readS_to_P (readsPrec i) 160 ipv4 <- RP.readS_to_P (readsPrec i)
@@ -159,9 +165,6 @@ instance Read NodeInfo where
159 (ip,port) <- case RP.readP_to_S raddr addrstr of 165 (ip,port) <- case RP.readP_to_S raddr addrstr of
160 [] -> fail "Bad address." 166 [] -> fail "Bad address."
161 ((ip,port),_):_ -> return (ip,port) 167 ((ip,port),_):_ -> return (ip,port)
162 nid <- case Base16.decode $ Char8.pack hexhash of
163 (bs,_) | B.length bs==20 -> return (NodeId bs)
164 _ -> fail "Bad node id."
165 return $ NodeInfo nid ip port 168 return $ NodeInfo nid ip port
166 169
167 170
@@ -174,12 +177,13 @@ instance Hashable NodeInfo where
174 177
175 178
176instance Show NodeInfo where 179instance Show NodeInfo where
177 show (NodeInfo (NodeId nid) ip port) = 180 showsPrec _ (NodeInfo nid ip port) =
178 Char8.unpack (Base16.encode nid) ++ "@" ++ show ip' ++ ":" ++ show port 181 shows nid . ('@' :) . showsip . (':' :) . shows port
179 where 182 where
180 ip' | IPv6 ip6 <- ip 183 showsip
181 , Just ip4 <- un4map ip6 = IPv4 ip4 184 | IPv4 ip4 <- ip = shows ip4
182 | otherwise = ip 185 | IPv6 ip6 <- ip , Just ip4 <- un4map ip6 = shows ip4
186 | otherwise = ('[' :) . shows ip . (']' :)
183 187
184{- 188{-
185 189
@@ -346,13 +350,22 @@ encodeMessage (R origin tid v ip)
346 Right (BDict vals) -> encodeResponse tid (BDict $ genericArgs origin False `BE.union` vals) ip 350 Right (BDict vals) -> encodeResponse tid (BDict $ genericArgs origin False `BE.union` vals) ip
347 Left err -> encodeError tid err 351 Left err -> encodeError tid err
348 352
353either4or6 :: SockAddr -> Either SockAddr SockAddr
354either4or6 a4@(SockAddrInet port addr) = Left a4
355either4or6 a6@(SockAddrInet6 port _ addr _)
356 | Just ip4 <- (fromSockAddr a6 >>= un4map) = Left (setPort port $ toSockAddr ip4)
357 | otherwise = Right a6
358
359
349encodeAddr :: SockAddr -> ByteString 360encodeAddr :: SockAddr -> ByteString
350encodeAddr (SockAddrInet port addr) 361encodeAddr = either encode4 encode6 . either4or6
351 = S.runPut (S.putWord32host addr >> S.putWord16be (fromIntegral port)) 362 where
352encodeAddr saddr@(SockAddrInet6 port _ addr _) 363 encode4 (SockAddrInet port addr)
353 | Just ip4 <- (fromSockAddr saddr >>= un4map) = encodeAddr (setPort port $ toSockAddr ip4) 364 = S.runPut (S.putWord32host addr >> S.putWord16be (fromIntegral port))
354 | otherwise = S.runPut (S.put addr >> S.putWord16be (fromIntegral port)) 365
355encodeAddr _ = B.empty 366 encode6 (SockAddrInet6 port _ addr _)
367 = S.runPut (S.put addr >> S.putWord16be (fromIntegral port))
368 encode6 _ = B.empty
356 369
357decodeAddr :: ByteString -> Either String SockAddr 370decodeAddr :: ByteString -> Either String SockAddr
358decodeAddr bs = S.runGet g bs 371decodeAddr bs = S.runGet g bs
@@ -393,7 +406,7 @@ showParseError bs addr err = L8.unpack $ L8.unlines es
393 where 406 where
394 es = map (L8.append prefix) (L8.pack err : L8.lines pp) 407 es = map (L8.append prefix) (L8.pack err : L8.lines pp)
395 408
396 prefix = L8.pack (show addr) <> " --> " 409 prefix = L8.pack (either show show $ either4or6 addr) <> " --> "
397 410
398 pp = either L8.pack showBEncode $ BE.decode bs 411 pp = either L8.pack showBEncode $ BE.decode bs
399 412