From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.1.3 (2006-06-01) on yquem.inria.fr X-Spam-Level: * X-Spam-Status: No, score=1.4 required=5.0 tests=AWL,DNS_FROM_RFC_POST autolearn=disabled version=3.1.3 Received: from mail4-relais-sop.national.inria.fr (mail4-relais-sop.national.inria.fr [192.134.164.105]) by yquem.inria.fr (Postfix) with ESMTP id E7B42BC69 for ; Fri, 28 Dec 2007 00:13:37 +0100 (CET) X-IronPort-Anti-Spam-Filtered: true X-IronPort-Anti-Spam-Result: AswMAA7Ac0fUKEUHbGdsb2JhbACBV443CwQGEBmcGg X-IronPort-AV: E=Sophos;i="4.24,213,1196636400"; d="scan'208";a="20737228" Received: from mail.dravanet.hu (HELO arwen.dravanet.hu) ([212.40.69.7]) by mail4-smtp-sop.national.inria.fr with ESMTP; 28 Dec 2007 00:13:37 +0100 Received: from arwen-vbmailshield (localhost.localdomain [127.0.0.1]) by arwen-vbmailshield (Postfix) with SMTP id A31DD8FA for ; Fri, 28 Dec 2007 00:13:36 +0100 (CET) Received: from arwen.dravanet.hu ([127.0.0.1]) by arwen ([192.168.69.23]) with SMTP (gateway) id A07E0995D82; Fri, 28 Dec 2007 00:13:36 +0100 Received: from [127.0.0.1] (unknown [212.40.87.69]) by arwen.dravanet.hu (Postfix) with ESMTP id 6742D8FA for ; Fri, 28 Dec 2007 00:13:36 +0100 (CET) Message-ID: <47743194.1080801@dravanet.hu> Date: Fri, 28 Dec 2007 00:13:24 +0100 From: =?ISO-8859-1?Q?=22M=E1rk_S=2E_Zolt=E1n=22?= User-Agent: Thunderbird 2.0.0.9 (Windows/20071031) MIME-Version: 1.0 To: Caml Mailing List Subject: Re: [Caml-list] Type visibility limitation in recursive modules References: <476E6FB7.6040100@dravanet.hu> <476F9B82.2060103@dravanet.hu> In-Reply-To: <476F9B82.2060103@dravanet.hu> Content-Type: text/plain; charset=ISO-8859-1; format=flowed Content-Transfer-Encoding: 7bit X-Antivirus: avast! (VPS 071215-0, 12/15/2007), Outbound message X-Antivirus-Status: Clean X-VBMailShield: version 1.57.6 at arwen - template: default X-Spam: no; 0.00; recursive:01 parametrized:01 constructors:01 sig:01 struct:01 sig:01 val:01 struct:01 val:01 mylist:01 mylist:01 compiler:01 bug:01 tconstr:01 tvariant:01 The problem only impacts types declared via parametrized type constructors. To wit: This does not work: ---------------------------------------- module rec Aleph : sig type t = Tag of Beth.t end = struct type t = Tag of Beth.t end and Beth : sig type t val v : Aleph.t end = struct type t = Aleph.t list let v = Aleph.Tag([]) end This does: ---------------------------------------- module rec Aleph : sig type t = Tag of Beth.t end = struct type t = Tag of Beth.t end and Beth : sig type t val v : Aleph.t end = struct type t = Nil | Cons of Aleph.t * t let v = Aleph.Tag(Nil) end And this does not: ---------------------------------------- type 'a mylist = Nil | Cons of 'a * 'a mylist module rec Aleph : sig type t = Tag of Beth.t end = struct type t = Tag of Beth.t end and Beth : sig type t val v : Aleph.t end = struct type t = Aleph.t mylist let v = Aleph.Tag(Nil) end I have spent a few (dozen) hours debugging the compiler, and came to the conclusion that the reason for this bug is that "strenghtening" does not take place for Tconstr's. Tconstr types use their type_manifest fields to hold a description of the type, while Tvariant types set it to None. When the typing process of recursive modules reaches the strenghtening phase, it dutifully avoids updating Tconstr's because their type_manifest matches Some _, not None. As a result, Tconstr type implementations cannot be hidden inside a recursive module. This issue has other interesting variations, e.g. this works: ----------------------------------------------- module type AT = sig type t val v : t end module type S = sig module Aleph : AT end module Make = functor(A : AT) -> (struct module Aleph = A end : S with module Aleph = A) module rec Al : AT = struct type t = string let v = "v" end and Ex : S with module Aleph = Al = Make(Al) This doesn't: ----------------------------------------------- module type AT = sig type t val v : t end module type S = sig module Aleph : AT end module Make = functor(A : AT) -> (struct module Aleph = A end : S with module Aleph = A) module rec Al : sig type t val v : t end (* NB: AT!!! *) = struct type t = string let v = "v" end and Ex : S with module Aleph = Al = Make(Al) ----------------------------------------------------- File "Anomaly.ml", line 34, characters 9-33: In this `with' constraint, the new definition of Aleph does not match its original definition in the constrained signature: Modules do not match: sig type t = Al.t end is not included in AT The field `v' is required but not provided ---------------------------------------------------- Cheers Z-