1. Memory leak or no memory leak..
Hi, I've big problem with memory use of my application. FastMM or AQTime's (trial version, if that matters) memory profiler doesn't find any leaks. AQTime finds with resource profiler about 10 "Task memory" leaks when GUIDToStr is called, but I think those are not real leaks. However memory usage grows steadily. FastMMUsageTracker shows new memory blocks added as "allocated" or "reserved" for system. Task manager also displays steady rise in memory usage (about 4 kb / s). The application uses COM to communicate with an OPC Server. There are a lot of variants used in interfaces, and it looks like the problem is present only when string or array of byte -data is transferred. Any ideas how to debug this?
3. ado memory leak? - source provided
I'm trying to find a memory leak in my code that uses ADO and have a sample
that exhibits the leak. I started with some sample code from Matt Neerincx
(thank you) and modified it to resemble the way it is executed in my program
and a COM
component.
The test includes a loop which:
1. connects to the database (jet)
2. executes a command to delete records from a table
3. executes a command (3 times) to add a record to the table
4. disconnects
I've constructed the test using commands in stored procedures, and using
commands as text with and without parameters. Compiling each way results in
the leak. The code is below. Can anyone
point out the leak?
Thanks.
#include "stdafx.h"
#include <atlbase.h>
//#include "Test2.h"
#include "conio.h"
#pragma warning( push )
#pragma warning( disable : 4146 )
#import "c:\Program Files\Common Files\system\ado\msadox.dll"
#import "c:\Program Files\Common Files\system\ado\msado15.dll"
rename("EOF","EndOfFile")
#pragma warning( pop )
#ifdef _DEBUG
#define new DEBUG_NEW
#undef THIS_FILE
static char THIS_FILE[] = __FILE__;
#endif
//#define USE_CMDPROC
//#define USE_PARAMS
void RunSample();
ADODB::_ConnectionPtr GetJetConnection();
void RunSingleLoop();
void Reset(ADODB::_ConnectionPtr conn);
void AddRecords(ADODB::_ConnectionPtr conn);
/////////////////////////////////////////////////////////////////////////////
// The one and only application object
CWinApp theApp;
using namespace std;
int _tmain(int argc, TCHAR* argv[], TCHAR* envp[])
{
int nRetCode = 0;
// initialize MFC and print and error on failure
if (!AfxWinInit(::GetModuleHandle(NULL), NULL, ::GetCommandLine(), 0))
{
// TODO: change error code to suit your needs
cerr << _T("Fatal Error: MFC initialization failed") << endl;
return -1;
}
CoInitialize(NULL);
RunSample();
CoUninitialize();
return nRetCode;
}
#define LOOP_COUNT 100000 // Number of loops to execute.
void RunSample()
{
#if defined(USE_CMDPROC) && defined(USE_PARAMS)
#error ("Invalid configuration")
#endif
ADODB::_ConnectionPtr global_conn = NULL;
int i;
try
{
// Open global conn to keep Jet loaded (perf).
global_conn = GetJetConnection();
try
{
global_conn->Execute(L"drop table
T1",NULL,ADODB::adExecuteNoRecords|ADODB::adCmdText);
}
catch ( _com_error ex )
{
}
global_conn->Execute(L"create table T1(f1 int, f2
int)",NULL,ADODB::adExecuteNoRecords|ADODB::adCmdText);
for (i=1; i<=LOOP_COUNT; i++ )
{
RunSingleLoop();
Sleep(5);
if ( 0 == (i%1000))
{
printf( "Completed %08lu of %08lu iterations.\n", i, LOOP_COUNT );
while ( _kbhit() )
{
int x = _getch();
if ( 'Q' == x || 'q' == x )
{
return;
}
}
}
}
}
catch( _com_error ex )
{
// Robust error trapping left as an exercise for the reader. (G)
ASSERT(FALSE);
}
return;
}
_bstr_t JET_CONNECT(L"Provider=Microsoft.Jet.OLEDB.4.0;Data
Source=C:\\NW99.mdb;");
ADODB::_ConnectionPtr GetJetConnection()
{
HRESULT hr;
ADODB::_ConnectionPtr conn = NULL;
hr = conn.CreateInstance( __uuidof(ADODB::Connection) );
//if ( FAILED( hr ) ) throw( _com_error( hr, NULL ) );
conn->CursorLocation = ADODB::adUseServer;
// Open connection.
conn->Open( JET_CONNECT, "", "", -1L );
//Setting this property doesn't help.
//conn->Properties->Item["Jet OLEDB:Max Buffer Size"]->Value = 500L;
return conn;
}
void RunSingleLoop()
{
ADODB::_ConnectionPtr conn = NULL;
// Open local conn for loop.
conn = GetJetConnection();
Reset(conn);
// The AddRecords generate the memory leaks
AddRecords(conn);
AddRecords(conn);
AddRecords(conn);
conn->Close();
conn = NULL;
}
void Reset(ADODB::_ConnectionPtr conn)
{
ADODB::_CommandPtr cmd = NULL;
CComVariant v1;
HRESULT hr = cmd.CreateInstance( __uuidof(ADODB::Command) );
/*
Query: qdMissingData
PARAMETERS P1 Long;
DELETE * FROM T1 WHERE f1=P1;
*/
cmd->ActiveConnection = conn;
#ifdef USE_CMDPROC
cmd->CommandText = L"qdMissingData";
cmd->CommandType = ADODB::adCmdStoredProc;
#else
#ifdef USE_PARAMS
cmd->CommandText = L"DELETE * FROM T1 WHERE f1=?";
#else
cmd->CommandText = L"DELETE * FROM T1 WHERE f1=1";
#endif
cmd->CommandType = ADODB::adCmdText;
#endif
#ifdef USE_PARAMS
v1 = 1L;
cmd->Parameters->Append(cmd->CreateParameter(
L"P1",ADODB::adInteger,ADODB::adParamInput,-1, v1));
v1.Clear();
#endif
cmd->Execute(NULL,NULL,ADODB::adExecuteNoRecords);
cmd->ActiveConnection = NULL;
cmd = NULL;
}
void AddRecords(ADODB::_ConnectionPtr conn)
{
ADODB::_CommandPtr cmd = NULL;
CComVariant v1;
CComVariant v2;
static long lCounter = 1;
// Now create parameterized ADO call.
HRESULT hr = cmd.CreateInstance( __uuidof(ADODB::Command) );
// if ( FAILED( hr ) ) throw( _com_error( hr, NULL ) );
cmd->ActiveConnection = conn;
/*
Query: qiMissingRecord:
PARAMETERS P1 Long, P2 DateTime;
INSERT INTO T1 ( f1, f2 ) VALUES (P1, P2);
*/
// Create insert statement and setup params.
#ifdef USE_CMDPROC
cmd->CommandText = L"qiMissingRecord";
cmd->CommandType = ADODB::adCmdStoredProc;
#else
#ifdef USE_PARAMS
cmd->CommandText = L"INSERT INTO T1 ( f1, f2 ) VALUES (?, ?)";
#else
cmd->CommandText = L"INSERT INTO T1 ( f1, f2 ) VALUES (1, 2)";
#endif
cmd->CommandType = ADODB::adCmdText;
#endif
#ifdef USE_PARAMS
v1 = 1L;
v2 = lCounter++;
cmd->Parameters->Append(cmd->CreateParameter(
L"P1",ADODB::adInteger,ADODB::adParamInput,-1, v1));
cmd->Parameters->Append(cmd->CreateParameter(
L"P2",ADODB::adInteger,ADODB::adParamInput,-1, v2));
v1.Clear();
v2.Clear();
#endif
// Execute statement.
cmd->Execute(NULL,NULL,ADODB::adExecuteNoRecords);
// Cleanup
cmd->ActiveConnection = NULL;
cmd = NULL;
}
5. How to detect memory leak and detect who causes a memory leak
6. ADO - permanent memory leak?!
7. Process Memory Leak? Delphi+MySql+ADO+MyOdbc
I've got some problems:
While using Mysql 4.0.20a for windows+MyODBC 3.51.07+Both delphi 6 or
delphi 7.
While testing for a MyODBC memory leak (present in myodbc before
3.51.07) I had this strange (for me) behaviour. The Heap it's apparently
perfect, BUT the Process Memory grows quite fast. As indicated by Task
Manager and the included function.
I've tried with different components, both MySQLDAC e Zeoslib gives no
sign of this .. but I've got the same problem in another apps with
ZeosLib (Still trying to reproduce the problem in a small example).
I've tested it all with memcheck. No heap leak.
Any idea?
I'll post the leakt.zip attachment on borland.public.attachment (Hoping
it's correct, sorry for any mistake.. :-( ).
Marco Banfi.
The "core" is:
for i:=0 to 10000 do begin
if StopMeCB.Checked then
begin
StopMeCB.Checked:=false;
Exit;
end;
ADOQuery := TADOQuery.Create(nil);
ADOQuery.ConnectionString := optConnString;
ADOQuery.CursorLocation := clUseClient; //No change..
ADOQuery.SQL.TEXT := 'SELECT * FROM log_option';
ADOQuery.Active := True;
FreeAndNil( ADOQuery);
iter:=i;
PsMemoryButtonClick(Sender);
Application.ProcessMessages;
end;