summaryrefslogtreecommitdiff
path: root/arch/sparc/lib/checksum_32.S
diff options
context:
space:
mode:
authorTkhai Kirill <tkhai@yandex.ru>2011-05-10 06:31:41 +0400
committerDavid S. Miller <davem@davemloft.net>2011-05-12 08:35:04 +0400
commitb1054282d752c5a026e2c0450616ebf37fc0413e (patch)
treed88dcef782fc8e33674109c5c82fb37f2829abdc /arch/sparc/lib/checksum_32.S
parentf486b3dc2d048e7309a733f97eb9f9f83d586df2 (diff)
downloadlinux-b1054282d752c5a026e2c0450616ebf37fc0413e.tar.xz
sparc32: Fixed unaligned memory copying in function __csum_partial_copy_sparc_generic
When we are in the label cc_dword_align, registers %o0 and %o1 have the same last 2 bits, but it's not guaranteed one of them is zero. So we can get unaligned memory access in label ccte. Example of parameters which lead to this: %o0=0x7ff183e9, %o1=0x8e709e7d, %g1=3 With the parameters I had a memory corruption, when the additional 5 bytes were rewritten. This patch corrects the error. One comment to the patch. We don't care about the third bit in %o1, because cc_end_cruft stores word or less. Signed-off-by: Tkhai Kirill <tkhai@yandex.ru> Signed-off-by: David S. Miller <davem@davemloft.net>
Diffstat (limited to 'arch/sparc/lib/checksum_32.S')
-rw-r--r--arch/sparc/lib/checksum_32.S12
1 files changed, 9 insertions, 3 deletions
diff --git a/arch/sparc/lib/checksum_32.S b/arch/sparc/lib/checksum_32.S
index 3632cb34e914..0084c3361e15 100644
--- a/arch/sparc/lib/checksum_32.S
+++ b/arch/sparc/lib/checksum_32.S
@@ -289,10 +289,16 @@ cc_end_cruft:
/* Also, handle the alignment code out of band. */
cc_dword_align:
- cmp %g1, 6
- bl,a ccte
+ cmp %g1, 16
+ bge 1f
+ srl %g1, 1, %o3
+2: cmp %o3, 0
+ be,a ccte
andcc %g1, 0xf, %o3
- andcc %o0, 0x1, %g0
+ andcc %o3, %o0, %g0 ! Check %o0 only (%o1 has the same last 2 bits)
+ be,a 2b
+ srl %o3, 1, %o3
+1: andcc %o0, 0x1, %g0
bne ccslow
andcc %o0, 0x2, %g0
be 1f