eclipse-iceoryx / iceoryx

Eclipse iceoryx™ - true zero-copy inter-process-communication
https://iceoryx.io
Apache License 2.0
1.57k stars 373 forks source link

SingleProcess example crashes on QNX #2292

Open tangzhiqiang3 opened 1 month ago

tangzhiqiang3 commented 1 month ago

Required information

Operating system: qnx710

Compiler version: aarch64-unknown-nto-qnx7.0.0-gcc (GCC) 5.4.0 [qnx700 1391]

Eclipse iceoryx version: v2.0.6

Additional helpful information

If there is a core dump, please run the following command and add the output to the issue in a separate comment

# ./single_process
Process 2106478737 (single_process) terminated SIGSEGV code=1 fltno=11 ip=00000037e31baefc(/var/data/./single_process@main+0x0000000000000008) mapaddr=000000000000defc. ref=00000009f849f300
Memory fault (core dumped) 

This GDB was configured as "--host=x86_64-pc-linux-gnu --target=aarch64-unknown-nto-qnx7.0.0".
Type "show configuration" for configuration details.Find the GDB manual and other documentation resources online at:
<http://www.gnu.org/software/gdb/documentation/>.
For help, type "help".
Type "apropos word" to search for commands related to "word"...
Reading symbols from single_process...done.

warning: exec file is newer than core file.
[New pid 2106478737 tid 1]

warning: Could not load shared library symbols for 4 libraries, e.g. /var/data/prefix/lib/libiceoryx_platform.so.
Use the "info sharedlibrary" command to see the complete listing.
Do you need "set solib-search-path" or "set sysroot"?
Program terminated with signal SIGSEGV, Segmentation fault.
#0  0x00000037e31baefc in main () at single_process.cpp:112
112     {
(gdb) bt
#0  0x00000037e31baefc in main () at single_process.cpp:112
elBoberido commented 1 month ago

Hi @tangzhiqiang3

it looks like the example is using too much stack. On QNX the stack size of the main thread is only 512kB. I'm not sure if it also works on QNX but on Linux one can use ulimit -s unlimited to increase the stack size until the next reboot. Alternatively, you can put the component with huge memory demands on the heap

-- iox::roudi::IceOryxRouDiComponents roudiComponents(config);
-- iox::roudi::RouDi roudi(roudiComponents.rouDiMemoryManager, roudiComponents.portManager, config);
++ std::unique_ptr<iox::roudi::IceOryxRouDiComponents> roudiComponents{new iox::roudi::IceOryxRouDiComponents (config)};
++ iox::roudi::RouDi roudi(roudiComponents->rouDiMemoryManager, roudiComponents->portManager, config);

If this works, can you please create a pull request with these changes?

tangzhiqiang3 commented 1 month ago

Change to smart pointer or the same crash: Process 648306807 (single_process) terminated SIGSEGV code=1 fltno=11 ip=000000282c37b36c(/var/data/./single_process@main+0x0000000000000008) mapaddr=000000000000a36c. ref=0000001396f62d80 Memory fault (core dumped)

patch:

     iox::RouDiConfig_t defaultRouDiConfig = iox::RouDiConfig_t().setDefaults();
-    iox::roudi::IceOryxRouDiComponents roudiComponents(defaultRouDiConfig);
+    // iox::roudi::IceOryxRouDiComponents roudiComponents(defaultRouDiConfig);
+    std::unique_ptr<iox::roudi::IceOryxRouDiComponents> roudiComponents{new iox::roudi::IceOryxRouDiComponents(defaultRouDi
Config)};

     constexpr bool TERMINATE_APP_IN_ROUDI_DTOR_FLAG = false;
     iox::roudi::RouDi roudi(
-        roudiComponents.rouDiMemoryManager,
-        roudiComponents.portManager,
+        roudiComponents->rouDiMemoryManager,
+        roudiComponents->portManager,
         iox::roudi::RouDi::RoudiStartupParameters{iox::roudi::MonitoringMode::OFF, TERMINATE_APP_IN_ROUDI_DTOR_FLAG});
elBoberido commented 1 month ago

Oh, while the IceOryxRouDiComponents is the largest object with more than 1MB in size, the others are also quite large and in sum blow the stack up. I think you also need to move at least roudi (200kB) and runtime (420kB) to the heap with an unique_ptr. The config is only 62kB and should be fine on the stack.

Alternatively, if you don't want to use the heap, it would also be possible to place the objects into the data segment with

#include "iox/optional.hpp"
#include "iox/scoped_static.hpp"
// ...
static iox::optional<iox::roudi::IceOryxRouDiComponents> roudiComponents;
auto roudiComponentsGuard = iox::makeScopedStatic(roudiComponents, config);
elBoberido commented 1 month ago

@tangzhiqiang3 did this work for you?