enable -Wunused-matches (#6423)

changelog_begin
changelog_end
This commit is contained in:
Shayne Fletcher 2020-06-19 15:35:10 -04:00 committed by GitHub
parent b10bfa1ba7
commit cec2693dc7
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
24 changed files with 112 additions and 73 deletions

View File

@ -12,7 +12,7 @@ jobs:
variables:
ghc-lib-sha: 'd2eadb7ef4a6d4f33a6a04056d2e57f11a59ef0f'
base-sha: '9c787d4d24f2b515934c8503ee2bbd7cfac4da20'
patches: 'd1e1a671bb0e653106c5bce23bfd0f4e1660c503 833ca63be2ab14871874ccb6974921e8952802e9'
patches: '0d86e4898d6ed03e23f3975e3043021687dd7e80 833ca63be2ab14871874ccb6974921e8952802e9'
flavor: 'ghc-8.8.1'
steps:
- checkout: self

View File

@ -663,6 +663,10 @@
# Not popular or useful
- ignore: {name: Use camelCase}
# Interacts badly with desugaring and the hack for
# -Wunused-matches. Also, it's generally considered by Neil to be
# dodgy.
- ignore: {name: Reduce duplication}
# Not relevant to DAML
- ignore: {name: Use newtype instead of data}
# Don't warn on redundant parens or $

View File

@ -82,7 +82,7 @@ showList__ _ [] s = "[]" ++ s
showList__ showx (x::xs) s = "[" ++ showx x (showl showx xs s)
showl : (a -> ShowS) -> [a] -> ShowS
showl showx [] s = "]" ++ s
showl _ [] s = "]" ++ s
showl showx (y::ys) s = "," ++ showx y (showl showx ys s)

View File

@ -124,7 +124,7 @@ identity x = x
instance Functor ((,) a) where
fmap f (x, y) = (x, f y)
v <$ (x, y) = (x, v)
v <$ (x, _) = (x, v)
instance Functor [] where
fmap = map
@ -172,7 +172,7 @@ foldl = primitive @"BEFoldl"
-- predicate `p` is true. There might not be such an element, which
-- is why this function returns an `Optional a`.
find : (a -> Bool) -> [a] -> Optional a
find p [] = None
find _ [] = None
find p (x::xs) = if p x then Some x else find p xs
-- | Gives the length of the list.
@ -294,17 +294,17 @@ optional _ f (Some x) = f x
instance Functor (Either e) where
fmap f (Left e) = Left e
fmap _ (Left e) = Left e
fmap f (Right a) = Right (f a)
instance Applicative (Either e) where
pure = Right
Left e <*> a = Left e
Left e <*> _ = Left e
Right f <*> a = fmap f a
instance Action (Either e) where
Left e >>= f = Left e
Left e >>= _ = Left e
Right a >>= f = f a
instance ActionFail (Either Text) where
@ -329,8 +329,8 @@ instance ActionFail (Either Text) where
-- ```
--
either : (a -> c) -> (b -> c) -> Either a b -> c
either f g (Left x) = f x
either f g (Right x) = g x
either f _ (Left x) = f x
either _ g (Right x) = g x
infixr 6 <>
-- | The class of semigroups (types with an associative binary operation).

View File

@ -230,7 +230,7 @@ replace : Eq a => [a] -> [a] -> [a] -> [a]
replace [] _ xs = xs
replace from to xs | Some xs <- stripPrefix from xs = to ++ replace from to xs
replace from to (x :: xs) = x :: replace from to xs
replace from to [] = []
replace _ _ [] = []
-- | Drops the given prefix from a list. It returns the original
-- sequence if the sequence doesn't start with the given prefix.
@ -269,7 +269,7 @@ stripSuffix a b = reverse <$> stripPrefix (reverse a) (reverse b)
stripInfix : Eq a => [a] -> [a] -> Optional ([a], [a])
stripInfix a b
| Some rest <- stripPrefix a b = Some ([], rest)
stripInfix a [] = None
stripInfix _ [] = None
stripInfix a (b::bs) = first (b::) <$> stripInfix a bs
-- | The `isPrefixOf` function takes two lists and returns `True` if
@ -354,7 +354,7 @@ breakEnd f = swap . both reverse . break f . reverse
-- *without* the match, use `stripInfix`.
breakOn : Eq a => [a] -> [a] -> ([a], [a])
breakOn needle haystack | needle `isPrefixOf` haystack = ([], haystack)
breakOn needle [] = ([], [])
breakOn _ [] = ([], [])
breakOn needle (x::xs) = first (x::) $ breakOn needle xs
-- | Similar to `breakOn`, but searches from the end of the
@ -406,7 +406,7 @@ last [] = error "last: empty list"
-- | Return all the elements of a list except the last one. The list
-- must be non-empty.
init : [a] -> [a]
init [x] = []
init [_] = []
init (x :: xs) = x :: init xs
init [] = error "init: empty list"

View File

@ -28,7 +28,7 @@ last : ActionFail m => [a] -> m a
last = foldl1 (flip const)
init : ActionFail m => [a] -> m [a]
init [x] = pure []
init [_] = pure []
init (x::xs) = do i <- init xs; pure (x :: i)
init [] = fail "init: empty list"

View File

@ -90,7 +90,7 @@ toNNF f = f
-- (see https://en.wikipedia.org/wiki/Disjunctive_normal_form).
toDNF : Formula t -> Formula t
toDNF f = case f of
f@(Proposition p) -> Disjunction [Conjunction [f]]
f@(Proposition _) -> Disjunction [Conjunction [f]]
Disjunction ds -> Disjunction $ concatMap (disjuncts . toDNF) ds
Conjunction cs -> Disjunction $ map Conjunction regroupedcs
where

View File

@ -39,15 +39,15 @@ dupe x = (x,x)
-- | Extract the 'fst' of a triple.
fst3 : (a,b,c) -> a
fst3 (a,b,c) = a
fst3 (a,_,_) = a
-- | Extract the 'snd' of a triple.
snd3 : (a,b,c) -> b
snd3 (a,b,c) = b
snd3 (_,b,_) = b
-- | Extract the final element of a triple.
thd3 : (a,b,c) -> c
thd3 (a,b,c) = c
thd3 (_,_,c) = c
-- | Converts an uncurried function to a curried function.
curry3 : ((a, b, c) -> d) -> a -> b -> c -> d

View File

@ -80,7 +80,7 @@ template DvpAllocated
assert $ bond.issuer == c.bondIssuer
assert $ bond.isin == c.bondIsin
assert $ bond.owner == c.seller
alloc <- create DvpAllocated with c; cashCid
_ <- create DvpAllocated with c; cashCid
bondCid <- exercise bondCid Bond.Transfer with newOwner = c.buyer
bondCid <- exercise bondCid Bond.Accept
@ -102,7 +102,7 @@ data SettleResult = SettleResult
notificationCid : DvpNotificationId
main = scenario do
now <- passToDate $ date 2018 May 14
_ <- passToDate $ date 2018 May 14
--2018-05-14T00:00Z
acmeBank <- getParty "AcmeBank"

View File

@ -58,8 +58,6 @@ template Helper
do
time <- getTime
someDate <- pure $ date 2018 May 14
let settleDvp (dvpAllocatedCid: DvpAllocatedId) (prev: HandleBondResult) = do
dvpAllocated <- fetch dvpAllocatedCid
assertMsg "settlement time is in the future" $ dvpAllocated.c.settleTime <= time
@ -77,7 +75,7 @@ main = scenario do
alice <- getParty "Alice"
bob <- getParty "Bob"
now <- passToDate $ date 2018 May 14
_ <- passToDate $ date 2018 May 14
cashAlice1Cid <- submit acmeBank do
create CashTransferRequest with

View File

@ -30,7 +30,6 @@ template T2
do pure ()
main = scenario do
p <- getParty "alice"
let c1 = C1
let c1' = C1'
let c2 = C2

View File

@ -12,6 +12,6 @@ template Foo
aScenario = scenario do
alice <- getParty "Alice"
bob <- getParty "Bob"
bobFooId <- submit bob do create Foo with p = bob
_ <- submit bob do create Foo with p = bob
_ <- submit alice $ fetchByKey @Foo bob
pure ()

View File

@ -1,6 +1,6 @@
-- Copyright (c) 2020 Digital Asset (Switzerland) GmbH and/or its affiliates. All rights reserved.
-- SPDX-License-Identifier: Apache-2.0
-- @ERROR range=11:23-11:33; Generic templates are no longer supported
-- @ERROR range=11:23-11:33; Generic templates are not supported
module GenericTemplateError where

View File

@ -140,7 +140,7 @@ main = scenario do
-- some things are broken because we have had to hack signatories
-- scheduled fix in DAML-LF for next week
let broken x = return ()
let broken _ = return ()
-- Alice can't create IOUs that are backed by Acme Bank.
broken $ submitMustFail alice do

View File

@ -122,7 +122,7 @@ testDedupSortBy = scenario do
testMergeBy = scenario do
[1, 3, 5, 2, 4, 6] === mergeBy (const $ const EQ) [1, 3, 5] [2, 4, 6]
[1, 2, 3, 4, 5, 6] === mergeBy compare [1, 3, 5] [2, 4, 6]
[5, 1, 3, 6, 7] === mergeBy (\x y -> compare (x % 5) (x % 5)) [5, 1, 3] [6, 7]
[5, 1, 3, 6, 7] === mergeBy (\x _ -> compare (x % 5) (x % 5)) [5, 1, 3] [6, 7]
testCombinePairs = scenario do
[] === combinePairs (+) ([] : [Int])

View File

@ -59,8 +59,8 @@ testMerge = scenario do
let m1 = fromList [(1, "bb"), (2, "dd"), (3, "aa"), (4, "cc"), (6, "ee")]
let m2 = fromList [(1, "a"), (2, "c"), (3, "b"), (5, "d"), (0, "e")]
[] === toList (merge (\k v -> Some v) (\k v -> Some v) (\k v w -> Some v) M.empty (M.empty : Map Int Text))
[] === toList (merge (\k v -> Some v) (\k v -> Some v) (\k v w -> None) m1 m1)
[(1, "bb"), (3, "aa")] === toList (merge (\k v -> if v <= "bb" then Some v else None) (\k v -> Some v) (\k v w -> None) m1 M.empty)
[(1, "a"), (3, "b")] === toList (merge (\k v -> Some v) (\k v -> if v <= "bb" then Some v else None) (\k v w -> None) M.empty m2)
[(1,"bb"), (2,"dd"), (3,"aa")] === toList (merge (\k v -> None) (\k v -> None) (\k v w -> Some v) m1 m2)
[] === toList (merge (\_ v -> Some v) (\_ v -> Some v) (\_ v _ -> Some v) M.empty (M.empty : Map Int Text))
[] === toList (merge (\_ v -> Some v) (\_ v -> Some v) (\_ _ _ -> None) m1 m1)
[(1, "bb"), (3, "aa")] === toList (merge (\_ v -> if v <= "bb" then Some v else None) (\_ v -> Some v) (\_ _ _ -> None) m1 M.empty)
[(1, "a"), (3, "b")] === toList (merge (\_ v -> Some v) (\_ v -> if v <= "bb" then Some v else None) (\_ _ _ -> None) M.empty m2)
[(1,"bb"), (2,"dd"), (3,"aa")] === toList (merge (\_ _ -> None) (\_ _ -> None) (\_ v _ -> Some v) m1 m2)

View File

@ -59,8 +59,8 @@ testMerge = scenario do
let m1 = fromList [(3, "aa"), (1, "bb"), (4, "cc"), (2, "dd"), (6, "ee")]
let m2 = fromList [(1, "a"), (3, "b"), (2, "c"), (5, "d"), (0, "e")]
[] === toList (merge (\k v -> Some v) (\k v -> Some v) (\k v w -> Some v) M.empty (M.empty : Map Int Text))
[] === toList (merge (\k v -> Some v) (\k v -> Some v) (\k v w -> None) m1 m1)
[(1, "bb"), (3, "aa")] === toList (merge (\k v -> if v <= "bb" then Some v else None) (\k v -> Some v) (\k v w -> None) m1 M.empty)
[(1, "a"), (3, "b")] === toList (merge (\k v -> Some v) (\k v -> if v <= "bb" then Some v else None) (\k v w -> None) M.empty m2)
[(1,"bb"), (2,"dd"), (3,"aa")] === toList (merge (\k v -> None) (\k v -> None) (\k v w -> Some v) m1 m2)
[] === toList (merge (\_ v -> Some v) (\_ v -> Some v) (\_ v _ -> Some v) M.empty (M.empty : Map Int Text))
[] === toList (merge (\_ v -> Some v) (\_ v -> Some v) (\_ _ _ -> None) m1 m1)
[(1, "bb"), (3, "aa")] === toList (merge (\_ v -> if v <= "bb" then Some v else None) (\_ v -> Some v) (\_ _ _ -> None) m1 M.empty)
[(1, "a"), (3, "b")] === toList (merge (\_ v -> Some v) (\_ v -> if v <= "bb" then Some v else None) (\_ _ _ -> None) M.empty m2)
[(1,"bb"), (2,"dd"), (3,"aa")] === toList (merge (\_ _ -> None) (\_ _ -> None) (\_ v _ -> Some v) m1 m2)

View File

@ -7,7 +7,7 @@
module Otherwise where
warning : Bool -> [a] -> [a]
warning b [] = []
warning _ [] = []
warning b (x :: xs')
| b = warning b xs'
| otherwise = x :: xs'

View File

@ -15,7 +15,7 @@ main = scenario do
rs <- minstd_initFromTime
(rs, s1) <- pure $ d6 rs
(rs, s2) <- pure $ d6 rs
(rs, s3) <- pure $ d6 rs
(_, s3) <- pure $ d6 rs
let s = s1 + s2 + s3
assert $ s >= 3 && s <= 18

View File

@ -70,8 +70,8 @@ testMerge = scenario do
let m1 = fromList [("C", "aa"), ("A", "bb"), ("D", "cc"), ("B", "dd"), ("F", "ee")]
let m2 = fromList [("A", "a"), ("C", "b"), ("B", "c"), ("E", "d"), ("", "e")]
[] === toList (merge (\k v -> Some v) (\k v -> Some v) (\k v w -> Some v) empty (empty : TextMap Text))
[] === toList (merge (\k v -> Some v) (\k v -> Some v) (\k v w -> None) m1 m1)
[("A", "bb"), ("C", "aa")] === toList (merge (\k v -> if v <= "bb" then Some v else None) (\k v -> Some v) (\k v w -> None) m1 empty)
[("A", "a"), ("C", "b")] === toList (merge (\k v -> Some v) (\k v -> if v <= "bb" then Some v else None) (\k v w -> None) empty m2)
[("A","bb"), ("B","dd"), ("C","aa")] === toList (merge (\k v -> None) (\k v -> None) (\k v w -> Some v) m1 m2)
[] === toList (merge (\_ v -> Some v) (\_ v -> Some v) (\_ v _ -> Some v) empty (empty : TextMap Text))
[] === toList (merge (\_ v -> Some v) (\_ v -> Some v) (\_ _ _ -> None) m1 m1)
[("A", "bb"), ("C", "aa")] === toList (merge (\_ v -> if v <= "bb" then Some v else None) (\_ v -> Some v) (\_ _ _ -> None) m1 empty)
[("A", "a"), ("C", "b")] === toList (merge (\_ v -> Some v) (\_ v -> if v <= "bb" then Some v else None) (\_ _ _ -> None) empty m2)
[("A","bb"), ("B","dd"), ("C","aa")] === toList (merge (\_ _ -> None) (\_ _ -> None) (\_ v _ -> Some v) m1 m2)

View File

@ -9,4 +9,4 @@ baz : (a1 -> a2) -> (b1 -> b2) -> (b1 -> b2)
baz f g = bar f g
bar : (b1 -> b2) -> (a1 -> a2) -> (a1 -> a2)
bar f g = g
bar _ g = g

View File

@ -0,0 +1,36 @@
-- Copyright (c) 2020, Digital Asset (Switzerland) GmbH and/or its
-- affiliates. All rights reserved.
-- @WARN range=12:2-12:3; Defined but not used
{-# OPTIONS_GHC -Wunused-matches #-}
module UnusedMatchTests where
-- It should be OK to enable -Wunused-matches and not get warnings
-- from template desugared code.
f x = 12 -- Defined but not used 'x'; prove unsed match detection.
template T
with
p : Party
q : Party
where
-- Include interaction with local binds.
let revokeRetVal = ()
(sig, obs) = (p, q)
assertion = True
plainEnglish = "Chop wood, carry water."
ident = "123"
-- None of the below should generate defined but not used
-- warnings.
signatory sig
observer obs
ensure assertion
agreement plainEnglish
key (sig, ident): (Party, Text)
maintainer key._1
choice Revoke: () with
controller p
do
pure revokeRetVal

View File

@ -299,29 +299,31 @@ dlintSmokeTests mbScenarioService = Tasty.testGroup "Dlint smoke tests"
setFilesOfInterest [foo]
expectNoErrors
expectDiagnostic DsInfo (foo, 2, 0) "Warning: Use fewer imports"
, testCase' "Reduce duplication" $ do
foo <- makeFile "Foo.daml" $ T.unlines
[ "daml 1.2"
, "module Foo where"
, "import DA.List"
, "testSort5 = scenario do"
, " let l = [ (2, const \"D\"), (1, const \"A\"), (1, const \"B\"), (3, const \"E\"), (1, const \"C\") ]"
, " m = sortOn fst l"
, " n = map fst m"
, " assert $ n == [1, 1, 1, 2, 3]"
, " let o = map (flip snd ()) m"
, " assert $ o == [\"A\", \"B\", \"C\", \"D\", \"E\"]"
, "testSort4 = scenario do"
, " let l = [ (2, const \"D\"), (1, const \"A\"), (1, const \"B\"), (3, const \"E\"), (1, const \"C\") ]"
, " m = sortBy (\\x y -> compare (fst x) (fst y)) l"
, " n = map fst m"
, " assert $ n == [1, 1, 1, 2, 3]"
, " let o = map (flip snd ()) m"
, " assert $ o == [\"A\", \"B\", \"C\", \"D\", \"E\"]"
]
setFilesOfInterest [foo]
expectNoErrors
expectDiagnostic DsInfo (foo, 7, 4) "Suggestion: Reduce duplication"
-- This hint is now disabled. See PR
-- https://github.com/digital-asset/daml/pull/6423 for details.
-- , testCase' "Reduce duplication" $ do
-- foo <- makeFile "Foo.daml" $ T.unlines
-- [ "daml 1.2"
-- , "module Foo where"
-- , "import DA.List"
-- , "testSort5 = scenario do"
-- , " let l = [ (2, const \"D\"), (1, const \"A\"), (1, const \"B\"), (3, const \"E\"), (1, const \"C\") ]"
-- , " m = sortOn fst l"
-- , " n = map fst m"
-- , " assert $ n == [1, 1, 1, 2, 3]"
-- , " let o = map (flip snd ()) m"
-- , " assert $ o == [\"A\", \"B\", \"C\", \"D\", \"E\"]"
-- , "testSort4 = scenario do"
-- , " let l = [ (2, const \"D\"), (1, const \"A\"), (1, const \"B\"), (3, const \"E\"), (1, const \"C\") ]"
-- , " m = sortBy (\\x y -> compare (fst x) (fst y)) l"
-- , " n = map fst m"
-- , " assert $ n == [1, 1, 1, 2, 3]"
-- , " let o = map (flip snd ()) m"
-- , " assert $ o == [\"A\", \"B\", \"C\", \"D\", \"E\"]"
-- ]
-- setFilesOfInterest [foo]
-- expectNoErrors
-- expectDiagnostic DsInfo (foo, 7, 4) "Suggestion: Reduce duplication"
, testCase' "Use language pragmas" $ do
foo <- makeFile "Foo.daml" $ T.unlines
[ "{-# OPTIONS_GHC -XDataKinds #-}"

View File

@ -3,10 +3,10 @@
resolver: lts-14.1
packages:
- archive: https://daml-binaries.da-ext.net/da-ghc-lib/ghc-lib-942755169bad510701179c8c40cddd3e.tar.gz
sha256: "367f779d564e01a98fe7e9c7f1d7c1a7936759aae9c273eb2dfc6f1ed1c51d07"
- archive: https://daml-binaries.da-ext.net/da-ghc-lib/ghc-lib-parser-942755169bad510701179c8c40cddd3e.tar.gz
sha256: "bf17b50a11369b67237e6e0e22589f7ead7b482d05e0e3c68654c9be5b3d3fac"
- archive: https://daml-binaries.da-ext.net/da-ghc-lib/ghc-lib-c26c76b98d45925456d37ac9bcee1a5c.tar.gz
sha256: "ae2d34fdddc33febafae1fb1027648c371b4b18e0fe7b1318d675411c2dd8880"
- archive: https://daml-binaries.da-ext.net/da-ghc-lib/ghc-lib-parser-c26c76b98d45925456d37ac9bcee1a5c.tar.gz
sha256: "3c4b87bad98f2174ca3a6ac920d29597d6504f639160278505a7aff7441ce1cf"
- github: digital-asset/hlint
commit: "3e78bce69749b22a80fec1e8eb853cc0c100c18e"
sha256: "cf39f2b378485afc77ffdad4dbb057d5d9b4dfc5a38c76ddc44e920e537fb0fa"