git.vger.kernel.org archive mirror
 help / color / mirror / Atom feed
* Issue with compiling git 1.8.4 under uclibc with gcc 4.6.3
@ 2013-08-26 20:10 Lance
  2013-08-26 20:18 ` Lukas Fleischer
  0 siblings, 1 reply; 9+ messages in thread
From: Lance @ 2013-08-26 20:10 UTC (permalink / raw)
  To: git

Up until the latest release, I've been able to compile git for a uclibc 
based embedded linux. The toolchain I use is from "entware", which is 
based off of the openwrt toolchain.
https://code.google.com/p/wl500g-repo/

Somewhere between git 1.8.3.4 & 1.8.4 there seems to be some changes 
that breaks compilation for my particular situation.  When cross 
compiling I receive the following error.  I also receive the same error 
when compiling natively on the uclibc based device itself.
Not sure if being uclibc based has anything to do with it, but is 
noteworthy. I am not a c programmer.
Both the cross compiler, and embedded device's version off gcc is 4.6.3.
Previous versions compile fine

     CC config.o
config.c: In function 'get_next_char':
config.c:220:14: error: expected identifier before '(' token
config.c:220:14: error: expected statement before ')' token
config.c:220:14: error: expected statement before ')' token
config.c:224:11: error: expected identifier before '(' token

Lance

^ permalink raw reply	[flat|nested] 9+ messages in thread

* Re: Issue with compiling git 1.8.4 under uclibc with gcc 4.6.3
  2013-08-26 20:10 Issue with compiling git 1.8.4 under uclibc with gcc 4.6.3 Lance
@ 2013-08-26 20:18 ` Lukas Fleischer
  2013-08-26 20:29   ` Lance
  0 siblings, 1 reply; 9+ messages in thread
From: Lukas Fleischer @ 2013-08-26 20:18 UTC (permalink / raw)
  To: Lance; +Cc: git

On Mon, Aug 26, 2013 at 02:10:43PM -0600, Lance wrote:
> Up until the latest release, I've been able to compile git for a
> uclibc based embedded linux. The toolchain I use is from "entware",
> which is based off of the openwrt toolchain.
> https://code.google.com/p/wl500g-repo/
> 
> Somewhere between git 1.8.3.4 & 1.8.4 there seems to be some changes
> that breaks compilation for my particular situation.  When cross
> compiling I receive the following error.  I also receive the same
> error when compiling natively on the uclibc based device itself.
> Not sure if being uclibc based has anything to do with it, but is
> noteworthy. I am not a c programmer.
> Both the cross compiler, and embedded device's version off gcc is 4.6.3.
> Previous versions compile fine
> 
>     CC config.o
> config.c: In function 'get_next_char':
> config.c:220:14: error: expected identifier before '(' token
> config.c:220:14: error: expected statement before ')' token
> config.c:220:14: error: expected statement before ')' token
> config.c:224:11: error: expected identifier before '(' token

Does changing line 220 of config.c to

    int c = (cf->fgetc)(cf);

fix it?

> 
> Lance
> --
> To unsubscribe from this list: send the line "unsubscribe git" in
> the body of a message to majordomo@vger.kernel.org
> More majordomo info at  http://vger.kernel.org/majordomo-info.html

^ permalink raw reply	[flat|nested] 9+ messages in thread

* Re: Issue with compiling git 1.8.4 under uclibc with gcc 4.6.3
  2013-08-26 20:18 ` Lukas Fleischer
@ 2013-08-26 20:29   ` Lance
  2013-08-26 20:31     ` Lukas Fleischer
  0 siblings, 1 reply; 9+ messages in thread
From: Lance @ 2013-08-26 20:29 UTC (permalink / raw)
  To: Lukas Fleischer; +Cc: git


On 8/26/2013 2:18 PM, Lukas Fleischer wrote:
> On Mon, Aug 26, 2013 at 02:10:43PM -0600, Lance wrote:
>> Up until the latest release, I've been able to compile git for a
>> uclibc based embedded linux. The toolchain I use is from "entware",
>> which is based off of the openwrt toolchain.
>> https://code.google.com/p/wl500g-repo/
>>
>> Somewhere between git 1.8.3.4 & 1.8.4 there seems to be some changes
>> that breaks compilation for my particular situation.  When cross
>> compiling I receive the following error.  I also receive the same
>> error when compiling natively on the uclibc based device itself.
>> Not sure if being uclibc based has anything to do with it, but is
>> noteworthy. I am not a c programmer.
>> Both the cross compiler, and embedded device's version off gcc is 4.6.3.
>> Previous versions compile fine
>>
>>      CC config.o
>> config.c: In function 'get_next_char':
>> config.c:220:14: error: expected identifier before '(' token
>> config.c:220:14: error: expected statement before ')' token
>> config.c:220:14: error: expected statement before ')' token
>> config.c:224:11: error: expected identifier before '(' token
> Does changing line 220 of config.c to
>
>      int c = (cf->fgetc)(cf);
>
> fix it?
I also had to change line 224 to the following

                 c = (cf->fgetc)(cf);

Once both places were changes, it compiled successfully.
thanks
>> Lance
>> --
>> To unsubscribe from this list: send the line "unsubscribe git" in
>> the body of a message to majordomo@vger.kernel.org
>> More majordomo info at  http://vger.kernel.org/majordomo-info.html

^ permalink raw reply	[flat|nested] 9+ messages in thread

* Re: Issue with compiling git 1.8.4 under uclibc with gcc 4.6.3
  2013-08-26 20:29   ` Lance
@ 2013-08-26 20:31     ` Lukas Fleischer
  2013-08-26 20:59       ` Jeff King
  2013-08-26 21:07       ` Issue with compiling git 1.8.4 under uclibc with gcc 4.6.3 Andreas Schwab
  0 siblings, 2 replies; 9+ messages in thread
From: Lukas Fleischer @ 2013-08-26 20:31 UTC (permalink / raw)
  To: Lance; +Cc: git

On Mon, Aug 26, 2013 at 02:29:12PM -0600, Lance wrote:
> [...]
> >>     CC config.o
> >>config.c: In function 'get_next_char':
> >>config.c:220:14: error: expected identifier before '(' token
> >>config.c:220:14: error: expected statement before ')' token
> >>config.c:220:14: error: expected statement before ')' token
> >>config.c:224:11: error: expected identifier before '(' token
> >Does changing line 220 of config.c to
> >
> >     int c = (cf->fgetc)(cf);
> >
> >fix it?
> I also had to change line 224 to the following
> 
>                 c = (cf->fgetc)(cf);
> 
> Once both places were changes, it compiled successfully.

Sounds like a parser bug to me. Should we patch this in Git in order to
make it compile with (broken?) GCC versions?
> [...]

^ permalink raw reply	[flat|nested] 9+ messages in thread

* Re: Issue with compiling git 1.8.4 under uclibc with gcc 4.6.3
  2013-08-26 20:31     ` Lukas Fleischer
@ 2013-08-26 20:59       ` Jeff King
  2013-08-26 21:57         ` [PATCH] config: do not use C function names as struct members Jeff King
  2013-08-26 21:07       ` Issue with compiling git 1.8.4 under uclibc with gcc 4.6.3 Andreas Schwab
  1 sibling, 1 reply; 9+ messages in thread
From: Jeff King @ 2013-08-26 20:59 UTC (permalink / raw)
  To: Lukas Fleischer; +Cc: Lance, git

On Mon, Aug 26, 2013 at 10:31:54PM +0200, Lukas Fleischer wrote:

> > I also had to change line 224 to the following
> > 
> >                 c = (cf->fgetc)(cf);
> > 
> > Once both places were changes, it compiled successfully.
> 
> Sounds like a parser bug to me. Should we patch this in Git in order to
> make it compile with (broken?) GCC versions?

Hmm. I wonder if fgetc is a macro in uclibc? Just grepping their
stdio.h, it looks like that is a possibility.

