Skip to content

Commit c83e6f5

Browse files
committed
runtime: aeshash, xor seed in earlier
Instead of doing: x = input one round of aes on x x ^= seed two rounds of aes on x Do: x = input x ^= seed three rounds of aes on x This change provides some additional seed-dependent scrambling which should help prevent collisions. Change-Id: I02c774d09c2eb6917cf861513816a1024a9b65d7 Reviewed-on: https://go-review.googlesource.com/23577 Reviewed-by: Ian Lance Taylor <[email protected]> Run-TryBot: Keith Randall <[email protected]> TryBot-Result: Gobot Gobot <[email protected]>
1 parent cea29c4 commit c83e6f5

File tree

2 files changed

+82
-35
lines changed

2 files changed

+82
-35
lines changed

src/runtime/asm_amd64.s

Lines changed: 62 additions & 35 deletions
Original file line numberDiff line numberDiff line change
@@ -914,8 +914,9 @@ aes0to15:
914914
MOVQ $masks<>(SB), AX
915915
PAND (AX)(CX*8), X1
916916
final1:
917-
AESENC X0, X1 // scramble input, xor in seed
918-
AESENC X1, X1 // scramble combo 2 times
917+
PXOR X0, X1 // xor data with seed
918+
AESENC X1, X1 // scramble combo 3 times
919+
AESENC X1, X1
919920
AESENC X1, X1
920921
MOVQ X1, (DX)
921922
RET
@@ -949,9 +950,13 @@ aes17to32:
949950
MOVOU (AX), X2
950951
MOVOU -16(AX)(CX*1), X3
951952

953+
// xor with seed
954+
PXOR X0, X2
955+
PXOR X1, X3
956+
952957
// scramble 3 times
953-
AESENC X0, X2
954-
AESENC X1, X3
958+
AESENC X2, X2
959+
AESENC X3, X3
955960
AESENC X2, X2
956961
AESENC X3, X3
957962
AESENC X2, X2
@@ -977,11 +982,16 @@ aes33to64:
977982
MOVOU 16(AX), X5
978983
MOVOU -32(AX)(CX*1), X6
979984
MOVOU -16(AX)(CX*1), X7
985+
986+
PXOR X0, X4
987+
PXOR X1, X5
988+
PXOR X2, X6
989+
PXOR X3, X7
980990

981-
AESENC X0, X4
982-
AESENC X1, X5
983-
AESENC X2, X6
984-
AESENC X3, X7
991+
AESENC X4, X4
992+
AESENC X5, X5
993+
AESENC X6, X6
994+
AESENC X7, X7
985995

986996
AESENC X4, X4
987997
AESENC X5, X5
@@ -1032,17 +1042,17 @@ aes65to128:
10321042
MOVOU -32(AX)(CX*1), X14
10331043
MOVOU -16(AX)(CX*1), X15
10341044

1035-
// scramble data, xor in seed
1036-
AESENC X0, X8
1037-
AESENC X1, X9
1038-
AESENC X2, X10
1039-
AESENC X3, X11
1040-
AESENC X4, X12
1041-
AESENC X5, X13
1042-
AESENC X6, X14
1043-
AESENC X7, X15
1045+
// xor with seed
1046+
PXOR X0, X8
1047+
PXOR X1, X9
1048+
PXOR X2, X10
1049+
PXOR X3, X11
1050+
PXOR X4, X12
1051+
PXOR X5, X13
1052+
PXOR X6, X14
1053+
PXOR X7, X15
10441054

1045-
// scramble twice
1055+
// scramble 3 times
10461056
AESENC X8, X8
10471057
AESENC X9, X9
10481058
AESENC X10, X10
@@ -1051,7 +1061,16 @@ aes65to128:
10511061
AESENC X13, X13
10521062
AESENC X14, X14
10531063
AESENC X15, X15
1054-
1064+
1065+
AESENC X8, X8
1066+
AESENC X9, X9
1067+
AESENC X10, X10
1068+
AESENC X11, X11
1069+
AESENC X12, X12
1070+
AESENC X13, X13
1071+
AESENC X14, X14
1072+
AESENC X15, X15
1073+
10551074
AESENC X8, X8
10561075
AESENC X9, X9
10571076
AESENC X10, X10
@@ -1105,21 +1124,31 @@ aes129plus:
11051124
MOVOU -32(AX)(CX*1), X14
11061125
MOVOU -16(AX)(CX*1), X15
11071126

1108-
// scramble input once, xor in seed
1109-
AESENC X0, X8
1110-
AESENC X1, X9
1111-
AESENC X2, X10
1112-
AESENC X3, X11
1113-
AESENC X4, X12
1114-
AESENC X5, X13
1115-
AESENC X6, X14
1116-
AESENC X7, X15
1127+
// xor in seed
1128+
PXOR X0, X8
1129+
PXOR X1, X9
1130+
PXOR X2, X10
1131+
PXOR X3, X11
1132+
PXOR X4, X12
1133+
PXOR X5, X13
1134+
PXOR X6, X14
1135+
PXOR X7, X15
11171136

11181137
// compute number of remaining 128-byte blocks
11191138
DECQ CX
11201139
SHRQ $7, CX
11211140

11221141
aesloop:
1142+
// scramble state
1143+
AESENC X8, X8
1144+
AESENC X9, X9
1145+
AESENC X10, X10
1146+
AESENC X11, X11
1147+
AESENC X12, X12
1148+
AESENC X13, X13
1149+
AESENC X14, X14
1150+
AESENC X15, X15
1151+
11231152
// scramble state, xor in a block
11241153
MOVOU (AX), X0
11251154
MOVOU 16(AX), X1
@@ -1138,7 +1167,11 @@ aesloop:
11381167
AESENC X6, X14
11391168
AESENC X7, X15
11401169

1141-
// scramble state
1170+
ADDQ $128, AX
1171+
DECQ CX
1172+
JNE aesloop
1173+
1174+
// 3 more scrambles to finish
11421175
AESENC X8, X8
11431176
AESENC X9, X9
11441177
AESENC X10, X10
@@ -1147,12 +1180,6 @@ aesloop:
11471180
AESENC X13, X13
11481181
AESENC X14, X14
11491182
AESENC X15, X15
1150-
1151-
ADDQ $128, AX
1152-
DECQ CX
1153-
JNE aesloop
1154-
1155-
// 2 more scrambles to finish
11561183
AESENC X8, X8
11571184
AESENC X9, X9
11581185
AESENC X10, X10

src/runtime/hash_test.go

Lines changed: 20 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -681,3 +681,23 @@ func BenchmarkUnalignedLoad(b *testing.B) {
681681
}
682682
sink = s
683683
}
684+
685+
func TestCollisions(t *testing.T) {
686+
for i := 0; i < 16; i++ {
687+
for j := 0; j < 16; j++ {
688+
if j == i {
689+
continue
690+
}
691+
var a [16]byte
692+
m := make(map[uint16]struct{}, 1<<16)
693+
for n := 0; n < 1<<16; n++ {
694+
a[i] = byte(n)
695+
a[j] = byte(n >> 8)
696+
m[uint16(BytesHash(a[:], 0))] = struct{}{}
697+
}
698+
if len(m) <= 1<<15 {
699+
t.Errorf("too many collisions i=%d j=%d outputs=%d out of 65536\n", i, j, len(m))
700+
}
701+
}
702+
}
703+
}

0 commit comments

Comments
 (0)