aboutsummaryrefslogtreecommitdiffhomepage
path: root/src/opts/opts_check_arm.cpp
diff options
context:
space:
mode:
authorGravatar digit@google.com <digit@google.com@2bbb7eff-a529-9590-31e7-b0007b416f81>2012-05-30 13:54:41 +0000
committerGravatar digit@google.com <digit@google.com@2bbb7eff-a529-9590-31e7-b0007b416f81>2012-05-30 13:54:41 +0000
commiteec9dbcace17b446d7ac3bf20f24c29cfd29736b (patch)
tree18c948328854ef584019bac7e8bf266afd94fa06 /src/opts/opts_check_arm.cpp
parentc20bc25b6e11fb068a9b4aefc1a2e576a98835ea (diff)
arm: First step towards dynamic NEON support.
This patch adds minimal support for dynamic ARM NEON support, i.e. the ability to probe the CPU at runtime for NEON and provide alternate code paths when it is available. - Add include/core/SkUtilsArm.h, which declares a few helper macros (e.g. SK_NEON_ARM_IS_DYNAMIC), plus the handy function 'sk_cpu_arm_has_neon()' which returns true if the target CPU supports the ARM NEON instruction set. Note that the header is in include/core/ because it will have to be included from NEON-specific code under src/code/ It would probably be more logical to put it under include/opts/ instead, but this would require moving all the NEON-specific stuff under src/code/ into src/opts/, which is not trivial due to the way the code is currently architected. - Add src/core/SkUtilsArm.cpp which implements 'sk_cpu_arm_has_neon' for ARM-based Linux systems, only when SK_NEON_ARM_IS_DYNAMIC is true. (For other cases, 'sk_cpu_arm_has_neon' is an inline function that returns a constant 'true' or 'false' value). There is no user-level accessible CPUID instruction on ARM, so do all CPU feature probing by parsing /proc/cpuinfo. This is Linux-specific. For Debug build types, the CPU probing result is printed to the Android log (or Linux command-line) for easier debugging. - Create a new 'opts_neon' target (static library) which shall contain all the NEON-specific code paths for the library. This is necessary because -mfpu=neon impacts also non-scalar code. Just like with -mssse3 on x86, we can't build the rest of the library with this flag. Note that for now, we only include memset16_neon and memset32_neon in this library. - Modify opts_check_arm.cpp to implement SK_ARM_NEON_IS_DYNAMIC properly. Compared to a 'xoom' build, the only difference is the use of NEON-optimized memset16/32 functions. Later patches will move more NEON-specific code paths to 'opts_neon'. Review URL: https://codereview.appspot.com/6247058 git-svn-id: http://skia.googlecode.com/svn/trunk@4069 2bbb7eff-a529-9590-31e7-b0007b416f81
Diffstat (limited to 'src/opts/opts_check_arm.cpp')
-rw-r--r--src/opts/opts_check_arm.cpp32
1 files changed, 23 insertions, 9 deletions
diff --git a/src/opts/opts_check_arm.cpp b/src/opts/opts_check_arm.cpp
index e7e39d3f9b..cd0f626993 100644
--- a/src/opts/opts_check_arm.cpp
+++ b/src/opts/opts_check_arm.cpp
@@ -16,7 +16,9 @@
#include "SkBlitRow.h"
#include "SkUtils.h"
-#if defined(__ARM_HAVE_NEON) && defined(SK_CPU_LENDIAN)
+#include "SkUtilsArm.h"
+
+#if defined(SK_CPU_LENDIAN) && !SK_ARM_NEON_IS_NONE
extern "C" void memset16_neon(uint16_t dst[], uint16_t value, int count);
extern "C" void memset32_neon(uint32_t dst[], uint32_t value, int count);
#endif
@@ -27,22 +29,34 @@ extern "C" void arm_memset32(uint32_t* dst, uint32_t value, int count);
#endif
SkMemset16Proc SkMemset16GetPlatformProc() {
-#if defined(__ARM_HAVE_NEON) && defined(SK_CPU_LENDIAN)
+#if !defined(SK_CPU_LENDIAN)
+ return NULL;
+#elif SK_ARM_NEON_IS_DYNAMIC
+ if (sk_cpu_arm_has_neon()) {
+ return memset16_neon;
+ } else {
+ return arm_memset16;
+ }
+#elif SK_ARM_NEON_IS_ALWAYS
return memset16_neon;
-#elif defined(SK_CPU_LENDIAN)
- return arm_memset16;
#else
- return NULL;
+ return arm_memset16;
#endif
}
SkMemset32Proc SkMemset32GetPlatformProc() {
-#if defined(__ARM_HAVE_NEON) && defined(SK_CPU_LENDIAN)
+#if !defined(SK_CPU_LENDIAN)
+ return NULL;
+#elif SK_ARM_NEON_IS_DYNAMIC
+ if (sk_cpu_arm_has_neon()) {
+ return memset32_neon;
+ } else {
+ return arm_memset32;
+ }
+#elif SK_ARM_NEON_IS_ALWAYS
return memset32_neon;
-#elif defined(SK_CPU_LENDIAN)
- return arm_memset32;
#else
- return NULL;
+ return arm_memset32;
#endif
}