summaryrefslogtreecommitdiffhomepage
diff options
context:
space:
mode:
authorJoey Hess <joeyh@joeyh.name>2017-05-20 17:09:28 -0400
committerJoey Hess <joeyh@joeyh.name>2017-05-20 17:21:08 -0400
commit73a310ce49c91f0884d05a8d2cd8c96c3c5447d3 (patch)
tree1d7489b13e5ae950a849508857111966e538625e
parent34b0151e125a6698f57ea476ccfa922c6275edf1 (diff)
downloaddebug-me-73a310ce49c91f0884d05a8d2cd8c96c3c5447d3.tar.gz
developer keyring verification
* gpg keyrings in /usr/share/debug-me/ will be checked to see if a connecting person is a known developer of software installed on the system, and so implicitly trusted already. Software packages/projects can install keyrings to that location. (Thanks to Sean Whitton for the idea.) * make install will install /usr/share/debug-me/debug-me_developer.gpg, which contains the key of Joey Hess. (stack and cabal installs don't include this file because they typically don't install system-wide) * debug-me.cabal: Added dependency on time. This commit was sponsored by Francois Marier on Patreon.
-rw-r--r--CHANGELOG9
-rw-r--r--ControlWindow.hs3
-rw-r--r--Gpg/Keyring.hs73
-rw-r--r--Gpg/Wot.hs5
-rw-r--r--Makefile3
-rw-r--r--debug-me.113
-rw-r--r--debug-me.cabal13
-rw-r--r--developer-keyring.gpgbin0 -> 5646 bytes
-rw-r--r--doc/faq.mdwn40
-rw-r--r--doc/index.mdwn10
-rw-r--r--doc/todo/use_distribution_keyrings.mdwn3
-rw-r--r--doc/todo/use_distribution_keyrings/comment_2_43e012511d2fc39d78789541482928b7._comment9
12 files changed, 160 insertions, 21 deletions
diff --git a/CHANGELOG b/CHANGELOG
index bafd9e9..e8ea5c1 100644
--- a/CHANGELOG
+++ b/CHANGELOG
@@ -1,6 +1,15 @@
debug-me (1.20170510) UNRELEASED; urgency=medium
* debug-me is available in Debian unstable.
+ * gpg keyrings in /usr/share/debug-me/ will be checked
+ to see if a connecting person is a known developer of software
+ installed on the system, and so implicitly trusted already.
+ Software packages/projects can install keyrings to that location.
+ (Thanks to Sean Whitton for the idea.)
+ * make install installs /usr/share/debug-me/a_debug-me_developer.gpg,
+ which contains the key of Joey Hess. (stack and cabal installs don't
+ include this file because they typically don't install system-wide)
+ * debug-me.cabal: Added dependency on time.
* stack.yaml: Update to new posix-pty version.
-- Joey Hess <id@joeyh.name> Sat, 20 May 2017 13:47:27 -0400
diff --git a/ControlWindow.hs b/ControlWindow.hs
index c5a6be9..bd79d0f 100644
--- a/ControlWindow.hs
+++ b/ControlWindow.hs
@@ -15,6 +15,7 @@ import ControlSocket
import VirtualTerminal
import Gpg
import Gpg.Wot
+import Gpg.Keyring
import Output
import System.IO
@@ -163,6 +164,8 @@ askToAllow ochan promptchan responsechan k@(GpgSigned pk _ _) = do
ws <- downloadWotStats gpgkeyid
putStrLn $ unlines $ map sanitizeForDisplay $
describeWot ws ss
+ mapM_ (putStrLn . keyringToDeveloperDesc ws)
+ =<< findKeyringsContaining gpgkeyid
promptconnect
where
promptconnect :: IO ()
diff --git a/Gpg/Keyring.hs b/Gpg/Keyring.hs
new file mode 100644
index 0000000..a0fa242
--- /dev/null
+++ b/Gpg/Keyring.hs
@@ -0,0 +1,73 @@
+{- Copyright 2017 Joey Hess <id@joeyh.name>
+ -
+ - Licensed under the GNU AGPL version 3 or higher.
+ -}
+
+-- | Gpg keyrings for debug-me
+
+module Gpg.Keyring where
+
+import Gpg
+import qualified Gpg.Wot
+
+import System.FilePath
+import Data.Char
+import System.Directory
+import Data.Time.Clock
+import Data.Time.Format
+import System.Process
+import System.Exit
+
+keyringDir :: FilePath
+keyringDir = "/usr/share/debug-me/keyring"
+
+data Keyring = Keyring FilePath UTCTime
+
+keyringToDeveloperDesc :: Maybe (Gpg.Wot.WotStats) -> Keyring -> String
+keyringToDeveloperDesc mws (Keyring f mtime) =
+ name ++ " is " ++ desc ++ " \t(as of " ++ showtime mtime ++ ")"
+ where
+ name = maybe "This person" Gpg.Wot.wotStatName mws
+ desc = map sanitize $ dropExtension $ takeFileName f
+ sanitize '_' = ' '
+ sanitize c
+ | isAlphaNum c || c `elem` "-+" = c
+ | otherwise = '?'
+ showtime = formatTime defaultTimeLocale "%c"
+
+findKeyringsContaining :: GpgKeyId -> IO [Keyring]
+findKeyringsContaining k =
+ go [] . map (keyringDir </>) =<< getDirectoryContents keyringDir
+ where
+ go c [] = return c
+ go c (f:fs) = do
+ isfile <- doesFileExist f
+ if isfile && takeExtension f == ".gpg"
+ then do
+ inkeyring <- isInKeyring k f
+ if inkeyring
+ then do
+ mtime <- getModificationTime f
+ let keyring = Keyring f mtime
+ go (keyring : c) fs
+ else go c fs
+ else go c fs
+
+-- | Check if the gpg key is included in the keyring file.
+--
+-- Similar to gpgv, this does not check if the key is revoked or expired,
+-- only if it's included in the keyring.
+isInKeyring :: GpgKeyId -> FilePath -> IO Bool
+isInKeyring (GpgKeyId k) f = do
+ -- gpg assumes non-absolute keyring files are relative to ~/.gnupg/
+ absf <- makeAbsolute f
+ let p = proc "gpg"
+ -- Avoid reading any keyrings except the specified one.
+ [ "--no-options"
+ , "--no-default-keyring"
+ , "--no-auto-check-trustdb"
+ , "--keyring", absf
+ , "--list-key", k
+ ]
+ (exitcode, _, _) <- readCreateProcessWithExitCode p ""
+ return (exitcode == ExitSuccess)
diff --git a/Gpg/Wot.hs b/Gpg/Wot.hs
index b29ccc7..2a6d541 100644
--- a/Gpg/Wot.hs
+++ b/Gpg/Wot.hs
@@ -107,7 +107,7 @@ describeWot (Just ws) (StrongSetAnalysis ss)
, theirname ++ " is probably a real person."
]
where
- theirname = stripEmail (uid (key ws))
+ theirname = wotStatName ws
sigs = cross_sigs ws ++ other_sigs ws
bestconnectedsigs = sortOn rank sigs
describeWot Nothing _ =
@@ -115,5 +115,8 @@ describeWot Nothing _ =
, "Their identity cannot be verified!"
]
+wotStatName :: WotStats -> String
+wotStatName ws = stripEmail (uid (key ws))
+
stripEmail :: String -> String
stripEmail = unwords . takeWhile (not . ("<" `isPrefixOf`)) . words
diff --git a/Makefile b/Makefile
index 3244942..01eaad3 100644
--- a/Makefile
+++ b/Makefile
@@ -61,6 +61,9 @@ install-files: debug-me install-mans
install -m 0755 debug-me.init $(DESTDIR)$(PREFIX)/etc/init.d/debug-me
install -d $(DESTDIR)$(PREFIX)/etc/default
install -m 0644 debug-me.default $(DESTDIR)$(PREFIX)/etc/default/debug-me
+ install -d $(DESTDIR)$(PREFIX)/usr/share/debug-me/keyring
+ install -m 0655 developer-keyring.gpg \
+ $(DESTDIR)$(PREFIX)/usr/share/debug-me/keyring/a_debug-me_developer.gpg
install-mans:
install -d $(DESTDIR)$(PREFIX)/usr/share/man/man1
diff --git a/debug-me.1 b/debug-me.1
index a0e108a..251e636 100644
--- a/debug-me.1
+++ b/debug-me.1
@@ -14,13 +14,16 @@ problem. Making your problem their problem gets it fixed fast.
A debug-me session is logged and signed with the developer's GnuPG
key, producing a chain of evidence of what they saw and what they did.
So the developer's good reputation is leveraged to make debug-me secure.
+If you trust a developer to ship software to your computer,
+you can trust them to debug-me.
.PP
When you start debug-me without any options, it will connect to a debug-me
server, and print out an url that you can give to the developer to get
them connected to you. Then debug-me will show you their GnuPG key and who
-has signed it. If the developer has a good reputation, you can proceed
-to let them type into your console in a debug-me session. Once the
-session is done, the debug-me server will email you the signed
+has signed it, and will let you know if they are a known developer
+of software on your computer. If the developer has a good reputation, you
+can proceed to let them type into your console in a debug-me session. Once
+the session is done, the debug-me server will email you the signed
evidence of what the developer did in the session.
.PP
It's a good idea to watch the debug-me session. The developer should be
@@ -101,6 +104,10 @@ exits.
.IP "~/.debug-me/log/remote/"
When using debug-me to connect to a remote session, the session will be
logged to here.
+.UP "/usr/share/debug-me/keyring/*.gpg"
+When verifying a developer's gpg key, debug-me checks if it's listed in
+the keyrings in this directory, which can be provided by software installed
+on the computer.
.SH SEE ALSO
<https://debug-me.branchable.com/>
.PP
diff --git a/debug-me.cabal b/debug-me.cabal
index 10b184e..3750f00 100644
--- a/debug-me.cabal
+++ b/debug-me.cabal
@@ -20,13 +20,16 @@ Description:
A debug-me session is logged and signed with the developer's GnuPG
key, producing a chain of evidence of what they saw and what they did.
So the developer's good reputation is leveraged to make debug-me secure.
+ If you trust a developer to ship software to your computer,
+ you can trust them to debug-me.
.
When you start debug-me without any options, it will connect to a debug-me
server, and print out an url that you can give to the developer to get
them connected to you. Then debug-me will show you their GnuPG key and who
- has signed it. If the developer has a good reputation, you can proceed
- to let them type into your console in a debug-me session. Once the
- session is done, the debug-me server will email you the signed
+ has signed it, and will let you know if they are a known developer
+ of software on your computer. If the developer has a good reputation,
+ you can proceed to let them type into your console in a debug-me session.
+ Once the session is done, the debug-me server will email you the signed
evidence of what the developer did in the session.
.
If the developer did do something bad, you'd have proof that they cannot
@@ -40,6 +43,7 @@ Extra-Source-Files:
debug-me.service
debug-me.init
debug-me.default
+ developer-keyring.gpg
Executable debug-me
Main-Is: debug-me.hs
@@ -81,6 +85,7 @@ Executable debug-me
, utf8-string (>= 1.0)
, network-uri (>= 2.6)
, mime-mail (>= 0.4)
+ , time (>= 1.6)
Other-Modules:
ControlWindow
ControlSocket
@@ -90,6 +95,7 @@ Executable debug-me
Graphviz
Gpg
Gpg.Wot
+ Gpg.Keyring
Hash
JSON
Log
@@ -109,6 +115,7 @@ Executable debug-me
SessionID
Types
Val
+ Verify
VirtualTerminal
WebSockets
diff --git a/developer-keyring.gpg b/developer-keyring.gpg
new file mode 100644
index 0000000..9ca0ee1
--- /dev/null
+++ b/developer-keyring.gpg
Binary files differ
diff --git a/doc/faq.mdwn b/doc/faq.mdwn
index c9b46ea..6884ec0 100644
--- a/doc/faq.mdwn
+++ b/doc/faq.mdwn
@@ -6,20 +6,28 @@
#### Should I let John Doe connect to my debug-me session? I don't know that guy.
-When a developer connects to your debug-me session, it will display
-their GnuPG key, and the number of people who have signed it. It will
-also list the names of some of those people (the best connected ones).
-
-If the developer of software you use is connecting to debug-me,
-their software documentation might say what their GnuPG key is. Then you
-can simply check that the GnuPG key ids match.
+When a developer connects to your debug-me session, debug-me will display
+their GnuPG key, and information about it, including
+the number of people who have signed it. It will also list the names
+of some of those people (the best connected ones).
+
+Suppose you're using Debian, and debug-me says "John Doe is a Debian
+developer". Then it's probably safe to let this person connect,
+because you already trust this guy implicitly, since you're using software
+he develops.
+
+How does debug-me know that John Doe is a Debian developer? It's checked
+that his gpg key is in the keyring at
+`/usr/share/debug-me/keyring/a_Debian_developer.gpg`, which is provided by
+Debian. Other software projects that are installed on your computer can
+also put keyrings in that directory, and then debug-me will be able to
+tell then a developer of a project is connecting.
If debug-me says that "John Doe is probably a real person", it means
that he's connected to the strong set of the GnuPG web of trust.
Other people, who certianly are real, have verified his identity.
-So even if you don't know his name, it can be safe to let him connect.
-
-But it's a gut call. If in doubt, don't let the developer connect.
+So even if you don't know his name, it can be safe to let him connect,
+but if in doubt, don't let him.
If debug-me says "identity cannot be verified!", it means that the GnuPG
key couldn't be downloaded at all, or the developer is not connected to the
@@ -67,6 +75,18 @@ Here's a quick checklist:
* Include your GnuPG key id in your project's documentation, so users
will know which key is yours. It also helps to sign git tags,
tarballs, git commits, etc with your key.
+* Make your software package install a gpg keyring of its developers to
+ /usr/share/debug-me/keyring/.
+
+ A file there named "a_Foo_developer.gpg"
+ will make debug-me tell the user that "Your Name is a Foo developer."
+ when you connect to their debug-me session, and so the user will be more
+ likely to trust you and let you connect.
+
+ For example:
+
+ gpg --export-options export-minimal --export C910D9222512E3C7 > a_Foo_developer.gpg
+
* When a user has a bug that you need more information to reproduce and
understand, ask if they'll use debug-me.
diff --git a/doc/index.mdwn b/doc/index.mdwn
index 84bc344..14fec93 100644
--- a/doc/index.mdwn
+++ b/doc/index.mdwn
@@ -20,19 +20,21 @@ problem. Making your problem their problem gets it fixed fast.
A debug-me session is logged and signed with the developer's GnuPG key,
producing a [[chain of evidence|evidence]] of what they saw and what they
did. So the developer's good reputation is leveraged to make debug-me
-secure.
+secure. If you trust a developer to ship software to your computer,
+you can trust them to debug-me.
When you start debug-me without any options, it will connect to a debug-me
[[server|servers]], and print out an url that you can give to the developer
-to get them connected to you. Then debug-me will show you their GnuPG key
-and who has signed it. If the developer has a good reputation, you can
+to get them connected to you. Then debug-me will show you their GnuPG key,
+who has signed it, and will let you know if they are a known developer
+of software on your computer. If the developer has a good reputation, you can
proceed to let them type into your console in a debug-me session. Once the
session is done, the debug-me server will email you the signed evidence of
what the developer did in the session.
If the developer did do something bad, you'd have proof that they cannot
be trusted, which you can share with the world. Knowing that is the case
-will keep most developers honest.
+will keep developers honest.
<video controls width=400 title="debug-me demo" src="https://downloads.kitenet.net/videos/debug-me/debug-me-demo.webm"></video>
<video controls width=400 title="debug-me logs" src="https://downloads.kitenet.net/videos/debug-me/debug-me-logs.webm"></video>
diff --git a/doc/todo/use_distribution_keyrings.mdwn b/doc/todo/use_distribution_keyrings.mdwn
index df21588..be4492e 100644
--- a/doc/todo/use_distribution_keyrings.mdwn
+++ b/doc/todo/use_distribution_keyrings.mdwn
@@ -5,3 +5,6 @@ Example output: `Sean Whitton is an official Debian Developer (information accur
Distribution packagers of debug-me could add the keyrings to be checked in this way to a configuration file, or possibly just hardcode them somewhere in debug-me's source.
--spwhitton
+
+> [[done]]; you'll need to include the symlinks to the debian keyring
+> in the keysafe.deb. --[[Joey]]
diff --git a/doc/todo/use_distribution_keyrings/comment_2_43e012511d2fc39d78789541482928b7._comment b/doc/todo/use_distribution_keyrings/comment_2_43e012511d2fc39d78789541482928b7._comment
new file mode 100644
index 0000000..8145e47
--- /dev/null
+++ b/doc/todo/use_distribution_keyrings/comment_2_43e012511d2fc39d78789541482928b7._comment
@@ -0,0 +1,9 @@
+[[!comment format=mdwn
+ username="joey"
+ subject="""comment 2"""
+ date="2017-05-20T21:10:36Z"
+ content="""
+Simplified that sligtly. The keyring filename can describe the
+relationship, eg "a_Debian_developer.gpg". The mtime of the keyring will be
+displayed so the user knows how up-to-date it is.
+"""]]