Page 1 of 1
Bug in dataset filter when filtering fixed character fields
Posted: Tue 20 Nov 2012 16:13
by a-s-z
Hi,
I have a problem when activating a filter in a dataset and the filtered field ist a fixed character field.
The field description yields Length = 1 and Size = 4, the Filter expression is NODETYPE = 'P'.
When activating the filter, not all records are found.
I have searched the sources and finally looked into TData.GetField and TData.GetFieldDataAsVariant which seem to work differently, when FieldDesc.Fixed is true.
Debugging into the function TData.Eval revealed, that the field data is not converted correctly in GetFieldDataAsVariant (MemData.pas ~l.3138) compared to GetField (~l.2831)?
Can you please send me a hotfix for this issue if it is a bug?
Regards
Re: Bug in dataset filter when filtering fixed character fields
Posted: Wed 21 Nov 2012 08:16
by AlexP
Hello,
Thank you for the information.
We have reproduced the problem.
We will try to fix it in the nearest product version.
Re: Bug in dataset filter when filtering fixed character fields
Posted: Wed 21 Nov 2012 08:32
by a-s-z
Hi,
this bug is critical for me. When will you release next version?
In the meantime I have patched GetFieldDataAsVariant by replacing the code for widestring (ansi uses PtrToStringAnsi):
Code: Select all
if Field.Fixed then
begin
t := TrimFixedChar;
l := Field.Length;
end
else
begin
t := TrimVarChar;
l := -1;
end;
if t then
// trim fixed char values
Value := TrimRight(Marshal.PtrToStringUni(FieldData, l))
else
Value := Marshal.PtrToStringUni(FieldData, l);
Please provide code patch, if there is more to do and next release takes a while. Thanks.
Regards
Re: Bug in dataset filter when filtering fixed character fields
Posted: Wed 21 Nov 2012 13:37
by AlexP
hello,
We have already fixed this problem, this fix will be included to the next build, which will be released in the beginning of the next month.
For the time being, you should correct the PrepareBlock method in the OraClasses module as follows.
The following code
Code: Select all
else begin
if (FieldDesc.DataType = dtString) and
(FieldDesc.SubDataType in [dtFixedChar, dtFixedNChar])
then
if FieldDesc.SubDataType in [dtFixedChar, dtFixedNChar] then
Marshal.WriteByte(Ptr, FieldDesc.Offset + FieldDesc.Length, 0)
else if (FieldDesc.DataType = dtWideString) and
(FieldDesc.SubDataType in [dtFixedWideChar, dtFixedNWideChar])
then
if FieldDesc.SubDataType in [dtFixedWideChar, dtFixedNWideChar] then
Marshal.WriteInt16(Ptr, FieldDesc.Offset + FieldDesc.Length * 2, 0);
end;
should be replaced with (2 if operators should be removed):
Code: Select all
else begin
if (FieldDesc.DataType = dtString) and
(FieldDesc.SubDataType in [dtFixedChar, dtFixedNChar])
then
Marshal.WriteByte(Ptr, FieldDesc.Offset + FieldDesc.Length, 0)
else if (FieldDesc.DataType = dtWideString) and
(FieldDesc.SubDataType in [dtFixedWideChar, dtFixedNWideChar])
then
Marshal.WriteInt16(Ptr, FieldDesc.Offset + FieldDesc.Length * 2, 0);
end;