From aa492bc65904a19f22ffdfc20d7a5e7052e2f54d Mon Sep 17 00:00:00 2001 From: Joey Hess Date: Wed, 22 Jul 2020 11:04:33 -0400 Subject: [PATCH] Fix a hang when using git-annex with an old openssh 7.2p2 This does mean a 2 second delay after transfers when using that ssh, but it's an old and apparently quite weirdly broken version of ssh. --- Utility/Metered.hs | 23 +++++++++++++++---- ...stems___40__Xenial__44___Jessie__41__.mdwn | 4 ++++ 2 files changed, 22 insertions(+), 5 deletions(-) diff --git a/Utility/Metered.hs b/Utility/Metered.hs index 1c35a9a056..dd49bd06d4 100644 --- a/Utility/Metered.hs +++ b/Utility/Metered.hs @@ -1,6 +1,6 @@ {- Metered IO and actions - - - Copyright 2012-2018 Joey Hess + - Copyright 2012-2020 Joey Hess - - License: BSD-2-clause -} @@ -46,6 +46,7 @@ import Common import Utility.Percentage import Utility.DataUnits import Utility.HumanTime +import Utility.ThreadScheduler import qualified Data.ByteString.Lazy as L import qualified Data.ByteString as S @@ -314,10 +315,22 @@ outputFilter cmd params environ outfilter errfilter = catchMaybeIO $ withCreateProcess p go where go _ (Just outh) (Just errh) pid = do - void $ concurrently - (tryIO (outfilter outh) >> hClose outh) - (tryIO (errfilter errh) >> hClose errh) - waitForProcess pid + outt <- async $ tryIO (outfilter outh) >> hClose outh + errt <- async $ tryIO (errfilter errh) >> hClose errh + ret <- waitForProcess pid + -- Normally, now that the process has exited, the threads + -- will finish processing its output and terminate. + -- But, just in case the process did something evil like + -- forking to the background while inheriting stderr, + -- it's possible that the threads will not finish, which + -- would result in a deadlock. So, wait a few seconds + -- maximum for them to finish and then cancel them. + -- (One program that has behaved this way in the past is + -- openssh.) + race_ + (wait outt >> wait errt) + (threadDelaySeconds (Seconds 2) >> cancel outt >> cancel errt) + return ret go _ _ _ _ = error "internal" p = (proc cmd (toCommand params)) diff --git a/doc/bugs/Recent_hang_with_rsync_remote_with_older_systems___40__Xenial__44___Jessie__41__.mdwn b/doc/bugs/Recent_hang_with_rsync_remote_with_older_systems___40__Xenial__44___Jessie__41__.mdwn index 1ef2e78b43..aad4c5ae35 100644 --- a/doc/bugs/Recent_hang_with_rsync_remote_with_older_systems___40__Xenial__44___Jessie__41__.mdwn +++ b/doc/bugs/Recent_hang_with_rsync_remote_with_older_systems___40__Xenial__44___Jessie__41__.mdwn @@ -161,3 +161,7 @@ in git-annex. [[!meta author=kyle]] [[!tag projects/datalad]] + +> [[fixed|done]] made it cancel the threads 2 seconds after the process +> exited if still running. So there will be a bit of a slow down when using +> that broken ssh version, but it will work. --[[Joey]]