Typecast clarification

N

Nick

Ben Bacarisse said:
I suspect there is another less deliberate error here, but I am not
sure.

There's another even bigger one. Where is that fprintf sending it's
output?

It's a good job I don't do code review though, I still can't see the
original error!
 
N

Nick

Nick said:
There's another even bigger one. Where is that fprintf sending it's
output?

It's a good job I don't do code review though, I still can't see the
original error!

Nor, apparently, does gcc...

Original code in your test harness:

$gcc -Wall jk.c
jk.c: In function ‘main’:
jk.c:9: warning: passing argument 1 of ‘fprintf’ from incompatible pointer type
/usr/include/stdio.h:333: note: expected ‘struct FILE * __restrict__’ but argument is of type ‘char *’
jk.c:9: warning: too many arguments for format

Fixed version (with stderr added):

#include <stdio.h>
#include <stdlib.h>
int main(void) {
#define SIZE 42
char *ptr = malloc(SIZE);
if (ptr == NULL) {
fprintf (stderr,"Out of memory: file %s, line %d\n",
__FILE__, __LINE__);
exit (EXIT_FAILURE);
}
return 0;
}


$gcc -Wall jk.c
$ ./a.out
$

Please enlighten me as to what the error the compiler is supposed to be
required to spot is!
 
K

Keith Thompson

Phil Carmody said:
But not necessarily of type. There may be only a conversion of
the qualified type, but not of the type, such as by adding or
casting away const. I think it's still useful to have a term
that specifies that a type conversion has taken place, and there
seem to be few better terms for that than "type casts".

Ah, but constness is part of the type; a qualified type is a type.
"const int" and "int" are two distinct types, and a cast that
converts from one to the other performs a type conversion.
 
N

Nick Keighley

Keith said:
To determine if a machine is little endian / big endian the [following] code
snippet is used...
int num = 1;
if( * (char *)&num == 1)
  printf ("\n Little Endian");
else
  printf("\n Big endian");
That will probably work, but it's not guaranteed.  And before you use
it, you should think about why you care whether your system is
little-endian or big-endian.  There are cases where you need to know,
but I think there are more cases where people *think* they need to know
but really don't.

For networking you need to know whether to swop the incoming and outgoing
byte order...

this is *the* example of when it matters. If its going out of the
machine it'll an external representation and then endianess etc.
matters. The other example is a binary file. (Actually *any* file- but
we seem to think that for text files it is easier to agree on a
representation (XML...)).
Yes, this is dumb. A void* and char* are exactly the same under the hood.

but they differ in their semantics (meaning).
A void* you can convert without a typecast but you can't dereference. A
char* you can dereference but not convert automatically. Why not have one
pointer type with both features??

because they mean different things. GCC allows dereferencing a null
pointer as an extension, but I think GCC is broken!

the memory is undisturbed.
But what I mean is that the int's memory is being regarded as a char,
isn't it?

not really...


don't some of the toupper() thingies need casts to gurantee correct
operation?

It would make life simpler if all typecasts were either disallowed or
guaranteed portable!

I don't think you really understand what casts are for. In many cases
you are using a cast *because* you want non-portable results. Eg. to
discover the endianess of your system...


--
Casting is almost always wrong,
and the places where it's right are rarely the places you'd guess.
Richard Heathfield


Abuse of casting leads to abuse of the type system
leads to sloppy programming leads to
unreliably, even undefined, behaviour.
And that is the path to the dark side....
Richard Bos/John Hascall


We recommend, rather, that users take advantage of the extensions of
GNU C and disregard the limitations of other compilers. Aside from
certain supercomputers and obsolete small machines, there is less
and less reason ever to use any other C compiler other than for
bootstrapping GNU CC.
(Using and Porting GNU CC)
 
B

Ben Bacarisse

Of course, but I was not commenting on that one since it had been posed
a puzzle -- I did not want to give the game away. I was pointing out
another potential problem that might have been missed.