I think they are probably wrong to do so (but I'd have to check the
standard). However, the cleaner workaround would probably be to call the
fgetc struct member something else.

-Peff

^ permalink raw reply	[flat|nested] 9+ messages in thread

* Re: Issue with compiling git 1.8.4 under uclibc with gcc 4.6.3
  2013-08-26 20:31     ` Lukas Fleischer
  2013-08-26 20:59       ` Jeff King
@ 2013-08-26 21:07       ` Andreas Schwab
  1 sibling, 0 replies; 9+ messages in thread
From: Andreas Schwab @ 2013-08-26 21:07 UTC (permalink / raw)
  To: Lukas Fleischer; +Cc: Lance, git

Lukas Fleischer <git@cryptocrack.de> writes:

> On Mon, Aug 26, 2013 at 02:29:12PM -0600, Lance wrote:
>> [...]
>> >>     CC config.o
>> >>config.c: In function 'get_next_char':
>> >>config.c:220:14: error: expected identifier before '(' token
>> >>config.c:220:14: error: expected statement before ')' token
>> >>config.c:220:14: error: expected statement before ')' token
>> >>config.c:224:11: error: expected identifier before '(' token
>> >Does changing line 220 of config.c to
>> >
>> >     int c = (cf->fgetc)(cf);
>> >
>> >fix it?
>> I also had to change line 224 to the following
>> 
>>                 c = (cf->fgetc)(cf);
>> 
>> Once both places were changes, it compiled successfully.
>
> Sounds like a parser bug to me.

No, it isn't.  fgetc may be a function-like macro that expands to an
arbitrary expression (same for ungetc or ftell, or any other indentifier
that matches a C library function, for that matter).

Andreas.

-- 
Andreas Schwab, schwab@linux-m68k.org
GPG Key fingerprint = 58CA 54C7 6D53 942B 1756  01D3 44D5 214B 8276 4ED5
"And now for something completely different."

^ permalink raw reply	[flat|nested] 9+ messages in thread

* [PATCH] config: do not use C function names as struct members
  2013-08-26 20:59       ` Jeff King
