reinterpret_cast, char * и неопределенное поведение

Каковы случаи, когдаreinterpret_castвchar* (или жеchar[N]) неопределенное поведение, и когда это определенное поведение? Какое эмпирическое правило я должен использовать, чтобы ответить на этот вопрос?

Как мы узнали изэтот вопрос, следующее неопределенное поведение:

alignas(int) char data[sizeof(int)];
int *myInt = new (data) int;           // OK
*myInt = 34;                           // OK
int i = *reinterpret_cast<int*>(data); // <== UB! have to use std::launder

Но в какой момент мы можем сделатьreinterpret_cast наchar массив и он НЕ будет неопределенным поведением? Вот несколько простых примеров:

нетnew, простоreinterpret_cast:

alignas(int) char data[sizeof(int)];
*reinterpret_cast<int*>(data) = 42;    // is the first cast write UB?
int i = *reinterpret_cast<int*>(data); // how about a read?
*reinterpret_cast<int*>(data) = 4;     // how about the second write?
int j = *reinterpret_cast<int*>(data); // or the second read?

Когда срок службы дляint Начните? Это с декларациейdata? Если да, то когдаdata конец?

Что, еслиdata были указатели?

char* data_ptr = new char[sizeof(int)];
*reinterpret_cast<int*>(data_ptr) = 4;     // is this UB?
int i = *reinterpret_cast<int*>(data_ptr); // how about the read?

Что, если я просто получаю структуры на проводе и хочу условно привести их на основе первого байта?

// bunch of handle functions that do stuff with the members of these types
void handle(MsgType1 const& );
void handle(MsgTypeF const& );

char buffer[100]; 
::recv(some_socket, buffer, 100)

switch (buffer[0]) {
case '1':
    handle(*reinterpret_cast<MsgType1*>(buffer)); // is this UB?
    break;
case 'F':
    handle(*reinterpret_cast<MsgTypeF*>(buffer));
    break;
// ...
}

Являются ли какие-либо из этих случаев UB? Все ли они? Меняется ли ответ на этот вопрос между C ++ 11 и C ++ 1z?

Ответы на вопрос(1)

Ваш ответ на вопрос