public inbox for gcc-bugs@sourceware.org
help / color / mirror / Atom feed
* [Bug c/111708] New: Calling external global function instead of local static function.
@ 2023-10-05 17:47 k.frolov at samsung dot com
  2023-10-05 18:08 ` [Bug c/111708] " pinskia at gcc dot gnu.org
                   ` (10 more replies)
  0 siblings, 11 replies; 12+ messages in thread
From: k.frolov at samsung dot com @ 2023-10-05 17:47 UTC (permalink / raw)
  To: gcc-bugs

https://gcc.gnu.org/bugzilla/show_bug.cgi?id=111708

            Bug ID: 111708
           Summary: Calling external global function instead of local
                    static function.
           Product: gcc
           Version: 14.0
            Status: UNCONFIRMED
          Severity: normal
          Priority: P3
         Component: c
          Assignee: unassigned at gcc dot gnu.org
          Reporter: k.frolov at samsung dot com
  Target Milestone: ---

I have a test case, in which as I believe GCC compiler must call local static
function but not external function instead. This test case work as I expect
with clang compiler, with gcc in C++ mode, but in C mode I have strange
behaviour when gcc tries to call external function instead of already defined
local function with same name.

The problem is reproducible with any available GCC version, starting from GCC
4.1 and ending with current trunk.

The problem is independend from the target platform and reproducible when
generating code for any platform. In following examples aarch64 is used as
target platform.

The problem depends on optimization options: with option "-O0" compiler
behaviour changes (see below).

///// Test code (.c source):

static int f(int);

int main(int argc, const char *argv[])
{
    (void)argv;
    return f(argc);
}

static int f(int f)
{
    int x = f;
    {
        int f(int);

        if (x < 1)
            return 0;
        else
            return f(x - 1);
    }
}

//// end of test source.

Code compiled with the following compiler options: 

-std=c99 -Wall -Wextra -fstrict-aliasing -Wcast-align -Os

With the following compilator options clang and gcc in C++ mode (with command
line option "-x c") produces same output:

main:
        mov     w0, 0
        ret

GCC in C mode produces following output:

main:
        cmp     w0, 0
        ble     .L2
        sub     w0, w0, #1
        b       f
.L2:
        mov     w0, 0
        ret

Where "f" is some unknown and global symbol.

With optimization turned off, following code is generated by GCC in C-mode:

        .global main
        .type   main, %function
main:
        stp     x29, x30, [sp, -32]!
        mov     x29, sp
        str     w0, [sp, 28]
        str     x1, [sp, 16]
        ldr     w0, [sp, 28]
        bl      f
        ldp     x29, x30, [sp], 32
        ret

        .type   f, %function
f:
        stp     x29, x30, [sp, -48]!
        mov     x29, sp
        str     w0, [sp, 28]
        ldr     w0, [sp, 28]
        str     w0, [sp, 44]
        ldr     w0, [sp, 44]
        cmp     w0, 0
        bgt     .L4
        mov     w0, 0
        b       .L5
.L4:
        ldr     w0, [sp, 44]
        sub     w0, w0, #1
        bl      f
.L5:
        ldp     x29, x30, [sp], 48
        ret


As you see, external symbol "f" is not referenced anymore, as compiler defines
"f" function by itself. Please note, there is neither ".local" nor ".global"
instruction for fuction "f". 

Code generated with "-O0" in C mode is (almost, differencies exist due to
symbol mangling) same as code generated with "-O0" in C++ mode. 

Link to godbolt site demonstrating the effect: https://godbolt.org/z/7d9GG8KvY

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

* [Bug c/111708] Calling external global function instead of local static function.
  2023-10-05 17:47 [Bug c/111708] New: Calling external global function instead of local static function k.frolov at samsung dot com