@ 2013-08-26 21:57         ` Jeff King
  2013-08-27  0:56           ` Lukas Fleischer
  2013-08-27  4:38           ` Junio C Hamano
  0 siblings, 2 replies; 9+ messages in thread
From: Jeff King @ 2013-08-26 21:57 UTC (permalink / raw)
  To: Lukas Fleischer; +Cc: Lance, git

On Mon, Aug 26, 2013 at 04:59:01PM -0400, Jeff King wrote:

> Hmm. I wonder if fgetc is a macro in uclibc? Just grepping their
> stdio.h, it looks like that is a possibility.
> 
> I think they are probably wrong to do so (but I'd have to check the
> standard). However, the cleaner workaround would probably be to call the
> fgetc struct member something else.

Nope, it's allowed. I think we should do the patch below:

-- >8 --
Subject: config: do not use C function names as struct members

According to C99, section 7.1.4:

  Any function declared in a header may be additionally
  implemented as a function-like macro defined in the
  header.

Therefore calling our struct member function pointer "fgetc"
may run afoul of unwanted macro expansion when we call:

  char c = cf->fgetc(cf);

This turned out to be a problem on uclibc, which defines
fgetc as a macro and causes compilation failure.

The standard suggests fixing this in a few ways:

  1. Using extra parentheses to inhibit the function-like
     macro expansion. E.g., "(cf->fgetc)(cf)". This is
     undesirable as it's ugly, and each call site needs to
     remember to use it (and on systems without the macro,
     forgetting will compile just fine).

  2. Using #undef (because a conforming implementation must
     also be providing fgetc as a function). This is
     undesirable because presumably the implementation was
     using the macro for a performance benefit, and we are
     dropping that optimization.

Instead, we can simply use non-colliding names.

Signed-off-by: Jeff King <peff@peff.net>
---
 config.c | 32 ++++++++++++++++----------------
 1 file changed, 16 insertions(+), 16 deletions(-)

diff --git a/config.c b/config.c
index e13a7b6..9f9bf0c 100644
--- a/config.c
+++ b/config.c
@@ -27,9 +27,9 @@ struct config_source {
 	struct strbuf value;
 	struct strbuf var;
 
-	int (*fgetc)(struct config_source *c);
-	int (*ungetc)(int c, struct config_source *conf);
-	long (*ftell)(struct config_source *c);
+	int (*do_fgetc)(struct config_source *c);
+	int (*do_ungetc)(int c, struct config_source *conf);
+	long (*do_ftell)(struct config_source *c);
 };
 
 static struct config_source *cf;
@@ -217,13 +217,13 @@ static int get_next_char(void)
 
 static int get_next_char(void)
 {
-	int c = cf->fgetc(cf);
+	int c = cf->do_fgetc(cf);
 
 	if (c == '\r') {
 		/* DOS like systems */
-		c = cf->fgetc(cf);
+		c = cf->do_fgetc(cf);
 		if (c != '\n') {
-			cf->ungetc(c, cf);
+			cf->do_ungetc(c, cf);
 			c = '\r';
 		}
 	}
@@ -992,9 +992,9 @@ int git_config_from_file(config_fn_t fn, const char *filename, void *data)
 		top.u.file = f;
 		top.name = filename;
 		top.die_on_error = 1;
-		top.fgetc = config_file_fgetc;
-		top.ungetc = config_file_ungetc;
-		top.ftell = config_file_ftell;
+		top.do_fgetc = config_file_fgetc;
+		top.do_ungetc = config_file_ungetc;
+		top.do_ftell = config_file_ftell;
 
 		ret = do_config_from(&top, fn, data);
 
@@ -1013,9 +1013,9 @@ int git_config_from_buf(config_fn_t fn, const char *name, const char *buf,
 	top.u.buf.pos = 0;
 	top.name = name;
 	top.die_on_error = 0;
-	top.fgetc = config_buf_fgetc;
-	top.ungetc = config_buf_ungetc;
-	top.ftell = config_buf_ftell;
+	top.do_fgetc = config_buf_fgetc;
+	top.do_ungetc = config_buf_ungetc;
+	top.do_ftell = config_buf_ftell;
 
 	return do_config_from(&top, fn, data);
 }
@@ -1196,7 +1196,7 @@ static int store_aux(const char *key, const char *value, void *cb)
 				return 1;
 			}
 
-			store.offset[store.seen] = cf->ftell(cf);
+			store.offset[store.seen] = cf->do_ftell(cf);
 			store.seen++;
 		}
 		break;
@@ -1223,19 +1223,19 @@ static int store_aux(const char *key, const char *value, void *cb)
 		 * Do not increment matches: this is no match, but we
 		 * just made sure we are in the desired section.
 		 */
-		store.offset[store.seen] = cf->ftell(cf);
+		store.offset[store.seen] = cf->do_ftell(cf);
 		/* fallthru */
 	case SECTION_END_SEEN:
 	case START:
 		if (matches(key, value)) {
-			store.offset[store.seen] = cf->ftell(cf);
+			store.offset[store.seen] = cf->do_ftell(cf);
 			store.state = KEY_SEEN;
 			store.seen++;
 		} else {
 			if (strrchr(key, '.') - key == store.baselen &&
 			      !strncmp(key, store.key, store.baselen)) {
 					store.state = SECTION_SEEN;
-					store.offset[store.seen] = cf->ftell(cf);
+					store.offset[store.seen] = cf->do_ftell(cf);
 			}
 		}
 	}
-- 
1.8.4.2.g87d4a77

^ permalink raw reply related	[flat|nested] 9+ messages in thread

* Re: [PATCH] config: do not use C function names as struct members
  2013-08-26 21:57         ` [PATCH] config: do not use C function names as struct members Jeff King
@ 2013-08-27  0:56           ` Lukas Fleischer
  2013-08-27  4:38           ` Junio C Hamano
  1 sibling, 0 replies; 9+ messages in thread
