Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Use parsec, drop parsec flag #4654

Merged
merged 5 commits into from
Aug 15, 2017
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
3 changes: 0 additions & 3 deletions .travis.yml
Original file line number Diff line number Diff line change
Expand Up @@ -54,9 +54,6 @@ matrix:
- env: GHCVER=8.0.2 SCRIPT=solver-debug-flags USE_GOLD=YES
sudo: required
os: linux
- env: GHCVER=8.0.2 SCRIPT=script PARSEC=YES TAGSUFFIX="-parsec" USE_GOLD=YES
os: linux
sudo: required
- env: GHCVER=8.0.2 SCRIPT=script DEBUG_EXPENSIVE_ASSERTIONS=YES TAGSUFFIX="-fdebug-expensive-assertions" USE_GOLD=YES
os: linux
sudo: required
Expand Down
58 changes: 26 additions & 32 deletions Cabal/Cabal.cabal
Original file line number Diff line number Diff line change
Expand Up @@ -32,6 +32,8 @@ extra-source-files:
-- Generated with 'misc/gen-extra-source-files.sh'
-- Do NOT edit this section manually; instead, run the script.
-- BEGIN gen-extra-source-files
tests/ParserTests/regressions/Octree-0.5.cabal
tests/ParserTests/regressions/encoding-0.8.cabal
tests/ParserTests/warnings/bom.cabal
tests/ParserTests/warnings/bool.cabal
tests/ParserTests/warnings/deprecatedfield.cabal
Expand Down Expand Up @@ -64,11 +66,6 @@ flag old-directory
description: Use directory < 1.2 and old-time
default: False

flag parsec
description: Use parsec parser
default: False
manual: True

flag parsec-struct-diff
description: Use StructDiff in parsec tests. Affects only parsec tests.
default: False
Expand Down Expand Up @@ -267,26 +264,23 @@ library
Language.Haskell.Extension
Distribution.Compat.Binary

if flag(parsec)
cpp-options: -DCABAL_PARSEC
build-depends:
transformers,
parsec >= 3.1.9 && <3.2
build-tools:
alex >=3.1.4 && <3.3
exposed-modules:
Distribution.Compat.Parsec
Distribution.PackageDescription.Parsec
Distribution.PackageDescription.Parsec.FieldDescr
Distribution.Parsec.Class
Distribution.Parsec.ConfVar
Distribution.Parsec.Lexer
Distribution.Parsec.LexerMonad
Distribution.Parsec.Parser
Distribution.Parsec.Types.Common
Distribution.Parsec.Types.Field
Distribution.Parsec.Types.FieldDescr
Distribution.Parsec.Types.ParseResult
build-depends:
transformers,
parsec >= 3.1.9 && <3.2
exposed-modules:
Distribution.Compat.Parsec
Distribution.PackageDescription.Parsec
Distribution.PackageDescription.Parsec.FieldDescr
Distribution.PackageDescription.Parsec.Legacy
Distribution.Parsec.Class
Distribution.Parsec.ConfVar
Distribution.Parsec.Lexer
Distribution.Parsec.LexerMonad
Distribution.Parsec.Parser
Distribution.Parsec.Types.Common
Distribution.Parsec.Types.Field
Distribution.Parsec.Types.FieldDescr
Distribution.Parsec.Types.ParseResult

other-modules:
Distribution.Backpack.PreExistingComponent
Expand Down Expand Up @@ -382,9 +376,6 @@ test-suite unit-tests
default-language: Haskell2010

test-suite parser-tests
if !flag(parsec)
buildable: False

type: exitcode-stdio-1.0
hs-source-dirs: tests
main-is: ParserTests.hs
Expand All @@ -400,15 +391,18 @@ test-suite parser-tests
default-language: Haskell2010

test-suite parser-hackage-tests
if !flag(parsec)
buildable: False

type: exitcode-stdio-1.0
main-is: ParserHackageTests.hs

-- TODO: need to get 01-index.tar on appveyor
if os(windows)
buildable: False

hs-source-dirs: tests
build-depends:
base,
base-orphans == 0.6.*,
base-compat >=0.9.3 && <0.10,
containers,
tar >=0.5 && <0.6,
bytestring,
Expand All @@ -418,7 +412,7 @@ test-suite parser-hackage-tests

