diff --git a/GNUmakefile-cross b/GNUmakefile-cross index 0a3717ae..ab5c7481 100755 --- a/GNUmakefile-cross +++ b/GNUmakefile-cross @@ -77,7 +77,12 @@ ifeq ($(IS_ANDROID),1) CXXFLAGS += -I$(AOSP_BITS_INC) endif + # STL headers LDLIBS += $(AOSP_STL_LIB) + + # Source files copied into PWD for Android cpu-features + # setenv-android.sh does the copying. Its a dirty compile. + AOSP_CPU_OBJ = cpu-features.o endif # ARM embedded cross-compile configuration. @@ -221,7 +226,7 @@ lean: static dynamic cryptest.exe .PHONY: clean clean: - -$(RM) adhoc.cpp.o adhoc.cpp.proto.o $(LIBOBJS) $(TESTOBJS) $(DLLOBJS) $(LIBIMPORTOBJS) $(TESTIMPORTOBJS) $(DLLTESTOBJS) + -$(RM) adhoc.cpp.o adhoc.cpp.proto.o $(LIBOBJS) cpu-features.o $(TESTOBJS) $(DLLOBJS) $(LIBIMPORTOBJS) $(TESTIMPORTOBJS) $(DLLTESTOBJS) @-$(RM) libcryptopp.a libcryptopp.dylib cryptopp.dll libcryptopp.dll.a libcryptopp.import.a @-$(RM) libcryptopp.so libcryptopp.so$(SOLIB_COMPAT_SUFFIX) libcryptopp.so$(SOLIB_VERSION_SUFFIX) @-$(RM) cryptest.exe dlltest.exe cryptest.import.exe cryptest.info ct rdrand-???.o @@ -282,8 +287,8 @@ remove uninstall: @-$(RM) $(DESTDIR)$(LIBDIR)/libcryptopp.so$(SOLIB_COMPAT_SUFFIX) @-$(RM) $(DESTDIR)$(LIBDIR)/libcryptopp.so -libcryptopp.a: $(LIBOBJS) - $(AR) $(ARFLAGS) $@ $(LIBOBJS) +libcryptopp.a: $(LIBOBJS) $(AOSP_CPU_OBJ) + $(AR) $(ARFLAGS) $@ $(LIBOBJS) $(AOSP_CPU_OBJ) $(RANLIB) $@ ifeq ($(HAS_SOLIB_VERSION),1) @@ -323,6 +328,9 @@ ifeq ($(wildcard GNUmakefile.deps),GNUmakefile.deps) -include GNUmakefile.deps endif # Dependencies +cpu-features.o: cpu-features.h cpu-features.c + $(CXX) $(strip $(CXXFLAGS) -fpermissive) -c cpu-features.c + %.o : %.cpp $(CXX) $(strip $(CXXFLAGS)) -c $< diff --git a/TestScripts/setenv-android.sh b/TestScripts/setenv-android.sh index b93ce796..af59640a 100755 --- a/TestScripts/setenv-android.sh +++ b/TestScripts/setenv-android.sh @@ -356,6 +356,22 @@ if [ ! -z "$AOSP_BITS_INC" ]; then export AOSP_BITS_INC fi +# Now that we are using cpu-features from Android rather than CPU probing, we +# need to copy cpu-features.h and cpu-features.c from the NDK into our source +# directory and then build it. + +if [[ ! -e "$ANDROID_NDK_ROOT/sources/android/cpufeatures/cpu-features.h" ]]; then + echo "ERROR: Unable to locate cpu-features.h" + [ "$0" = "$BASH_SOURCE" ] && exit 1 || return 1 +fi +cp "$ANDROID_NDK_ROOT/sources/android/cpufeatures/cpu-features.h" . + +if [[ ! -e "$ANDROID_NDK_ROOT/sources/android/cpufeatures/cpu-features.c" ]]; then + echo "ERROR: Unable to locate cpu-features.c" + [ "$0" = "$BASH_SOURCE" ] && exit 1 || return 1 +fi +cp "$ANDROID_NDK_ROOT/sources/android/cpufeatures/cpu-features.c" . + ##################################################################### VERBOSE=1 @@ -371,6 +387,10 @@ if [ ! -z "$VERBOSE" ] && [ "$VERBOSE" != "0" ]; then if [ ! -z "$AOSP_BITS_INC" ]; then echo "AOSP_BITS_INC: $AOSP_BITS_INC" fi + + if [ -e "cpu-features.h" ] && [ -e "cpu-features.c" ]; then + echo "CPU FEATURES: cpu-features.h and cpu-features.c are present" + fi fi ##################################################################### diff --git a/cpu.cpp b/cpu.cpp index 6e5125bc..11baa702 100644 --- a/cpu.cpp +++ b/cpu.cpp @@ -17,15 +17,62 @@ # include #endif +#if defined(__linux__) +# include +# ifndef HWCAP_ASIMD +# define HWCAP_ASIMD (1 << 1) +# endif +# ifndef HWCAP_ARM_NEON +# define HWCAP_ARM_NEON 4096 +# endif +# ifndef HWCAP_CRC32 +# define HWCAP_CRC32 (1 << 7) +# endif +# ifndef HWCAP2_CRC32 +# define HWCAP2_CRC32 (1 << 4) +# endif +# ifndef HWCAP_PMULL +# define HWCAP_PMULL (1 << 4) +# endif +# ifndef HWCAP2_PMULL +# define HWCAP2_PMULL (1 << 1) +# endif +# ifndef HWCAP_AES +# define HWCAP_AES (1 << 3) +# endif +# ifndef HWCAP2_AES +# define HWCAP2_AES (1 << 0) +# endif +# ifndef HWCAP_SHA1 +# define HWCAP_SHA1 (1 << 5) +# endif +# ifndef HWCAP_SHA2 +# define HWCAP_SHA2 (1 << 6) +# endif +# ifndef HWCAP2_SHA1 +# define HWCAP2_SHA1 (1 << 2) +# endif +# ifndef HWCAP2_SHA2 +# define HWCAP2_SHA2 (1 << 3) +# endif +#endif + +#if defined(__APPLE__) && defined(__aarch64__) +# include +#endif + +// http://android.googlesource.com/platform/ndk/+/master/sources/android/cpufeatures/cpu-features.h +// The cpu-features header and source file are located in ANDROID_NDK_ROOT/sources/android +// setenv-android.sh will copy the header and source file into PWD and the makefile will build it in place. +#if defined(__ANDROID__) +# include "cpu-features.h" +#endif + #ifdef CRYPTOPP_GNU_STYLE_INLINE_ASSEMBLY # include # include #endif -#if defined(__ANDROID__) -# include -#endif - NAMESPACE_BEGIN(CryptoPP) #ifndef CRYPTOPP_MS_STYLE_INLINE_ASSEMBLY @@ -324,50 +371,6 @@ void DetectX86Features() #elif (CRYPTOPP_BOOL_ARM32 || CRYPTOPP_BOOL_ARM64) -#if defined(__linux__) -# include -# ifndef HWCAP_ASIMD -# define HWCAP_ASIMD (1 << 1) -# endif -# ifndef HWCAP_ARM_NEON -# define HWCAP_ARM_NEON 4096 -# endif -# ifndef HWCAP_CRC32 -# define HWCAP_CRC32 (1 << 7) -# endif -# ifndef HWCAP2_CRC32 -# define HWCAP2_CRC32 (1 << 4) -# endif -# ifndef HWCAP_PMULL -# define HWCAP_PMULL (1 << 4) -# endif -# ifndef HWCAP2_PMULL -# define HWCAP2_PMULL (1 << 1) -# endif -# ifndef HWCAP_AES -# define HWCAP_AES (1 << 3) -# endif -# ifndef HWCAP2_AES -# define HWCAP2_AES (1 << 0) -# endif -# ifndef HWCAP_SHA1 -# define HWCAP_SHA1 (1 << 5) -# endif -# ifndef HWCAP_SHA2 -# define HWCAP_SHA2 (1 << 6) -# endif -# ifndef HWCAP2_SHA1 -# define HWCAP2_SHA1 (1 << 2) -# endif -# ifndef HWCAP2_SHA2 -# define HWCAP2_SHA2 (1 << 3) -# endif -#endif - -#if defined(__APPLE__) && defined(__aarch64__) -# include -#endif - bool CRYPTOPP_SECTION_INIT g_ArmDetectionDone = false; bool CRYPTOPP_SECTION_INIT g_hasNEON = false, CRYPTOPP_SECTION_INIT g_hasPMULL = false, CRYPTOPP_SECTION_INIT g_hasCRC32 = false; bool CRYPTOPP_SECTION_INIT g_hasAES = false, CRYPTOPP_SECTION_INIT g_hasSHA1 = false, CRYPTOPP_SECTION_INIT g_hasSHA2 = false; @@ -395,11 +398,13 @@ extern bool CPU_ProbePMULL(); inline bool CPU_QueryNEON() { -#if defined(__ANDROID__) && (defined(__aarch32__) || defined(__aarch64__)) - if (android_getCpuFeatures() & ANDROID_CPU_ARM64_FEATURE_ASIMD) +#if defined(__ANDROID__) && defined(__aarch64__) + if ((android_getCpuFamily() & ANDROID_CPU_FAMILY_ARM64) && + (android_getCpuFeatures() & ANDROID_CPU_ARM64_FEATURE_ASIMD)) return true; #elif defined(__ANDROID__) && defined(__arm__) - if (android_getCpuFeatures() & ANDROID_CPU_ARM_FEATURE_NEON) + if ((android_getCpuFamily() & ANDROID_CPU_FAMILY_ARM) && + (android_getCpuFeatures() & ANDROID_CPU_ARM_FEATURE_NEON)) return true; #elif defined(__linux__) && defined(__aarch64__) if (getauxval(AT_HWCAP) & HWCAP_ASIMD) @@ -419,8 +424,13 @@ inline bool CPU_QueryNEON() inline bool CPU_QueryCRC32() { -#if defined(__ANDROID__) && (defined(__aarch64__) || defined(__aarch32__)) - if (android_getCpuFeatures() & ANDROID_CPU_ARM64_FEATURE_CRC32) +#if defined(__ANDROID__) && defined(__aarch64__) + if ((android_getCpuFamily() & ANDROID_CPU_FAMILY_ARM64) && + (android_getCpuFeatures() & ANDROID_CPU_ARM64_FEATURE_CRC32)) + return true; +#elif defined(__ANDROID__) && defined(__aarch32__) + if ((android_getCpuFamily() & ANDROID_CPU_FAMILY_ARM) && + (android_getCpuFeatures() & ANDROID_CPU_ARM_FEATURE_CRC32)) return true; #elif defined(__linux__) && defined(__aarch64__) if (getauxval(AT_HWCAP) & HWCAP_CRC32) @@ -437,8 +447,13 @@ inline bool CPU_QueryCRC32() inline bool CPU_QueryPMULL() { -#if defined(__ANDROID__) && (defined(__aarch64__) || defined(__aarch32__)) - if (android_getCpuFeatures() & ANDROID_CPU_ARM64_FEATURE_PMULL) +#if defined(__ANDROID__) && defined(__aarch64__) + if ((android_getCpuFamily() & ANDROID_CPU_FAMILY_ARM64) && + (android_getCpuFeatures() & ANDROID_CPU_ARM64_FEATURE_PMULL)) + return true; +#elif defined(__ANDROID__) && defined(__aarch32__) + if ((android_getCpuFamily() & ANDROID_CPU_FAMILY_ARM) && + (android_getCpuFeatures() & ANDROID_CPU_ARM_FEATURE_PMULL)) return true; #elif defined(__linux__) && defined(__aarch64__) if (getauxval(AT_HWCAP) & HWCAP_PMULL) @@ -455,8 +470,13 @@ inline bool CPU_QueryPMULL() inline bool CPU_QueryAES() { -#if defined(__ANDROID__) && (defined(__aarch64__) || defined(__aarch32__)) - if (android_getCpuFeatures() & ANDROID_CPU_ARM64_FEATURE_AES) +#if defined(__ANDROID__) && defined(__aarch64__) + if ((android_getCpuFamily() & ANDROID_CPU_FAMILY_ARM64) && + (android_getCpuFeatures() & ANDROID_CPU_ARM64_FEATURE_AES) + return true; +#elif defined(__ANDROID__) && defined(__aarch32__) + if (android_getCpuFamily() & ANDROID_CPU_FAMILY_ARM)) && + (android_getCpuFeatures() & ANDROID_CPU_ARM_FEATURE_AES) return true; #elif defined(__linux__) && defined(__aarch64__) if (getauxval(AT_HWCAP) & HWCAP_AES) @@ -485,8 +505,13 @@ inline bool CPU_QueryAES() inline bool CPU_QuerySHA1() { -#if defined(__ANDROID__) && (defined(__aarch64__) || defined(__aarch32__)) - if (android_getCpuFeatures() & ANDROID_CPU_ARM64_FEATURE_SHA1) +#if defined(__ANDROID__) && defined(__aarch64__) + if ((android_getCpuFamily() & ANDROID_CPU_FAMILY_ARM64) && + (android_getCpuFeatures() & ANDROID_CPU_ARM64_FEATURE_SHA1)) + return true; +#elif defined(__ANDROID__) && defined(__aarch32__) + if ((android_getCpuFamily() & ANDROID_CPU_FAMILY_ARM) && + (android_getCpuFeatures() & ANDROID_CPU_ARM_FEATURE_SHA1)) return true; #elif defined(__linux__) && defined(__aarch64__) if (getauxval(AT_HWCAP) & HWCAP_SHA1) @@ -515,8 +540,13 @@ inline bool CPU_QuerySHA1() inline bool CPU_QuerySHA2() { -#if defined(__ANDROID__) && (defined(__aarch64__) || defined(__aarch32__)) - if (android_getCpuFeatures() & ANDROID_CPU_ARM64_FEATURE_SHA2) +#if defined(__ANDROID__) && defined(__aarch64__) + if ((android_getCpuFamily() & ANDROID_CPU_FAMILY_ARM64) && + (android_getCpuFeatures() & ANDROID_CPU_ARM64_FEATURE_SHA2)) + return true; +#elif defined(__ANDROID__) && defined(__aarch32__) + if ((android_getCpuFamily() & ANDROID_CPU_FAMILY_ARM) && + (android_getCpuFeatures() & ANDROID_CPU_ARM_FEATURE_SHA2)) return true; #elif defined(__linux__) && defined(__aarch64__) if (getauxval(AT_HWCAP) & HWCAP_SHA2) diff --git a/setenv-android.sh b/setenv-android.sh index b93ce796..af59640a 100755 --- a/setenv-android.sh +++ b/setenv-android.sh @@ -356,6 +356,22 @@ if [ ! -z "$AOSP_BITS_INC" ]; then export AOSP_BITS_INC fi +# Now that we are using cpu-features from Android rather than CPU probing, we +# need to copy cpu-features.h and cpu-features.c from the NDK into our source +# directory and then build it. + +if [[ ! -e "$ANDROID_NDK_ROOT/sources/android/cpufeatures/cpu-features.h" ]]; then + echo "ERROR: Unable to locate cpu-features.h" + [ "$0" = "$BASH_SOURCE" ] && exit 1 || return 1 +fi +cp "$ANDROID_NDK_ROOT/sources/android/cpufeatures/cpu-features.h" . + +if [[ ! -e "$ANDROID_NDK_ROOT/sources/android/cpufeatures/cpu-features.c" ]]; then + echo "ERROR: Unable to locate cpu-features.c" + [ "$0" = "$BASH_SOURCE" ] && exit 1 || return 1 +fi +cp "$ANDROID_NDK_ROOT/sources/android/cpufeatures/cpu-features.c" . + ##################################################################### VERBOSE=1 @@ -371,6 +387,10 @@ if [ ! -z "$VERBOSE" ] && [ "$VERBOSE" != "0" ]; then if [ ! -z "$AOSP_BITS_INC" ]; then echo "AOSP_BITS_INC: $AOSP_BITS_INC" fi + + if [ -e "cpu-features.h" ] && [ -e "cpu-features.c" ]; then + echo "CPU FEATURES: cpu-features.h and cpu-features.c are present" + fi fi #####################################################################