diff options
author | Joe Crayne <joe@jerkface.net> | 2020-05-19 17:40:39 -0400 |
---|---|---|
committer | Joe Crayne <joe@jerkface.net> | 2020-05-24 14:11:07 -0400 |
commit | 9cc0b24375b6b40eb7c3412983e75b6e3fe3a3f6 (patch) | |
tree | 88e7add38a551703db90abd6287bc5878c184863 | |
parent | a3a517892426b0fb2cffbfcca5f749f06d710842 (diff) |
Commandline option to use v5 key packets.
-rw-r--r-- | cokiki.hs | 33 | ||||
-rw-r--r-- | kiki.hs | 13 | ||||
-rw-r--r-- | lib/KeyRing.hs | 3 | ||||
-rw-r--r-- | lib/KeyRing/BuildKeyDB.hs | 3 | ||||
-rw-r--r-- | lib/KeyRing/Types.hs | 9 | ||||
-rw-r--r-- | lib/Kiki.hs | 15 |
6 files changed, 46 insertions, 30 deletions
@@ -25,6 +25,7 @@ usage = unlines | |||
25 | [ "cokiki <command> [--chroot=ROOTDIR]" | 25 | [ "cokiki <command> [--chroot=ROOTDIR]" |
26 | , " [--homedir=HOMEDIR]" | 26 | , " [--homedir=HOMEDIR]" |
27 | , " [--passphrase-fd=FD]" | 27 | , " [--passphrase-fd=FD]" |
28 | , " [-(4|5)]" | ||
28 | , "" | 29 | , "" |
29 | , "cokiki modifies system configuration to recognize generated files" | 30 | , "cokiki modifies system configuration to recognize generated files" |
30 | , "in /var/cache/kiki. In addition to each command's documented effects" | 31 | , "in /var/cache/kiki. In addition to each command's documented effects" |
@@ -61,12 +62,12 @@ usage = unlines | |||
61 | main = do | 62 | main = do |
62 | (cmd,args) <- splitAt 1 <$> getArgs | 63 | (cmd,args) <- splitAt 1 <$> getArgs |
63 | uid <- getEffectiveUserID | 64 | uid <- getEffectiveUserID |
64 | let msel = case cmd of | 65 | let msel = fmap (\c -> c <$> Kiki.dashdashPGPVersion <*> Kiki.dashdashChroot <*> Kiki.dashdashHomedir) $ case cmd of |
65 | ["ssh-client"] -> Just $ sshClient uid <$> Kiki.dashdashChroot <*> Kiki.dashdashHomedir | 66 | ["ssh-client"] -> Just $ sshClient uid |
66 | ["ssh-server"] -> Just $ sshServer uid <$> Kiki.dashdashChroot <*> Kiki.dashdashHomedir | 67 | ["ssh-server"] -> Just $ sshServer uid |
67 | ["strongswan"] -> Just $ strongswan uid <$> Kiki.dashdashChroot <*> Kiki.dashdashHomedir | 68 | ["strongswan"] -> Just $ strongswan uid |
68 | ["tor"] -> Just $ configureTor uid <$> Kiki.dashdashChroot <*> Kiki.dashdashHomedir | 69 | ["tor"] -> Just $ configureTor uid |
69 | ["hosts"] -> Just $ configureHosts uid <$> Kiki.dashdashChroot <*> Kiki.dashdashHomedir | 70 | ["hosts"] -> Just $ configureHosts uid |
70 | _ -> Nothing | 71 | _ -> Nothing |
71 | spec = uncurry fancy Kiki.kikiOptions "" | 72 | spec = uncurry fancy Kiki.kikiOptions "" |
72 | errorQuit msg = do | 73 | errorQuit msg = do |
@@ -97,7 +98,7 @@ whenRoot uid root cmn action | |||
97 | where | 98 | where |
98 | no = hPutStrLn stderr "operation requires root." | 99 | no = hPutStrLn stderr "operation requires root." |
99 | 100 | ||
100 | sshClient uid root cmn = whenRoot uid root cmn $ do | 101 | sshClient uid pgpver root cmn = whenRoot uid root cmn $ do |
101 | -- /etc/ssh/config/ssh_config <-- 'GlobalKnownHostsFile /var/cache/kiki/ssh_known_hosts' | 102 | -- /etc/ssh/config/ssh_config <-- 'GlobalKnownHostsFile /var/cache/kiki/ssh_known_hosts' |
102 | sshconfig <- parseSshConfig . fromMaybe "" <$> maybeReadFile (root "/etc/ssh/ssh_config") | 103 | sshconfig <- parseSshConfig . fromMaybe "" <$> maybeReadFile (root "/etc/ssh/ssh_config") |
103 | let (ps,qs) = sshSplitAtDirective "GlobalKnownHostsFile" sshconfig | 104 | let (ps,qs) = sshSplitAtDirective "GlobalKnownHostsFile" sshconfig |
@@ -122,9 +123,9 @@ sshClient uid root cmn = whenRoot uid root cmn $ do | |||
122 | maybe (return ()) (myWriteFile (root "/etc/ssh/ssh_config") . unparseSshConfig) sshconfig' | 123 | maybe (return ()) (myWriteFile (root "/etc/ssh/ssh_config") . unparseSshConfig) sshconfig' |
123 | 124 | ||
124 | -- /var/cache/kiki/config/ssh_known_hosts <-- contains known hosts from /root/.gnupg/... | 125 | -- /var/cache/kiki/config/ssh_known_hosts <-- contains known hosts from /root/.gnupg/... |
125 | Kiki.importAndRefresh root cmn Unencrypted | 126 | Kiki.importAndRefresh pgpver root cmn Unencrypted |
126 | 127 | ||
127 | sshServer uid root cmn = whenRoot uid root cmn $ do | 128 | sshServer uid pgpver root cmn = whenRoot uid root cmn $ do |
128 | sshconfig <- parseSshConfig . fromMaybe "" <$> maybeReadFile (root "/etc/ssh/sshd_config") | 129 | sshconfig <- parseSshConfig . fromMaybe "" <$> maybeReadFile (root "/etc/ssh/sshd_config") |
129 | let p:gs = groupBy (\_ d -> not $ sshIsDirective "HostKey" d) $ ["#"]:sshconfig | 130 | let p:gs = groupBy (\_ d -> not $ sshIsDirective "HostKey" d) $ ["#"]:sshconfig |
130 | got = filter (\(d:ds) -> elem "/var/cache/kiki/config/ssh_host_rsa_key" d) gs | 131 | got = filter (\(d:ds) -> elem "/var/cache/kiki/config/ssh_host_rsa_key" d) gs |
@@ -135,9 +136,9 @@ sshServer uid root cmn = whenRoot uid root cmn $ do | |||
135 | hPutStrLn stderr "adding HostKey directive" | 136 | hPutStrLn stderr "adding HostKey directive" |
136 | myWriteFile (root "/etc/ssh/sshd_config") $ unparseSshConfig sshconfig' | 137 | myWriteFile (root "/etc/ssh/sshd_config") $ unparseSshConfig sshconfig' |
137 | -- /etc/ssh/sshd_config <-- 'HostKey /var/cache/kiki/config/ssh_host_ecdsa_key' etc. | 138 | -- /etc/ssh/sshd_config <-- 'HostKey /var/cache/kiki/config/ssh_host_ecdsa_key' etc. |
138 | Kiki.importAndRefresh root cmn Unencrypted | 139 | Kiki.importAndRefresh pgpver root cmn Unencrypted |
139 | 140 | ||
140 | strongswan uid root cmn = whenRoot uid root cmn $ do | 141 | strongswan uid pgpver root cmn = whenRoot uid root cmn $ do |
141 | -- (1) /etc/ipsec.conf <-- 'include /var/cache/kiki/config/ipsec.conf' | 142 | -- (1) /etc/ipsec.conf <-- 'include /var/cache/kiki/config/ipsec.conf' |
142 | -- Parsing as if ssh config, that's not right, but good enough for now. | 143 | -- Parsing as if ssh config, that's not right, but good enough for now. |
143 | ipsecconf <- parseSshConfig . fromMaybe "" <$> maybeReadFile (root "/etc/ipsec.conf") | 144 | ipsecconf <- parseSshConfig . fromMaybe "" <$> maybeReadFile (root "/etc/ipsec.conf") |
@@ -161,9 +162,9 @@ strongswan uid root cmn = whenRoot uid root cmn $ do | |||
161 | stmt = ["include", " ", "/var/cache/kiki/config/ipsec.secrets"] | 162 | stmt = ["include", " ", "/var/cache/kiki/config/ipsec.secrets"] |
162 | hPutStrLn stderr "adding include directive" | 163 | hPutStrLn stderr "adding include directive" |
163 | myWriteFile (root "/etc/ipsec.secrets") $ unparseSshConfig ipsecconf' | 164 | myWriteFile (root "/etc/ipsec.secrets") $ unparseSshConfig ipsecconf' |
164 | Kiki.importAndRefresh root cmn Unencrypted | 165 | Kiki.importAndRefresh pgpver root cmn Unencrypted |
165 | 166 | ||
166 | configureTor uid root cmn = whenRoot uid root cmn $ do | 167 | configureTor uid pgpver root cmn = whenRoot uid root cmn $ do |
167 | -- Parsing as if ssh config, that's not right, but good enough for now. | 168 | -- Parsing as if ssh config, that's not right, but good enough for now. |
168 | torrc <- parseSshConfig . fromMaybe "" <$> maybeReadFile (root "/etc/tor/torrc") | 169 | torrc <- parseSshConfig . fromMaybe "" <$> maybeReadFile (root "/etc/tor/torrc") |
169 | let p:gs = groupBy (\_ d -> not $ sshIsDirective "HiddenServiceDir" d) $ ["#"]:torrc | 170 | let p:gs = groupBy (\_ d -> not $ sshIsDirective "HiddenServiceDir" d) $ ["#"]:torrc |
@@ -215,11 +216,11 @@ configureTor uid root cmn = whenRoot uid root cmn $ do | |||
215 | , ["HiddenServicePort"," ","22"," ","127.0.0.1:22"] | 216 | , ["HiddenServicePort"," ","22"," ","127.0.0.1:22"] |
216 | , ["HiddenServicePort"," ","25"," ","127.0.0.1:25"] ] | 217 | , ["HiddenServicePort"," ","25"," ","127.0.0.1:25"] ] |
217 | myWriteFile (root "/etc/tor/torrc") $ unparseSshConfig torrc' | 218 | myWriteFile (root "/etc/tor/torrc") $ unparseSshConfig torrc' |
218 | Kiki.importAndRefresh root cmn Unencrypted | 219 | Kiki.importAndRefresh pgpver root cmn Unencrypted |
219 | return () | 220 | return () |
220 | 221 | ||
221 | configureHosts uid root cmn = whenRoot uid root cmn $ do | 222 | configureHosts uid pgpver root cmn = whenRoot uid root cmn $ do |
222 | Kiki.importAndRefresh root cmn Unencrypted | 223 | Kiki.importAndRefresh pgpver root cmn Unencrypted |
223 | hosts <- Hosts.decode . fromMaybe "" <$> maybeReadFile (root "/etc/hosts") | 224 | hosts <- Hosts.decode . fromMaybe "" <$> maybeReadFile (root "/etc/hosts") |
224 | kikihosts <- Hosts.decode . fromMaybe "" <$> maybeReadFile (root "/var/cache/kiki/config/hosts") | 225 | kikihosts <- Hosts.decode . fromMaybe "" <$> maybeReadFile (root "/var/cache/kiki/config/hosts") |
225 | let hosts' = hosts `Hosts.plus` kikihosts | 226 | let hosts' = hosts `Hosts.plus` kikihosts |
@@ -1568,8 +1568,9 @@ kiki "init" args | "--help" `elem` args = do | |||
1568 | putStr . unlines $ | 1568 | putStr . unlines $ |
1569 | [ "kiki init [ --passphrase-fd=FD" | 1569 | [ "kiki init [ --passphrase-fd=FD" |
1570 | , " | --homedir[=HOMEDIR]" | 1570 | , " | --homedir[=HOMEDIR]" |
1571 | , " | --chroot=ROOTDIR ]" | 1571 | , " | --chroot=ROOTDIR" |
1572 | , " | --cipher="++intercalate "|" (map ciphername ciphers)++" ] ..." | 1572 | , " | --cipher="++intercalate "|" (map ciphername ciphers) |
1573 | , " | -(4|5) ] ..." | ||
1573 | , "" | 1574 | , "" |
1574 | , "Modify your GnuPG keyring and update /var/cache/kiki. The following" | 1575 | , "Modify your GnuPG keyring and update /var/cache/kiki. The following" |
1575 | , "changes will occur to the keyring:" | 1576 | , "changes will occur to the keyring:" |
@@ -1589,10 +1590,16 @@ kiki "init" args | "--help" `elem` args = do | |||
1589 | , " variable is ignored and you must use --homedir to specify" | 1590 | , " variable is ignored and you must use --homedir to specify" |
1590 | , " a value other than /root/.gnupg." | 1591 | , " a value other than /root/.gnupg." |
1591 | , "" | 1592 | , "" |
1593 | , " -4" | ||
1594 | , " New PGP key packets should use the v4 (default) format." | ||
1595 | , "" | ||
1596 | , " -5" | ||
1597 | , " New PGP key packets should use the v5 format and use the" | ||
1598 | , " SHA256-based v5 fingerprints." | ||
1592 | , "" | 1599 | , "" |
1593 | ] ++ documentHomeDir ++ [""] ++ documentPassphraseFDFlag True True True | 1600 | ] ++ documentHomeDir ++ [""] ++ documentPassphraseFDFlag True True True |
1594 | 1601 | ||
1595 | kiki "init" args = run args $ importAndRefresh <$> dashdashChroot <*> dashdashHomedir <*> dashdashCipher | 1602 | kiki "init" args = run args $ importAndRefresh <$> dashdashPGPVersion <*> dashdashChroot <*> dashdashHomedir <*> dashdashCipher |
1596 | kiki "spawn" args | "--help" `elem` args = | 1603 | kiki "spawn" args | "--help" `elem` args = |
1597 | putStr . unlines $ | 1604 | putStr . unlines $ |
1598 | [ "kiki spawn [ --passphrase-fd=FD" | 1605 | [ "kiki spawn [ --passphrase-fd=FD" |
diff --git a/lib/KeyRing.hs b/lib/KeyRing.hs index 5b51a93..9669430 100644 --- a/lib/KeyRing.hs +++ b/lib/KeyRing.hs | |||
@@ -87,8 +87,7 @@ import KeyRing.BuildKeyDB (allNames', Hostnames, | |||
87 | readSecretPEMFile, | 87 | readSecretPEMFile, |
88 | secp256k1_id, | 88 | secp256k1_id, |
89 | selectPublicKey, | 89 | selectPublicKey, |
90 | usageFromFilter, | 90 | usageFromFilter) |
91 | preferredPGPVersion) | ||
92 | 91 | ||
93 | import KeyRing.Types | 92 | import KeyRing.Types |
94 | import KeyDB | 93 | import KeyDB |
diff --git a/lib/KeyRing/BuildKeyDB.hs b/lib/KeyRing/BuildKeyDB.hs index c2b2703..3993c66 100644 --- a/lib/KeyRing/BuildKeyDB.hs +++ b/lib/KeyRing/BuildKeyDB.hs | |||
@@ -79,9 +79,6 @@ import GnuPGAgent | |||
79 | import ByteStringUtil | 79 | import ByteStringUtil |
80 | import Text.XXD | 80 | import Text.XXD |
81 | 81 | ||
82 | preferredPGPVersion :: KeyRingOperation -> Word8 | ||
83 | preferredPGPVersion _ = 4 -- TODO: v5 | ||
84 | |||
85 | newtype IPsToWriteToHostsFile = IPsToWriteToHostsFile [SockAddr] | 82 | newtype IPsToWriteToHostsFile = IPsToWriteToHostsFile [SockAddr] |
86 | -- | buildKeyDB | 83 | -- | buildKeyDB |
87 | -- | 84 | -- |
diff --git a/lib/KeyRing/Types.hs b/lib/KeyRing/Types.hs index dbcc22c..c272efc 100644 --- a/lib/KeyRing/Types.hs +++ b/lib/KeyRing/Types.hs | |||
@@ -32,13 +32,16 @@ data KeyRingOperation = KeyRingOperation | |||
32 | -- ^ If provided, this is the directory where the 'HomeSec' and 'HomePub' | 32 | -- ^ If provided, this is the directory where the 'HomeSec' and 'HomePub' |
33 | -- files reside. Otherwise, the evironment variable $GNUPGHOME is consulted | 33 | -- files reside. Otherwise, the evironment variable $GNUPGHOME is consulted |
34 | -- and if that is not set, it falls back to $HOME/.gnupg. | 34 | -- and if that is not set, it falls back to $HOME/.gnupg. |
35 | , preferredPGPVersion :: Word8 | ||
36 | -- ^ Newly created PGP key packets will use this version. It should be set | ||
37 | -- to either 4 or 5. | ||
35 | } | 38 | } |
36 | deriving (Eq,Show) | 39 | deriving (Eq,Show) |
37 | instance Semigroup KeyRingOperation where | 40 | instance Semigroup KeyRingOperation where |
38 | KeyRingOperation f p t h <> KeyRingOperation f' p' t' h' = | 41 | KeyRingOperation f p t h v <> KeyRingOperation f' p' t' h' v' = |
39 | KeyRingOperation (f <> f') (p <> p') (t <> t') (h <> h') | 42 | KeyRingOperation (f <> f') (p <> p') (t <> t') (h <> h') (max v v') |
40 | instance Monoid KeyRingOperation where | 43 | instance Monoid KeyRingOperation where |
41 | mempty = KeyRingOperation Map.empty [] [] Nothing | 44 | mempty = KeyRingOperation Map.empty [] [] Nothing 4 |
42 | 45 | ||
43 | data InputFile = HomeSec | 46 | data InputFile = HomeSec |
44 | -- ^ A file named secring.gpg located in the home directory. | 47 | -- ^ A file named secring.gpg located in the home directory. |
diff --git a/lib/Kiki.hs b/lib/Kiki.hs index 222c1bb..a0e2d07 100644 --- a/lib/Kiki.hs +++ b/lib/Kiki.hs | |||
@@ -152,6 +152,7 @@ minimalOp isHomeless cap = op | |||
152 | return $ PassphraseSpec Nothing Nothing pfile | 152 | return $ PassphraseSpec Nothing Nothing pfile |
153 | , opTransforms = [] | 153 | , opTransforms = [] |
154 | , opHome = cap_homespec cap | 154 | , opHome = cap_homespec cap |
155 | , preferredPGPVersion = 4 | ||
155 | } | 156 | } |
156 | 157 | ||
157 | run :: [String] -> Args (IO ()) -> IO () | 158 | run :: [String] -> Args (IO ()) -> IO () |
@@ -203,8 +204,8 @@ peminfo bits usage = StreamInfo | |||
203 | , transforms = [] | 204 | , transforms = [] |
204 | } | 205 | } |
205 | 206 | ||
206 | importAndRefresh :: (FilePath -> FilePath) -> CommonArgsParsed -> SymmetricAlgorithm -> IO () | 207 | importAndRefresh :: Word8 -> (FilePath -> FilePath) -> CommonArgsParsed -> SymmetricAlgorithm -> IO () |
207 | importAndRefresh root cmn cipher = do | 208 | importAndRefresh pgpver root cmn cipher = do |
208 | let rootdir = do guard (root "x" /= "x") | 209 | let rootdir = do guard (root "x" /= "x") |
209 | Just $ root "" | 210 | Just $ root "" |
210 | me <- getEffectiveUserID | 211 | me <- getEffectiveUserID |
@@ -214,7 +215,6 @@ importAndRefresh root cmn cipher = do | |||
214 | let homespec = mplus (slash <$> rootdir <*> cap_homespec cmn) | 215 | let homespec = mplus (slash <$> rootdir <*> cap_homespec cmn) |
215 | (fmap (++"/root/.gnupg") rootdir) | 216 | (fmap (++"/root/.gnupg") rootdir) |
216 | passfd = cap_passfd cmn | 217 | passfd = cap_passfd cmn |
217 | pgpver = preferredPGPVersion $ minimalOp False cmn | ||
218 | (home,secring,pubring,mbwk) <- unconditionally $ getHomeDir homespec | 218 | (home,secring,pubring,mbwk) <- unconditionally $ getHomeDir homespec |
219 | osHomeDir <- if bUnprivileged then getHomeDirectory else return "/root" | 219 | osHomeDir <- if bUnprivileged then getHomeDirectory else return "/root" |
220 | 220 | ||
@@ -326,6 +326,7 @@ importAndRefresh root cmn cipher = do | |||
326 | return $ PassphraseSpec Nothing Nothing pfd | 326 | return $ PassphraseSpec Nothing Nothing pfd |
327 | , opHome = homespec | 327 | , opHome = homespec |
328 | , opTransforms = [] | 328 | , opTransforms = [] |
329 | , preferredPGPVersion = pgpver | ||
329 | } | 330 | } |
330 | nop = | 331 | nop = |
331 | KeyRingOperation | 332 | KeyRingOperation |
@@ -340,6 +341,7 @@ importAndRefresh root cmn cipher = do | |||
340 | return $ PassphraseSpec Nothing Nothing pfd | 341 | return $ PassphraseSpec Nothing Nothing pfd |
341 | , opHome=homespec | 342 | , opHome=homespec |
342 | , opTransforms = [] | 343 | , opTransforms = [] |
344 | , preferredPGPVersion = pgpver | ||
343 | } | 345 | } |
344 | when bUnprivileged $ do | 346 | when bUnprivileged $ do |
345 | hPutStrLn stderr "Insufficient privilege generating system service keys." | 347 | hPutStrLn stderr "Insufficient privilege generating system service keys." |
@@ -473,6 +475,7 @@ generateHostsFile fw rt = do | |||
473 | , opPassphrases = [] | 475 | , opPassphrases = [] |
474 | , opHome = Just $ takeDirectory (rtPubring rt) | 476 | , opHome = Just $ takeDirectory (rtPubring rt) |
475 | , opTransforms = [] | 477 | , opTransforms = [] |
478 | , preferredPGPVersion = 4 -- Does not matter (no fill of pgp files). | ||
476 | } | 479 | } |
477 | KikiResult _ report <- runKeyRing op | 480 | KikiResult _ report <- runKeyRing op |
478 | outputReport report | 481 | outputReport report |
@@ -723,6 +726,12 @@ slash "" ('/':xs) = '/':xs | |||
723 | slash "" xs = '/':xs | 726 | slash "" xs = '/':xs |
724 | slash (y:ys) xs = y:slash ys xs | 727 | slash (y:ys) xs = y:slash ys xs |
725 | 728 | ||
729 | dashdashPGPVersion :: Args Word8 | ||
730 | dashdashPGPVersion = liftA2 (\is4 is5 -> if is5 then 5 else if is4 then 4 else defaultV) (flag "-4") (flag "-5") | ||
731 | where | ||
732 | defaultV = 4 -- Use v4 packets by default for now. | ||
733 | |||
734 | |||
726 | dashdashChroot :: Args (FilePath -> FilePath) | 735 | dashdashChroot :: Args (FilePath -> FilePath) |
727 | dashdashChroot = pure (\r a -> slash r a) <*> arg "--chroot" <|> pure id | 736 | dashdashChroot = pure (\r a -> slash r a) <*> arg "--chroot" <|> pure id |
728 | 737 | ||