For Programmers: Free Programming Magazines  


Home > Archive > Compilers > October 2006 > Translating OO program to procedural program









You are viewing an archived Text-only version of the thread. To view this thread in it's original format and/or if you want to reply to this thread please [click here]

 

Author Translating OO program to procedural program
moop

2006-10-12, 7:11 pm

Hi,

I am working on a project translates OO programs to procedural
programs, such as translating C++ to C and the like. I hope this
effort can be spreaded out to other langs, so I am working on to
abstract the common issues of doing so. I know there is a pinoneer
attempt is C Front which produce C++ programs via a C compiler, I want
to have a look on that, but still cannot find it now, anyone can
suggest this to me?

My approach is just to rename the methods with the instance name so
that they can be placed in a single source file and then be compiled
later by the procedural lang compiler. For instance,

class A{
B b;
void method(){
b.run();
}
}

class B{
void run(){
....
}
}

If the main rountine is
void main(){
A a = new A();
a.method();
}

then the program would be translated to
void a_method(){
a_b_run();
}

void a_b_run(){
....
}
But I feel it is really not an adaptable way when dealing with
declaration inside iterations whose number of iteration is not sure,
means that we cannot change the names of the reference inside the
iteration.
for(...){
A a = new A();
}
So far I am a little bit frustrated on this approach, anyone has
better idea? Pls share your thoughts, thank you!
Pascal Bourguignon

2006-10-12, 7:11 pm

"moop." <samhng@gmail.com> writes:

> I am working on a project translates OO programs to procedural
> programs, such as translating C++ to C and the like. I hope this
> effort can be spreaded out to other langs, so I am working on to
> abstract the common issues of doing so. I know there is a pinoneer
> attempt is C Front which produce C++ programs via a C compiler, I want
> to have a look on that, but still cannot find it now, anyone can
> suggest this to me?
>
> My approach is just to rename the methods with the instance name so
> that they can be placed in a single source file and then be compiled
> later by the procedural lang compiler. For instance,
> [...]
> So far I am a little bit frustrated on this approach, anyone has
> better idea? Pls share your thoughts, thank you!


About C++, you should have a look at method name mangling, (google for
C++ mangling): there are different methods for different type of
arguments! You can consider the type of the hidden 'this' object in
the name mangling, so you don't need to prefix the method name by a
class name.

And mind:
class a{void m(void);};
class A{void m(void);};
!

Since you're interested in some generality, I'd advise you to study
Objective-C (also implemented originally as a pre-processor in front
of C), and CLOS (Common Lisp). With both, you will probably find out
that you have to broaden notably your preconceptions: OO models are
widely different from one language to the other, in general.


--
__Pascal Bourguignon__ http://www.informatimago.com/
napi

2006-10-12, 7:11 pm

moop wrote:
> Hi,
>
> I am working on a project translates OO programs to procedural
> programs, such as translating C++ to C and the like. I hope this


Hi:

Are you going to support the entire C++ and translate it to ANSI C
eventually?
If that's the case it will be useful as a substitute to EDG's C++ to C
translator, or the one from Comeau. Another similar project is called
Lightweight C++ which you can find more info at:
http://students.ceid.upatras.gr/~sxanth/lwc/index.html. But, it does
not support the entire C++ standard.

One note is that when translating from C++ to C it would be a good idea
IMO that the target is ANSI C 1989 since most C compilers support that
standard as opposed to ISO/ANSI C 1999.

CFront from Lucent is no longer supported and it's way behind the
current C++ standard.
I bought the CD about 3 years ago from Lucent for $199, but I don't
think it's available for purchase now. I may be wrong though. I
recommend against using CFront for this purpose due to its significant
outdated-ness.

Napi
Eric

2006-10-12, 7:11 pm

moop wrote:

> My approach is just to rename the methods with the instance name so
> that they can be placed in a single source file and then be compiled
> later by the procedural lang compiler.


This can get nasty with instances being created dynamically. I can
create hundreds of instances at runtime, and you won't know this at
compile time. You would have to implement the "new" mechanism yourself,
and you'd have to track the locals for all of my instances dynamically.
This is far more complicated than a simple text translation.

The only option that makes sense to me if to use a C++ compiler that
produces an output in the form of C code - C would be the target
language. This would be a full compiler and not a simple program.

Dmitry A. Kazakov

