Recent

Author Topic: Different result of shr and shl  (Read 3460 times)

Okoba

  • Hero Member
  • *****
  • Posts: 616
Different result of shr and shl
« on: December 28, 2024, 06:56:26 pm »
Hi
Can anyone help me understand why value of B and C are different? To me they should have the same result and C is the correct one.
Code: Pascal  [Select][+][-]
  1. program Project1;
  2.  
  3. var
  4.   A, B, C: QWord;
  5. begin
  6.   A := 140737488355327;
  7.   WriteLn(BinStr(A, 64)); //0000000000000000011111111111111111111111111111111111111111111111
  8.   B := (A shr 47) shl 48;
  9.   WriteLn(BinStr(B, 64)); //0000000000000000111111111111111111111111111111110000000000000000
  10.  
  11.   C := A shr 47;
  12.   C := C shl 48;
  13.   WriteLn(BinStr(C, 64)); //0000000000000000000000000000000000000000000000000000000000000000
  14. end.            

Bart

  • Hero Member
  • *****
  • Posts: 5537
    • Bart en Mariska's Webstek
Re: Different result of shr and shl
« Reply #1 on: December 28, 2024, 07:12:54 pm »
SLightly more verbose:
Code: Pascal  [Select][+][-]
  1.   A := 140737488355327;
  2.   WriteLn('A                : ',BinStr(A, 64));
  3.   B := (A shr 47) shl 48;
  4.   WriteLn('(A shr 47) shl 48: ',BinStr(B, 64));
  5.  
  6.   C := A shr 47;
  7.   writeln('C := A shr 47    : ',BinStr(C, 64));
  8.   C := C shl 48;
  9.   WriteLn('C := C shl 48    : ',BinStr(C, 64));

Gives:
Code: [Select]
A                : 0000000000000000011111111111111111111111111111111111111111111111
(A shr 47) shl 48: 0000000000000000000000000000000000000000000000000000000000000000
C := A shr 47    : 0000000000000000000000000000000000000000000000000000000000000000
C := C shl 48    : 0000000000000000000000000000000000000000000000000000000000000000

Tested with fpc 3.2.2 and fpc main for both 32- and 64-bit on Windows.

Bart

Okoba

  • Hero Member
  • *****
  • Posts: 616
Re: Different result of shr and shl
« Reply #2 on: December 28, 2024, 07:16:02 pm »
Code: Pascal  [Select][+][-]
  1. A                : 0000000000000000011111111111111111111111111111111111111111111111
  2. (A shr 47) shl 48: 0000000000000000111111111111111111111111111111110000000000000000
  3. C := A shr 47    : 0000000000000000000000000000000000000000000000000000000000000000
  4. C := C shl 48    : 0000000000000000000000000000000000000000000000000000000000000000
Lazarus 4.99 (rev d9c3191562) FPC 3.3.1 x86_64-win64-win32/win64

AlexTP

  • Hero Member
  • *****
  • Posts: 2541
    • UVviewsoft
Re: Different result of shr and shl
« Reply #3 on: December 28, 2024, 07:49:11 pm »
It looks like a FPC bug, maybe worth to report it to bugtracker.

dseligo

  • Hero Member
  • *****
  • Posts: 1479
Re: Different result of shr and shl
« Reply #4 on: December 28, 2024, 07:52:15 pm »
If I ran it in Lazarus I get same result as Okoba.

If I compile it with with ppc386 or ppcx64 or run it in Lazarus without debugging (Shift+Ctrl+F9) I get correct results.

It looks like Lazarus bug.

In Lazarus it doesn't matter if all debugging options are turned off, it must be run without debugging.

Windows 11, FPC 3.2.2, Lazarus 3.6.

Okoba, next time write details of your environment, it will be easier for others to test.

Fibonacci

  • Hero Member
  • *****
  • Posts: 653
  • Internal Error Hunter
Re: Different result of shr and shl
« Reply #5 on: December 28, 2024, 08:06:32 pm »
Depends on Optimization Level. Bug. Report it.

AlanTheBeast

  • Sr. Member
  • ****
  • Posts: 370
  • My software never cras....
Re: Different result of shr and shl
« Reply #6 on: December 28, 2024, 08:18:29 pm »
I believe the QWord code needs critical review.

