public inbox for gcc-bugs@sourceware.org
help / color / mirror / Atom feed
* [Bug c/102452] New: Structs with flexible array members are not optimized on stack
@ 2021-09-22 13:22 peter at peterzhu dot ca
  2021-09-22 17:49 ` [Bug ipa/102452] " pinskia at gcc dot gnu.org
                   ` (5 more replies)
  0 siblings, 6 replies; 7+ messages in thread
From: peter at peterzhu dot ca @ 2021-09-22 13:22 UTC (permalink / raw)
  To: gcc-bugs

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

            Bug ID: 102452
           Summary: Structs with flexible array members are not optimized
                    on stack
           Product: gcc
           Version: 9.3.0
            Status: UNCONFIRMED
          Severity: normal
          Priority: P3
         Component: c
          Assignee: unassigned at gcc dot gnu.org
          Reporter: peter at peterzhu dot ca
  Target Milestone: ---

Created attachment 51494
  --> https://gcc.gnu.org/bugzilla/attachment.cgi?id=51494&action=edit
test.c

Structs with flexible array members are not optimized on the stack. Testing
with the test.c file shown below (which outputs the runtime in seconds), we see
that the compiled program is significantly slower when the struct has a
flexible array member than when it does not. This was tested on GCC 9.3.0 and
10.3.0 on Ubuntu 20.04.

$ gcc -O3 test.c
$ ./a.out
0.302769
$ gcc -O3 -DUSE_FLEX_ARR=1 test.c
$ ./a.out
0.728760

clang does not have this issue.

$ clang -O3 test.c
$ ./a.out
0.312194
$ clang -O3 -DUSE_FLEX_ARR=1 test.c
$ ./a.out
0.301175

This is what test.c looks like:

#include <stdlib.h>
#include <stdio.h>
#include <time.h>
#include <string.h>

struct Test {
    long is_a;
    union {
        struct {
            long one;
            long two;
            long three;
        } a;
        struct {
            int one;
            int two;
            int three;
            int four;
#if USE_FLEX_ARR
            char arr[];
#endif
        } b;
    } as;
};

#define COUNT 100000000

static inline struct Test make_test_a(struct Test *test)
{
    if (test->is_a) {
        return *test;
    } else {
        struct Test ret;
        ret.as.a.one = test->as.b.one;
        ret.as.a.two = test->as.b.two;
        ret.as.a.three = test->as.b.three;
        return ret;
    }
}

/* This function should be optimized to not allocate struct Test on the stack
 * since it only uses attribute "three". */
static inline long get_three(struct Test *test)
{
    return make_test_a(test).as.a.three;
}

int main(int argc, char *argv[])
{
    struct timespec start, end;

    struct Test *mem = malloc(sizeof(struct Test) * COUNT);
    memset(mem, 0, sizeof(struct Test) * COUNT);

    clock_gettime(CLOCK_MONOTONIC, &start);
    {
        for (int i = 0; i < COUNT; i++) {
            long three = get_three(&mem[i]);
            if (three) {
                /* Impossible case. */
                printf("what\n");
            }
        }
    }
    clock_gettime(CLOCK_MONOTONIC, &end);

    double time = (end.tv_sec - start.tv_sec) + (end.tv_nsec - start.tv_nsec) /
1000000000.0;
    printf("%f\n", time);

    return 0;
}

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

end of thread, other threads:[~2021-09-23  7:21 UTC | newest]

Thread overview: 7+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2021-09-22 13:22 [Bug c/102452] New: Structs with flexible array members are not optimized on stack peter at peterzhu dot ca
2021-09-22 17:49 ` [Bug ipa/102452] " pinskia at gcc dot gnu.org
2021-09-23  6:42 ` rguenth at gcc dot gnu.org
2021-09-23  6:57 ` pinskia at gcc dot gnu.org
2021-09-23  7:05 ` [Bug tree-optimization/102452] " pinskia at gcc dot gnu.org
2021-09-23  7:16 ` rguenther at suse dot de
2021-09-23  7:21 ` rguenther at suse dot de

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).