Bug Report
What's the issue you encountered?
After recently updating my devkitARM/GBA environment, I started getting a runtime abort on GBA when copying a std::shared_ptr or when creating a std::weak_ptr from a std::shared_ptr.
I tested the same code with two devkitARM versions:
devkitARM r67: does not work
devkitARM r66: works
With devkitARM r67, the program aborts at runtime when the smart pointer reference counter is incremented. With devkitARM r66, the same code runs correctly.
The issue does not depend on Butano. The examples below are plain C++ GBA tests using only the mGBA debug log registers.
How can the issue be reproduced?
Create a C++ source file, for example main.cpp, and compile it for GBA with devkitARM.
Common mGBA logging helper
// mgba_log.hpp
#pragma once
#include <cstdint>
namespace mgba {
inline void log(const char* message) {
volatile uint16_t& debug_enable_register =
*reinterpret_cast<volatile uint16_t*>(0x04FFF780);
debug_enable_register = 0xC0DE;
constexpr int max_characters_per_line = 256;
const char* message_data = message;
while(*message_data) {
int characters_to_write = 0;
volatile char* debug_string_register =
reinterpret_cast<volatile char*>(0x04FFF600);
while(message_data[characters_to_write] &&
characters_to_write < max_characters_per_line) {
debug_string_register[characters_to_write] =
message_data[characters_to_write];
++characters_to_write;
}
debug_string_register[characters_to_write] = '\0';
volatile uint16_t& debug_flags_register =
*reinterpret_cast<volatile uint16_t*>(0x04FFF700);
debug_flags_register = uint16_t(2) | 0x100;
message_data += characters_to_write;
}
}
inline void log_bool(bool value) {
log(value ? "1" : "0");
}
}
Test 1: gthread state
// main.cpp
#include "mgba_log.hpp"
#include <bits/gthr.h>
#include <ext/atomicity.h>
void test_gthread_state() {
#ifdef __GTHREADS
mgba::log("__GTHREADS defined");
mgba::log("__gthread_active_p =");
mgba::log_bool(__gthread_active_p());
#else
mgba::log("__GTHREADS not defined");
#endif
mgba::log("__is_single_threaded =");
mgba::log_bool(__gnu_cxx::__is_single_threaded());
}
int main() {
mgba::log("program start");
test_gthread_state();
mgba::log("program end");
while(true) {
}
}
With devkitARM r67, I get:
program start
__GTHREADS defined
__gthread_active_p =
1
__is_single_threaded =
0
program end
With devkitARM r66, I get:
program start
__GTHREADS defined
__gthread_active_p =
0
__is_single_threaded =
1
program end
Test 2: std::shared_ptr copy
// main.cpp
#include "mgba_log.hpp"
#include <memory>
void test_shared_ptr_copy() {
mgba::log("sp make");
std::shared_ptr<int> original_ptr = std::make_shared<int>(123);
mgba::log("sp copy before");
// Runtime abort happens here with devkitARM r67.
std::shared_ptr<int> copied_ptr = original_ptr;
mgba::log("sp copy after");
}
int main() {
mgba::log("program start");
test_shared_ptr_copy();
mgba::log("program end");
while(true) {
}
}
With devkitARM r67, the output is:
program start
sp make
sp copy before
So std::make_shared<int>(123) succeeds, but copying the resulting std::shared_ptr aborts.
With devkitARM r66, the same test works:
program start
sp make
sp copy before
sp copy after
program end
Environment?
arm-none-eabi-g++ (devkitARM) 15.2.0
Additional context?
I do not know the exact cause yet, but my initial tests suggest that the smart pointer reference counter may no longer be using the single-threaded path in the r67 devkitARM/libstdc++ build.
Could this be related to the unified buildscript or the libstdc++/gthreads configuration used to build devkitARM r67?
5124435#diff-e472a28f68a79d6f66e4b0f10d1c63e24de38e6eda838e695101a44967efafa1
This change could be related :
--enable-threads --disable-win32-registry --disable-nls --disable-debug
into
--enable-threads=posix --disable-win32-registry --disable-nls --disable-debug \
Bug Report
What's the issue you encountered?
After recently updating my devkitARM/GBA environment, I started getting a runtime abort on GBA when copying a
std::shared_ptror when creating astd::weak_ptrfrom astd::shared_ptr.I tested the same code with two devkitARM versions:
With devkitARM r67, the program aborts at runtime when the smart pointer reference counter is incremented. With devkitARM r66, the same code runs correctly.
The issue does not depend on Butano. The examples below are plain C++ GBA tests using only the mGBA debug log registers.
How can the issue be reproduced?
Create a C++ source file, for example
main.cpp, and compile it for GBA with devkitARM.Common mGBA logging helper
Test 1: gthread state
With devkitARM r67, I get:
With devkitARM r66, I get:
Test 2:
std::shared_ptrcopyWith devkitARM r67, the output is:
So
std::make_shared<int>(123)succeeds, but copying the resultingstd::shared_ptraborts.With devkitARM r66, the same test works:
Environment?
Host OS: Windows
Shell: devkitPro MSYS2 shell
Official release or unofficial/self-compiled build:
Current compiler:
Additional context?
I do not know the exact cause yet, but my initial tests suggest that the smart pointer reference counter may no longer be using the single-threaded path in the r67 devkitARM/libstdc++ build.
Could this be related to the unified buildscript or the libstdc++/gthreads configuration used to build devkitARM r67?
5124435#diff-e472a28f68a79d6f66e4b0f10d1c63e24de38e6eda838e695101a44967efafa1
This change could be related :
--enable-threads --disable-win32-registry --disable-nls --disable-debug
into
--enable-threads=posix --disable-win32-registry --disable-nls --disable-debug \