summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorMathieu Boespflug <m@tweag.io>2014-07-18 23:55:18 -0500
committerAustin Seipp <austin@well-typed.com>2014-07-20 16:55:51 -0500
commitfb936e0db55b0522ddcabd39833c99c7c2871170 (patch)
treef4cb208d08be978e8155d8d41de2a6338c3f145f
parentd996a1bb4db84727fbf1a8e9461a032e04e544e7 (diff)
downloadhaskell-fb936e0db55b0522ddcabd39833c99c7c2871170.tar.gz
Make GHCi permissions checks ignore root user.
Summary: As a security precaution, GHCi helpfully refuses to run a .ghci file if it is owned by another user. But if the that other user is root, then arguably GHCi should not refuse to interpret the file, because if root really was malicious, then the user would be having a bad day anyways. This means that .ghci files installed in a global location, say under /usr/local/, can now be read. Fixes #9324 Test Plan: ``` $ sudo touch .ghci $ ghci ``` Notice that the warning about the file being owned by someone else is now gone. Reviewers: austin Reviewed By: austin Subscribers: phaskell, simonmar, carter, nomeata, relrod Projects: #ghc Differential Revision: https://phabricator.haskell.org/D75
-rw-r--r--ghc/InteractiveUI.hs25
1 files changed, 11 insertions, 14 deletions
diff --git a/ghc/InteractiveUI.hs b/ghc/InteractiveUI.hs
index ef48c348bd..c66b025739 100644
--- a/ghc/InteractiveUI.hs
+++ b/ghc/InteractiveUI.hs
@@ -586,8 +586,9 @@ nextInputLine show_prompt is_tty
fileLoop stdin
-- NOTE: We only read .ghci files if they are owned by the current user,
--- and aren't world writable. Otherwise, we could be accidentally
--- running code planted by a malicious third party.
+-- and aren't world writable (files owned by root are ok, see #9324).
+-- Otherwise, we could be accidentally running code planted by
+-- a malicious third party.
-- Furthermore, We only read ./.ghci if . is owned by the current user
-- and isn't writable by anyone else. I think this is sufficient: we
@@ -602,18 +603,14 @@ checkPerms name =
handleIO (\_ -> return False) $ do
st <- getFileStatus name
me <- getRealUserID
- if fileOwner st /= me then do
- putStrLn $ "WARNING: " ++ name ++ " is owned by someone else, IGNORING!"
- return False
- else do
- let mode = System.Posix.fileMode st
- if (groupWriteMode == (mode `intersectFileModes` groupWriteMode))
- || (otherWriteMode == (mode `intersectFileModes` otherWriteMode))
- then do
- putStrLn $ "*** WARNING: " ++ name ++
- " is writable by someone else, IGNORING!"
- return False
- else return True
+ let mode = System.Posix.fileMode st
+ ok = (fileOwner st == me || fileOwner st == 0) &&
+ groupWriteMode /= mode `intersectFileModes` groupWriteMode &&
+ otherWriteMode /= mode `intersectFileModes` otherWriteMode
+ unless ok $
+ putStrLn $ "*** WARNING: " ++ name ++
+ " is writable by someone else, IGNORING!"
+ return ok
#endif
incrementLineNo :: InputT GHCi ()