Skip to content

Commit 7be16f3

Browse files
committed
Made corrections in the comments andthe code
Changed the comments to: 1. Note that the algorithm was version 2. 2. Correct the comment on the underlying algorithm for NMHASH32X_9to255 gfortran under strict checking didn't like specifying the arguments to NMH_READLE32 and NMH_READLE16 as p(:) and preferred P(1:4) and p(1:2) respectively. NMHASH32X_9to255 was not as endian independent as I liked, so I changed some of its code. [ticket: X]
1 parent d8b2fde commit 7be16f3

File tree

1 file changed

+27
-22
lines changed

1 file changed

+27
-22
lines changed

src/stdlib_32_bit_nmhashes.fypp

100644100755
+27-22
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
!!------------------------------------------------------------------------------
22
!! `NM_HASH32` and `NM_HASH32X` are translations to Fortran 2008 and signed
3-
!! two's complement arithmetic of the `nmhash32` and `nmhash32x` scalar
3+
!! two's complement arithmetic of the `nmhash32` and `nmhash32x` V. 2 scalar
44
!! algorithms of James Z. M. Gao, copyright 2021. James Z. M. Gao's original
55
!! C++ code, `nmhash.h`, is available at the URL:
66
!! https://github.com/gzm55/hash-garage/blob/a8913138bdb3b7539c202edee30a7f0794bbd835/nmhash.h
@@ -9,7 +9,7 @@
99
!! The algorithms come in multiple versions, depending on whether the
1010
!! vectorized instructions SSE2 or AVX2 are available. As neither instruction
1111
!! is available in portable Fortran 2008, the algorithms that do not use these
12-
!! instructions are used.
12+
!! instructions.
1313
!!
1414
!! The BSD 2-Clause license is as follows:
1515
!!
@@ -93,7 +93,7 @@ contains
9393

9494
pure function nmh_readle32( p ) result( v )
9595
integer(int32) :: v
96-
integer(int8), intent(in) :: p(:)
96+
integer(int8), intent(in) :: p(1:4)
9797

9898
if ( little_endian ) then
9999
v = transfer( p(1:4), 0_int32 )
@@ -105,7 +105,7 @@ contains
105105

106106
pure function nmh_readle16( p ) result( v )
107107
integer(int16) :: v
108-
integer(int8), intent(in) :: p(:)
108+
integer(int8), intent(in) :: p(1:2)
109109

110110
if ( little_endian ) then
111111
v = transfer( p(1:2), 0_int16 )
@@ -125,11 +125,11 @@ contains
125125
integer(int32), parameter :: m2 = int(z'3FB39C65', int32)
126126
integer(int32), parameter :: m3 = int(z'E9139917', int32)
127127

128-
integer(int16) :: vx16(2)
128+
integer(int16) :: vx16(0:1)
129129
integer(int16), parameter :: &
130-
m116(2) = transfer( m1, 0_int16, 2 ), &
131-
m216(2) = transfer( m2, 0_int16, 2 ), &
132-
m316(2) = transfer( m3, 0_int16, 2 )
130+
m116(0:1) = transfer( m1, 0_int16, 2 ), &
131+
m216(0:1) = transfer( m2, 0_int16, 2 ), &
132+
m316(0:1) = transfer( m3, 0_int16, 2 )
133133

134134
vx32 = x
135135
vx32 = ieor( vx32, ieor( ishft( vx32, -12 ), ishft( vx32, -6 ) ) )
@@ -149,11 +149,11 @@ contains
149149

150150
end function nmhash32_0to8
151151

152-
pure function nmhash32_9to255( p, seed, full_avalanche ) result( result )
152+
pure function nmhash32_9to255( p, seed, full_avalanche ) result( hash )
153153
integer(int8), intent(in) :: p(0:)
154154
integer(int32), intent(in) :: seed
155155
logical, intent(in) :: full_avalanche
156-
integer(int32) :: result
156+
integer(int32) :: hash
157157

158158
integer(int32) :: xu32(0:3), yu32(0:3)
159159
integer(int16) :: xu16(0:1)
@@ -169,7 +169,6 @@ contains
169169
! base mixer: [f0d9649b 5 -13 29a7935d -9 11 55d35831 -20 -10 ] =
170170
! 0.93495901789135362
171171

172-
result = 0
173172
length = size( p, kind=int64 )
174173
length32 = transfer(length, 0_int32, 2)
175174
if (little_endian) then
@@ -268,7 +267,7 @@ contains
268267
xu32(0) = transfer( xu16, 0_int32 )
269268
xu32(0) = ieor(xu32(0), &
270269
ieor(ishft(xu32(0), -10), ishft(xu32(0), -20) ) )
271-
result = xu32(0)
270+
hash = xu32(0)
272271

273272
end function nmhash32_9to255
274273

@@ -389,13 +388,11 @@ contains
389388
u32 = x
390389
u32 = ieor( u32, ieor( ishft( u32, -8 ), ishft( u32, -21 ) ) )
391390
u16 = transfer( u32, 0_int16, 2 )
392-
u16(0) = u16(0) * m1_16(0)
393-
u16(1) = u16(1) * m1_16(1)
391+
u16 = u16 * m1_16
394392
u32 = transfer( u16, 0_int32 )
395393
u32 = ieor( u32, ieor( ishft( u32, 12 ), ishft( u32, -7 ) ) )
396394
u16 = transfer( u32, 0_int16, 2 )
397-
u16(0) = u16(0) * m2_16(0)
398-
u16(1) = u16(1) * m2_16(1)
395+
u16 = u16 * m2_16
399396
u32 = transfer( u16, 0_int32 )
400397
u32 = ieor( u32, ieor( ishft( u32, -8 ), ishft( u32, -21 ) ) )
401398

@@ -529,20 +526,24 @@ contains
529526
integer(int32) :: x
530527

531528
integer(int64) :: len
532-
integer(int32) :: len32(0:1), len_base
529+
integer(int32) :: len32(0:1)
530+
integer(int8) :: len8(0:7)
531+
integer(int32) :: len_base
533532
integer(int32) :: y
534533
integer(int32) :: a, b
535534
integer(int64) :: i, r
536535

537-
! 5 to 9 bytes
538-
! mixer: [11049a7d 23 bcccdc7b 12 065e9dad 12] = 0.16577596555667246
536+
! - at least 9 bytes
537+
! base mixer: [11049a7d 23 bcccdc7b 12 065e9dad 12] = 0.16577596555667246
538+
! tail mixer: [16 a52fb2cd 15 551e4d49 16] = 0.17162579707098322
539539

540540
len = size(p, kind=int64)
541+
len8 = transfer(len, 0_int8, 8)
541542
len32 = transfer(len, 0_int32, 2)
542543
if (little_endian) then
543-
len_base = len32(0)
544+
len_base = transfer( [len8(0), 0_int8, 0_int8, 0_int8], 0_int32 )
544545
else
545-
len_base = len32(1)
546+
len_base = transfer( [0_int8, 0_int8, 0_int8, len8(7)], 0_int32 )
546547
end if
547548
x = nmh_prime32_3
548549
y = seed
@@ -618,7 +619,11 @@ contains
618619
x = x * int(z'551E4D49', int32)
619620
end if
620621

621-
x = ieor(x, len_base )
622+
if ( little_endian ) then
623+
x = ieor(x, len32(0) )
624+
else
625+
x = ieor(x, len32(1) )
626+
end if
622627
x = ieor(x, ishftc(a, 27)) ! rotate one lane to pass Diff test
623628
x = ieor(x, ishft(x,-14))
624629
x = x * int(z'141CC535', int32 )

0 commit comments

Comments
 (0)