comp.lang.ada
 help / color / mirror / Atom feed
From: Robert A Duff <bobduff@shell01.TheWorld.com>
Subject: Re: What's it's name again?
Date: Wed, 31 Jul 2002 20:38:42 GMT
Date: 2002-07-31T20:38:42+00:00	[thread overview]
Message-ID: <wccptx31vl9.fsf@shell01.TheWorld.com> (raw)
In-Reply-To: ai8jqt$11ll1d$1@ID-77047.news.dfncis.de

Dmitry A.Kazakov <mailbox@dmitry-kazakov.de> writes:

> > I'm not sure which part you think is hard.  You could put procedure
> > bodies in specs (like in C++) and make inlining easier.
> 
> C++ is awful! All that idiotic rules that inlined function are compiled as 
> if all class declarations were appear before the function body. Then header 
> files of 1K+ lines long ...

I'm not familiar with the details of these rules.  I'm willing to
believe that they are awful.

> I see, but there is also a difference. The body of a subroutine is not a 
> part of its declaration, so you can continue compilation of specifications 
> no matter how the body looks like.

Not if you're trying to inline the code.

>... In contrary to this the size of a type 
> is a function of its declaration. So there might be no difference when some 
> other comilation unit is being compiled, but for a compilation the 
> package's specification I think there is a difference.

I don't see any difference, in principle.  If the compiler doesn't know
the size of the type, it has to generate less efficient code.

> > Here are the solutions that come to mind:
> > 
> > 1. Make the private information part of the spec.  This is what Ada does
> >    for private types -- the compiler can see the full type declaration.
> >    This is also what C++ uses for the inlined-call case: to inline
> >    something, you include the "body" in the "spec" of the class.
> >    (Please correct me if my memory of C++ is hazy.)
> 
> Something like:
> 
> package ... is
>    ...
>    procedure Foo; -- To be inlined (no extra pragma)
>    ...
> private
>    ...
>    procedure Foo is -- Implementation here
>    begin
>       ...
>    end Foo;
>    ...

Yes, something like that.  This is essentially what C++ does for
inlining.

> There is a problem that Foo will see no package body, which might contain 
> some implementation-dependent things it needs.

Everything Foo references must *also* be moved to the spec for this idea
to work.  That's annoying, but it is not in principle different from the
fact that everything a private type refers to must be in the spec:

    type T is private;
    
    ...
    Max: constant := 1234;
    type My_Int is range 1..Max;
    function F return My_Int;
    type T is
        record
            X: My_Int := F(...);

Because Ada requires the full type of T to occur in the spec, it also
implicitly requires Max, My_Int, and F to be declared in the spec.

> > 2. Put the private info in the body.  But let the compiler "peek" into
> >    the body in some cases (pragma Inline present, inlining-enabled
> >    switch turned on, phase of moon is blue, etc).  This is what Ada does
> >    for the inlined-call case.  I would claim Ada *could* do something
> >    similar for the private type case.  (Note that in languages where
> >    "everything's a pointer", you get this kind of (lack of) efficiency.)
> > 
> >    This idea seems nice in that it gives the programmer control over the
> >    compile-time speed vs. run-time speed trade-off.  (By the way, I
> >    claim that computers are many years away from being so fast that this
> >    tradeoff doesn't matter.  Especially since every hardware gain is
> >    offset by more software bloat.)
> 
> Sort of pragma Inline for incomplete types and values (deferred constants)? 

Yeah.

> Do you think it is technically possible?

Yes.  It would cause some pretty slow code without the Inline_Type, but
that's the programmer's choice (compile-time efficiency vs run-time
efficiency).

>... I has not much thought about it, 
> but we must ensure absence of any circular dependencies, which could 
> prevent compiler from calculation of the object size.

Yes.  Ada already has a rule that type T cannot have a [sub]component of
type T (the programmer has to insert a level of indirection).  This rule
would have to be removed, because the compiler doesn't always see the
full type.  This would mean that the *compiler* would be responsible for
inserting the extra level of indirection.  (This is similar to what
happens in Java and other "everything's a pointer" sorts of languages --
in those languages, there is *always* an extra level of indirection.)

Another problem is parameter passing mechanisms.  Ada defines it to be
by-copy for some types, by-reference for some types, and compiler-choice
for some types.  It would be pretty disgusting (from an efficiency point
of view) if this choice had to be made at run time.  But this is an
Ada-specific issue.  I don't like the Ada rules here, and we're talking
about languae design (an Ada-like language that is not Ada), so it's
fair for me to ignore this issue.

> > 3. Define packages as *three* parts: the interface, the
> >    efficiency-critical parts of the implementation, and the
> >    implementation.
> >    The second part is really the "private part" of Ada, but split
> >    out into a separate syntactic unit (probably in a separate file).
> >    In the traditional Ada compiler dependency setup, a change to the
> >    second part would trigger recompilation of all with-ing compilation
> >    units.
> 
> This is attractive, because with tagged types [especially when you need to 
> add some public and some private components] the specifications get too 
> long. It is also good because then one could require that the compiler 
> never ever looks in *.adb. But does not it also suffer the problem of 
> not-seeing *.adb?

No big problem -- as I said above, it just means that everything
referenced in the second part (transitively) has to be declared in the
second part.  Not necessarily their "bodies" (or "full types"), unless
you want *those* inlined, too.  No such thing as a free lunch.  ;-)

> > I claim that any of these 3 possibilities is suitable for the
> > private-type case, and the inline-procedure case, and every other case.
> > I also claim that it would simplify the language to choose one of the
> > above, and use it for all such interface-vs-impl kinds of features.
> > 
> > I lean toward 2, but 3 also has merit.  Number 1, as in Ada private
> > types, has a severe disadvantage: you can't put the full type in a
> > different file from the private type.  It doesn't get a different
> > revision number in the CM system.  And if you have multiple versions
> > (say, for different target hardware), you have to duplicate the visible
> > part.
> 
> What if to allow something like:
> 
> package X
>    ...
> private is separate;
> end X;
> 
> Then there should be X-XX.ads containing a completion of X.

Right.  I think I remember the GNAT folks talking about implementing
something like this.  The idea was that the RM doesn't define the
"source representation" of compilation_units, so there's nothing wrong
with an implementation allowing (or requiring?!) the private part to be
in a different file.  Good idea, but if the language were designed with
that in mind, it would work more smoothly in practise.

The language heavily *implies* that each compilation_unit be represented
as a contiguous piece of text in one file.  For example, the private
part syntax doesn't include the package name at the front.

Also, there's the issue of with_clauses.  It would be nice to attach
with_clauses to the private_part.

- Bob



  reply	other threads:[~2002-07-31 20:38 UTC|newest]

Thread overview: 11+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2002-07-29 23:13 What's it's name again? chris.danx
2002-07-29 23:32 ` Larry Elmore
2002-07-30  0:08   ` chris.danx
2002-07-29 23:47 ` Robert A Duff
2002-07-30  0:50   ` chris.danx
2002-07-30  8:21   ` Dmitry A. Kazakov
2002-07-30 18:53     ` Robert A Duff
2002-08-01  0:11       ` Dmitry A.Kazakov
2002-07-31 20:38         ` Robert A Duff [this message]
2002-08-02  2:21           ` Dmitry A.Kazakov
2002-07-30 18:55   ` Richard Riehle
replies disabled

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox