Compile C Code With A CPP Compiler?

E

entropy123

Hey all,

I'm working with some legacy C code and I would like to compile it as
a CPP file.

I get the following error message:

driver.cpp:87: cannot convert `void *' to `GenericStruct *' in
assignment

Reading through the web I've come across vague references to the
'void' issue between C and C++, I don't know C++ well and would
appreciate any pointers or references which might help me out.

Thanks!

entropy
 
M

Mark A. Odell

(e-mail address removed) (entropy123) wrote in

I'm working with some legacy C code and I would like to compile it as
a CPP file.

To what end?
I get the following error message:

driver.cpp:87: cannot convert `void *' to `GenericStruct *' in
assignment

I believe C++ requires explicit casts on void pointers, you might ask this
in C++.
Reading through the web I've come across vague references to the
'void' issue between C and C++, I don't know C++ well and would
appreciate any pointers or references which might help me out.

Two approaches: (1) after finding out the C++ appropriate method of
converting void pointers to other types, fix-up all such conversions with
casts, (2) off-topic but you might find that there is a compiler override
switch to force the C++ compiler to theat a .cpp file as a .c file.

The latter has the benefit of allowing you to use one compiler for both
your C and C++ sources but won't allow you to add C++ features to said
files.

I'm not sure what benefit compiling a true C file as a .cpp file with a
C++ compiler will give you. Oddly enough, I have had to do that on my
current procject because it was once thought we'd convert drivers to C++.
Hence, I have told our compiler (Diab) to treat my .cpp files as .c files.
I've also wrapped the contents of the entire file with:

#ifdef __cplusplus
extern "C" {
#endif

/* File */

#ifdef __cplusplus
}
#endif
 
D

dis

Hey all,

I'm working with some legacy C code and I would like to compile it as
a CPP file.

I get the following error message:

driver.cpp:87: cannot convert `void *' to `GenericStruct *' in
assignment

Reading through the web I've come across vague references to the
'void' issue between C and C++, I don't know C++ well and would
appreciate any pointers or references which might help me out.

Your c++ related question is best answered in one of the c++ specific
newsgroups, e.g. comp.lang.c++.

[OT] Without seeing the actual code, my best guess would be that you need to
cast the expression of type void* to type GenericStruct*, as no implicit
conversion from void* to GenericStruct* exists under C++. [/OT]
 
M

Mike Wahler

entropy123 said:
Hey all,

I'm working with some legacy C code and I would like to compile it as
a CPP file.

'CPP file' is not a concept defined by either the
C or C++ languages. Did you mean you wanted to
translate a file originally written in C with
a C++ compiler? This causes me to ask, why?

Note that some C constructs
are not valid in C++, and vice versa.

Also note that C++ is not topical here.
I get the following error message:

driver.cpp:87: cannot convert `void *' to `GenericStruct *' in
assignment

This is a valid diagnostic for a C++ program, but not
for a C program.
Reading through the web I've come across vague references to the
'void' issue between C and C++,

You cannot learn either language, or the differences,
by surfing the web. You need books.
I don't know C++ well

Books! :)
and would
appreciate any pointers or references which might help me out.

I point and refer you to C++ books:
http://www.accu.org/bookreviews/public/reviews/0sb/beginner_s_c__.htm

and address your immediate problem:

C allows the conversion of 'void*' to and from any
other pointer type without a cast. C++ requires
a cast. (I'm guessing this is happening with an
invocation of 'malloc()')

#include <stdlib.h>

int main()
{
struct GenericStruct
{
/* whatever */
} the_data;

GenericStruct* gsp = (GenericStruct*)malloc(sizeof the_data);
/* whatever */
free((void*)gsp);
return 0;
}

Further discussions about this belong in a C++ group,
or the 'alt.comp.lang.learn.c-c++' group, where both
langs are topical.

Followups set.

-Mike
 
D

Dan Pop

In said:
I'm working with some legacy C code and I would like to compile it as
a CPP file.

This is a brain dead idea, unless you're both a C and C++ expert and you
know perfectly well what you're doing.
I get the following error message:

driver.cpp:87: cannot convert `void *' to `GenericStruct *' in
assignment

Reading through the web I've come across vague references to the
'void' issue between C and C++, I don't know C++ well and would
appreciate any pointers or references which might help me out.

1. By what kind of logic have you decided that comp.lang.c is the right
place for asking C++ questions? Do you also post your C questions to
comp.lang.c++ ? ;-)

2. If you don't know C++ well, you don't use a C++ compiler (except for
C++ learning purposes).

Dan
 
E

entropy123

Thanks for the replies. I spent all summer with C and I'm just
starting to learn C++. The idea with the legacy code is to convert it
from C/bison to C++. Most of the SRC files are written in "C" as well
as the driver. I was thinking if the driver is compiled in C++ then I
could start writing additional code in C++ without worry.

As I understand the situation, C programs may be compiled as C++, but
generally not the other way around.

Inasmuch as the replies involved C++ language I have no clue, but I do
own D&Ds C++ book which I've found excellent at least through the
first 100 easy pages..

Sorry for being OT.

entropy
 
D

Dan Pop

In said:
As I understand the situation, C programs may be compiled as C++, but
generally not the other way around.

Your understanding is completely wrong. If you know what you're doing,
it is possible to write C programs that can be compiled with C++
compilers, but a well written, non-trivial C program is highly unlikely
to be acceptable to a C++ compiler.

C and C++ have a common subset. It doesn't make much sense to write
programs using only this common subset: they would be considered as
badly written from both the C and C++ point of view.

Until you *fully* understand these issues, don't try to compile C code
with a C++ compiler, unless you love shooting yourself in the foot.

Dan
 
M

Mike Wahler

entropy123 said:
Thanks for the replies. I spent all summer with C and I'm just
starting to learn C++. The idea with the legacy code is to convert it
from C/bison to C++.

Again, why? If you're wanting to learn C++, the best
way imo is to write your C++ programs from scratch.
C and C++ syntax is similar enough, but the behavior
of each is (often subtly) different enough, that what
you're attempting will not only prevent learning,
but cause you to 'learn' things which are not correct.
Most of the SRC files are written in "C" as well
as the driver. I was thinking if the driver is compiled in C++ then I
could start writing additional code in C++ without worry.

What has that to do with the C code?
As I understand the situation, C programs may be compiled as C++, but
generally not the other way around.

Then you don't understand. See Dan's reply.
Inasmuch as the replies involved C++ language I have no clue,

And you should not expect anyone here to have any 'clues'
about C++ either. This group is about C. Some folks here,
including myself, have at least some understanding of C++,
but we don't discuss it here, as I pointed out in my previous
reply. I also referred you to a group where both languages
*are* topical.
but I do
own D&Ds C++ book which I've found excellent at least through the
first 100 easy pages..

I think that's a pretty decent book, although there are others
I consider superior (it's a good idea to have more than one
book about a subject you're learning anyway).
Sorry for being OT.

Here's the link to info telling what the topic here is:
http://www.angelfire.com/ms3/bchambless0/welcome_to_clc.html

The C++ groups have similar documents, check them out
before posting there, either. You can find these documents
by perusing the posts in those groups. Links to them
are posted periodically, and are contained in the .sigs
of some of the regulars.


-Mike
 
E

entropy123

Mike Wahler said:
Again, why? If you're wanting to learn C++, the best
way imo is to write your C++ programs from scratch.

Agreed, but the project relies upon about 10 years worth of legacy 'C'
code. I've been working in C, and, after a few conversations, decided
C++ is a better longterm decision for the code.

'main' is in a *.c file with approximately 15 subordinate *.c files.
My understanding is that 'C' will compile just fine in 'C++' but not
vice versa. As it looks like C++ will be a better programming language
for this project I need to start moving the legacy 'C' code to 'C++'.

If the changes to the *.c driver are small it will all be worth it, if
not...
 
M

Mark A. Odell

(e-mail address removed) (entropy123) wrote in

My understanding is that 'C' will compile just fine in 'C++' but not
vice versa.

Not true. All your variables with names like 'new', 'class', etc. will
cause syntax errors.
 
M

Mike Wahler

entropy123 said:
Agreed, but the project relies upon about 10 years worth of legacy 'C'
code. I've been working in C, and, after a few conversations, decided
C++ is a better longterm decision for the code.

It's still often (but perhaps not always) a better idea
to rewrite the whole thing. Many C idioms don't translate
well into well designed C++. A 'direct' translation of
existing algorithms could even concievably reduce, not
enhance code quality, maintainability, readability, etc.
'main' is in a *.c file with approximately 15 subordinate *.c files.
My understanding is that 'C' will compile just fine in 'C++'

You've already been told by me and Dan (who I feel has
considerable more knowledge than I) that that 'understanding'
is unfounded.
but not
vice versa. As it looks like C++ will be a better programming language
for this project

Upon what do you base this conclusion? I'm not saying
it's a poor conclusion, but be sure you have valid
premises.
I need to start moving the legacy 'C' code to 'C++'.

I recommend you first identify valid premises for this
conclusion. You could easily wind up doing much
unnecessary (and possibly even harmful) work.

If the changes to the *.c driver are small it will all be worth it,

Ease of translation is imo no justification of the 'worth'
of such a translation.
if
not...

"if". Hmmm. Find out for sure.

.... you might be doing unnecessary work.

IMO that's a very naive conclusion.

-Mike
 
C

Chris Torek

My understanding is that 'C' will compile just fine in 'C++' but not
vice versa.

Aside from the obvious problems with identifiers in C that are
keywords in C++ (such as "new" and "virtual"), try compiling
the following as C, then again as C++:

#include <stdio.h>

#define MAX 10

struct A {
int n;
struct A_stats {
int in, out;
} stats[MAX];
};

void printstat(struct A_stats *p) {
printf("%d in, %d out\n", p->in, p->out);
}

void print_all_stats(struct A *p) {
int i;

for (i = 0; i < p->n; i++)
printstat(&p->stats);
}

The scoping here, which makes this valid C code and invalid C++,
is one of the more subtle differences between C and C++. With care
-- or by a particularly (un?)lucky accident -- it can be used to
create code that compiles in both languages, yet has completely
different semantics.
 
P

pete

If you have both kinds of compilers,
then this is two different programs:

/* BEGIN new.c or new.cpp */

#include <stdio.h>

char foo;

int main(void)
{
struct foo {
char a[2];
};

if (sizeof (foo) == 1) {
puts("\nC mode");
} else {
puts("\nC++ mode");
}
return 0;
}

/* END new.c or new.cpp */
 
G

goose

Chris Torek said:
My understanding is that 'C' will compile just fine in 'C++' but not
vice versa.

Aside from the obvious problems with identifiers in C that are
keywords in C++ (such as "new" and "virtual"), try compiling
the following as C, then again as C++:

#include <stdio.h>

#define MAX 10

struct A {
int n;
struct A_stats {
int in, out;
} stats[MAX];
};

void printstat(struct A_stats *p) {
printf("%d in, %d out\n", p->in, p->out);
}

void print_all_stats(struct A *p) {
int i;

for (i = 0; i < p->n; i++)
printstat(&p->stats);
}

The scoping here, which makes this valid C code and invalid C++,
is one of the more subtle differences between C and C++. With care
-- or by a particularly (un?)lucky accident -- it can be used to
create code that compiles in both languages, yet has completely
different semantics.


even worse, iirc the OP said something about writing "drivers" ?
in that case, using C++ presents yet another problem ... default
exception handling code is generated for constructors/destructors.

in which case just having something like

class foo_t a { ... }

....
foo_t bar;
....
generates code that the programmer does not even see ...

goose
 
E

entropy123

Hmmm,

Well thank you all for the advice. I've decided to wait until I know
more C++ to decide whether or not to make the change. My colleagues
believe Templates and Vectors alone will make the change worthwhile,
but they do not work directly with this code...and I don't know C++
yet...

Thanks,
entropy
 
M

Mike Wahler

entropy123 said:
Hmmm,

Well thank you all for the advice. I've decided to wait until I know
more C++ to decide whether or not to make the change. My colleagues
believe Templates and Vectors alone will make the change worthwhile,
but they do not work directly with this code...and I don't know C++
yet...

IMO about the only thing which would make the change "worthwhile"
is if the application *design* is better suited to the new language.
In which case, a "write from scratch" approach could still be the
best route. Don't be afraid of a "total rewrite", my experience
has been that even when done in the same language, the result is
usually better than the original.

-Mike
 
M

Micah Cowan

Agreed, but the project relies upon about 10 years worth of legacy 'C'
code. I've been working in C, and, after a few conversations, decided
C++ is a better longterm decision for the code.

'main' is in a *.c file with approximately 15 subordinate *.c files.
My understanding is that 'C' will compile just fine in 'C++' but not
vice versa.

This is a fallacy, as you are discovering. There are many C
programs which will fail to compile in C++. And, as it turns out,
idiomatically "correct" C code will especially tend not to
compile in C++ (for example, casting void*).

I'd highly recommend compiling the C code as C code, since you
can easily *link* to the results from C++ object code (this
ability is specified by the C++ standard; the C standard has no
knowledge of C++).

-Micah
 
C

CBFalconer

Micah said:
.... snip ...

I'd highly recommend compiling the C code as C code, since you
can easily *link* to the results from C++ object code (this
ability is specified by the C++ standard; the C standard has no
knowledge of C++).

Not quite. No C compiler or program is allowed to define
__cplusplus__ thus allowing the ubiquitious wrapper:

#ifdef __cplusplus__
#extern 'C' {
#endif
....
#ifdef __cplusplus__
}
#endif

to allow .h files to be used in C++ code and generate the correct
links.
 
P

Peter Nilsson

CBFalconer said:
Not quite. No C compiler or program is allowed to define
__cplusplus__
^^
No C99 implementation will define __cplusplus, but AFAIK C90 implementations
are not constrained in that regard.
 
D

Dan Pop

In said:
^^
No C99 implementation will define __cplusplus, but AFAIK C90 implementations
are not constrained in that regard.

Indeed. This is a last moment addition to the C99 standard (missing from
N869).

Dan
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Members online

Forum statistics

Threads
473,755
Messages
2,569,536
Members
45,007
Latest member
obedient dusk

Latest Threads

Top