Beefy Boxes and Bandwidth Generously Provided by pair Networks
No such thing as a small change
 
PerlMonks  

Why does $Config{ccflags} include "-fwrapv" on many gcc builds of perl ?

by syphilis (Archbishop)
on Apr 19, 2021 at 04:58 UTC ( [id://11131454]=perlquestion: print w/replies, xml ) Need Help??

syphilis has asked for the wisdom of the Perl Monks concerning the following question:

Hi,

The -fwrapv documentation states:
This option instructs the compiler to assume that signed arithmetic ov +erflow of addition, subtraction and multiplication wraps around using + twos-complement representation.
I thought that this was the usual (default) behaviour, anyway. And some quick experimentation I've done supports that notion.
So, why is the flag specified on so many gcc bulds of perl (eg Windows and Ubuntu) ?

Is it just a case of deciding that the perl flags might as well be open and specific about this ?
Perhaps -fwrapv is present simply to alert us to the fact that another option (-ftrapv) is available ? (Not that I think you'd want to build perl with -ftrapv)
Or are there actually cases where -fwrapv is not the gcc default ?

Cheers,
Rob

PS: For those curious, the -ftrapv documentation states:
This option generates traps for signed overflow on addition, subtracti +on, multiplication operations.
The documentation also points out that -ftrapv and -fwrapv override each other - ie, you can have one or the other, but not both.

Replies are listed 'Best First'.
Re: Why does $Config{ccflags} include "-fwrapv" on many gcc builds of perl ?
by dave_the_m (Monsignor) on Apr 19, 2021 at 06:31 UTC
    It was to fix this issue. I haven't read the ticket closely so can't otherwise comment.

    Dave.

      It was to fix this issue.

      Thanks Dave.
      I haven't managed to prove that the inclusion of -fwrapv achieves anything wrt perl, but there are some well credentialed perl developers saying that it does (or, at least, that it once did).
      I'm not about to start arguing the point with them.
      I guess, that if its inclusion does something useful then that's well and good. And if it doesn't do anything useful then it's harmless, anyway.

      Interesting that the -SvIVX(sv) is still present in sv.c, because I think it's still undefined behaviour when SvIVX(sv) is IV_MIN (aka LONG_MIN), even if -fwrapv is somehow masking it when perl is involved.
      UPDATE: The above sentence was incorrect. On reading the code properly (which involved minimal widening of my field of vision), I realize that -SvIVX(sv) is never reached if SvIVX(sv) is IV_MIN.

      I haven't yet found any evidence that, in C, that switch ever alters anything.
      $ cat LONG_MIN.c #include <stdio.h> #include <limits.h> int main(void) { printf("%ld %ld\n", LONG_MIN, -LONG_MIN); return 0; } $ gcc -o LONG_MIN LONG_MIN.c LONG_MIN.c: In function ‘main’: LONG_MIN.c:6:33: warning: integer overflow in expression ‘-92233720368 +54775808’ of type ‘long int’ results in ‘-9223372036854775808’ [-Wove +rflow] 6 | printf("%ld %ld\n", LONG_MIN, -LONG_MIN); | ^ $ ./LONG_MIN -9223372036854775808 -9223372036854775808
      The compilation warning relates only to "-LONG_MIN".
      It's exactly the same (in every respect) when I compile using the -fwrapv switch, and -ftrapv catches nothing.

      Cheers,
      Rob

        -fwrapv gives implementation defined behaviour for wrapping variables but not constants.

        #include <limits.h> #include <stdio.h> int main() { printf(" LONG_MIN %ld\n", LONG_MIN); printf(" LONG_MAX %ld\n", LONG_MAX); printf("-LONG_MAX %ld\n", -LONG_MIN); // line 9 long lval = LONG_MIN; lval = lval * -1; // this is okay with -fwrapv printf("wrap lval %ld\n", lval); }
        $ gcc -Wall -Wextra -Woverflow -fwrapv -fsanitize=undefined t.c -o t & +& ./t t.c: In function ‘main’: t.c:9:31: warning: integer overflow in expression ‘-922337203685477580 +8’ of type ‘long int’ results in ‘-9223372036854775808’ [-Woverflow] 9 | printf("-LONG_MAX %ld\n", -LONG_MIN); // line 9 | ^ LONG_MIN -9223372036854775808 LONG_MAX 9223372036854775807 -LONG_MAX -9223372036854775808 wrap lval 9223372036854775807

        I see that the patch fixes it by changing to unsigned int so it seems the wrapping is irrelevant there.

        In the past I've noted a lot of change for the sake of change. Not to say it is the case here, but that is the case nonetheless in bleed.

Log In?
Username:
Password:

What's my password?
Create A New User
Domain Nodelet?
Node Status?
node history
Node Type: perlquestion [id://11131454]
Front-paged by Corion
help
Chatterbox?
and the web crawler heard nothing...

How do I use this?Last hourOther CB clients
Other Users?
Others exploiting the Monastery: (4)
As of 2024-04-19 23:56 GMT
Sections?
Information?
Find Nodes?
Leftovers?
    Voting Booth?

    No recent polls found