Sign in to follow this  

dx - memory leak, but I really can't see where

This topic is 3460 days old which is more than the 365 day threshold we allow for new replies. Please post a new topic.

If you intended to correct an error in the post then please contact us.

Recommended Posts

DirectX reports a memory leak, I know it's in the texture code because if I don't create a texture theres no leak...but I can't see how since I'm releasing the texture interface, and the destruture is called because ive checked that...
	Texture* TextureCreateFromFile (Core* Owner, const std::string &Path)
	{
		LibTexture *NewTex = new LibTexture;
		NewTex->Owner = Owner;

		D3DXIMAGE_INFO Info;
		if(FAILED(D3DXCreateTextureFromFileEx(
			((LibCore*)Owner)->D3dDevice, Path.c_str(),
			NULL,NULL, 1, 0, D3DFMT_A8R8G8B8,
			D3DPOOL_MANAGED, D3DX_FILTER_NONE, D3DX_DEFAULT,
			NULL, &Info, NULL, &NewTex->Tex)))
		{
			delete NewTex;
			return NULL;
		}
		NewTex->h = Info.Height;
		NewTex->w = Info.Width;
		return NewTex;
	}
	LibTexture::~LibTexture()
	{
		if(Tex)Tex->Release();
	}


Share this post


Link to post
Share on other sites
There's no leak in that code. I suspect it's caused by you failing to delete a texture, which would cause your destructor not to be called, and the texture not to be Release()d.

Share this post


Link to post
Share on other sites
Wells theres only one texture for the purpose of testing, and if I didn't delete it, then the app wouldn't end either...


void Update(fw::Core *This)
{
if(This->WndClose)
{
delete Circle;//<-- deleted here
This->DestroyAll();//<--cleans up the base d3d stuff (D3dDevice, basic vertex buffer, etc) + destroys the window
}
}





[Edited by - Sync Views on June 24, 2008 12:51:37 PM]

Share this post


Link to post
Share on other sites
Quote:
Original post by Sync Views
Wells theres only one texture for the purpose of testing, and if I didn't delete it, then the app wouldn't end either...

*** Source Snippet Removed ***


Are you manually calling a destructor? Can you copy and paste your full code?

Share this post


Link to post
Share on other sites
no..that doesn't even compile I don't think lol...I trtied simpifiing it so that it wasn't a bunch of iterating and screwed it up lol... Either way it's getting decontructed at the right point because I put a break point in their to see if it was getting decontruted..

Share this post


Link to post
Share on other sites
you need to put up the code that's calling the texture creation steps.

Looking at your code, you may not be releasing the contents of the buffer, while your releasing the buffer the contents may still be held in memory.

i found that when the buffer was released the texture variable still held the memory spaces for the buffer, Nulled it out in the deconstruction process and it seemed to fix it.

Share this post


Link to post
Share on other sites
test.cpp

Texture* Circle = NULL;
void StartUp(fw::Core *This)//called just before entering the message loop
{
Circle = TextureCreateFromFile(This, "circle.png");
}
void Update(fw::Core *This)//called 30 times a second
{
if(This->WndClose)
{
Circle->Release();
This->DestroyAll();
}
}




dll
texture.h

...
class Texture
{
public:
virtual void Release()=0;
virtual unsigned GetW()=0;
virtual unsigned GetH()=0;

//draw functions
virtual bool Draw(const math::Matrix<4,4> &Transform)=0;
};
DLL Texture* TextureCreateFromFile (Core* Owner, const std::string &Path);
DLL Texture* TextureCreateFromFileMem (Core* Owner, void *Men, unsigned Length);
DLL Texture* TextureCreateFromResource(Core* Owner, const std::string &Res);
//note: the bit after this is not in the import header, the rest is
class LibTexture : public Texture
{
public:
IDirect3DTexture9* Tex;
unsigned w,h;
Core* Owner;

LibTexture();

virtual void Release();

virtual unsigned GetW();
virtual unsigned GetH();

virtual bool Draw(const math::Matrix<4,4> &Transform);//not tested, or used yet
};