@ 2023-10-05 18:08 ` pinskia at gcc dot gnu.org
  2023-10-05 18:12 ` pinskia at gcc dot gnu.org
                   ` (9 subsequent siblings)
  10 siblings, 0 replies; 12+ messages in thread
From: pinskia at gcc dot gnu.org @ 2023-10-05 18:08 UTC (permalink / raw)
  To: gcc-bugs

https://gcc.gnu.org/bugzilla/show_bug.cgi?id=111708

Andrew Pinski <pinskia at gcc dot gnu.org> changed:

           What    |Removed                     |Added
----------------------------------------------------------------------------
           See Also|                            |https://gcc.gnu.org/bugzill
                   |                            |a/show_bug.cgi?id=90472

--- Comment #1 from Andrew Pinski <pinskia at gcc dot gnu.org> ---
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=90472#c3

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

* [Bug c/111708] Calling external global function instead of local static function.
  2023-10-05 17:47 [Bug c/111708] New: Calling external global function instead of local static function k.frolov at samsung dot com
  2023-10-05 18:08 ` [Bug c/111708] " pinskia at gcc dot gnu.org
@ 2023-10-05 18:12 ` pinskia at gcc dot gnu.org
  2023-10-06 11:56 ` k.frolov at samsung dot com
                   ` (8 subsequent siblings)
  10 siblings, 0 replies; 12+ messages in thread
From: pinskia at gcc dot gnu.org @ 2023-10-05 18:12 UTC (permalink / raw)
  To: gcc-bugs

https://gcc.gnu.org/bugzilla/show_bug.cgi?id=111708

--- Comment #2 from Andrew Pinski <pinskia at gcc dot gnu.org> ---
Note ICC rejects this as invalid:
```
<source>(14): error #172: external/internal linkage conflict with previous
declaration at line 10
          int f(int);
              ^
```

Which is what I had expected to happen similar to variables as PR 90472 rejects
variable declarations too.

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

* [Bug c/111708] Calling external global function instead of local static function.
  2023-10-05 17:47 [Bug c/111708] New: Calling external global function instead of local static function k.frolov at samsung dot com
  2023-10-05 18:08 ` [Bug c/111708] " pinskia at gcc dot gnu.org
  2023-10-05 18:12 ` pinskia at gcc dot gnu.org
@ 2023-10-06 11:56 ` k.frolov at samsung dot com
  2023-10-06 12:14 ` k.frolov at samsung dot com
                   ` (7 subsequent siblings)
  10 siblings, 0 replies; 12+ messages in thread
From: k.frolov at samsung dot com @ 2023-10-06 11:56 UTC (permalink / raw)
  To: gcc-bugs

https://gcc.gnu.org/bugzilla/show_bug.cgi?id=111708

