forked from Minki/linux
84d69848c9
Pull kbuild updates from Michal Marek: - EXPORT_SYMBOL for asm source by Al Viro. This does bring a regression, because genksyms no longer generates checksums for these symbols (CONFIG_MODVERSIONS). Nick Piggin is working on a patch to fix this. Plus, we are talking about functions like strcpy(), which rarely change prototypes. - Fixes for PPC fallout of the above by Stephen Rothwell and Nick Piggin - fixdep speedup by Alexey Dobriyan. - preparatory work by Nick Piggin to allow architectures to build with -ffunction-sections, -fdata-sections and --gc-sections - CONFIG_THIN_ARCHIVES support by Stephen Rothwell - fix for filenames with colons in the initramfs source by me. * 'kbuild' of git://git.kernel.org/pub/scm/linux/kernel/git/mmarek/kbuild: (22 commits) initramfs: Escape colons in depfile ppc: there is no clear_pages to export powerpc/64: whitelist unresolved modversions CRCs kbuild: -ffunction-sections fix for archs with conflicting sections kbuild: add arch specific post-link Makefile kbuild: allow archs to select link dead code/data elimination kbuild: allow architectures to use thin archives instead of ld -r kbuild: Regenerate genksyms lexer kbuild: genksyms fix for typeof handling fixdep: faster CONFIG_ search ia64: move exports to definitions sparc32: debride memcpy.S a bit [sparc] unify 32bit and 64bit string.h sparc: move exports to definitions ppc: move exports to definitions arm: move exports to definitions s390: move exports to definitions m68k: move exports to definitions alpha: move exports to actual definitions x86: move exports to actual definitions ...
83 lines
2.4 KiB
ArmAsm
83 lines
2.4 KiB
ArmAsm
#include <linux/linkage.h>
|
|
#include <asm/export.h>
|
|
|
|
#include <asm/asm.h>
|
|
|
|
/*
|
|
* unsigned int __sw_hweight32(unsigned int w)
|
|
* %rdi: w
|
|
*/
|
|
ENTRY(__sw_hweight32)
|
|
|
|
#ifdef CONFIG_X86_64
|
|
movl %edi, %eax # w
|
|
#endif
|
|
__ASM_SIZE(push,) %__ASM_REG(dx)
|
|
movl %eax, %edx # w -> t
|
|
shrl %edx # t >>= 1
|
|
andl $0x55555555, %edx # t &= 0x55555555
|
|
subl %edx, %eax # w -= t
|
|
|
|
movl %eax, %edx # w -> t
|
|
shrl $2, %eax # w_tmp >>= 2
|
|
andl $0x33333333, %edx # t &= 0x33333333
|
|
andl $0x33333333, %eax # w_tmp &= 0x33333333
|
|
addl %edx, %eax # w = w_tmp + t
|
|
|
|
movl %eax, %edx # w -> t
|
|
shrl $4, %edx # t >>= 4
|
|
addl %edx, %eax # w_tmp += t
|
|
andl $0x0f0f0f0f, %eax # w_tmp &= 0x0f0f0f0f
|
|
imull $0x01010101, %eax, %eax # w_tmp *= 0x01010101
|
|
shrl $24, %eax # w = w_tmp >> 24
|
|
__ASM_SIZE(pop,) %__ASM_REG(dx)
|
|
ret
|
|
ENDPROC(__sw_hweight32)
|
|
EXPORT_SYMBOL(__sw_hweight32)
|
|
|
|
ENTRY(__sw_hweight64)
|
|
#ifdef CONFIG_X86_64
|
|
pushq %rdi
|
|
pushq %rdx
|
|
|
|
movq %rdi, %rdx # w -> t
|
|
movabsq $0x5555555555555555, %rax
|
|
shrq %rdx # t >>= 1
|
|
andq %rdx, %rax # t &= 0x5555555555555555
|
|
movabsq $0x3333333333333333, %rdx
|
|
subq %rax, %rdi # w -= t
|
|
|
|
movq %rdi, %rax # w -> t
|
|
shrq $2, %rdi # w_tmp >>= 2
|
|
andq %rdx, %rax # t &= 0x3333333333333333
|
|
andq %rdi, %rdx # w_tmp &= 0x3333333333333333
|
|
addq %rdx, %rax # w = w_tmp + t
|
|
|
|
movq %rax, %rdx # w -> t
|
|
shrq $4, %rdx # t >>= 4
|
|
addq %rdx, %rax # w_tmp += t
|
|
movabsq $0x0f0f0f0f0f0f0f0f, %rdx
|
|
andq %rdx, %rax # w_tmp &= 0x0f0f0f0f0f0f0f0f
|
|
movabsq $0x0101010101010101, %rdx
|
|
imulq %rdx, %rax # w_tmp *= 0x0101010101010101
|
|
shrq $56, %rax # w = w_tmp >> 56
|
|
|
|
popq %rdx
|
|
popq %rdi
|
|
ret
|
|
#else /* CONFIG_X86_32 */
|
|
/* We're getting an u64 arg in (%eax,%edx): unsigned long hweight64(__u64 w) */
|
|
pushl %ecx
|
|
|
|
call __sw_hweight32
|
|
movl %eax, %ecx # stash away result
|
|
movl %edx, %eax # second part of input
|
|
call __sw_hweight32
|
|
addl %ecx, %eax # result
|
|
|
|
popl %ecx
|
|
ret
|
|
#endif
|
|
ENDPROC(__sw_hweight64)
|
|
EXPORT_SYMBOL(__sw_hweight64)
|