From: Lukas Fleischer @ 2013-08-27  0:56 UTC (permalink / raw)
  To: Jeff King; +Cc: Lance, git

On Mon, Aug 26, 2013 at 05:57:18PM -0400, Jeff King wrote:
> On Mon, Aug 26, 2013 at 04:59:01PM -0400, Jeff King wrote:
> 
> > Hmm. I wonder if fgetc is a macro in uclibc? Just grepping their
> > stdio.h, it looks like that is a possibility.
> > 
> > I think they are probably wrong to do so (but I'd have to check the
> > standard). However, the cleaner workaround would probably be to call the
> > fgetc struct member something else.
> 
> Nope, it's allowed. I think we should do the patch below:
> 
> -- >8 --
> Subject: config: do not use C function names as struct members
> [...]
> 
> Instead, we can simply use non-colliding names.

Yes, this sounds like a better idea to me. So, FWIW, +1 from me.

> 
> Signed-off-by: Jeff King <peff@peff.net>
> ---
>  config.c | 32 ++++++++++++++++----------------
>  1 file changed, 16 insertions(+), 16 deletions(-)
> 
> [...]

^ permalink raw reply	[flat|nested] 9+ messages in thread

* Re: [PATCH] config: do not use C function names as struct members
  2013-08-26 21:57         ` [PATCH] config: do not use C function names as struct members Jeff King
  2013-08-27  0:56           ` Lukas Fleischer