--- Comment #3 from Kirill Frolov <k.frolov at samsung dot com> ---
Looks like example demonstrates undefined behaviour. This article 
(https://wiki.sei.cmu.edu/confluence/display/c/DCL36-C.+Do+not+declare+an+identifier+with+conflicting+linkage+classifications)
contains table, which shows that I can use "extern" keyword in second
declaration to refer symbol with internal linkage. So I fixed the
source:

static int f(int);

int main(int argc, const char *argv[])
{
    (void)argv;
    return f(argc);
}

static int f(int f)
{
    int x = f;
    {
        extern int f(int);

        if (x < 1)
            return 0;
        else
            return f(x - 1);
    }
}

The problem still persist.  See an example: https://godbolt.org/z/reGbM67Kj
GCC still references external function "f", but I expect that internal function
must be referenced instead.

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

* [Bug c/111708] Calling external global function instead of local static function.
  2023-10-05 17:47 [Bug c/111708] New: Calling external global function instead of local static function k.frolov at samsung dot com
                   ` (2 preceding siblings ...)
  2023-10-06 11:56 ` k.frolov at samsung dot com
@ 2023-10-06 12:14 ` k.frolov at samsung dot com
  2023-10-06 12:32 ` k.frolov at samsung dot com
                   ` (6 subsequent siblings)
  10 siblings, 0 replies; 12+ messages in thread
From: k.frolov at samsung dot com @ 2023-10-06 12:14 UTC (permalink / raw)
  To: gcc-bugs

https://gcc.gnu.org/bugzilla/show_bug.cgi?id=111708

--- Comment #4 from Kirill Frolov <k.frolov at samsung dot com> ---
With updated source ICC still gives an error. 
MSVC works from my point of view correcly, same as Clang.

Lets see to a C-standard
(https://files.lhmouse.com/standards/ISO%20C%20N2176.pdf),
section 6.2.2 states that:

| 4) For an identifier declared with the storage-class specifier extern
| in a scope in which a prior declaration of that identifier is visible [31]
| if the prior declaration specifies internal or external linkage,
| the linkage of the identifier at the later declaration is the same as
| the linkage specified at the prior declaration. If no prior declaration
| _is_ _visible_, or if the prior declaration specifies no linkage, then the
| identifier has external linkage.

| [31] As specified in 6.2.1, the later declaration might hide the
| prior declaration.

Lets see section 6.2.1:

| 4) ... Within the inner scope, the identifier designates the entity
|   declared in the inner scope; the entity declared in the outer scope
|   is hidden (and _not_ _visible_) within the inner scope.

As a result, I must conclude that GCC generates code right, but
Clang, MSVC and ICC works incorrectly. But this happens with "-Os"
options.

With "-O0" option GCC generates _wrong_ _code_, as it avoids calling
of _external_ function (https://godbolt.org/z/6GbPdc9vT):

main:
        push    rbp
        mov     rbp, rsp
        sub     rsp, 16
        mov     DWORD PTR [rbp-4], edi
        mov     QWORD PTR [rbp-16], rsi
        mov     eax, DWORD PTR [rbp-4]
        mov     edi, eax
        call    f
        leave
        ret
f:
        push    rbp
        mov     rbp, rsp
        sub     rsp, 32
        mov     DWORD PTR [rbp-20], edi
        mov     eax, DWORD PTR [rbp-20]
        mov     DWORD PTR [rbp-4], eax
        cmp     DWORD PTR [rbp-4], 0
        jg      .L4
        mov     eax, 0
        jmp     .L5
.L4:
        mov     eax, DWORD PTR [rbp-4]
        sub     eax, 1
        mov     edi, eax
        call    f
.L5:
        leave
        ret

In any case, GCC generated different code with -O0 and -Os, and such behaviour
is definitely a bug.

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

* [Bug c/111708] Calling external global function instead of local static function.
  2023-10-05 17:47 [Bug c/111708] New: Calling external global function instead of local static function k.frolov at samsung dot com
                   ` (3 preceding siblings ...)
  2023-10-06 12:14 ` k.frolov at samsung dot com
@ 2023-10-06 12:32 ` k.frolov at samsung dot com
  2023-10-08  8:36 ` muecker at gwdg dot de
                   ` (5 subsequent siblings)
  10 siblings, 0 replies; 12+ messages in thread
From: k.frolov at samsung dot com @ 2023-10-06 12:32 UTC (permalink / raw)
  To: gcc-bugs

https://gcc.gnu.org/bugzilla/show_bug.cgi?id=111708

--- Comment #5 from Kirill Frolov <k.frolov at samsung dot com> ---
C standard states,that:

6.2.2 Linkages of identifiers

7) If, within a translation unit, the same identifier appears with both
internal and external linkage, the behavior is undefined. 

So, I think only ICC has adequate behaviour. Other compilers miss at least
warning message.

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

* [Bug c/111708] Calling external global function instead of local static function.
  2023-10-05 17:47 [Bug c/111708] New: Calling external global function instead of local static function k.frolov at samsung dot com
                   ` (4 preceding siblings ...)
  2023-10-06 12:32 ` k.frolov at samsung dot com
