* explicit typecasting of any ordinal type to a boolean of the same

size must happen without any mangling of the value (mantis #11027)
  * moved checking for signed-to-unsigned (or vice versa) type
    conversions in assignments from htypechk to ncnv (where there
    was already code for similar checks) and added support for
    bool_to_bool there as well

git-svn-id: trunk@10521 -
This commit is contained in:
Jonas Maebe 2008-03-21 14:44:58 +00:00
parent e0593d7e6a
commit 62e66d2a56
9 changed files with 33 additions and 42 deletions

1
.gitattributes vendored
View File

@ -8105,6 +8105,7 @@ tests/webtbs/tw10966.pp svneol=native#text/plain
tests/webtbs/tw1097.pp svneol=native#text/plain
tests/webtbs/tw10979.pp svneol=native#text/plain
tests/webtbs/tw11006.pp svneol=native#text/plain
tests/webtbs/tw11027.pp svneol=native#text/plain
tests/webtbs/tw1103.pp svneol=native#text/plain
tests/webtbs/tw1104.pp svneol=native#text/plain
tests/webtbs/tw1111.pp svneol=native#text/plain

View File

@ -190,14 +190,11 @@ implementation
if codegenerror then
exit;
{ bytebool(byte) or wordbool(word) or longbool(longint) must }
{ be accepted for var parameters, and must not change the }
{ the ordinal value }
{ Explicit typecasts from any ordinal type to a boolean type }
{ must not change the ordinal value }
if (nf_explicit in flags) and
(left.resultdef.size=resultdef.size) and
not(left.location.loc in [LOC_FLAGS,LOC_JUMP]) and
is_cbool(resultdef) and
not is_pasbool(left.resultdef) then
not(left.location.loc in [LOC_FLAGS,LOC_JUMP]) then
begin
location_copy(location,left.location);
location.size:=def_cgsize(resultdef);

View File

@ -1068,16 +1068,6 @@ implementation
CGMessagePos2(hp.fileinfo,type_e_typecast_wrong_size_for_assignment,tostr(fromdef.size),tostr(todef.size));
end;
{ when typecasting to the same size but changing the signdness of
an ordinal, the value cannot be in a register if it's < sizeof(aint).
The reason is that a tc_int_2_int type conversion changing the sign
of a such value in a register also has to modify this register (JM) }
if is_ordinal(fromdef) and is_ordinal(todef) and
(fromdef.size=todef.size) and
(fromdef.size<sizeof(aint)) and
(is_signed(fromdef) xor is_signed(todef)) then
make_not_regable(hp,[ra_addr_regable]);
{ don't allow assignments to typeconvs that need special code }
if not(gotsubscript or gotvec or gotderef) and
not(ttypeconvnode(hp).assign_allowed) then

View File

@ -164,14 +164,11 @@ implementation
{$warning needs LOC_JUMP support, because called for bool_to_bool from ncgcnv }
{ bytebool(byte) or wordbool(word) or longbool(longint) must }
{ be accepted for var parameters, and must not change the }
{ the ordinal value }
{ Explicit typecasts from any ordinal type to a boolean type }
{ must not change the ordinal value }
if (nf_explicit in flags) and
(left.resultdef.size=resultdef.size) and
not(left.location.loc in [LOC_FLAGS,LOC_JUMP]) and
is_cbool(resultdef) and
not is_pasbool(left.resultdef) then
not(left.location.loc in [LOC_FLAGS,LOC_JUMP]) then
begin
location_copy(location,left.location);
location.size:=def_cgsize(resultdef);

View File

@ -2923,13 +2923,18 @@ implementation
)
) or
{ int 2 bool/bool 2 int, explicit typecast, see also nx86cnv }
((convtype in [tc_int_2_bool,tc_bool_2_int]) and
((convtype in [tc_int_2_bool,tc_bool_2_int,tc_bool_2_bool]) and
(nf_explicit in flags) and
(resultdef.size=left.resultdef.size));
{ When using only a part of the value it can't be in a register since
that will load the value in a new register first }
if (resultdef.size<left.resultdef.size) then
{ the same goes for changing the sign of equal-sized values which
are smaller than an entire register }
if (resultdef.size<left.resultdef.size) or
((resultdef.size=left.resultdef.size) and
(left.resultdef.size<sizeof(aint)) and
(is_signed(resultdef) xor is_signed(left.resultdef))) then
make_not_regable(left,[ra_addr_regable]);
end;

View File

@ -85,14 +85,11 @@ implementation
if codegenerror then
exit;
{ bytebool(byte) or wordbool(word) or longbool(longint) must }
{ be accepted for var parameters, and must not change the }
{ the ordinal value }
{ Explicit typecasts from any ordinal type to a boolean type }
{ must not change the ordinal value }
if (nf_explicit in flags) and
(left.resultdef.size=resultdef.size) and
not(left.location.loc in [LOC_FLAGS,LOC_JUMP]) and
is_cbool(resultdef) and
not is_pasbool(left.resultdef) then
not(left.location.loc in [LOC_FLAGS,LOC_JUMP]) then
begin
location_copy(location,left.location);
location.size:=def_cgsize(resultdef);

View File

@ -233,14 +233,11 @@ implementation
if codegenerror then
exit;
{ bytebool(byte) or wordbool(word) or longbool(longint) must }
{ be accepted for var parameters, and must not change the }
{ the ordinal value }
{ Explicit typecasts from any ordinal type to a boolean type }
{ must not change the ordinal value }
if (nf_explicit in flags) and
(left.resultdef.size=resultdef.size) and
not(left.location.loc in [LOC_FLAGS,LOC_JUMP]) and
is_cbool(resultdef) and
not is_pasbool(left.resultdef) then
not(left.location.loc in [LOC_FLAGS,LOC_JUMP]) then
begin
location_copy(location,left.location);
location.size:=def_cgsize(resultdef);

View File

@ -102,14 +102,11 @@ implementation
secondpass(left);
if codegenerror then
exit;
{ bytebool(byte) or wordbool(word) or longbool(longint) must }
{ be accepted for var parameters, and must not change the }
{ the ordinal value }
{ Explicit typecasts from any ordinal type to a boolean type }
{ must not change the ordinal value }
if (nf_explicit in flags) and
(left.resultdef.size=resultdef.size) and
not(left.location.loc in [LOC_FLAGS,LOC_JUMP]) and
is_cbool(resultdef) and
not is_pasbool(left.resultdef) then
not(left.location.loc in [LOC_FLAGS,LOC_JUMP]) then
begin
location_copy(location,left.location);
location.size:=def_cgsize(resultdef);

10
tests/webtbs/tw11027.pp Normal file
View File

@ -0,0 +1,10 @@
var i : char;
bb: bytebool;
begin
boolean(i) := (1=1);
if not boolean(i) then
halt(1);
boolean(bb):=boolean(i);
if not(bb) then
halt(2);
end.