2006-10-12, 7:11 pm

On 10 Oct 2006 23:36:02 -0400, moop wrote:

> I am working on a project translates OO programs to procedural
> programs, such as translating C++ to C and the like. I hope this
> effort can be spreaded out to other langs, so I am working on to
> abstract the common issues of doing so. I know there is a pinoneer
> attempt is C Front which produce C++ programs via a C compiler, I want
> to have a look on that, but still cannot find it now, anyone can
> suggest this to me?


Hmm, I presume there is a lot of C++ to C compilers out here...

> My approach is just to rename the methods with the instance name so
> that they can be placed in a single source file and then be compiled
> later by the procedural lang compiler. For instance,
>
> class A{
> B b;
> void method(){
> b.run();
> }
> }
>
> class B{
> void run(){
> ...
> }
> }
>
> If the main rountine is
> void main(){
> A a = new A();
> a.method();
> }
>
> then the program would be translated to
> void a_method(){
> a_b_run();
> }
>
> void a_b_run(){
> ...
> }



Why? To me, obviously, it should be sort of:

void A_method (A * this)
{
A_method (B * this);
}

void main ()
{
A * a;
a = (A *) malloc (...);
A_default_ctor (a); // omitted if empty
A_method (a);
}

> But I feel it is really not an adaptable way when dealing with
> declaration inside iterations whose number of iteration is not sure,
> means that we cannot change the names of the reference inside the
> iteration.
> for(...){
> A a = new A();
> }
> So far I am a little bit frustrated on this approach, anyone has
> better idea? Pls share your thoughts, thank you!


You can't resolve dynamic dispatch at compile time, can you? So you have to
pass the hidden parameter explicitly, rather than trying to pack it in some
naming scheme. In general, which is not OO-specific, you seem to be trying
to remove parameter of a procedure by making one new procedure per each
possible parameter value! (:-)) Just consider a recursive procedure.

--
Regards,
Dmitry A. Kazakov
http://www.dmitry-kazakov.de
[There's only a few C++ to C compilers, since it's no easier to do that
than to generate machine code. See the previous message for some
references. -John]
oliverhunt@gmail.com

2006-10-12, 7:11 pm

moop wrote:
> I am working on a project translates OO programs to procedural
> programs, such as translating C++ to C and the like. I hope this
> effort can be spreaded out to other langs, so I am working on to
> abstract the common issues of doing so. I know there is a pinoneer
> attempt is C Front which produce C++ programs via a C compiler, I want
> to have a look on that, but still cannot find it now, anyone can
> suggest this to me?


What you're trying to do is a very well understood task, as all object
oriented languages must be compiled to non OO code (well, excluding
interpreted languages, and those compilers targeting OOVMs -- though
in that case the vm is taking over the task of converting to non-oo
structures).

Anyway, I have answered a similar question before in this thread,
going over the basic of how single inheritance works in a vtable based
OO language. I can't remember when i posted (John, you may know), but
i have a copy in my poorly updated and unread blog --
http://thepageofdoom.blogspot.com/2...om_archive.html

--Oliver
[It's http://compilers.iecc.com/comparch/article/06-03-083. Google is
your friend; I've designed the archives to be very thoroughly indexed.
-John]
Hans-Peter Diettrich

2006-10-12, 7:11 pm

moop wrote:

> I am working on a project translates OO programs to procedural
> programs, such as translating C++ to C and the like. I hope this
> effort can be spreaded out to other langs, so I am working on to
> abstract the common issues of doing so. I know there is a pinoneer
> attempt is C Front which produce C++ programs via a C compiler, I want
> to have a look on that, but still cannot find it now, anyone can
> suggest this to me?


If an old Cfront version really is unavailable (John?), I'd suggest
that you look into open source OO compilers or systems, to get an idea
how objects and methods are implemented there.

IMO two general object models exist, one with fixed class types (e.g.
C++), and one with objects that exchange messages (e.g. Smalltalk?).

> My approach is just to rename the methods with the instance name so
> that they can be placed in a single source file and then be compiled
> later by the procedural lang compiler.


In C++ type languages the actual instance typically is passed to a
method as a (hidden) argument. What you'll have to do is mangling the
*class* name and the method name. In other languages an object might
be implemented by a list of methods, and a general Dispatch function
for every object. Perhaps a study of the CORBA or ActiveX
documentation will shed some light on possible implementations of such
objects.