@ 2023-10-08  8:36 ` muecker at gwdg dot de
  2023-10-08 18:19 ` muecker at gwdg dot de
                   ` (4 subsequent siblings)
  10 siblings, 0 replies; 12+ messages in thread
From: muecker at gwdg dot de @ 2023-10-08  8:36 UTC (permalink / raw)
  To: gcc-bugs

https://gcc.gnu.org/bugzilla/show_bug.cgi?id=111708

Martin Uecker <muecker at gwdg dot de> changed:

           What    |Removed                     |Added
----------------------------------------------------------------------------
                 CC|                            |muecker at gwdg dot de

--- Comment #6 from Martin Uecker <muecker at gwdg dot de> ---

I think your nested declaration of "extern int f(int);" has external linkage,
because the declaration with internal linkage is not visible (it is hidden by
the definition of the object with no linkage). So I agree this is compile-time
UB and we miss the warning which we have for objects.

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

* [Bug c/111708] Calling external global function instead of local static function.
  2023-10-05 17:47 [Bug c/111708] New: Calling external global function instead of local static function k.frolov at samsung dot com
                   ` (5 preceding siblings ...)
  2023-10-08  8:36 ` muecker at gwdg dot de
@ 2023-10-08 18:19 ` muecker at gwdg dot de
  2023-10-14 12:43 ` muecker at gwdg dot de
                   ` (3 subsequent siblings)
  10 siblings, 0 replies; 12+ messages in thread
From: muecker at gwdg dot de @ 2023-10-08 18:19 UTC (permalink / raw)
  To: gcc-bugs

https://gcc.gnu.org/bugzilla/show_bug.cgi?id=111708

--- Comment #7 from Martin Uecker <muecker at gwdg dot de> ---
Created attachment 56075
  --> https://gcc.gnu.org/bugzilla/attachment.cgi?id=56075&action=edit
patch adding error external / internal mismatch of functions


Untested patch.

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

* [Bug c/111708] Calling external global function instead of local static function.
  2023-10-05 17:47 [Bug c/111708] New: Calling external global function instead of local static function k.frolov at samsung dot com
                   ` (6 preceding siblings ...)
  2023-10-08 18:19 ` muecker at gwdg dot de
@ 2023-10-14 12:43 ` muecker at gwdg dot de
  2023-10-17 18:19 ` cvs-commit at gcc dot gnu.org
                   ` (2 subsequent siblings)
  10 siblings, 0 replies; 12+ messages in thread
From: muecker at gwdg dot de @ 2023-10-14 12:43 UTC (permalink / raw)
  To: gcc-bugs

https://gcc.gnu.org/bugzilla/show_bug.cgi?id=111708

--- Comment #8 from Martin Uecker <muecker at gwdg dot de> ---
PATCH: https://gcc.gnu.org/pipermail/gcc-patches/2023-October/632999.html

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

* [Bug c/111708] Calling external global function instead of local static function.
  2023-10-05 17:47 [Bug c/111708] New: Calling external global function instead of local static function k.frolov at samsung dot com
                   ` (7 preceding siblings ...)
  2023-10-14 12:43 ` muecker at gwdg dot de
@ 2023-10-17 18:19 ` cvs-commit at gcc dot gnu.org
  2023-11-03 19:14 ` uecker at gcc dot gnu.org
  2023-12-17 20:51 ` pinskia at gcc dot gnu.org
  10 siblings, 0 replies; 12+ messages in thread
From: cvs-commit at gcc dot gnu.org @ 2023-10-17 18:19 UTC (permalink / raw)
  To: gcc-bugs

https://gcc.gnu.org/bugzilla/show_bug.cgi?id=111708

--- Comment #9 from CVS Commits <cvs-commit at gcc dot gnu.org> ---
The master branch has been updated by Martin Uecker <uecker@gcc.gnu.org>:

https://gcc.gnu.org/g:1f186f64b8602d74769af4a6250255e51227f744