texture.cpp

Texture* TextureCreateFromFile (Core* Owner, const std::string &Path)
{
LibTexture *NewTex = new LibTexture;
NewTex->Owner = Owner;

D3DXIMAGE_INFO Info;
if(FAILED(D3DXCreateTextureFromFileEx(
((LibCore*)Owner)->D3dDevice, Path.c_str(),
NULL,NULL, 1, 0, D3DFMT_A8R8G8B8,
D3DPOOL_MANAGED, D3DX_FILTER_NONE, D3DX_DEFAULT,
NULL, &Info, NULL, &NewTex->Tex)))
{
delete NewTex;
return NULL;
}
NewTex->h = Info.Height;
NewTex->w = Info.Width;
return NewTex;
}
Texture* TextureCreateFromFileMem(Core* Owner, void *Mem, unsigned Length)
{
...
}
Texture* TextureCreateFromResource(Core* Owner, const std::string &Res)
{
...
}


LibTexture::LibTexture()
:Tex(NULL)
{}

unsigned LibTexture::GetW()
{
return w;
}
unsigned LibTexture::GetH()
{
return h;
}
void LibTexture::Release()
{
if(Tex)Tex->Release();
delete this;
}
bool LibTexture::Draw(const math::Matrix<4,4> &Transform)
{
float *m = new float[4*4];
for(int x=0; x<4; ++x)
for(int y=0; y<4; ++y)
m[x + y*4] = (float)Transform.m[x][y];//I really need a better way to get froma 4x4 array of doubles to a 16 array of floats...

D3DXMATRIX D3dMat(m);
((LibCore*)Owner)->D3dDevice->SetTexture(0, Tex);
((LibCore*)Owner)->D3dDevice->SetTransform(D3DTS_WORLD, &D3dMat);
if(FAILED(((LibCore*)Owner)->D3dDevice->DrawPrimitive(D3DPT_TRIANGLEFAN, 0, 2)))
{
log::Add(log::Error, "Texture::Draw", "Failed to textured quad");
return false;
}
else return true;
}



Appart from the d3d startup/destroy functions (which just create a device + vertex buffer with 4 verteces for a 1x1 quad around 0,0) that is all my directX code... Just those 2 calls in my start and update exist...

Share this post


Link to post
Share on other sites
have you tried putting a break point right at the start of the the test.cpp code, open task manager (if your on a windows box obviously) and let the code run through, if it comes back to the start of test.cpp then you know its looping and creating the texture over and over. You will also be able to see easier (at least i find) where memory is being allocated and so forth.

Share this post


Link to post
Share on other sites

void LibCore::DestroyAll()
{
quiting = true;//stops the loop from calling Update, or Render again (if it was to do so, crashes are almost certain)
D3dDestroy();
DestroyWindow(Wnd);
}
void LibCore::D3dDestroy()
{
BackBuffer->Release();//I get this at the start, such that I can put the render target back if I ever change it
VertexBufferBase->Release();//Currently just holds 4 vertices froa quad around 0,0
D3dDevice->Release();
D3d->Release();
}

Share this post


Link to post
Share on other sites
I had the same problem once. It could be, that some other D3D function called YourTexture->AddRef() - for example render targets. If you have 2 times addref and one time ->Release() the texture wont be released. You need to check the reference count!

Share this post


Link to post
Share on other sites
What debug output do you get when there's the leak? And are you using any other memory leak checking code to check for standard memory leaks? I'd do that first, since if you're not delete-ing a texture it'll show up obviously that way.

Share this post


Link to post
Share on other sites

This topic is 3460 days old which is more than the 365 day threshold we allow for new replies. Please post a new topic.

If you intended to correct an error in the post then please contact us.

Create an account or sign in to comment

You need to be a member in order to leave a comment

Create an account

Sign up for a new account in our community. It's easy!

Register a new account

Sign in

Already have an account? Sign in here.

Sign In Now

Sign in to follow this