DoDi
[I have never seen a legal copy of cfront for free. But as others have
noted, the cfront language is quite different from modern C++. -John
Torben gidius Mogensen

2006-10-12, 7:11 pm

"moop" <samhng@gmail.com> writes:

> I am working on a project translates OO programs to procedural
> programs, such as translating C++ to C and the like.
>
> My approach is just to rename the methods with the instance name so
> that they can be placed in a single source file and then be compiled
> later by the procedural lang compiler.


This will, at best, give you static method calls, but to handle
dynamic method calls, you need something more. I suggest you look in
a compiler textbook to see how OO languages are compiled and use the
methods presented there. Not all compiler textbooks describe OO, so
look before you buy. Andrew Appel's "Modern Compiler Implementation
in {C | Java | ML}" has a section on OO that should be sufficient for
your needs.

Torben
Wolfram Fenske

2006-10-12, 7:11 pm

moop wrote:

> Hi,
>
> I am working on a project translates OO programs to procedural
> programs, such as translating C++ to C and the like. I hope this
> effort can be spreaded out to other langs, so I am working on to
> abstract the common issues of doing so. I know there is a pinoneer
> attempt is C Front which produce C++ programs via a C compiler, I want
> to have a look on that, but still cannot find it now, anyone can
> suggest this to me?
>
> My approach is just to rename the methods with the instance name so
> that they can be placed in a single source file and then be compiled
> later by the procedural lang compiler. For instance,


[...]

> But I feel it is really not an adaptable way when dealing with
> declaration inside iterations whose number of iteration is not sure,
> means that we cannot change the names of the reference inside the
> iteration.
> for(...){
> A a = new A();
> }
> So far I am a little bit frustrated on this approach, anyone has
> better idea? Pls share your thoughts, thank you!


AFAIK, the right thing to do (TM) would be to transform the classes
into structs that contain instance variables and to transform the
methods to take as their first parameter an implicit this-pointer,
which points to the instance. I. e. you need to transform this:

--8<---------------cut here---------------start------------->8---
#include <stdio.h>

class A
{
int x;
public:
A() { x = 0; }
void set_x(int new_x) { x = new_x; }
int get_x() { return x; }
};

int main(int argc, char *argv[])
{
A a;
a.set_x(argc);
printf("%d\n", a.get_x());
return 0;
}
--8<---------------cut here---------------end--------------->8---

into this

--8<---------------cut here---------------start------------->8---
#include <stdio.h>

typedef struct A
{
int x;
} A;

void A__init(A *this)
{
this->x = 0;
}

void A__set_x(A *this, int new_x) { this->x = new_x; }

int A__get_x(A *this) { return this->x; }

int main(int argc, char *argv[])
{
A a; A__init(&a);
A__set_x(&a, argc);
printf("%d\n", A__get_x(&a));
/* A__finalize(&a); */
return 0;
}
--8<---------------cut here---------------end--------------->8---

Some thoughts:

* Function names like A__set_x() etc. are just a lame attempt at
name-mangeling. In practice you would have to generate unique
names.

* Because the this pointer in instance methods is implicit in C++,
you have to do some additional work in resolving variable names in
a method definition.

* The comment /* A__finalize(&a); */ is there to indicate that you
have to call the destructor on every lexical variable before
exiting a function.

* There is no inheritance in my example. I have some ideas, though,
on how it could be done in a relatively straight forward fashion.

* There's a lot of other stuff you'll have to figure out,
e. g. templates, exception handling, virtual functions.

IMO, the only way to accomplish all this is to implement a full C++
compiler, which is going to be a lot of work. But you probably knew
that. ;-) Maybe you can leverage an existing C++ compiler.


Wolfram
Tommy Thorn

2006-10-12, 7:11 pm

moop wrote:
> I am working on a project translates OO programs to procedural
> programs, such as translating C++ to C and the like. I hope this
> effort can be spreaded out to other langs, so I am working on to
> abstract the common issues of doing so. I know there is a pinoneer
> attempt is C Front which produce C++ programs via a C compiler, I want
> to have a look on that, but still cannot find it now, anyone can
> suggest this to me?


I suggest writing an interpreter first. Once it works, you're
understand all/most of the issues and writing an interpreter is much
easier.

