[commit: testsuite] master: Add a test for #6117 (66f65ac)

Ian Lynagh <[email protected]>
Newsgroups gmane.comp.lang.haskell.cvs.ghc
Message-ID <[email protected]>
Repository : ssh://darcs.haskell.org//srv/darcs/testsuite

On branch  : master

http://hackage.haskell.org/trac/ghc/changeset/66f65ac9da2c0626a40d67515be07db9febb3628

>---------------------------------------------------------------

commit 66f65ac9da2c0626a40d67515be07db9febb3628
Author: Ian Lynagh <[email protected]>
Date:   Thu Oct 11 20:57:10 2012 +0100

    Add a test for #6117

>---------------------------------------------------------------

 tests/typecheck/should_run/T6117.hs |   53 +++++++++++++++++++++++++++++++++++
 tests/typecheck/should_run/all.T    |    1 +
 2 files changed, 54 insertions(+), 0 deletions(-)

diff --git a/tests/typecheck/should_run/T6117.hs b/tests/typecheck/should_run/T6117.hs
new file mode 100644
index 0000000..2fe9f29
--- /dev/null
+++ b/tests/typecheck/should_run/T6117.hs
@@ -0,0 +1,53 @@
+{-# LANGUAGE FlexibleContexts #-}
+
+{-
+[Summary of the program] Ring is defined as a subclass of Semigroup,
+inheriting multiplication.  Additive is a wrapper that extracts the additive
+structure of Ring and reifies it as Semigroup.  For simplicity, the code omits
+ring operations (+ and *) and defines only the additive and multiplicative
+identities.
+
+[The bug] If there is a cyclic class hierarchy like
+
+    class B a => Semigroup a                  where ...
+    class Semigroup (Additive a) => Ring a    where ...
+    instance Ring a => Semigroup (Additive a) where ...
+
+then uses of B's methods on (Additive a) in the method implementations of the
+third declaration "instance Ring a => Semigroup (Additive a)" will:
+
+    1. be accepted by the compiler even in cases where B (Additive a) is not
+       derivable.
+    2. result in <<loop>>.
+ -}
+
+class B a where
+    b :: a
+class B a => Semigroup a where
+    unit :: a
+class (Semigroup a, Semigroup (Additive a)) => Ring a where
+    zero :: a
+newtype Additive a = Additive a
+
+-- The source compiles whether with or without this instance declaration in GHC
+-- 7.2.1 - 7.4.1 and produces <<loop>>.
+--
+-- GHC 7.0.4 rejects this source without this declaration and produces
+-- terminating code with the declaration.
+instance B a => B (Additive a) where
+   b = Additive b
+
+instance Ring a => Semigroup (Additive a) where
+    unit = b -- Use a method of type (B a => ...) with a instantiated as
+             -- (Additive a).  This causes <<loop>>.
+
+
+-- Now try to instantiate Ring and evaluate `unit'.
+instance B Int where
+    b = 1234567890
+instance Semigroup Int where
+    unit = 1
+instance Ring Int where
+    zero = 0
+main = case (unit :: Additive Int) of -- Force the additive identity of Int.
+         Additive x -> print x
diff --git a/tests/typecheck/should_run/all.T b/tests/typecheck/should_run/all.T
index 2f236d8..709bb32 100755
--- a/tests/typecheck/should_run/all.T
+++ b/tests/typecheck/should_run/all.T
@@ -96,3 +96,4 @@ test('T5573a', compose(omit_ways(['ghci']),only_compiler_types(['ghc'])), compil
 test('T5573b', compose(omit_ways(['ghci']),only_compiler_types(['ghc'])), compile_and_run, [''])
 test('T7023', normal, compile_and_run, [''])
 test('T7126', normal, compile_and_run, [''])
+test('T6117', expect_broken(6117), compile_and_run, [''])
lmpx.com only provides a reader for public news (NNTP) servers. It is not affiliated with the servers or forums shown here and is not responsible for the content of articles, which is written by their respective authors.