diff --git a/compiler/nmat.pas b/compiler/nmat.pas index dce92dd60d..ade96bbbf6 100644 --- a/compiler/nmat.pas +++ b/compiler/nmat.pas @@ -959,6 +959,29 @@ implementation left:=nil; exit; end; + if is_real(left.resultdef) then + begin + { + -(left-right) => right-left + + As this result in -(1.0-1.0)=0.0 instead of 0.0, this is only valid in fastmath mode + } + if (cs_opt_fastmath in current_settings.optimizerswitches) and (left.nodetype=subn) then + begin + result:=caddnode.create(subn,taddnode(left).right.getcopy,taddnode(left).left.getcopy); + exit; + end; + + { --node => node + this operation is always valid as reals do not use a two's complement representation for negative + numbers, -real means just flip the sign bit + } + if left.nodetype=unaryminusn then + begin + result:=tunarynode(left).left.getcopy; + exit; + end; + end; end; diff --git a/tests/tbs/tb0685.pp b/tests/tbs/tb0685.pp index f44e307fff..1970538db0 100644 --- a/tests/tbs/tb0685.pp +++ b/tests/tbs/tb0685.pp @@ -31,5 +31,18 @@ begin if (d3<>1.0) or (TDoubleRec(d3).Sign) then halt(5); + d1:=1.0; + d2:=1.0; + d3:=-(d2-d1); + writeln(d3); + if (d3<>0.0) or not(TDoubleRec(d3).Sign) then + halt(6); + + d1:=-0.0; + d3:=--d1; + writeln(d3); + if (d3<>0.0) or not(TDoubleRec(d3).Sign) then + halt(7); + writeln('ok'); end.