C ++: Cra sh при компиляции с g cc 9.1, 9.2 с любым уровнем оптимизации - PullRequest
1 голос
/ 12 февраля 2020

Следующий код вылетает при компиляции с g cc .9.1 и 9.2. Если скомпилирован с более старым g cc все в порядке.

#include <cstdlib>

struct A
{
    A()
    {
        set( nullptr );
    }

    std::ptrdiff_t offset_;

    void set( void* ptr )
    { 
        offset_ = reinterpret_cast<char*>( ptr ) - reinterpret_cast<char*>( this );
    }

    void* get()
    {
        return reinterpret_cast<char*>( this ) + offset_;
    }
};

int main()
{
    A a;

    int *b = static_cast<int*>( a.get() );

    if( !b )
        a.set( b = new int{ 10 } );

    return *b;
}

Ссылка на код на coliru: http://coliru.stacked-crooked.com/a/3f5b4623a98fd0b5

Глядя на ассемблер вижу что g cc исключает оператор if. Ссылка на крестик: https://godbolt.org/z/HrX3Uc

Итак, вопрос: это ошибка в g cc, о которой нужно сообщить, или моя программа содержит некоторое UB?

1 Ответ

0 голосов
/ 25 февраля 2020
struct A
{
    A()
    {
        set( this );
    }

    std::ptrdiff_t offset_;

    void set( void* ptr )
    { 
        offset_ = reinterpret_cast<char*>( this ) - reinterpret_cast<char*>( ptr );
    }
    bool hasValue()
    {
        return offset_ != 0;
    }
    void* get()
    {
        return reinterpret_cast<char*>( this ) - offset_;
    }
};

int main()
{
    A a;

    int *b = static_cast<int*>( a.get() );

    // nullptr != 0
    if(!a.hasValue())
        a.set( b = new int{ 10 } );

    return *b;
}
...