> My approach is just to rename the methods with the instance name so
> that they can be placed in a single source file and then be compiled
> later by the procedural lang compiler.


As a general approach to compiling C++ to C this approach won't work.
Granted, as an optimization, specializing member functions to
particular instances is _sometimes_ worthwhile, but let's crawl before
we run.

Class declarations open up a new name space. To represent such a name
in a flat name space such as globals in C, you'd have to flatten it,
say prefix in some manner with the class name. Your example below
could be void A_run(). In practice, C++ compilers to try guard against
linking type incompatible code, so they encode the type of the method
and it's parameters in the name as well, leading to unreadable
"mangled" names.

The key thing about methods is that they have a hidden parameter which
is the instance they are applied to. Usually this is called "this" or
"self". Thus, a class like

class A {
int privated_var;
final void increment() { ++private_var; }
};

could be compiled to

struct A {
int private_var;
};
void A_increment(struct A *this) { ++this->private_var; }

Virtual methods and polymorphism adds a bit more complication as in
general you cannot _statically_ (without a global analysis) determine
exactly which method is being called. Enter the vtable. The vtable
entry in every object is a pointer to a table of the virtual method in
effect for this object. This table is shared by all instances of the
same class. Fx. without the "final" above, the result could be
something like the following (the casting is unavoidable as this is not
expressible directly with C's type system):

typedef void (*A_increment_method_type)(struct A *);
enum { A_increment_method };
struct A {
void **vtable;
int private_var;
};
void *A_vtable[] = { &A_increment };

And a usage of this, such as, a->increment, could be compiled to

((A_increment_method_type)a->vtable[A_increment_method])(a);


Tommy
Joachim Pimiskern

2006-10-12, 7:11 pm

"moop" <samhng@gmail.com> schrieb:
> I am working on a project translates OO programs to procedural
> programs, such as translating C++ to C and the like. I hope this
> effort can be spreaded out to other langs, so I am working on to
> abstract the common issues of doing so.


That's the way Perl was made object-oriented:

A function bless(<ptr>,<namespace> ) was introduced to connect a
pointer to a namespace. The pointer references a data structure for
the member variables of an object instance. The namespace comprises
all functions that belong to the class (member functions).

Functions were made object-oriented by assuming the first parameter is
always <ptr>, the pointer to the member variable data structure.

Whenever a function call of an oop function is
made, e.g. $o->foo(param1,...), the runtime system searches
for the namespace associated with the reference $o
an then calls in that namespace foo($o, param1, ...).

Regards,
Joachim
gnorik@gmail.com

2006-10-30, 7:32 pm

I can recommend you to read this paper :
http://www.planetpdf.com/developer/...?ContentID=6635
html:
http://209.85.129.104/search?q=cach...f.com/developer
/article.asp%3FContentID%3D6635+Object-oriented+programming+is+the+current+cu
re-all&hl=ru&ct=clnk&cd=1&client=firefox-a

regards

Norayr Chilingaryan

---
http://geocities.com/n0rayr


"moop™ писал(а):
"
> Hi,
>
> I am working on a project translates OO programs to procedural
> programs, such as translating C++ to C and the like. I hope this
> effort can be spreaded out to other langs, so I am working on to
> abstract the common issues of doing so. I know there is a pinoneer
> attempt is C Front which produce C++ programs via a C compiler, I want
> to have a look on that, but still cannot find it now, anyone can
> suggest this to me?
>
> My approach is just to rename the methods with the instance name so
> that they can be placed in a single source file and then be compiled
> later by the procedural lang compiler. For instance,
>
> class A{
> B b;
> void method(){
> b.run();
> }
> }
>
> class B{
> void run(){
> ...
> }
> }
>
> If the main rountine is
> void main(){
> A a = new A();
> a.method();
> }
>
> then the program would be translated to
> void a_method(){
> a_b_run();
> }
>
> void a_b_run(){
> ...
> }
> But I feel it is really not an adaptable way when dealing with
> declaration inside iterations whose number of iteration is not sure,
> means that we cannot change the names of the reference inside the
> iteration.
> for(...){
> A a = new A();
> }
> So far I am a little bit frustrated on this approach, anyone has
> better idea? Pls share your thoughts, thank you!


Sponsored Links







Also available: Server administration forum archive | Web Design forum archive | Software forum archive | Hardware reviews archive

Copyright 2008 codecomments.com