Joost van der Sluis wrote 16 lines
On Wed, 2006-08-02 at 06:57 +0200, Martin Schreiber wrote:
> > > Did you fix Mantis 6898 in the meantime?
> >
> > You said that TBufDataset can use invalid pointers, even if there
> > wasn't any exception, if a dataset is opened and closed more then once.
>
> No, the problem is if here was a db exception on open. Without any
> exception it is OK.
Well, then that exception should be handled correctly. If you don't call
InternalClose, you'll have a mem-leak.
I don't think that any exception (except out-of-memory) can occur in
InternalConnect. So I think you mean an exceptions like 'transaction not
set', or 'invalid password'? Which problem do you have in particular?
Edit TSQLQuery.SQL with the SQL editor in MSEide.
Enter a valid query ("select * from table1").
Press the 'Test' button -> the dataset will be opened, data fetched, tbufdataset.ffirstrecbuf and fcurrentrecbuf are set, dataset is closed, ffirstrecbuf is now invalid.
Enter a invalid query ("select sdf%&/we$$ from table1"). Press the 'Test' button.
Exception in TSQLQuery.internalopen, dointernalclose calls internalclose which uses the
invalid ffirstrecbuf -> AV or freeing of wrong memory (that hapend in MSEide, I needed 20 hours to find the cause).
procedure TBufDataset.InternalClose;
var pc : pchar;
begin
FOpen:=False;
FCurrentRecBuf := FFirstRecBuf; <<<<<<<<<<<<<------!!!!!
SetLength(FUpdateBuffer,0);
while assigned(FCurrentRecBuf) do
begin
pc := pointer(FCurrentRecBuf);
FCurrentRecBuf := FCurrentRecBuf^.next;
FreeRecordBuffer(pc); <<<<<<<<<<<<<<<<-------!!!!
end;
SetLength(FFieldBufPositions,0);
end;
Possibly it is enough to set ffirstrecbuf to nil in internalclose (untested!).
Martin