Watch, Follow, &
Connect with Us
Public Report
Report From: Delphi-BCB/RTL/Delphi    [ Add a report in this area ]  
Report #:  107254   Status: Closed
Erroneous operating with FmtBcd values after summarizing them as Variant
Project:  Delphi Build #:  16.0.4429.46931
Version:    16.4 Submitted By:   Serge (Developer Express Support)
Report Type:  Crash / Data loss / Total failure Date Reported:  7/20/2012 4:09:41 AM
Severity:    Serious / Highly visible problem Last Updated: 7/31/2012 1:36:23 AM
Platform:    All versions Internal Tracking #:   30302
Resolution: Test Case Error (Resolution Comments) Resolved in Build: : None
Duplicate of:  None
Voting and Rating
Overall Rating: No Ratings Yet
0.00 out of 5
Total Votes: None
Description
Incorrect summarizing result for FmtBcd values

var
  Bcd1, Bcd2: TBcd;
  A,B,Sum: Variant;
...
  StrToFloat(VarToStr(Sum)); //exception here

---------
First chance exception at $761BB9BC. Exception class EConvertError with message ''134.4228:' is not a valid floating point value'. Process Project1.exe (1692)
---------
Steps to Reproduce:
1. Run the attached project;
2. Click the "Button1" button.

Result - exception.

procedure TForm1.Button1Click(Sender: TObject);
var
  Bcd1, Bcd2: TBcd;
  A,B,Sum: Variant;
  D1, D2, SumD: Double;
begin
  //the first BCD value is 133.14205
  FillChar(Bcd1, SizeOf(TBcd), 0);
  Bcd1.Precision := 8;
  Bcd1.SignSpecialPlaces := 5;
  Bcd1.Fraction[0] := 19;
  Bcd1.Fraction[1] := 49;
  Bcd1.Fraction[2] := 66;
  Bcd1.Fraction[3] := 5;
  //the second BCD value is 1.2807
  FillChar(Bcd2, SizeOf(TBcd), 0);
  Bcd2.Precision := 32;
  Bcd2.SignSpecialPlaces := 4;
  Bcd2.Fraction[13] := 1;
  Bcd2.Fraction[14] := 40;
  Bcd2.Fraction[15] := 7;
  Bcd2.Fraction[16] := 242;
  Bcd2.Fraction[17] := 18;
  Bcd2.Fraction[19] := 77;
  Bcd2.Fraction[20] := 244;
  Bcd2.Fraction[21] := 101;
  Bcd2.Fraction[23] := 85;
  Bcd2.Fraction[24] := 244;
  Bcd2.Fraction[25] := 101;
  Bcd2.Fraction[31] := 64;
  //test on Double
  D1 := BcdToDouble(Bcd1);
  D2 := BcdToDouble(Bcd2);
  SumD := D1 + D2; //correct value: 134.42275
  //test on Variant
  A := VarFMTBcdCreate(Bcd1);
  B := VarFMTBcdCreate(Bcd2);
  Sum := A + B;    //incorrect float value: 134.4228:

  if SumD = Sum then
    ShowMessage('Correct!')
  else
    ShowMessage(VarToStr(Sum) + ' <> ' + FloatToStr(SumD));

  StrToFloat(VarToStr(Sum)); //exception here
end;
Workarounds
None
Attachment
Sample.ZIP
Comments

Tomohiro Takahashi at 7/24/2012 5:43:20 AM -
This report was opened with valid Internal Tracking Number.
Thanks.

Tomohiro Takahashi at 7/31/2012 9:51:22 PM -
This is a comment from internal tracking system.
<<<<<<<<<<
The problem is that the second BCD is not valid.

Bcd2.Fraction[16] := 242; -> 1111 0010 .The max value is 1001 (9)

So the test case is wrong.
An improve can be check if the BCD value is valid in NormalizeBcd function.
So we can add the next code at the begining:

//Check if InBCD is a valid BCD value
  for I := 0 to InBcd.Precision - 1 do
  begin
    if (I and 1) = 0 then
      B := InBcd.Fraction[I] div $10
    else
      B := InBcd.Fraction[I] and $F;
    if B > $9 then BcdErrorFmt(SInvalidBcdValue,'');
  end;

If we add this code all BCD operations will require valid BCDs.
>>>>>>>>>>

Server Response from: ETNACODE01