Velocity Reviews - Computer Hardware Reviews

Velocity Reviews > Newsgroups > Programming > C Programming > warning: return makes integer from pointer without a cast

Reply
Thread Tools

warning: return makes integer from pointer without a cast

 
 
Ton 't Lam
Guest
Posts: n/a
 
      11-24-2008
Please, consider the following minimal example code:

# more f.l
%option noyywrap

%{
#include <string.h>
%}

%%

[0-9]+ return( strdup (yytext));

%%

# more main.c
#include <stdio.h>

main()
{
printf( "%s\n", yylex());
}

# flex f.l
# cc -o prog main.c lex.yy.c
f.l: In function ‘yylex’:
f.l:9: warning: return makes integer from pointer without a cast

The program 'main' works correctly.

gcc version 4.1.2 20070925 (Red Hat 4.1.2-33)
flex 2.5.33

If I cast with (char *) on several places, I see no improvement.
Googling didn't lead me to a solution either.

How can I corect the code, so I don't have this warning?

Many thanks,
Ton
 
Reply With Quote
 
 
 
 
Nate Eldredge
Guest
Posts: n/a
 
      11-24-2008
Ton 't Lam <(E-Mail Removed)> writes:

> Please, consider the following minimal example code:
>
> # more f.l
> %option noyywrap
>
> %{
> #include <string.h>
> %}
>
> %%
>
> [0-9]+ return( strdup (yytext));
>
> %%
>
> # more main.c
> #include <stdio.h>
>
> main()
> {
> printf( "%s\n", yylex());
> }
>
> # flex f.l
> # cc -o prog main.c lex.yy.c
> f.l: In function ‘yylex’:
> f.l:9: warning: return makes integer from pointer without a cast
>
> The program 'main' works correctly.
>
> gcc version 4.1.2 20070925 (Red Hat 4.1.2-33)
> flex 2.5.33
>
> If I cast with (char *) on several places, I see no improvement.
> Googling didn't lead me to a solution either.
>
> How can I corect the code, so I don't have this warning?


This is not a question about C, but about flex. The yylex function it
generates is declared by default as returning int, but your return
statement (which gets inserted into yylex) returns a char *. Read
Chaper 9 of the flex manual ("The Generated Scanner") which explains how
change the return type. Further questions should go to a forum that
deals with flex specifically.
 
Reply With Quote
 
 
 
 
Ton 't Lam
Guest
Posts: n/a
 
      11-25-2008
You're right. This is not a question about C, but about flex.

Anyway, the solution is to have:

%option noyywrap

%{
#include <string.h>
#define YY_PROTO(proto) proto
#define YY_DECL char *yylex YY_PROTO(( void ))
%}

%%

[0-9]+ return( (char *) strdup (yytext));

%%
 
Reply With Quote
 
Keith Thompson
Guest
Posts: n/a
 
      11-25-2008
Ton 't Lam <(E-Mail Removed)> writes:
> You're right. This is not a question about C, but about flex.
>
> Anyway, the solution is to have:
>
> %option noyywrap
>
> %{
> #include <string.h>
> #define YY_PROTO(proto) proto
> #define YY_DECL char *yylex YY_PROTO(( void ))
> %}
>
> %%
>
> [0-9]+ return( (char *) strdup (yytext));
>
> %%


Since you didn't post any context from previous articles, it's
difficult to tell what you changed. Lookup upthread, you originally had:
[0-9]+ return( strdup (yytext));
which you've now changed to
[0-9]+ return( (char *) strdup (yytext));

That silences the warning, but the warning wasn't the problem. Adding
a cast to silence a warning is almost never a good idea. Without
seeing the full C code that's generated from your flex input, it's
difficult to tell, but here's what I think is happening:

strdup returns a result of type char*. Your compiler isn't seeing a
declaration for strdup, so it assumes that it returns int. This alone
invokes undefined behavior. You were lucky enough to get a warning
because you tried to use the result in a context that requires a char*
value (the return statement).

After you added the cast, the compiler is *still* assuming,
incorrectly, that strdup returns a result of type int. When the call
is executed at run time, likely results are that the actual char*
value returned by the function is treated as an int, or an int value
is grabbed from some arbitrary location, giving you a garbage int
value. The cast does two things: it converts this garbage int value
to char*, and it silences the warning because you've told the compiler
that you know what you're doing (sorry, but you don't).

strdup is not a standard function. (It's very commonly provided, but
the ANSI committee chose not to standardize it back in 1989.) Even if
your implementation provides strdup, it probably doesn't provide a
declaration of it in <string.h> unless you do something special to
enable it.