commit r14-4689-g1f186f64b8602d74769af4a6250255e51227f744
Author: Martin Uecker <uecker@tugraz.at>
Date:   Sat Oct 14 09:09:07 2023 +0200

    c: error for function with external and internal linkage [PR111708]

    Declaring a function with both external and internal linkage
    in the same TU is translation-time UB.  Add an error for this
    case as already done for objects.

            PR c/111708

    gcc/c/ChangeLog:

            * c-decl.cc (grokdeclarator): Add error.

    gcc/testsuite/ChangeLog:

            * gcc.dg/pr111708-1.c: New test.
            * gcc.dg/pr111708-2.c: New test.

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

* [Bug c/111708] Calling external global function instead of local static function.
  2023-10-05 17:47 [Bug c/111708] New: Calling external global function instead of local static function k.frolov at samsung dot com
                   ` (8 preceding siblings ...)
  2023-10-17 18:19 ` cvs-commit at gcc dot gnu.org
@ 2023-11-03 19:14 ` uecker at gcc dot gnu.org
  2023-12-17 20:51 ` pinskia at gcc dot gnu.org
  10 siblings, 0 replies; 12+ messages in thread
From: uecker at gcc dot gnu.org @ 2023-11-03 19:14 UTC (permalink / raw)
  To: gcc-bugs

https://gcc.gnu.org/bugzilla/show_bug.cgi?id=111708

uecker at gcc dot gnu.org changed:

           What    |Removed                     |Added
----------------------------------------------------------------------------
             Status|UNCONFIRMED                 |RESOLVED
                 CC|                            |uecker at gcc dot gnu.org
      Known to work|                            |14.0
         Resolution|---                         |FIXED
   Target Milestone|---                         |14.0
      Known to fail|                            |4.1.2

--- Comment #10 from uecker at gcc dot gnu.org ---
Fixed on trunk.

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

* [Bug c/111708] Calling external global function instead of local static function.
  2023-10-05 17:47 [Bug c/111708] New: Calling external global function instead of local static function k.frolov at samsung dot com
                   ` (9 preceding siblings ...)
  2023-11-03 19:14 ` uecker at gcc dot gnu.org
@ 2023-12-17 20:51 ` pinskia at gcc dot gnu.org
  10 siblings, 0 replies; 12+ messages in thread
From: pinskia at gcc dot gnu.org @ 2023-12-17 20:51 UTC (permalink / raw)
  To: gcc-bugs

https://gcc.gnu.org/bugzilla/show_bug.cgi?id=111708

Andrew Pinski <pinskia at gcc dot gnu.org> changed:

           What    |Removed                     |Added
----------------------------------------------------------------------------
                 CC|                            |cookevillain at yahoo dot com

--- Comment #11 from Andrew Pinski <pinskia at gcc dot gnu.org> ---
*** Bug 55422 has been marked as a duplicate of this bug. ***

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

end of thread, other threads:[~2023-12-17 20:51 UTC | newest]

Thread overview: 12+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2023-10-05 17:47 [Bug c/111708] New: Calling external global function instead of local static function k.frolov at samsung dot com
2023-10-05 18:08 ` [Bug c/111708] " pinskia at gcc dot gnu.org
2023-10-05 18:12 ` pinskia at gcc dot gnu.org
2023-10-06 11:56 ` k.frolov at samsung dot com
2023-10-06 12:14 ` k.frolov at samsung dot com
2023-10-06 12:32 ` k.frolov at samsung dot com
2023-10-08  8:36 ` muecker at gwdg dot de
2023-10-08 18:19 ` muecker at gwdg dot de
2023-10-14 12:43 ` muecker at gwdg dot de
2023-10-17 18:19 ` cvs-commit at gcc dot gnu.org
2023-11-03 19:14 ` uecker at gcc dot gnu.org
2023-12-17 20:51 ` pinskia at gcc dot gnu.org

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 read-only IMAP folder(s) and NNTP newsgroup(s).