The other day I had a strange compiler message - but shrugged it off and ignored it .

Code: Pascal  [Select][+][-]
  1. Function factorial(f:QWord):QWord;
  2. BEGIN
  3.         if f <2 then exit(1);
  4.         factorial := f * factorial (f-1);
  5. END;
  6.  
  7. Procedure fact;
  8. VAR
  9.         n:QWord;
  10.         k:int64 absolute n;
  11. BEGIN
  12.         n := $FFFFFFFFFFFFFFFF;
  13.         writeln (n);
  14.         writeln (k);
  15.         Repeat
  16.                 write (' : '); Readln (n);
  17.                 writeln (factorial(n));
  18.         Until n=0;
  19. END;

Produced a compiler warning:
Quote
testhis.pas(236,7) Warning: range check error while evaluating constants (-1 must be between 0 and 18446744073709551615)
 235BEGIN
 236   n := $FFFFFFFFFFFFFFFF;
 237   writeln (n);
Everyone talks about the weather but nobody does anything about it.
..Samuel Clemens.

dseligo

  • Hero Member
  • *****
  • Posts: 1479
Re: Different result of shr and shl
« Reply #7 on: December 28, 2024, 09:59:17 pm »
Depends on Optimization Level. Bug. Report it.

It looks like you are correct. As soon as -Ox (x being 1 to 4) is specified bug appears.

jamie

  • Hero Member
  • *****
  • Posts: 6823
Re: Different result of shr and shl
« Reply #8 on: December 28, 2024, 10:39:07 pm »
If you use variables instead of constants for the shift values it works ok in any -O level
Code: Pascal  [Select][+][-]
  1. program Project1;
  2. {$mode Objfpc}
  3.  
  4. var
  5.   A, B, C,X,Y: QWord;
  6. begin
  7.   X:= 47; Y:= 48;
  8.   A := 140737488355327;
  9.   WriteLn(BinStr(A, 64)); //0000000000000000011111111111111111111111111111111111111111111111
  10.   B := (A shr X) shl Y;
  11.   WriteLn(BinStr(B, 64)); //0000000000000000111111111111111111111111111111110000000000000000
  12.  
  13.   C := A shr X;
  14.   C := C shl Y;
  15.   WriteLn(BinStr(C, 64)); //0000000000000000000000000000000000000000000000000000000000000000
  16.   Readln;
  17. end.
  18.  

 This makes it look like the compiler isn't properly generating proper code when using constants in this case.
  if the last one fails if you use -O4 but works with variables.
The only true wisdom is knowing you know nothing

Seenkao

  • Hero Member
  • *****
  • Posts: 674
    • New ZenGL.
Re: Different result of shr and shl
« Reply #9 on: December 28, 2024, 11:12:58 pm »
Возможно это проблема 63-го бита QWord. Я давно сталкивался с подобной ситуацией и просто уходил от этой размерности, там где нужно было проверить 63-й бит.

Google translate:
Perhaps this is a problem with the 63rd bit of QWord. I have encountered a similar situation for a long time and simply avoided this dimension where it was necessary to check the 63rd bit.
Rus: Стремлюсь к созданию минимальных и достаточно быстрых приложений.

Eng: I strive to create applications that are minimal and reasonably fast.
Working on ZenGL

Bart

  • Hero Member
  • *****
  • Posts: 5537
    • Bart en Mariska's Webstek
Re: Different result of shr and shl
« Reply #10 on: December 28, 2024, 11:48:33 pm »
Depends on Optimization Level. Bug. Report it.

It looks like you are correct. As soon as -Ox (x being 1 to 4) is specified bug appears.

Yes, it requires -O1 and compilation for 64-bit.
I cannot recreate for 32-bit, no matter what optimization level.
It also seems NOT to depend on range or overflow checking.

Bart

Bart

  • Hero Member
  • *****
  • Posts: 5537
    • Bart en Mariska's Webstek
Re: Different result of shr and shl
« Reply #11 on: December 29, 2024, 12:03:18 am »
Reported as Issue #41079.

Bug seems to have been introduced in fpc 3.2.0.

Bart

 

TinyPortal © 2005-2018