[m-dev.] For review: Using MR_TypeCtorInfo for generated type_ctor_infos

Fergus Henderson fjh at cs.mu.OZ.AU
Fri Aug 6 20:11:14 AEST 1999


On 06-Aug-1999, Warwick Harvey <wharvey at cs.monash.edu.au> wrote:
> Fergus wrote:
> > On 05-Aug-1999, Warwick Harvey <wharvey at cs.monash.edu.au> wrote:
> > > Fergus wrote:
> > > > Changing just the hand-defined ones might still lead to problems,
> > > > because the compiler creates compiler-generated declarations for
> > > > uses of the hand-defined ones, and these declarations might conflict
> > > > with the hand-defined definitions.
> > > 
> > > Yes, it does and they do (which is why I changed the compiler-generated 
> > > declarations), but I found a solution to that: #define the 
> > > compiler-generated type to `MR_TypeCtorInfo_struct' for any hand-defined 
> > > type_ctor_infos.
> > 
> > Is that sufficient?  Won't that lead to conflicting definitions for
> > `struct MR_TypeCtorInfo_struct'?  I think the compiler-generated
> > declarations of the hand-defined type_ctor_infos will contain
> > compiler-generated _definitions_ of their types, and I think these
> > definitions will conflict with the hand-defined definition of that struct.
> 
> I think we're just not understanding each other, due to far too many 
> independent things which may or may not be compiler generated, and which 
> have declarations and definitions...  :-)  The entities we seem to be 
> dealing with here are:  the name of the type_ctor_info object, the 
> initialised contents of the type_ctor_info object, the name of the type used 
> for the type_ctor_info object, and the contents of that type.
> 
> In hand-generated type_ctor_infos, the user provides the initialised 
> contents of the type_ctor_info object.  Currently the user also provides the 
> contents of the type used, but we want to change that to use the 
> MR_TypeCtorInfo type instead.  The compiler thinks it knows the name of the 
> type to use, and uses this name to generate declarations for the object, but 
> it does *not* generate the contents of the type.

OK, I thought the compiler might generate the contents of the type.
But looking at the code more closely I see that it only does that
for stuff defined in the module.

> > The invariants in question are these:
> > (1) the compiler should know the type of every field that it initializes
> > (2) the compiler should know the type of every expression that it generates
> 
> > Previously, the compiler assumed that the arguments of a type_ctor_info
> > struct were all `Word'; this is indicated by the `uniform(no)' in the
> > following code

As Zoltan pointed out, I was mistaken about that.
`uniform(no)' means that the type is determined by the arguments.

> Perhaps one of the reasons I had trouble seeing "the right way" to fix the 
> problem is that I don't think the above statement has been true for at least 
> 12 months.  If I remember correctly, ever since I first encountered a 
> base_type_info (as they were then called), they have contained fields of 
> type `Integer' and `Word *'.  I was surprised that the "uniform" code was 
> being used, but figured I just did not understand what "uniform" meant.  It 
> seemed to be extracting the type from the actual argument, and the actual 
> argument was a string constant... which was being treated as a `Word *' 
> rather than a `String'.  So the problem seemed to me not so much that I'd 
> changed the type of the field, but that the compiler seemed to be calling an 
> apple a pear...  So I tried to disabuse it by telling it that string 
> constants should be of type `String' rather than `Word *'.

OK, that sounds reasonable.
If you do that, then you will indeed preserve invariant (1).

> > This is what caused the compiler warnings.
> > Your proposed fix to insert a cast in the generated code for `string_consts'
> > without changing llds_const_type/2 accordingly breaks (2).
> 
> But the mail you replied to *does* change llds_const_type.  As I discovered 
> later, without it I do get a different set of warnings, as then (2) would 
> indeed be broken, as you say.

Yes, if you change llds_const_type, then you can preserve (2).

> > I think a fix which maintained invariants (1) and (2) would be better
> > than your proposed change.
> 
> I actually happen to think that my change (with just one tweak - changing 
> `string_const()' to cast to `String' rather than `Word *' so the other casts 
> to `String' are not longer necessary) does *not* violate either of these 
> invariants.

You are correct.

> Of course there's still the following question: is there a particular reason 
> why string constants should be of type `Word *' rather than `String'?

No, the reasons for them having type `Word *' are historical.

Originally, we used the very simple invariant that everything had type `Word'.
The string_const() macro included a cast to Word to preserve this invariant.

Then, we found that using just `Word' didn't work, because ANSI C says that
casting from a pointer to an integer in a static initializer is
undefined behaviour.  So we changed things.  But we made the minimal
change: rather than adding a whole lot of new pointer types, the only
new types we added were `data_ptr' (Word *) and `code_ptr' (Code *).
Thus strings had to have type `data_ptr' (Word *).

It was only quite recently (April 99) that Zoltan added `string'
as a new alternative in the `llds_type' type.

-- 
Fergus Henderson <fjh at cs.mu.oz.au>  |  "I have always known that the pursuit
WWW: <http://www.cs.mu.oz.au/~fjh>  |  of excellence is a lethal habit"
PGP: finger fjh at 128.250.37.3        |     -- the last words of T. S. Garp.
--------------------------------------------------------------------------
mercury-developers mailing list
Post messages to:       mercury-developers at cs.mu.oz.au
Administrative Queries: owner-mercury-developers at cs.mu.oz.au
Subscriptions:          mercury-developers-request at cs.mu.oz.au
--------------------------------------------------------------------------



More information about the developers mailing list