The quick solution would be to find out how to enable the declaration
of strdup in your C implementation. A more portable solution would be
to write your own strdup implementation (it's not difficult) and give
it a different name, such as dupstr.

Either way, lose the cast.

--
Keith Thompson (The_Other_Keith) http://www.velocityreviews.com/forums/(E-Mail Removed) <http://www.ghoti.net/~kst>
Nokia
"We must do something. This is something. Therefore, we must do this."
-- Antony Jay and Jonathan Lynn, "Yes Minister"
 
Reply With Quote
 
Keith Thompson
Guest
Posts: n/a
 
      11-25-2008
Eric Sosman <(E-Mail Removed)> writes:
> Keith Thompson wrote:

[...]
>> Since you didn't post any context from previous articles, it's
>> difficult to tell what you changed. Lookup upthread, you originally had:
>> [0-9]+ return( strdup (yytext));
>> which you've now changed to
>> [0-9]+ return( (char *) strdup (yytext));
>> That silences the warning, but the warning wasn't the problem.
>> Adding
>> a cast to silence a warning is almost never a good idea. Without
>> seeing the full C code that's generated from your flex input, it's
>> difficult to tell, but here's what I think is happening:
>> strdup returns a result of type char*. Your compiler isn't seeing a
>> declaration for strdup, so it assumes that it returns int. This alone
>> invokes undefined behavior. You were lucky enough to get a warning
>> because you tried to use the result in a context that requires a char*
>> value (the return statement).

>
> If so, the diagnostic was extremely misleading. Note the sense
> of the conversion it complained about: not integer to pointer, but
> pointer to integer. If the diagnostic is to be believed, then the
> compiler knew [1] that strdup() returns a pointer, and [2] that the
> pointer was being converted to an integer in `return'.


D'oh! You're right.

> As you say, adding a cast to silence a warning is seldom a good
> idea, and in this case I suspect it had nothing to do with the cure.
> The cure was probably the introduction of the YY_PROTO and YY_DECL
> macros, which most likely changed the return type of the generated
> C function from `int' to `char*'. If I'm right, then the cast in
> the `return' statement is harmless, but useless.


Agreed.

--
Keith Thompson (The_Other_Keith) (E-Mail Removed) <http://www.ghoti.net/~kst>
Nokia
"We must do something. This is something. Therefore, we must do this."
-- Antony Jay and Jonathan Lynn, "Yes Minister"
 
Reply With Quote
 
Ton 't Lam
Guest
Posts: n/a
 
      11-26-2008
Keith Thompson wrote:
> Eric Sosman <(E-Mail Removed)> writes:
>> Keith Thompson wrote:

> [...]
>>> Since you didn't post any context from previous articles, it's
>>> difficult to tell what you changed. Lookup upthread, you originally had:
>>> [0-9]+ return( strdup (yytext));
>>> which you've now changed to
>>> [0-9]+ return( (char *) strdup (yytext));
>>> That silences the warning, but the warning wasn't the problem.
>>> Adding
>>> a cast to silence a warning is almost never a good idea. Without
>>> seeing the full C code that's generated from your flex input, it's
>>> difficult to tell, but here's what I think is happening:
>>> strdup returns a result of type char*. Your compiler isn't seeing a
>>> declaration for strdup, so it assumes that it returns int. This alone
>>> invokes undefined behavior. You were lucky enough to get a warning
>>> because you tried to use the result in a context that requires a char*
>>> value (the return statement).

>> If so, the diagnostic was extremely misleading. Note the sense
>> of the conversion it complained about: not integer to pointer, but
>> pointer to integer. If the diagnostic is to be believed, then the
>> compiler knew [1] that strdup() returns a pointer, and [2] that the
>> pointer was being converted to an integer in `return'.

>
> D'oh! You're right.
>
>> As you say, adding a cast to silence a warning is seldom a good
>> idea, and in this case I suspect it had nothing to do with the cure.
>> The cure was probably the introduction of the YY_PROTO and YY_DECL
>> macros, which most likely changed the return type of the generated
>> C function from `int' to `char*'. If I'm right, then the cast in
>> the `return' statement is harmless, but useless.

>
> Agreed.
>



Yes, this seems to misleading indeed. It took me quite some re-reading
to comprehend this error, which is correct anyway.

It is the return() in flex that returns an integer by default, however
in this case it ought to be a pointer to character. So you have to declare

#define YY_PROTO(proto) proto
#define YY_DECL char *yylex YY_PROTO(( void ))

From here the return() in flex will return a pointer to a character.

At first I thought it was the strdup as well, but this is another story.
I've seen that if you don't strdup the yytext, then on a next invokation
of yylex() you may get weird results, because yytext (a pointer)
changes! You simply have to run of a copy, and always save.

The #include <string.h> contains the declaration of strdup().

My code now compiles warning free.

Many thanks for all replies.

Ton 't Lam

 
Reply With Quote
 
 
 
Reply

Thread Tools

Posting Rules
You may not post new threads
You may not post replies
You may not post attachments
You may not edit your posts

BB code is On
Smilies are On
[IMG] code is On
HTML code is Off
Trackbacks are On
Pingbacks are On
Refbacks are Off


Similar Threads
Thread Thread Starter Forum Replies Last Post
Help: "Assignment makes integer from pointer without a cast" Juggernaut C Programming 10 04-09-2005 08:00 AM
warning: passing arg 1 of `atoi' makes pointer from integer without a cast francescomoi@europe.com C Programming 2 04-01-2005 05:30 PM
warning: assignment makes integer from pointer without a cast Dawn Minnis C Programming 4 02-20-2005 07:02 PM
fmemopen: assignment makes pointer from integer without a cast Markus Dehmann C Programming 14 06-28-2004 01:12 PM
assignment makes pointer from integer without a cast...help please. Rocke Robertson C Programming 14 10-02-2003 01:35 PM



Advertisments