@ 2013-08-27  4:38           ` Junio C Hamano
  1 sibling, 0 replies; 9+ messages in thread
From: Junio C Hamano @ 2013-08-27  4:38 UTC (permalink / raw)
  To: Jeff King; +Cc: Lukas Fleischer, Lance, git

Jeff King <peff@peff.net> writes:

> On Mon, Aug 26, 2013 at 04:59:01PM -0400, Jeff King wrote:
>
>> Hmm. I wonder if fgetc is a macro in uclibc? Just grepping their
>> stdio.h, it looks like that is a possibility.
>> 
>> I think they are probably wrong to do so (but I'd have to check the
>> standard). However, the cleaner workaround would probably be to call the
>> fgetc struct member something else.
>
> Nope, it's allowed. I think we should do the patch below:

Thanks.

> -- >8 --
> Subject: config: do not use C function names as struct members
>
> According to C99, section 7.1.4:
>
>   Any function declared in a header may be additionally
>   implemented as a function-like macro defined in the
>   header.
>
> Therefore calling our struct member function pointer "fgetc"
> may run afoul of unwanted macro expansion when we call:
>
>   char c = cf->fgetc(cf);
>
> This turned out to be a problem on uclibc, which defines
> fgetc as a macro and causes compilation failure.
>
> The standard suggests fixing this in a few ways:
>
>   1. Using extra parentheses to inhibit the function-like
>      macro expansion. E.g., "(cf->fgetc)(cf)". This is
>      undesirable as it's ugly, and each call site needs to
>      remember to use it (and on systems without the macro,
>      forgetting will compile just fine).
>
>   2. Using #undef (because a conforming implementation must
>      also be providing fgetc as a function). This is
>      undesirable because presumably the implementation was
>      using the macro for a performance benefit, and we are
>      dropping that optimization.
>
> Instead, we can simply use non-colliding names.
>
> Signed-off-by: Jeff King <peff@peff.net>
> ---
>  config.c | 32 ++++++++++++++++----------------
>  1 file changed, 16 insertions(+), 16 deletions(-)
>
> diff --git a/config.c b/config.c
> index e13a7b6..9f9bf0c 100644
> --- a/config.c
> +++ b/config.c
> @@ -27,9 +27,9 @@ struct config_source {
>  	struct strbuf value;
>  	struct strbuf var;
>  
> -	int (*fgetc)(struct config_source *c);
> -	int (*ungetc)(int c, struct config_source *conf);
> -	long (*ftell)(struct config_source *c);
> +	int (*do_fgetc)(struct config_source *c);
> +	int (*do_ungetc)(int c, struct config_source *conf);
> +	long (*do_ftell)(struct config_source *c);
>  };
>  
>  static struct config_source *cf;
> @@ -217,13 +217,13 @@ static int get_next_char(void)
>  
>  static int get_next_char(void)
>  {
> -	int c = cf->fgetc(cf);
> +	int c = cf->do_fgetc(cf);
>  
>  	if (c == '\r') {
>  		/* DOS like systems */
> -		c = cf->fgetc(cf);
> +		c = cf->do_fgetc(cf);
>  		if (c != '\n') {
> -			cf->ungetc(c, cf);
> +			cf->do_ungetc(c, cf);
>  			c = '\r';
>  		}
>  	}
> @@ -992,9 +992,9 @@ int git_config_from_file(config_fn_t fn, const char *filename, void *data)
>  		top.u.file = f;
>  		top.name = filename;
>  		top.die_on_error = 1;
> -		top.fgetc = config_file_fgetc;
> -		top.ungetc = config_file_ungetc;
> -		top.ftell = config_file_ftell;
> +		top.do_fgetc = config_file_fgetc;
> +		top.do_ungetc = config_file_ungetc;
> +		top.do_ftell = config_file_ftell;
>  
>  		ret = do_config_from(&top, fn, data);
>  
> @@ -1013,9 +1013,9 @@ int git_config_from_buf(config_fn_t fn, const char *name, const char *buf,
>  	top.u.buf.pos = 0;
>  	top.name = name;
>  	top.die_on_error = 0;
> -	top.fgetc = config_buf_fgetc;
> -	top.ungetc = config_buf_ungetc;
> -	top.ftell = config_buf_ftell;
> +	top.do_fgetc = config_buf_fgetc;
> +	top.do_ungetc = config_buf_ungetc;
> +	top.do_ftell = config_buf_ftell;
>  
>  	return do_config_from(&top, fn, data);
>  }
> @@ -1196,7 +1196,7 @@ static int store_aux(const char *key, const char *value, void *cb)
>  				return 1;
>  			}
>  
> -			store.offset[store.seen] = cf->ftell(cf);
> +			store.offset[store.seen] = cf->do_ftell(cf);
>  			store.seen++;
>  		}
>  		break;
> @@ -1223,19 +1223,19 @@ static int store_aux(const char *key, const char *value, void *cb)
>  		 * Do not increment matches: this is no match, but we
>  		 * just made sure we are in the desired section.
>  		 */
> -		store.offset[store.seen] = cf->ftell(cf);
> +		store.offset[store.seen] = cf->do_ftell(cf);
>  		/* fallthru */
>  	case SECTION_END_SEEN:
>  	case START:
>  		if (matches(key, value)) {
> -			store.offset[store.seen] = cf->ftell(cf);
> +			store.offset[store.seen] = cf->do_ftell(cf);
>  			store.state = KEY_SEEN;
>  			store.seen++;
>  		} else {
>  			if (strrchr(key, '.') - key == store.baselen &&
>  			      !strncmp(key, store.key, store.baselen)) {
>  					store.state = SECTION_SEEN;
> -					store.offset[store.seen] = cf->ftell(cf);
> +					store.offset[store.seen] = cf->do_ftell(cf);
>  			}
>  		}
>  	}

^ permalink raw reply	[flat|nested] 9+ messages in thread

end of thread, other threads:[~2013-08-27  4:39 UTC | newest]

Thread overview: 9+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2013-08-26 20:10 Issue with compiling git 1.8.4 under uclibc with gcc 4.6.3 Lance
2013-08-26 20:18 ` Lukas Fleischer
2013-08-26 20:29   ` Lance
2013-08-26 20:31     ` Lukas Fleischer
2013-08-26 20:59       ` Jeff King
2013-08-26 21:57         ` [PATCH] config: do not use C function names as struct members Jeff King
2013-08-27  0:56           ` Lukas Fleischer
2013-08-27  4:38           ` Junio C Hamano
2013-08-26 21:07       ` Issue with compiling git 1.8.4 under uclibc with gcc 4.6.3 Andreas Schwab

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).