Browse Source

* do not convert the second argument of inc/dec(ptrtype,value) into a
pointer, because that will force "value" to become unsigned, which
result in errors in case of negative 64bit constants in case they
are multiplied by the size of the pointed type in ncginl (the
tconstexprint type operators have to handle positive and
negative numbers differently) (mantis #17342)

git-svn-id: trunk@15951 -

Jonas Maebe 15 years ago
parent
commit
a311607ca6
3 changed files with 28 additions and 1 deletions
  1. 1 0
      .gitattributes
  2. 12 1
      compiler/ninl.pas
  3. 15 0
      tests/webtbs/tw17342.pp

+ 1 - 0
.gitattributes

@@ -10642,6 +10642,7 @@ tests/webtbs/tw17220a.pp svneol=native#text/plain
 tests/webtbs/tw17236.pp svneol=native#text/pascal
 tests/webtbs/tw17283.pp svneol=native#text/plain
 tests/webtbs/tw17337.pp svneol=native#text/plain
+tests/webtbs/tw17342.pp svneol=native#text/plain
 tests/webtbs/tw1735.pp svneol=native#text/plain
 tests/webtbs/tw1737.pp svneol=native#text/plain
 tests/webtbs/tw1744.pp svneol=native#text/plain

+ 12 - 1
compiler/ninl.pas

@@ -2316,7 +2316,18 @@ implementation
                                    convert this to a regular add, and for proper
                                    checking we need the original type }
                                  if ([cs_check_range,cs_check_overflow]*current_settings.localswitches=[]) then
-                                   if is_integer(tcallparanode(left).left.resultdef) then
+                                   if (tcallparanode(left).left.resultdef.typ=pointerdef) then
+                                     begin
+                                       { don't convert values added to pointers into the pointer types themselves,
+                                         because that will turn signed values into unsigned ones, which then
+                                         goes wrong when they have to be multiplied with the size of the elements
+                                         to which the pointer points in ncginl (mantis #17342) }
+                                       if is_signed(tcallparanode(tcallparanode(left).right).left.resultdef) then
+                                         inserttypeconv(tcallparanode(tcallparanode(left).right).left,ptrsinttype)
+                                       else
+                                         inserttypeconv(tcallparanode(tcallparanode(left).right).left,ptruinttype)
+                                     end
+                                   else if is_integer(tcallparanode(left).left.resultdef) then
                                      inserttypeconv(tcallparanode(tcallparanode(left).right).left,tcallparanode(left).left.resultdef)
                                    else
                                      inserttypeconv_internal(tcallparanode(tcallparanode(left).right).left,tcallparanode(left).left.resultdef);

+ 15 - 0
tests/webtbs/tw17342.pp

@@ -0,0 +1,15 @@
+var
+  P1, P2: PCardinal;
+  I: Integer;
+begin
+
+  // random pointer
+  P1 := @I;
+  P2 := P1;
+
+  Inc(P1, 97);
+  Inc(P1, -97);
+
+  if (P1 <> P2) then
+    halt(1);
+end.