[Date Prev][Date Next][Thread Prev][Thread Next][Author Index][Date Index][Thread Index]

Smalltalk to C++ translator



I've been intending to write an explanation of our tools,
for people that don't see them everyday.  This isn't that explanation.  
This is a small example of translated smalltalk, to give you some flavor 
of how things work with the translator.

The translator generates the C++ code and the related declarations,
putting the C++ code in .cxx files and the declarations in .hxx
files.  It also does automatic generation of include file dependencies.

The translator is written in ParcPlace Smalltalk, the type 
information is hidden in {} which Smalltalk has been modified to
ignore.

I'm including a sample with a little commentary, this
has been selected randomly, more or less:

{XuRegion} regionAt: index {IntegerVar}
        | axis {Orientation} start {IntegerVar} stop {IntegerVar} |
        (boundaries domain hasMember.IntegerVar: index) not
                ifTrue: [^(XuRectangle create:  0 with: 0 with: 0 with: 0 )].
        axis _ styleInternal axis.
        start _ ((boundaries get.IntegerVar: index) cast: XuInteger) asIntegerVar.
        stop _  ((boundaries get.IntegerVar: index + 1) cast: XuInteger) asIntegerVar - styleInternal spacing.
        ^XuRectangle create: (axis orient: (XuPoint create: start with: -10000))                with: (axis orient: (XuPoint create: stop  with: 10000))!

turns into

SPTR(XuRegion) BoundingListComp::regionAt (IntegerVar index){
        SPTR(XuRegion)  returnValue;
        SPTR(Orientation) axis;
        IntegerVar start;
        IntegerVar stop;

        if (!boundaries->domain()->hasMember(index)) {
                returnValue = new XuRectangle(0, 0, 0, 0);
                return returnValue;
        }
        axis = styleInternal->axis();
        start = CAST(XuInteger,boundaries->get(index))->asIntegerVar();
        stop = CAST(XuInteger,boundaries->get(index + 1))->asIntegerVar() - styleInternal->spacing();
        returnValue = new XuRectangle(axis->orient(new XuPoint(start, -10000)),
axis->orient(new XuPoint(stop, 10000)));
        return returnValue;
}

The Smalltalk version is in Smalltalk fileout format, the "_"
displays in Smalltalk as a leftpointinting arrow for that
looks like a one character version of <-  it means assignment.
Note how simple assignment and message send look almost the same in
both languages,
axis <- styleInternal axis.
axis =  styleInternal->axis();

Of course this all required some thinking about how to use C++
initially, but the style of C++ that we chose made the translator
very natural.  For example all classes are passed by pointer
rather than value or reference (a screwy thing in C++ that
can cause lots of confusion).  All methods except possibly leaf 
methods are virtual.  

There's lots more, but we haven't written down the explanation yet.
Mostly it boils down to, we're writing in the intersection of the two
languages, and though C++ is bigger than it should be, there are a few
things that Smalltalk has that C++ doesn't:

1) block & continuation passing
	We restrict ourselves to certain special cases that we
	have constructed classes for.  This improves our coding 
	style anyway, so it is an improvement.  
2) unrestricted polymorphism
	So we restrict our polymorphism, this is no big deal.  It just
	requires some care and design, a good thing anyway.

Things that C++ can do that most people don't believe it can or are confused about.
These are the things that we have implemented, so we know they work.

1) exception handling with unwind protect.
	implemented with macros & cleverness.
2) garbage collection, real industrial strength garbage collection
	some people already knew you could do this, decwrl has done
	some kind of gc , but I'm still waiting for them to send
	their Tech Report on it.
3) passing objects through RPC
	We do it, from machine generated protocol modules.


Stay tuned for more "Excerpts from unwritten documentation"