Skip to content

Fatal segfault crash when using ImPlot or ImNodes #114

@DragonMaster14545

Description

@DragonMaster14545

Hi, I just wanted to start using this lib, but Im getting fatal sefaults left and right. I don't really have a lot of experience with raw rendering, but I wanted to try, so I just took the SDL3 OpenGl example. That worked fine. But, as soon as I want to render anything using ImPlot or ImNodes, the program insta crashes with sefault. I have no idea why. Below you find the code. I left it as near to the original example as possible. I use the newest version of all deps.

I tried finding out more using gdb, but all I got was the following:

#0  0x00007fbead68b2a0 in ImPlot::BeginPlot(char const*, ImVec2 const&, int) () from /mnt/shared/programming/TheInfinityGame/TestApplications/ImGui copy/bin/Debug/net8.0/cimplot.so
#1  0x00007fbead6663ec in ImPlot_BeginPlot () from /mnt/shared/programming/TheInfinityGame/TestApplications/ImGui copy/bin/Debug/net8.0/cimplot.so
#2  0x00007fff78d4bcd2 in ?? ()
#3  0x0000000000f11c41 in ?? ()
#4  0x00007ffff766d8a8 in vtable for InlinedCallFrame () from /usr/share/dotnet/shared/Microsoft.NETCore.App/8.0.22/libcoreclr.so
#5  0xffffffffffffffff in ?? ()
#6  0x0000000000000000 in ?? ()

Not that helpful. Im on linux manjaro (Arch based) if that helps. I also searched for a similar problem in the other issues, but couldn't find anything. I hope this is fixable. Thanks a lot in advance.
Btw, why is the whole api basically unsave using pointers? Why not use normal c# types?

// See https://aka.ms/new-console-template for more information
using Hexa.NET.ImGui;
using Hexa.NET.ImPlot;
using Hexa.NET.ImGui.Backends.OpenGL3;
using Hexa.NET.ImGui.Backends.SDL3;
using Hexa.NET.OpenGL;
using Hexa.NET.SDL3;
using SDLEvent = Hexa.NET.SDL3.SDLEvent;
using SDLWindow = Hexa.NET.SDL3.SDLWindow;

SDL.SetHint(SDL.SDL_HINT_MOUSE_FOCUS_CLICKTHROUGH, "1");
SDL.Init(SDLInitFlags.Events | SDLInitFlags.Video);

double[] values = {1.0, 3.0, 50};

