<html>
<head>
<style><!--
.hmmessage P
{
margin:0px;
padding:0px
}
body.hmmessage
{
font-size: 12pt;
font-family:Calibri
}
--></style></head>
<body class='hmmessage'><div dir='ltr'>> Well, I agree wholeheartedly, yes.<br><br><br> Tony: can we put in range checks on float to int conversions? <br> I'd be ok with initially: <br> if float < FIRST(INTEGER) - 1 or float > LAST(INTEGER) + 1 <br> error <br><br> The "1" isn't quite right, but "0" is also wrong. <br><br><br> I'd like to see what Java and C# do also (safe/optionally safe languages in good standing). <br><br> And then we also have to do something in m3-comm/events to stop it failing on AMD64_NT today and everything else "soon".<br><br><br> - Jay<br><br><br><div>> To: jay.krell@cornell.edu<br>> Date: Wed, 4 Sep 2013 09:32:17 -0700<br>> From: mika@async.caltech.edu<br>> CC: m3devel@elegosoft.com<br>> Subject: Re: [M3devel] rounding very large magnitude longreal, time, events?<br>> <br>> Jay K writes:<br>> >--_ab947ec4-5d41-4d75-ba7b-1dd04573736b_<br>> >Content-Type: text/plain; charset="iso-8859-1"<br>> >Content-Transfer-Encoding: quoted-printable<br>> ><br>> >> If I am understanding properly what is going on I think this means your n=<br>> >ew<br>> >> Modula-3-to-C compiler is the most reasonably behaving Modula-3 implement=<br>> >ation.<br>> ><br>> ><br>> >I wish=2C but no=2C it is the same as the others.<br>> <br>> I see...<br>> <br>> ><br>> ><br>> >It is all a bit subtle.<br>> <br>> As always...<br>> <br>> ><br>> ...<br>> ><br>> ><br>> >I believe=2C based on what you are saying=2C<br>> >the frontend should generate range checks before<br>> >floor/trunc/ceiling.<br>> ><br>> >Roughly it should be an error to convert<br>> >a float < FIRST(INTEGER) or > LAST(INTEGER) to a double.<br>> >Plus or minus one though.<br>> ><br>> ><br>> >That is=2C<br>> > FLOOR(LAST(INTEGER) + .99999) is ok.<br>> > CEILING(FIRST(INTEGER) - .99999) is ok.<br>> > ROUND(LAST(INTEGER) - .499999) is ok.<br>> > ROUND(FIRST(INTEGER) + .499999) is ok.<br>> >=20<br>> ><br>> >I'm not sure where "round to even" is=2C so -.5 and +.5 might be ok.<br>> ><br>> ><br>> >Oh wait. It depends on the relative ranges of float and integer.<br>> ><br>> ><br>> >In particular=2C a 53bit mantissa longreal converted to a 32bit integer<br>> >needs the checks I describe. But a 53bit mantissa converted to<br>> >a 64bit integer=2C no range check is needed.<br>> ><br>> ><br>> >The frontend has some of those optimizations already -- converting<br>> >from a smaller range to a larger range needs no check.<br>> ><br>> ><br>> >Agreed? Surely this is not a difficult change?<br>> <br>> Well, I agree wholeheartedly, yes.<br>> <br>> >Nor particularly inefficient?<br>> ><br>> ><br>> ><br>> > - Jay<br>> ><br>> ><br>> ><br>> ><br>> >> To: jay.krell@cornell.edu<br>> >> Subject: Re: [M3devel] rounding very large magnitude longreal=2C time=2C =<br>> >events?<br>> >> Date: Tue=2C 3 Sep 2013 23:42:12 -0700<br>> >> From: mika@async.caltech.edu<br>> >>=20<br>> >> Jay K writes:<br>> >> ...<br>> >> ><br>> >> >Ok=3D2C so this is three dilemnas/questions/bugs in one.<br>> >> ><br>> >> ><br>> >> >http://modula3.elegosoft.com/cm3/doc/reference/complete/html/2_6_10Arith=<br>> >met=3D<br>> >> >ic_operations.html<br>> >> ><br>> >> ><br>> >> >ROUND(r) is the nearest integer to r=3D3B ties are broken according to t=<br>> >he co=3D<br>> >> >nstant RoundDefault<br>> >> ><br>> >> ><br>> >> >1) How should ROUND be defined? Is Modula-3 adequately safe here?<br>> >> ><br>> >> ><br>> >> > What should round of numbers less than FIRST(INTEGER)-1=3D20<br>> >> > or greater than LAST(INTEGER) + 1 round to?=3D20<br>> >> ><br>> >> ><br>> >> > By the simple definition=3D2C they should round to FIRST(INTEGER)=3D20<br>> >> > and LAST(INTEGER). But is it safe?<br>> >> ><br>> >>=20<br>> >> No=2C I read the definition as saying "integer"=2C not "INTEGER". That i=<br>> >s=2C<br>> >> "integer" is the abstract mathematical concept of an integer=2C not the<br>> >> Modula-3 data type INTEGER.<br>> >>=20<br>> >> I think the intent of the Green Book is that INTEGER should be a range-li=<br>> >mited<br>> >> form of integer=2C that is=2C it should behave like an integer as much as=<br>> > possible=2C<br>> >> and when the implementation can no longer accomplish that=2C it should si=<br>> >gnal a=20<br>> >> runtime error. =20<br>> >>=20<br>> >> It happens that many existing implementions of Modula-3=2C as an implemen=<br>> >tation<br>> >> restriction=2C do not handle out-of-range situations correctly. Things<br>> >> such as what you describe SHOULD lead to a runtime error=2C value out of =<br>> >range.<br>> >> Some implementations wrap instead=2C but I don't even think that's right.=<br>> > Of<br>> >> course it's not as bad as it might be in C where you might be indexing an<br>> >> array with the incorrectly calculated integer and send your program off i=<br>> >n<br>> >> never-never land. In Modula-3 you'll at least get a runtime error at THA=<br>> >T<br>> >> point. But it's still not right.<br>> >>=20<br>> >> If I am understanding properly what is going on I think this means your n=<br>> >ew<br>> >> Modula-3-to-C compiler is the most reasonably behaving Modula-3 implement=<br>> >ation.<br>> >>=20<br>> >> Mika<br>> > =<br>> ><br>> >--_ab947ec4-5d41-4d75-ba7b-1dd04573736b_<br>> >Content-Type: text/html; charset="iso-8859-1"<br>> >Content-Transfer-Encoding: quoted-printable<br>> ><br>> ><html><br>> ><head><br>> ><style><!--<br>> >.hmmessage P<br>> >{<br>> >margin:0px=3B<br>> >padding:0px<br>> >}<br>> >body.hmmessage<br>> >{<br>> >font-size: 12pt=3B<br>> >font-family:Calibri<br>> >}<br>> >--></style></head><br>> ><body class=3D'hmmessage'><div dir=3D'ltr'>>=3B If I am understanding pro=<br>> >perly what is going on I think this means your new<br>>=3B Modula-3-to-C =<br>> >compiler is the most reasonably behaving Modula-3 implementation.<br><br><b=<br>> >r>I wish=2C but no=2C it is the same as the others.<br><br><br>It is all a =<br>> >bit subtle.<br><br><br>Here is what I believe happens:<br><br><br>I386_NT: =<br>> >from any double=2C round will give us<br>some integer=2C a 32bit integer=2C=<br>> > that can be<br>successfully assigned to this range=2C with or without<br>a=<br>> > range check.<br><br><br>m3cc: Posix: The values are in range.<br>With or w=<br>> >ithout a range check=2C the code succeeds.<br>For a "few" more years.<br><b=<br>> >r><br>C backend: Similar.<br>I'm using the C backend all the time on Darwon=<br>> >.<br>Again=2C Posix: the values are in range.<br>I386_NT: round will give u=<br>> >s a 32bit integer and it will "work"<br>AMD64_NT: round gives us a 64bit in=<br>> >teger=2C the range check fails.<br><br><br>In a "few" years=2C 64bit Posix =<br>> >systems will fail here.<br>32bit Posix would continue to round to some 32bi=<br>> >t integer=2C which would then<br>successfully pass into the identical subra=<br>> >nge -- like I386_NT today.<br><br><br><br>The backends don't add range chec=<br>> >ks.<br>Mostly or entirely=2C they should not.<br>As long as the frontend kn=<br>> >ows enough=2C it should do it.<br>The frontend knows the range of INTEGER a=<br>> >nd at least roughly<br>the range of longreal.<br>Possibly the range of a lo=<br>> >ngreal is target-dependent and knowledge<br>of it should only exist in the =<br>> >backend. In reality=2C as long as you ignore VAX=2C<br>roughly everything i=<br>> >s the same since around the early 1980s.<br><br><br><br>I believe=2C based =<br>> >on what you are saying=2C<br>the frontend should generate range checks befo=<br>> >re<br>floor/trunc/ceiling.<br><br>Roughly it should be an error to convert<=<br>> >br>a float <=3B FIRST(INTEGER) or >=3B LAST(INTEGER) to a double.<br>Pl=<br>> >us or minus one though.<br><br><br>That is=2C<br> =3BFLOOR(LAST(INTEGER=<br>> >) + .99999) is ok.<br> =3BCEILING(FIRST(INTEGER) - .99999) is ok.<br>&n=<br>> >bsp=3BROUND(LAST(INTEGER) - .499999) is ok.<br> =3BROUND(FIRST(INTEGER)=<br>> > + .499999) is ok.<br> =3B<br><br>I'm not sure where "round to even" is=<br>> >=2C so -.5 and +.5 might be ok.<br><br><br>Oh wait. It depends on the relat=<br>> >ive ranges of float and integer.<br><br><br>In particular=2C a 53bit mantis=<br>> >sa longreal converted to a 32bit integer<br>needs the checks I describe. Bu=<br>> >t a 53bit mantissa converted to<br>a 64bit integer=2C no range check is nee=<br>> >ded.<br><br><br>The frontend has some of those optimizations already -- con=<br>> >verting<br>from a smaller range to a larger range needs no check.<br><br><b=<br>> >r>Agreed? Surely this is not a difficult change?<br>Nor particularly ineffi=<br>> >cient?<br><br><br><br> =3B- Jay<br><br><br><br><br><div>>=3B To: jay.=<br>> >krell@cornell.edu<br>>=3B Subject: Re: [M3devel] rounding very large magn=<br>> >itude longreal=2C time=2C events?<br>>=3B Date: Tue=2C 3 Sep 2013 23:42:1=<br>> >2 -0700<br>>=3B From: mika@async.caltech.edu<br>>=3B <br>>=3B Jay K w=<br>> >rites:<br>>=3B ...<br>>=3B >=3B<br>>=3B >=3BOk=3D2C so this is th=<br>> >ree dilemnas/questions/bugs in one.<br>>=3B >=3B<br>>=3B >=3B<br>&g=<br>> >t=3B >=3Bhttp://modula3.elegosoft.com/cm3/doc/reference/complete/html/2_6=<br>> >_10Arithmet=3D<br>>=3B >=3Bic_operations.html<br>>=3B >=3B<br>>=<br>> >=3B >=3B<br>>=3B >=3BROUND(r) is the nearest integer to r=3D3B ties a=<br>> >re broken according to the co=3D<br>>=3B >=3Bnstant RoundDefault<br>>=<br>> >=3B >=3B<br>>=3B >=3B<br>>=3B >=3B1) How should ROUND be defined?=<br>> > Is Modula-3 adequately safe here?<br>>=3B >=3B<br>>=3B >=3B<br>>=<br>> >=3B >=3B What should round of numbers less than FIRST(INTEGER)-1=3D20<br>=<br>> >>=3B >=3B or greater than LAST(INTEGER) + 1 round to?=3D20<br>>=3B &g=<br>> >t=3B<br>>=3B >=3B<br>>=3B >=3B By the simple definition=3D2C they s=<br>> >hould round to FIRST(INTEGER)=3D20<br>>=3B >=3B and LAST(INTEGER). But =<br>> >is it safe?<br>>=3B >=3B<br>>=3B <br>>=3B No=2C I read the definiti=<br>> >on as saying "integer"=2C not "INTEGER". That is=2C<br>>=3B "integer" is=<br>> > the abstract mathematical concept of an integer=2C not the<br>>=3B Modul=<br>> >a-3 data type INTEGER.<br>>=3B <br>>=3B I think the intent of the Green=<br>> > Book is that INTEGER should be a range-limited<br>>=3B form of integer=<br>> >=2C that is=2C it should behave like an integer as much as possible=2C<br>&=<br>> >gt=3B and when the implementation can no longer accomplish that=2C it shoul=<br>> >d signal a <br>>=3B runtime error. <br>>=3B <br>>=3B It happens tha=<br>> >t many existing implementions of Modula-3=2C as an implementation<br>>=3B=<br>> > restriction=2C do not handle out-of-range situations correctly. Things<br=<br>> >>>=3B such as what you describe SHOULD lead to a runtime error=2C value o=<br>> >ut of range.<br>>=3B Some implementations wrap instead=2C but I don't eve=<br>> >n think that's right. Of<br>>=3B course it's not as bad as it might be i=<br>> >n C where you might be indexing an<br>>=3B array with the incorrectly cal=<br>> >culated integer and send your program off in<br>>=3B never-never land. I=<br>> >n Modula-3 you'll at least get a runtime error at THAT<br>>=3B point. Bu=<br>> >t it's still not right.<br>>=3B <br>>=3B If I am understanding properly=<br>> > what is going on I think this means your new<br>>=3B Modula-3-to-C compi=<br>> >ler is the most reasonably behaving Modula-3 implementation.<br>>=3B <br>=<br>> >>=3B Mika<br></div> </div></body><br>> ></html>=<br>> ><br>> >--_ab947ec4-5d41-4d75-ba7b-1dd04573736b_--<br></div> </div></body>
</html>