Eh? It looks to me like you've just pointed it out by asking "where is
fprintf sending it's output"? The missing FILE * is the "original
error".
Nor, apparently, does gcc...

Original code in your test harness:

$gcc -Wall jk.c
jk.c: In function ‘main’:
jk.c:9: warning: passing argument 1 of ‘fprintf’ from incompatible pointer type
/usr/include/stdio.h:333: note: expected ‘struct FILE * __restrict__’ but argument is of type ‘char *’
jk.c:9: warning: too many arguments for format

Surely this is gcc answering the question? Eric deliberately missed off
the FILE * to show that, if char * were automatically convertible like
void * is (as the OP seemed to advocating) then such problems would go
undiagnosed.
Fixed version (with stderr added):

#include <stdio.h>
#include <stdlib.h>
int main(void) {
#define SIZE 42
char *ptr = malloc(SIZE);
if (ptr == NULL) {
fprintf (stderr,"Out of memory: file %s, line %d\n",
__FILE__, __LINE__);
exit (EXIT_FAILURE);
}
return 0;
}


$gcc -Wall jk.c
$ ./a.out
$

Please enlighten me as to what the error the compiler is supposed to be
required to spot is!

Well, yes, but fixing the error and then saying you can't find it is
odd! Maybe (since you were replying to me) you thought I had suggested
that there was some other error that needs to diagnosed by a compiler?
I did not intend that. The problem with __LINE__ will often be silent.
 
B

Ben Bacarisse

Nick Keighley said:
On 26 May, 20:40, Roger Tombey <[email protected]> wrote:

because they mean different things. GCC allows dereferencing a null
pointer as an extension, but I think GCC is broken!

Does it? I can't get my copy to do that. Are you thinking of gcc
extension that allows arithmetic on void * but taking sizeof(void) to be
1?

<snip>
 
N

Nick Keighley

Does it?  I can't get my copy to do that.  Are you thinking of gcc
extension that allows arithmetic on void * but taking sizeof(void) to be
1?

yes I was
 
Z

Zarquon

Hi Folks,

To determine if a machine is little endian / big endian the foll. code
snippet is used...
[snip trollery]

Thanks a lot for your help. Appreciate it.

With the exception that the original contained one question more, your
message is word-for-word identical to
<[email protected]>,
which was posted 12 February 2009.

Go away, troll.
 
N

Nick

Ben Bacarisse said:
Of course, but I was not commenting on that one since it had been posed
a puzzle -- I did not want to give the game away. I was pointing out
another potential problem that might have been missed.


Eh? It looks to me like you've just pointed it out by asking "where is
fprintf sending it's output"? The missing FILE * is the "original
error".


Surely this is gcc answering the question? Eric deliberately missed off
the FILE * to show that, if char * were automatically convertible like
void * is (as the OP seemed to advocating) then such problems would go
undiagnosed.


Well, yes, but fixing the error and then saying you can't find it is
odd! Maybe (since you were replying to me) you thought I had suggested
that there was some other error that needs to diagnosed by a compiler?
I did not intend that. The problem with __LINE__ will often be silent.

Ah! I assumed (as perhaps I was meant to do) that it was in the
malloc!

Of course, gcc would have given the final complaint even if char* was
interconvertable - but there's no requirement for compilers to be that
helpful.

And yes, I do make that mistake from time to time to mention a point
earlier in the thread.
 
E

Eric Sosman

[...]
Ah! I assumed (as perhaps I was meant to do) that it was in the
malloc!

I wanted to make the error look plausible, and to look like
something an incautious reader might well overlook. Hence the
ordinary-appearing context -- camouflage, that's all.

Had I offered

fprintf ("This should be a FILE*, not a char*!\n");

.... I suspect many readers might have denied they could fail
to notice the mistake.

Would that all mistakes were so aesy to spot ...
 

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
474,093
Messages
2,570,610
Members
47,230
Latest member
RenaldoDut

Latest Threads

Top