unsafe
{
    float main_scale = SDL.GetDisplayContentScale(SDL.GetPrimaryDisplay());
    var window = SDL.CreateWindow("Test Window", (int)(1280 * main_scale), (int)(720 * main_scale), SDLWindowFlags.Resizable | SDLWindowFlags.Opengl | SDLWindowFlags.HighPixelDensity);
    var windowId = SDL.GetWindowID(window);

    var guiContext = ImGui.CreateContext();
    ImGui.SetCurrentContext(guiContext);

	ImPlot.SetImGuiContext(guiContext);
    var plotContext = ImPlot.CreateContext();
    ImPlot.SetCurrentContext(plotContext);

    // Setup ImGui config.
    var io = ImGui.GetIO();
    io.ConfigFlags |= ImGuiConfigFlags.NavEnableKeyboard;     // Enable Keyboard Controls
    io.ConfigFlags |= ImGuiConfigFlags.NavEnableGamepad;      // Enable Gamepad Controls
    io.ConfigFlags |= ImGuiConfigFlags.DockingEnable;         // Enable Docking
    io.ConfigFlags |= ImGuiConfigFlags.ViewportsEnable;       // Enable Multi-Viewport / Platform Windows
    io.ConfigViewportsNoAutoMerge = false;
    io.ConfigViewportsNoTaskBarIcon = false;

    var style = ImGui.GetStyle();
    style.ScaleAllSizes(main_scale);        // Bake a fixed style scale. (until we have a solution for dynamic style scaling, changing this requires resetting Style + calling this again)
    style.FontScaleDpi = main_scale;        // Set initial font scale. (using io.ConfigDpiScaleFonts=true makes this unnecessary. We leave both here for documentation purpose)
    io.ConfigDpiScaleFonts = true;          // [Experimental] Automatically overwrite style.FontScaleDpi in Begin() when Monitor DPI changes. This will scale fonts but _NOT_ scale sizes/padding for now.
    io.ConfigDpiScaleViewports = true;

    var context = SDL.GLCreateContext(window);

    ImGuiImplSDL3.SetCurrentContext(guiContext);
    if (!ImGuiImplSDL3.InitForOpenGL(new SDLWindowPtr((Hexa.NET.ImGui.Backends.SDL3.SDLWindow*)window), (void*)context.Handle))
    {
        Console.WriteLine("Failed to init ImGui Impl SDL3");
        SDL.Quit();
        return;
    }

    ImGuiImplOpenGL3.SetCurrentContext(guiContext);
    if (!ImGuiImplOpenGL3.Init((byte*)null))
    {
        Console.WriteLine("Failed to init ImGui Impl OpenGL3");
        SDL.Quit();
        return;
    }

    GL GL = new(new BindingsContext(window, context));

    SDLEvent sdlEvent = default;
    bool exiting = false;
    while (!exiting)
    {
        SDL.PumpEvents();

        while (SDL.PollEvent(ref sdlEvent))
        {
            ImGuiImplSDL3.ProcessEvent((Hexa.NET.ImGui.Backends.SDL3.SDLEvent*)&sdlEvent);

            switch ((SDLEventType)sdlEvent.Type)
            {
                case SDLEventType.Quit:
                    exiting = true;
                    break;

                case SDLEventType.Terminating:
                    exiting = true;
                    break;

                case SDLEventType.WindowCloseRequested:
                    var windowEvent = sdlEvent.Window;
                    if (windowEvent.WindowID == windowId)
                    {
                        exiting = true;
                    }
                    break;
            }
        }

        GL.MakeCurrent();
        GL.ClearColor(1, 0.8f, 0.75f, 1);
        GL.Clear(GLClearBufferMask.ColorBufferBit);

        ImGuiImplOpenGL3.NewFrame();
        ImGuiImplSDL3.NewFrame();
        ImGui.NewFrame();

        ImGui.ShowDemoWindow();

		if (ImGui.Begin("Hello, world!")) {
			ImGui.Text("Hello again");
			if (ImPlot.BeginPlot("My Plot")) {

		// 		fixed(double* valuesPtr = values){
		// 			ImPlot.PlotLine("Values", valuesPtr, values.Length);
		// 		}
		 		ImPlot.EndPlot();
			}
		}
		ImGui.End();


        ImGui.Render();
        ImGui.EndFrame();

        GL.MakeCurrent();
        ImGuiImplOpenGL3.RenderDrawData(ImGui.GetDrawData());

        if ((io.ConfigFlags & ImGuiConfigFlags.ViewportsEnable) != 0)
        {
            ImGui.UpdatePlatformWindows();
            ImGui.RenderPlatformWindowsDefault();
        }

        GL.MakeCurrent();

        // Swap front and back buffers (double buffering)
        GL.SwapBuffers();
    }

    ImGuiImplOpenGL3.Shutdown();
    ImGuiImplSDL3.Shutdown();
    ImGui.DestroyContext();
	ImPlot.DestroyContext();
    GL.Dispose();

    SDL.DestroyWindow(window);
    SDL.Quit();
}

internal unsafe class BindingsContext : HexaGen.Runtime.IGLContext
{
    private readonly SDLWindow* window;
    private readonly SDLGLContext context;

    public BindingsContext(SDLWindow* window, SDLGLContext context)
    {
        this.window = window;
        this.context = context;
    }

    public nint Handle => (nint)window;

    public bool IsCurrent => SDL.GLGetCurrentContext() == context;

    public void Dispose()
    {
    }

    public nint GetProcAddress(string procName)
    {
        return (nint)SDL.GLGetProcAddress(procName);
    }

    public bool IsExtensionSupported(string extensionName)
    {
        return SDL.GLExtensionSupported(extensionName);
    }

    public void MakeCurrent()
    {
        SDL.GLMakeCurrent(window, context);
    }

    public void SwapBuffers()
    {
        SDL.GLSwapWindow(window);
    }

    public void SwapInterval(int interval)
    {
        SDL.GLSetSwapInterval(interval);
    }

    public bool TryGetProcAddress(string procName, out nint procAddress)
    {
        procAddress = (nint)SDL.GLGetProcAddress(procName);
        return procAddress != 0;
    }
}

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions