diff options
-rw-r--r-- | Assistant/Pairing.hs | 2 | ||||
-rw-r--r-- | Assistant/Threads/PairListener.hs | 34 | ||||
-rw-r--r-- | debian/changelog | 7 | ||||
-rw-r--r-- | doc/bugs/Local_pairing_fails:_received_PairMsg_loop.mdwn | 14 |
4 files changed, 45 insertions, 12 deletions
diff --git a/Assistant/Pairing.hs b/Assistant/Pairing.hs index 4736c4396..bb1384a15 100644 --- a/Assistant/Pairing.hs +++ b/Assistant/Pairing.hs @@ -28,7 +28,7 @@ data PairStage | PairAck {- "I saw your PairAck; you can stop sending them." -} | PairDone - deriving (Eq, Read, Show, Ord) + deriving (Eq, Read, Show, Ord, Enum) newtype PairMsg = PairMsg (Verifiable (PairStage, PairData, SomeAddr)) deriving (Eq, Read, Show) diff --git a/Assistant/Threads/PairListener.hs b/Assistant/Threads/PairListener.hs index 482b0923c..cd95ab5a4 100644 --- a/Assistant/Threads/PairListener.hs +++ b/Assistant/Threads/PairListener.hs @@ -16,6 +16,7 @@ import Assistant.WebApp.Types import Assistant.Alert import Assistant.DaemonStatus import Utility.ThreadScheduler +import Utility.Format import Git import Network.Multicast @@ -42,20 +43,32 @@ pairListenerThread urlrenderer = namedThread "PairListener" $ do (pip, verified) <- verificationCheck m =<< (pairingInProgress <$> getDaemonStatus) let wrongstage = maybe False (\p -> pairMsgStage m <= inProgressPairStage p) pip - case (wrongstage, sane, pairMsgStage m) of - -- ignore our own messages, and - -- out of order messages - (True, _, _) -> go reqs cache sock - (_, False, _) -> go reqs cache sock - (_, _, PairReq) -> if m `elem` reqs + let fromus = maybe False (\p -> remoteSshPubKey (pairMsgData m) == remoteSshPubKey (inProgressPairData p)) pip + case (wrongstage, fromus, sane, pairMsgStage m) of + (_, True, _, _) -> do + debug ["ignoring message that looped back"] + go reqs cache sock + (_, _, False, _) -> go reqs cache sock + -- PairReq starts a pairing process, so a + -- new one is always heeded, even if + -- some other pairing is in process. + (_, _, _, PairReq) -> if m `elem` reqs then go reqs (invalidateCache m cache) sock else do pairReqReceived verified urlrenderer m go (m:take 10 reqs) (invalidateCache m cache) sock - (_, _, PairAck) -> do + (True, _, _, _) -> do + debug + ["ignoring out of order message" + , show (pairMsgStage m) + , "expected" + , show (succ . inProgressPairStage <$> pip) + ] + go reqs cache sock + (_, _, _, PairAck) -> do cache' <- pairAckReceived verified pip m cache go reqs cache' sock - (_, _, PairDone) -> do + (_,_ , _, PairDone) -> do pairDoneReceived verified pip m go reqs cache sock @@ -75,11 +88,10 @@ pairListenerThread urlrenderer = namedThread "PairListener" $ do verified = verifiedPairMsg m pip sameuuid = pairUUID (inProgressPairData pip) == pairUUID (pairMsgData m) - {- Various sanity checks on the content of the message. -} - checkSane msg + checkSane msg {- Control characters could be used in a - console poisoning attack. -} - | any isControl msg || any (`elem` "\r\n") msg = do + | any isControl (filter (/= '\n') (decode_c msg)) = do liftAnnex $ warning "illegal control characters in pairing message; ignoring" return False diff --git a/debian/changelog b/debian/changelog index 193976ac9..6c743e19a 100644 --- a/debian/changelog +++ b/debian/changelog @@ -1,3 +1,10 @@ +git-annex (4.20131102) UNRELEASED; urgency=low + + * Improve local pairing behavior when two computers both try to start + the pairing process separately. + + -- Joey Hess <joeyh@debian.org> Sat, 02 Nov 2013 14:54:36 -0400 + git-annex (4.20131101) unstable; urgency=low * The "git annex content" command is renamed to "git annex wanted". diff --git a/doc/bugs/Local_pairing_fails:_received_PairMsg_loop.mdwn b/doc/bugs/Local_pairing_fails:_received_PairMsg_loop.mdwn index 1751429be..63f423e2c 100644 --- a/doc/bugs/Local_pairing_fails:_received_PairMsg_loop.mdwn +++ b/doc/bugs/Local_pairing_fails:_received_PairMsg_loop.mdwn @@ -23,3 +23,17 @@ I'm on Ubuntu Raring 13.04. I installed git-annex 4.20131024 from the Precise P ...and so on and so on... # End of transcript or log. """]] + +> I was able to reproduce something very like this by starting +> pairing separately on both computers under poor network conditions (ie, +> weak wifi on my front porch). +> +> So, I've made a new PairReq message that has not been seen before +> always make the alert pop up, even if the assistant thinks it is +> in the middle of its own pairing process (or even another pairing process +> with a different box on the LAN). +> +> (This shouldn't cause a rogue PairAck to disrupt a pairing process part +> way through.) +> +> [[done]] --[[Joey]] |