Linux kernel mirror (for testing) git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel os linux

ARM: findbit: fix overflowing offset

When offset is larger than the size of the bit array, we should not
attempt to access the array as we can perform an access beyond the
end of the array. Fix this by changing the pre-condition.

Using "cmp r2, r1; bhs ..." covers us for the size == 0 case, since
this will always take the branch when r1 is zero, irrespective of
the value of r2. This means we can fix this bug without adding any
additional code!

Tested-by: Guenter Roeck <linux@roeck-us.net>
Signed-off-by: Russell King (Oracle) <rmk+kernel@armlinux.org.uk>

+8 -8
+8 -8
arch/arm/lib/findbit.S
··· 40 40 * Prototype: int find_next_zero_bit(void *addr, unsigned int maxbit, int offset) 41 41 */ 42 42 ENTRY(_find_next_zero_bit_le) 43 - teq r1, #0 44 - beq 3b 43 + cmp r2, r1 44 + bhs 3b 45 45 ands ip, r2, #7 46 46 beq 1b @ If new byte, goto old routine 47 47 ARM( ldrb r3, [r0, r2, lsr #3] ) ··· 81 81 * Prototype: int find_next_zero_bit(void *addr, unsigned int maxbit, int offset) 82 82 */ 83 83 ENTRY(_find_next_bit_le) 84 - teq r1, #0 85 - beq 3b 84 + cmp r2, r1 85 + bhs 3b 86 86 ands ip, r2, #7 87 87 beq 1b @ If new byte, goto old routine 88 88 ARM( ldrb r3, [r0, r2, lsr #3] ) ··· 115 115 ENDPROC(_find_first_zero_bit_be) 116 116 117 117 ENTRY(_find_next_zero_bit_be) 118 - teq r1, #0 119 - beq 3b 118 + cmp r2, r1 119 + bhs 3b 120 120 ands ip, r2, #7 121 121 beq 1b @ If new byte, goto old routine 122 122 eor r3, r2, #0x18 @ big endian byte ordering ··· 149 149 ENDPROC(_find_first_bit_be) 150 150 151 151 ENTRY(_find_next_bit_be) 152 - teq r1, #0 153 - beq 3b 152 + cmp r2, r1 153 + bhs 3b 154 154 ands ip, r2, #7 155 155 beq 1b @ If new byte, goto old routine 156 156 eor r3, r2, #0x18 @ big endian byte ordering