if flag(parsec-struct-diff)
build-depends:
generics-sop ==0.2.*,
generics-sop >= 0.2.5 && <0.3,
these >=0.7.1 && <0.8,
singleton-bool >=0.1.1.0 && <0.2,
keys
Expand Down
51 changes: 11 additions & 40 deletions Cabal/Distribution/PackageDescription/Parsec.hs
Original file line number Diff line number Diff line change
Expand Up @@ -38,6 +38,7 @@ import qualified Data.Map as Map
import qualified Distribution.Compat.SnocList as SnocList
import Distribution.PackageDescription
import Distribution.PackageDescription.Parsec.FieldDescr
import Distribution.PackageDescription.Parsec.Legacy (patchLegacy)
import Distribution.Parsec.Class (parsec)
import Distribution.Parsec.ConfVar
(parseConditionConfVar)
Expand Down Expand Up @@ -103,10 +104,15 @@ readGenericPackageDescription = readAndParseFile parseGenericPackageDescription
--
-- TODO: add lex warnings
parseGenericPackageDescription :: BS.ByteString -> ParseResult GenericPackageDescription
parseGenericPackageDescription bs = case readFields' bs of
Right (fs, lexWarnings) -> parseGenericPackageDescription' lexWarnings fs
parseGenericPackageDescription bs = case readFields' bs' of
Right (fs, lexWarnings) -> do
when patched $
parseWarning zeroPos PWTLegacyCabalFile "Legacy cabal file"
parseGenericPackageDescription' lexWarnings fs
-- TODO: better marshalling of errors
Left perr -> parseFatalFailure (Position 0 0) (show perr)
Left perr -> parseFatalFailure zeroPos (show perr)
where
(patched, bs') = patchLegacy bs

-- | 'Maybe' variant of 'parseGenericPackageDescription'
parseGenericPackageDescriptionMaybe :: BS.ByteString -> Maybe GenericPackageDescription
Expand Down Expand Up @@ -168,7 +174,8 @@ parseGenericPackageDescription' lexWarnings fs = do
gpd <- goFields emptyGpd fs'
-- Various post checks
maybeWarnCabalVersion syntax (packageDescription gpd)
checkForUndefinedFlags gpd
-- TODO: this does nothing
-- checkForUndefinedFlags gpd
-- TODO: do other validations
return gpd
where
Expand Down Expand Up @@ -326,42 +333,6 @@ parseGenericPackageDescription' lexWarnings fs = do

maybeWarnCabalVersion _ _ = return ()

{-
handleFutureVersionParseFailure :: Version -> ParseResult a -> ParseResult GenericPackageDescription
handleFutureVersionParseFailure _cabalVersionNeeded _parseBody =
error "handleFutureVersionParseFailure"
-}

{-
undefined (unless versionOk (warning message) >> parseBody)
`catchParseError` \parseError -> case parseError of
TabsError _ -> parseFail parseError
_ | versionOk -> parseFail parseError
| otherwise -> fail message
where versionOk = cabalVersionNeeded <= cabalVersion
message = "This package requires at least Cabal version "
++ display cabalVersionNeeded
-}

checkForUndefinedFlags
:: GenericPackageDescription
-> ParseResult ()
checkForUndefinedFlags _gpd = pure ()
{-
let definedFlags = map flagName flags
mapM_ (checkCondTreeFlags definedFlags) (maybeToList mlib)
mapM_ (checkCondTreeFlags definedFlags . snd) sub_libs
mapM_ (checkCondTreeFlags definedFlags . snd) exes
mapM_ (checkCondTreeFlags definedFlags . snd) tests

checkCondTreeFlags :: [FlagName] -> CondTree ConfVar c a -> PM ()
checkCondTreeFlags definedFlags ct = do
let fv = nub $ freeVars ct
unless (all (`elem` definedFlags) fv) $
fail $ "These flags are used without having been defined: "
++ intercalate ", " [ n | FlagName n <- fv \\ definedFlags ]
-}

parseName :: Position -> [SectionArg Position] -> ParseResult String
parseName pos args = case args of
[SecArgName _pos secName] ->
Expand Down
165 changes: 165 additions & 0 deletions Cabal/Distribution/PackageDescription/Parsec/Legacy.hs
Original file line number Diff line number Diff line change
@@ -0,0 +1,165 @@
{-# LANGUAGE RankNTypes #-}
{-# LANGUAGE OverloadedStrings #-}
-- |
--
-- @since 2.2.0.0
module Distribution.PackageDescription.Parsec.Legacy (patchLegacy) where

import Prelude ()
import Distribution.Compat.Prelude
import GHC.Fingerprint (Fingerprint (..), fingerprintData)
import Foreign.Ptr (castPtr)
import System.IO.Unsafe (unsafeDupablePerformIO)

import qualified Data.ByteString as BS
import qualified Data.ByteString.Unsafe as BS
import qualified Data.Map as Map

-- | Patch legacy @.cabal@ file contents to allow parsec parser to accept
-- all of Hackage.
--
-- Bool part of the result tells whether the output is modified.
--
-- @since 2.2.0.0
patchLegacy :: BS.ByteString -> (Bool, BS.ByteString)
patchLegacy bs = case Map.lookup (BS.take 256 bs, md5 bs) patches of
Nothing -> (False, bs)
Just (post, f)
| post /= md5 output -> (False, bs)
| otherwise -> (True, output)
where
output = f bs

md5 :: BS.ByteString -> Fingerprint
md5 bs = unsafeDupablePerformIO $ BS.unsafeUseAsCStringLen bs $ \(ptr, len) ->
fingerprintData (castPtr ptr) len

-- | 'patches' contains first 256 bytes, pre- and post-fingerprints and a patch function.
--
--
patches :: Map.Map (BS.ByteString, Fingerprint) (Fingerprint, BS.ByteString -> BS.ByteString)
patches = Map.fromList
-- http://hackage.haskell.org/package/unicode-transforms-0.3.3
-- other-modules: .
-- ReadP assumed dot is empty line
[ mk "-- This file has been generated from package.yaml by hpack version 0.17.0.\n--\n-- see: https://github.com/sol/hpack\n\nname: unicode-transforms\nversion: 0.3.3\nsynopsis: Unicode normalization\ndescription: Fast Unic"
(Fingerprint 15958160436627155571 10318709190730872881)
(Fingerprint 11008465475756725834 13815629925116264363)
(bsRemove " other-modules:\n .\n") -- TODO: remove traling \n to test structural-diff
-- http://hackage.haskell.org/package/DSTM-0.1.2
-- http://hackage.haskell.org/package/DSTM-0.1.1
-- http://hackage.haskell.org/package/DSTM-0.1
-- Other Modules: no dash
-- ReadP parsed as section
, mk "Name: DSTM\nVersion: 0.1.2\nCopyright: (c) 2010, Frank Kupke\nLicense: LGPL\nLicense-File: LICENSE\nAuthor: Frank Kupke\nMaintainer: frk@informatik.uni-kiel.de\nCabal-Version: >= 1.2.3\nStability: provisional\nSynopsis: A framework for using STM within distributed "
(Fingerprint 6919263071548559054 9050746360708965827)
(Fingerprint 17015177514298962556 11943164891661867280)
(bsReplace "Other modules:" "-- ")
, mk "Name: DSTM\nVersion: 0.1.1\nCopyright: (c) 2010, Frank Kupke\nLicense: LGPL\nLicense-File: LICENSE\nAuthor: Frank Kupke\nMaintainer: frk@informatik.uni-kiel.de\nCabal-Version: >= 1.2.3\nStability: provisional\nSynopsis: A framework for using STM within distributed "
(Fingerprint 17313105789069667153 9610429408495338584)
(Fingerprint 17250946493484671738 17629939328766863497)
(bsReplace "Other modules:" "-- ")
, mk "Name: DSTM\nVersion: 0.1\nCopyright: (c) 2010, Frank Kupke\nLicense: LGPL\nLicense-File: LICENSE\nAuthor: Frank Kupke\nMaintainer: frk@informatik.uni-kiel.de\nCabal-Version: >= 1.2.3\nStability: provisional\nSynopsis: A framework for using STM within distributed sy"
(Fingerprint 10502599650530614586 16424112934471063115)
(Fingerprint 13562014713536696107 17899511905611879358)
(bsReplace "Other modules:" "-- ")
-- http://hackage.haskell.org/package/control-monad-exception-mtl-0.10.3
, mk "name: control-monad-exception-mtl\nversion: 0.10.3\nCabal-Version: >= 1.10\nbuild-type: Simple\nlicense: PublicDomain\nauthor: Pepe Iborra\nmaintainer: pepeiborra@gmail.com\nhomepage: http://pepeiborra.github.com/control-monad-exception\nsynopsis: MTL instances f"
(Fingerprint 18274748422558568404 4043538769550834851)
(Fingerprint 11395257416101232635 4303318131190196308)
(bsReplace " default- extensions:" "unknown-section")
-- http://hackage.haskell.org/package/vacuum-opengl-0.0
-- \DEL character
, mk "Name: vacuum-opengl\nVersion: 0.0\nSynopsis: Visualize live Haskell data structures using vacuum, graphviz and OpenGL.\nDescription: \DELVisualize live Haskell data structures using vacuum, graphviz and OpenGL.\n "
(Fingerprint 5946760521961682577 16933361639326309422)
(Fingerprint 14034745101467101555 14024175957788447824)
(bsRemove "\DEL")
, mk "Name: vacuum-opengl\nVersion: 0.0.1\nSynopsis: Visualize live Haskell data structures using vacuum, graphviz and OpenGL.\nDescription: \DELVisualize live Haskell data structures using vacuum, graphviz and OpenGL.\n "
(Fingerprint 10790950110330119503 1309560249972452700)
(Fingerprint 1565743557025952928 13645502325715033593)
(bsRemove "\DEL")
-- http://hackage.haskell.org/package/ixset-1.0.4
-- {- comments -}
, mk "Name: ixset\nVersion: 1.0.4\nSynopsis: Efficient relational queries on Haskell sets.\nDescription:\n Create and query sets that are indexed by multiple indices.\nLicense: BSD3\nLicense-file: COPYING\nAut"
(Fingerprint 11886092342440414185 4150518943472101551)
(Fingerprint 5731367240051983879 17473925006273577821)
(bsRemoveStarting "{-")
-- : after section
-- http://hackage.haskell.org/package/ds-kanren
, mk "name: ds-kanren\nversion: 0.2.0.0\nsynopsis: A subset of the miniKanren language\ndescription:\n ds-kanren is an implementation of the <http://minikanren.org miniKanren> language.\n .\n == What's in ds-kanren?\n .\n ['dis"
(Fingerprint 2804006762382336875 9677726932108735838)
(Fingerprint 9830506174094917897 12812107316777006473)
(bsReplace "Test-Suite test-unify:" "Test-Suite \"test-unify:\"" . bsReplace "Test-Suite test-list-ops:" "Test-Suite \"test-list-ops:\"")
, mk "name: ds-kanren\nversion: 0.2.0.1\nsynopsis: A subset of the miniKanren language\ndescription:\n ds-kanren is an implementation of the <http://minikanren.org miniKanren> language.\n\nlicense: MIT\nlicense-file: "
(Fingerprint 9130259649220396193 2155671144384738932)
(Fingerprint 1847988234352024240 4597789823227580457)
(bsReplace "Test-Suite test-unify:" "Test-Suite \"test-unify:\"" . bsReplace "Test-Suite test-list-ops:" "Test-Suite \"test-list-ops:\"")
, mk "name: metric\nversion: 0.1.4\nsynopsis: Metric spaces.\nlicense: MIT\nlicense-file: LICENSE\nauthor: Vikram Verma\nmaintainer: me@vikramverma.com\ncategory: Data\nbuild-type:"
(Fingerprint 6150019278861565482 3066802658031228162)
(Fingerprint 9124826020564520548 15629704249829132420)
(bsReplace "test-suite metric-tests:" "test-suite \"metric-tests:\"")
, mk "name: metric\nversion: 0.2.0\nsynopsis: Metric spaces.\nlicense: MIT\nlicense-file: LICENSE\nauthor: Vikram Verma\nmaintainer: me@vikramverma.com\ncategory: Data\nbuild-type:"
(Fingerprint 4639805967994715694 7859317050376284551)
(Fingerprint 5566222290622325231 873197212916959151)
(bsReplace "test-suite metric-tests:" "test-suite \"metric-tests:\"")
, mk "name: phasechange\ncategory: Data\nversion: 0.1\nauthor: G\195\161bor Lehel\nmaintainer: G\195\161bor Lehel <illissius@gmail.com>\nhomepage: http://github.com/glehel/phasechange\ncopyright: Copyright (C) 2012 G\195\161bor Lehel\nlicense: "
(Fingerprint 10546509771395401582 245508422312751943)
(Fingerprint 5169853482576003304 7247091607933993833)
(bsReplace "impl(ghc >= 7.4):" "erroneous-section" . bsReplace "impl(ghc >= 7.6):" "erroneous-section")
, mk "Name: smartword\nSynopsis: Web based flash card for Word Smart I and II vocabularies\nVersion: 0.0.0.5\nHomepage: http://kyagrd.dyndns.org/~kyagrd/project/smartword/\nCategory: Web,Education\nLicense: "
(Fingerprint 7803544783533485151 10807347873998191750)
(Fingerprint 1665635316718752601 16212378357991151549)
(bsReplace "build depends:" "--")
, mk "name: shelltestrunner\n-- sync with README.md, ANNOUNCE:\nversion: 1.3\ncategory: Testing\nsynopsis: A tool for testing command-line programs.\ndescription:\n shelltestrunner is a cross-platform tool for testing command-line\n program"
(Fingerprint 4403237110790078829 15392625961066653722)
(Fingerprint 10218887328390239431 4644205837817510221)
(bsReplace "other modules:" "--")
]
where
mk a b c d = ((a, b), (c, d))

-- | Helper to create entries in patches
_makePatchKey :: FilePath -> (BS.ByteString -> BS.ByteString) -> NoCallStackIO ()
_makePatchKey fp transform = do
contents <- BS.readFile fp
let output = transform contents
let Fingerprint hi lo = md5 contents
let Fingerprint hi' lo' = md5 output
putStrLn
$ showString " , mk "
. shows (BS.take 256 contents)
. showString "\n (Fingerprint "
. shows hi
. showString " "
. shows lo
. showString ")\n (Fingerprint "
. shows hi'
. showString " "
. shows lo'
. showString ")"
$ ""

-------------------------------------------------------------------------------
-- Patch helpers
-------------------------------------------------------------------------------

bsRemove
:: BS.ByteString -- ^ needle
-> BS.ByteString -> BS.ByteString
bsRemove needle haystack = case BS.breakSubstring needle haystack of
(h, t) -> BS.append h (BS.drop (BS.length needle) t)

bsReplace
:: BS.ByteString -- ^ needle
-> BS.ByteString -- ^ replacement
-> BS.ByteString -> BS.ByteString
bsReplace needle repl haystack = case BS.breakSubstring needle haystack of
(h, t)
| not (BS.null t) -> BS.append h (BS.append repl (BS.drop (BS.length needle) t))
| otherwise -> haystack

bsRemoveStarting
:: BS.ByteString -- ^ needle
-> BS.ByteString -> BS.ByteString
bsRemoveStarting needle haystack = case BS.breakSubstring needle haystack of
(h, _) -> h
10 changes: 5 additions & 5 deletions Cabal/Distribution/Parsec/Class.hs
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,7 @@ import Data.Functor.Identity (Identity)
import qualified Distribution.Compat.Parsec as P
import Distribution.Parsec.Types.Common
(PWarnType (..), PWarning (..), Position (..))
import Distribution.Utils.Generic (lowercase)
import qualified Text.Parsec as Parsec
import qualified Text.Parsec.Language as Parsec
import qualified Text.Parsec.Token as Parsec
Expand Down Expand Up @@ -126,12 +127,11 @@ instance Parsec ModuleName where
validModuleChar c = isAlphaNum c || c == '_' || c == '\''

instance Parsec FlagName where
parsec = mkFlagName . map toLower . intercalate "-" <$> P.sepBy1 component (P.char '-')
parsec = mkFlagName . lowercase <$> parsec'
where
-- http://hackage.haskell.org/package/cabal-debian-4.24.8/cabal-debian.cabal
-- has flag with all digit component: pretty-112
component :: P.Stream s Identity Char => P.Parsec s [PWarning] String
component = P.munch1 (\c -> isAlphaNum c || c `elem` "_")
parsec' = (:) <$> lead <*> rest
lead = P.satisfy (\c -> isAlphaNum c || c == '_')
rest = P.munch (\c -> isAlphaNum c || c == '_' || c == '-')

instance Parsec Dependency where
parsec = do
Expand Down
Loading