Skip to content

Commit d4dcaa2

Browse files
Merge #4989
4989: Add null backend r=def- a=ChillerDragon Thanks to `@Jupeyy` for the idea. Replacing graphics_threaded_null.h with a null backend makes code maintenance and memory cleanup easier. Fixes these memory leaks in headless client (ddnet/ddnet#4970) ``` Direct leak of 1048576 byte(s) in 1 object(s) allocated from: #0 0x4b6f6d in malloc (/home/runner/work/ddnet/ddnet/san/DDNet+0x4b6f6d) #1 0xd92ffb in CTextRender::InitTextures(int, int, IGraphics::CTextureHandle (&) [2], unsigned char* (&) [2]) /home/runner/work/ddnet/ddnet/src/engine/client/text.cpp:325:24 #2 0xd53795 in CTextRender::LoadFont(char const*, unsigned char const*, unsigned long) /home/runner/work/ddnet/ddnet/src/engine/client/text.cpp:729:3 #3 0xade5cd in CClient::LoadFont() /home/runner/work/ddnet/ddnet/src/engine/client/client.cpp:4070:32 #4 0x155b3de in CGameClient::OnInit() /home/runner/work/ddnet/ddnet/src/game/client/gameclient.cpp:246:12 #5 0xa8ecfe in CClient::Run() /home/runner/work/ddnet/ddnet/src/engine/client/client.cpp:2933:16 #6 0xaf6726 in main /home/runner/work/ddnet/ddnet/src/engine/client/client.cpp:4458:11 #7 0x7fadd9e610b2 in __libc_start_main (/lib/x86_64-linux-gnu/libc.so.6+0x240b2) ``` ## Checklist - [x] Tested the change ingame - [ ] Provided screenshots if it is a visual change - [ ] Tested in combination with possibly related configuration options - [ ] Written a unit test if it works standalone, system.c especially - [ ] Considered possible null pointers and out of bounds array indexing - [ ] Changed no physics that affect existing maps - [x] Tested the change with [ASan+UBSan or valgrind's memcheck](https://github.com/ddnet/ddnet/#using-addresssanitizer--undefinedbehavioursanitizer-or-valgrinds-memcheck) (optional) Co-authored-by: ChillerDrgon <[email protected]>
2 parents 2825ceb + 9ee3534 commit d4dcaa2

File tree

6 files changed

+93
-222
lines changed

6 files changed

+93
-222
lines changed

CMakeLists.txt

+2-1
Original file line numberDiff line numberDiff line change
@@ -1824,6 +1824,8 @@ if(CLIENT)
18241824
backend/backend_base.h
18251825
backend/glsl_shader_compiler.cpp
18261826
backend/glsl_shader_compiler.h
1827+
backend/null/backend_null.cpp
1828+
backend/null/backend_null.h
18271829
backend/opengl/backend_opengl.cpp
18281830
backend/opengl/backend_opengl.h
18291831
backend/opengl/backend_opengl3.cpp
@@ -1858,7 +1860,6 @@ if(CLIENT)
18581860
graphics_defines.h
18591861
graphics_threaded.cpp
18601862
graphics_threaded.h
1861-
graphics_threaded_null.h
18621863
http.cpp
18631864
http.h
18641865
input.cpp
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,59 @@
1+
#include "backend_null.h"
2+
3+
bool CCommandProcessorFragment_Null::RunCommand(const CCommandBuffer::SCommand *pBaseCommand)
4+
{
5+
switch(pBaseCommand->m_Cmd)
6+
{
7+
case CCommandProcessorFragment_Null::CMD_INIT:
8+
Cmd_Init(static_cast<const SCommand_Init *>(pBaseCommand));
9+
break;
10+
case CCommandBuffer::CMD_TEXTURE_CREATE:
11+
Cmd_Texture_Create(static_cast<const CCommandBuffer::SCommand_Texture_Create *>(pBaseCommand));
12+
break;
13+
case CCommandBuffer::CMD_TEXT_TEXTURES_CREATE:
14+
Cmd_TextTextures_Create(static_cast<const CCommandBuffer::SCommand_TextTextures_Create *>(pBaseCommand));
15+
break;
16+
case CCommandBuffer::CMD_TEXT_TEXTURE_UPDATE:
17+
Cmd_TextTexture_Update(static_cast<const CCommandBuffer::SCommand_TextTexture_Update *>(pBaseCommand));
18+
break;
19+
}
20+
return true;
21+
}
22+
23+
bool CCommandProcessorFragment_Null::Cmd_Init(const SCommand_Init *pCommand)
24+
{
25+
pCommand->m_pCapabilities->m_TileBuffering = false;
26+
pCommand->m_pCapabilities->m_QuadBuffering = false;
27+
pCommand->m_pCapabilities->m_TextBuffering = false;
28+
pCommand->m_pCapabilities->m_QuadContainerBuffering = false;
29+
30+
pCommand->m_pCapabilities->m_MipMapping = false;
31+
pCommand->m_pCapabilities->m_NPOTTextures = false;
32+
pCommand->m_pCapabilities->m_3DTextures = false;
33+
pCommand->m_pCapabilities->m_2DArrayTextures = false;
34+
pCommand->m_pCapabilities->m_2DArrayTexturesAsExtension = false;
35+
pCommand->m_pCapabilities->m_ShaderSupport = false;
36+
37+
pCommand->m_pCapabilities->m_TrianglesAsQuads = false;
38+
39+
pCommand->m_pCapabilities->m_ContextMajor = 0;
40+
pCommand->m_pCapabilities->m_ContextMinor = 0;
41+
pCommand->m_pCapabilities->m_ContextPatch = 0;
42+
return false;
43+
}
44+
45+
void CCommandProcessorFragment_Null::Cmd_Texture_Create(const CCommandBuffer::SCommand_Texture_Create *pCommand)
46+
{
47+
free(pCommand->m_pData);
48+
}
49+
50+
void CCommandProcessorFragment_Null::Cmd_TextTextures_Create(const CCommandBuffer::SCommand_TextTextures_Create *pCommand)
51+
{
52+
free(pCommand->m_pTextData);
53+
free(pCommand->m_pTextOutlineData);
54+
}
55+
56+
void CCommandProcessorFragment_Null::Cmd_TextTexture_Update(const CCommandBuffer::SCommand_TextTexture_Update *pCommand)
57+
{
58+
free(pCommand->m_pData);
59+
}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,16 @@
1+
#ifndef ENGINE_CLIENT_BACKEND_NULL_BACKEND_NULL_H
2+
#define ENGINE_CLIENT_BACKEND_NULL_BACKEND_NULL_H
3+
4+
#include <engine/client/backend/backend_base.h>
5+
6+
class CCommandProcessorFragment_Null : public CCommandProcessorFragment_GLBase
7+
{
8+
virtual bool GetPresentedImageData(uint32_t &Width, uint32_t &Height, uint32_t &Format, std::vector<uint8_t> &DstData) { return false; };
9+
virtual bool RunCommand(const CCommandBuffer::SCommand *pBaseCommand);
10+
bool Cmd_Init(const SCommand_Init *pCommand);
11+
virtual void Cmd_Texture_Create(const CCommandBuffer::SCommand_Texture_Create *pCommand);
12+
virtual void Cmd_TextTextures_Create(const CCommandBuffer::SCommand_TextTextures_Create *pCommand);
13+
virtual void Cmd_TextTexture_Update(const CCommandBuffer::SCommand_TextTexture_Update *pCommand);
14+
};
15+
16+
#endif

src/engine/client/backend_sdl.cpp

+16
Original file line numberDiff line numberDiff line change
@@ -34,6 +34,8 @@
3434

3535
#include "backend_sdl.h"
3636

37+
#include "backend/null/backend_null.h"
38+
3739
#if !defined(CONF_BACKEND_OPENGL_ES)
3840
#include "backend/opengl/backend_opengl3.h"
3941
#endif
@@ -266,6 +268,9 @@ CCommandProcessor_SDL_GL::CCommandProcessor_SDL_GL(EBackendType BackendType, int
266268
{
267269
m_BackendType = BackendType;
268270

271+
#if defined(CONF_HEADLESS_CLIENT)
272+
m_pGLBackend = new CCommandProcessorFragment_Null();
273+
#else
269274
if(BackendType == BACKEND_TYPE_OPENGL_ES)
270275
{
271276
#if defined(CONF_BACKEND_OPENGL_ES) || defined(CONF_BACKEND_OPENGL_ES3)
@@ -306,6 +311,7 @@ CCommandProcessor_SDL_GL::CCommandProcessor_SDL_GL(EBackendType BackendType, int
306311
m_pGLBackend = CreateVulkanCommandProcessorFragment();
307312
#endif
308313
}
314+
#endif
309315
}
310316

311317
CCommandProcessor_SDL_GL::~CCommandProcessor_SDL_GL()
@@ -858,6 +864,15 @@ CGraphicsBackend_SDL_GL::CGraphicsBackend_SDL_GL()
858864

859865
int CGraphicsBackend_SDL_GL::Init(const char *pName, int *pScreen, int *pWidth, int *pHeight, int *pRefreshRate, int FsaaSamples, int Flags, int *pDesktopWidth, int *pDesktopHeight, int *pCurrentWidth, int *pCurrentHeight, IStorage *pStorage)
860866
{
867+
#if defined(CONF_HEADLESS_CLIENT)
868+
int InitError = 0;
869+
const char *pErrorStr = NULL;
870+
int GlewMajor = 0;
871+
int GlewMinor = 0;
872+
int GlewPatch = 0;
873+
IsVersionSupportedGlew(m_BackendType, g_Config.m_GfxGLMajor, g_Config.m_GfxGLMinor, g_Config.m_GfxGLPatch, GlewMajor, GlewMinor, GlewPatch);
874+
BackendInitGlew(m_BackendType, GlewMajor, GlewMinor, GlewPatch);
875+
#else
861876
// print sdl version
862877
{
863878
SDL_version Compiled;
@@ -1102,6 +1117,7 @@ int CGraphicsBackend_SDL_GL::Init(const char *pName, int *pScreen, int *pWidth,
11021117

11031118
return EGraphicsBackendErrorCodes::GRAPHICS_BACKEND_ERROR_CODE_GL_VERSION_FAILED;
11041119
}
1120+
#endif // CONF_HEADLESS_CLIENT
11051121

11061122
// start the command processor
11071123
dbg_assert(m_pProcessor == nullptr, "Processor was not cleaned up properly.");

src/engine/client/graphics_threaded.cpp

-5
Original file line numberDiff line numberDiff line change
@@ -31,7 +31,6 @@
3131
#endif
3232

3333
#include "graphics_threaded.h"
34-
#include "graphics_threaded_null.h"
3534

3635
static CVideoMode g_aFakeModes[] = {
3736
{8192, 4320, 8192, 4320, 0, 8, 8, 8, 0}, {7680, 4320, 7680, 4320, 0, 8, 8, 8, 0}, {5120, 2880, 5120, 2880, 0, 8, 8, 8, 0},
@@ -2842,9 +2841,5 @@ int CGraphics_Threaded::GetVideoModes(CVideoMode *pModes, int MaxModes, int Scre
28422841

28432842
extern IEngineGraphics *CreateEngineGraphicsThreaded()
28442843
{
2845-
#ifdef CONF_HEADLESS_CLIENT
2846-
return new CGraphics_ThreadedNull();
2847-
#else
28482844
return new CGraphics_Threaded();
2849-
#endif
28502845
}

src/engine/client/graphics_threaded_null.h

-216
This file was deleted.

0 commit comments

Comments
 (0)