diff --git a/README.md b/README.md index bcc1db5..0d0b105 100644 --- a/README.md +++ b/README.md @@ -6,9 +6,9 @@ * **Bug reports**: https://github.com/wrathematics/argon2/issues -**argon2** is an R package for secure password hashing via the argon2 algorithm. It is a relatively new hashing algorithm and is believed to be very secure. The package also includes some utilities that should be useful for digest authentication, including a wrapper of blake2b. For similar R packages, see **sodium** and **bcrypt**. +**argon2** is an R package for secure password hashing via the argon2 algorithm. It is a relatively new hashing algorithm and is believed to be very secure. The package also includes some utilities that should be useful for digest authentication, including a wrapper of blake2b. For similar R packages, see **sodium** and **bcrypt**. -The package includes a source distribution of the latest implementation from the argon2 developers: https://github.com/P-H-C/phc-winner-argon2. Note that we are unaffiliated with their project; if we break something, don't blame them! +The package includes a source distribution of the latest implementation from the argon2 developers: https://github.com/P-H-C/phc-winner-argon2. Note that we are unaffiliated with their project; if we break something, don't blame them! @@ -26,6 +26,8 @@ The development version is maintained on GitHub: remotes::install_github("wrathematics/argon2") ``` +If you build the package from source, you can enable CPU vectorization optimizations by using the configure flag `--enable-vec`. This improvement can not be made the default because of CRAN rules which I disagree with. + ## Usage diff --git a/configure b/configure index c0406e1..b5f6255 100755 --- a/configure +++ b/configure @@ -584,6 +584,7 @@ PACKAGE_URL= ac_unique_file="DESCRIPTION" ac_subst_vars='LTLIBOBJS LIBOBJS +ADDL_CFLAGS FILL_IMPL OBJEXT EXEEXT @@ -634,6 +635,7 @@ SHELL' ac_subst_files='' ac_user_opts=' enable_option_checking +enable_vec ' ac_precious_vars='build_alias host_alias @@ -1257,6 +1259,12 @@ if test -n "$ac_init_help"; then cat <<\_ACEOF +Optional Features: + --disable-option-checking ignore unrecognized --enable/--with options + --disable-FEATURE do not include FEATURE (same as --enable-FEATURE=no) + --enable-FEATURE[=ARG] include FEATURE [ARG=yes] + --enable-vec Enable vectorized optimizations. + Some influential environment variables: CC C compiler command CFLAGS C compiler flags @@ -1844,22 +1852,33 @@ ac_compiler_gnu=$ac_cv_c_compiler_gnu -# Get C compiler from R -: ${R_HOME=`R RHOME`} -if test -z "${R_HOME}"; then - echo "could not determine R_HOME" - exit 1 + +# Check whether --enable-vec was given. +if test "${enable_vec+set}" = set; then : + enableval=$enable_vec; USE_VEC="yes" +else + USE_VEC="no" + fi -CC=`"${R_HOME}/bin/R" CMD config CC` -ac_ext=c + +if test "X${USE_VEC}" = "Xyes"; then + # Get C compiler from R + : ${R_HOME=`R RHOME`} + if test -z "${R_HOME}"; then + echo "could not determine R_HOME" + exit 1 + fi + CC=`"${R_HOME}/bin/R" CMD config CC` + + ac_ext=c ac_cpp='$CPP $CPPFLAGS' ac_compile='$CC -c $CFLAGS $CPPFLAGS conftest.$ac_ext >&5' ac_link='$CC -o conftest$ac_exeext $CFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS >&5' ac_compiler_gnu=$ac_cv_c_compiler_gnu -ac_ext=c + ac_ext=c ac_cpp='$CPP $CPPFLAGS' ac_compile='$CC -c $CFLAGS $CPPFLAGS conftest.$ac_ext >&5' ac_link='$CC -o conftest$ac_exeext $CFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS >&5' @@ -2684,14 +2703,14 @@ fi fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ax_cv_gcc_check_x86_cpu_init" >&5 $as_echo "$ax_cv_gcc_check_x86_cpu_init" >&6; } -if test "X$ax_cv_gcc_check_x86_cpu_init" = "Xno"; then : + if test "X$ax_cv_gcc_check_x86_cpu_init" = "Xno"; then : CC_IS_GCC="no" else CC_IS_GCC="yes" fi -if test "X${CC_IS_GCC}" = "Xyes"; then - ac_ext=c + if test "X${CC_IS_GCC}" = "Xyes"; then + ac_ext=c ac_cpp='$CPP $CPPFLAGS' ac_compile='$CC -c $CFLAGS $CPPFLAGS conftest.$ac_ext >&5' ac_link='$CC -o conftest$ac_exeext $CFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS >&5' @@ -2738,72 +2757,6 @@ fi - ac_ext=c -ac_cpp='$CPP $CPPFLAGS' -ac_compile='$CC -c $CFLAGS $CPPFLAGS conftest.$ac_ext >&5' -ac_link='$CC -o conftest$ac_exeext $CFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS >&5' -ac_compiler_gnu=$ac_cv_c_compiler_gnu - - - { $as_echo "$as_me:${as_lineno-$LINENO}: checking for x86 avx512f instruction support" >&5 -$as_echo_n "checking for x86 avx512f instruction support... " >&6; } -if ${ax_cv_gcc_x86_cpu_supports_avx512f+:} false; then : - $as_echo_n "(cached) " >&6 -else - if test "$cross_compiling" = yes; then : - { { $as_echo "$as_me:${as_lineno-$LINENO}: error: in \`$ac_pwd':" >&5 -$as_echo "$as_me: error: in \`$ac_pwd':" >&2;} -as_fn_error $? "cannot run test program while cross compiling -See \`config.log' for more details" "$LINENO" 5; } -else - cat confdefs.h - <<_ACEOF >conftest.$ac_ext -/* end confdefs.h. */ -#include -int -main () -{ - __builtin_cpu_init (); - if (__builtin_cpu_supports("avx512f")) - return 0; - return 1; - - ; - return 0; -} -_ACEOF -if ac_fn_c_try_run "$LINENO"; then : - ax_cv_gcc_x86_cpu_supports_avx512f=yes -else - ax_cv_gcc_x86_cpu_supports_avx512f=no - -fi -rm -f core *.core core.conftest.* gmon.out bb.out conftest$ac_exeext \ - conftest.$ac_objext conftest.beam conftest.$ac_ext -fi - - -fi -{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $ax_cv_gcc_x86_cpu_supports_avx512f" >&5 -$as_echo "$ax_cv_gcc_x86_cpu_supports_avx512f" >&6; } - ac_ext=c -ac_cpp='$CPP $CPPFLAGS' -ac_compile='$CC -c $CFLAGS $CPPFLAGS conftest.$ac_ext >&5' -ac_link='$CC -o conftest$ac_exeext $CFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS >&5' -ac_compiler_gnu=$ac_cv_c_compiler_gnu - - if test "x$ax_cv_gcc_x86_cpu_supports_avx512f" = xyes; then : - -$as_echo "#define HAVE_AVX512F_INSTRUCTIONS 1" >>confdefs.h - - HAS_AVX512F="yes" -else - HAS_AVX512F="no" - -fi - - - - ac_ext=c ac_cpp='$CPP $CPPFLAGS' ac_compile='$CC -c $CFLAGS $CPPFLAGS conftest.$ac_ext >&5' @@ -2935,28 +2888,42 @@ fi - if test "X${HAS_AVX512F}" = "Xno" -a "X${HAS_AVX2}" = "Xno" -a "X${HAS_SSE2}" = "Xno"; then - FILL_IMPL="ref.o" + if test "X${HAS_AVX2}" = "Xyes"; then + FILL_IMPL="opt.o" + ADDL_CFLAGS="-mavx2" + elif test "X${HAS_SSE2}" = "Xyes"; then + FILL_IMPL="opt.o" + ADDL_CFLAGS="-msse2" + else + FILL_IMPL="ref.o" + ADDL_CFLAGS="" + fi else - FILL_IMPL="opt.o" + HAS_AVX2="unknown - couldn't find gcc" + HAS_SSE2="unknown - couldn't find gcc" + ADDL_CFLAGS="" + FILL_IMPL="ref.o" fi else - HAS_AVX512F="unknown - couldn't find gcc" - HAS_AVX2="${HAS_AVX512F}" - HAS_SSE2="${HAS_AVX512F}" + HAS_AVX2="unknown - did not check" + HAS_SSE2="unknown - did not check" + ADDL_CFLAGS="" FILL_IMPL="ref.o" fi + + echo " " echo "****************** Results of argon2 package configure *******************" echo "* Arch Report" -echo "* >> AVX512f = ${HAS_AVX512F}" echo "* >> AVX2 = ${HAS_AVX2}" echo "* >> SSE2 = ${HAS_SSE2}" +echo "* >> CFLAGS += ${ADDL_CFLAGS}" echo "**************************************************************************" echo " " + ac_config_files="$ac_config_files src/Makevars" cat >confcache <<\_ACEOF diff --git a/configure.ac b/configure.ac index 2e90bbf..9ac1b4e 100644 --- a/configure.ac +++ b/configure.ac @@ -3,40 +3,57 @@ AC_INIT AC_CONFIG_SRCDIR([DESCRIPTION]) m4_include([tools/ax_gcc_x86_cpu_supports.m4]) -# Get C compiler from R -: ${R_HOME=`R RHOME`} -if test -z "${R_HOME}"; then - echo "could not determine R_HOME" - exit 1 -fi -CC=`"${R_HOME}/bin/R" CMD config CC` - - -AC_LANG_PUSH([C]) -AC_CACHE_CHECK([for ${CC} __builtin_cpu_init function], - [ax_cv_gcc_check_x86_cpu_init], - [AC_RUN_IFELSE( - [AC_LANG_PROGRAM([#include ], - [__builtin_cpu_init ();]) - ], - [ax_cv_gcc_check_x86_cpu_init=yes], - [ax_cv_gcc_check_x86_cpu_init=no])]) -AS_IF([test "X$ax_cv_gcc_check_x86_cpu_init" = "Xno"], [CC_IS_GCC="no"], [CC_IS_GCC="yes"]) - -if test "X${CC_IS_GCC}" = "Xyes"; then - AX_GCC_X86_CPU_SUPPORTS(avx512f, [HAS_AVX512F="yes"],[HAS_AVX512F="no"]) - AX_GCC_X86_CPU_SUPPORTS(avx2, [HAS_AVX2="yes"],[HAS_AVX2="no"]) - AX_GCC_X86_CPU_SUPPORTS(sse2, [HAS_SSE2="yes"],[HAS_SSE2="no"]) + +AC_ARG_ENABLE(vec, + AC_HELP_STRING([--enable-vec], [Enable vectorized optimizations.]), + [USE_VEC="yes"], [USE_VEC="no"] +) + + +if test "X${USE_VEC}" = "Xyes"; then + # Get C compiler from R + : ${R_HOME=`R RHOME`} + if test -z "${R_HOME}"; then + echo "could not determine R_HOME" + exit 1 + fi + CC=`"${R_HOME}/bin/R" CMD config CC` - if test "X${HAS_AVX512F}" = "Xno" -a "X${HAS_AVX2}" = "Xno" -a "X${HAS_SSE2}" = "Xno"; then - FILL_IMPL="ref.o" + AC_LANG_PUSH([C]) + AC_CACHE_CHECK([for ${CC} __builtin_cpu_init function], + [ax_cv_gcc_check_x86_cpu_init], + [AC_RUN_IFELSE( + [AC_LANG_PROGRAM([#include ], + [__builtin_cpu_init ();]) + ], + [ax_cv_gcc_check_x86_cpu_init=yes], + [ax_cv_gcc_check_x86_cpu_init=no])]) + AS_IF([test "X$ax_cv_gcc_check_x86_cpu_init" = "Xno"], [CC_IS_GCC="no"], [CC_IS_GCC="yes"]) + + if test "X${CC_IS_GCC}" = "Xyes"; then + AX_GCC_X86_CPU_SUPPORTS(avx2, [HAS_AVX2="yes"],[HAS_AVX2="no"]) + AX_GCC_X86_CPU_SUPPORTS(sse2, [HAS_SSE2="yes"],[HAS_SSE2="no"]) + + if test "X${HAS_AVX2}" = "Xyes"; then + FILL_IMPL="opt.o" + ADDL_CFLAGS="-mavx2" + elif test "X${HAS_SSE2}" = "Xyes"; then + FILL_IMPL="opt.o" + ADDL_CFLAGS="-msse2" + else + FILL_IMPL="ref.o" + ADDL_CFLAGS="" + fi else - FILL_IMPL="opt.o" + HAS_AVX2="unknown - couldn't find gcc" + HAS_SSE2="unknown - couldn't find gcc" + ADDL_CFLAGS="" + FILL_IMPL="ref.o" fi else - HAS_AVX512F="unknown - couldn't find gcc" - HAS_AVX2="${HAS_AVX512F}" - HAS_SSE2="${HAS_AVX512F}" + HAS_AVX2="unknown - did not check" + HAS_SSE2="unknown - did not check" + ADDL_CFLAGS="" FILL_IMPL="ref.o" fi @@ -45,12 +62,13 @@ fi echo " " echo "****************** Results of argon2 package configure *******************" echo "* Arch Report" -echo "* >> AVX512f = ${HAS_AVX512F}" echo "* >> AVX2 = ${HAS_AVX2}" echo "* >> SSE2 = ${HAS_SSE2}" +echo "* >> CFLAGS += ${ADDL_CFLAGS}" echo "**************************************************************************" echo " " AC_SUBST(FILL_IMPL) +AC_SUBST(ADDL_CFLAGS) AC_CONFIG_FILES([src/Makevars]) AC_OUTPUT diff --git a/src/Makevars.in b/src/Makevars.in index 5fc1cef..6977512 100644 --- a/src/Makevars.in +++ b/src/Makevars.in @@ -1,4 +1,4 @@ -PKG_CFLAGS = $(SHLIB_OPENMP_CFLAGS) -I./argon2 +PKG_CFLAGS = $(SHLIB_OPENMP_CFLAGS) -I./argon2 @ADDL_CFLAGS@ PKG_LIBS = $(SHLIB_OPENMP_CFLAGS) ARGON2_OBJS = \ @@ -17,11 +17,8 @@ R_OBJS = \ raw_as_char.o OBJECTS = $(ARGON2_OBJS) $(R_OBJS) - all: $(SHLIB) - $(SHLIB): $(OBJECTS) - clean: rm -rf *.o *.so *.dll diff --git a/src/Makevars.win b/src/Makevars.win index 26f93bc..ed955e9 100644 --- a/src/Makevars.win +++ b/src/Makevars.win @@ -17,11 +17,8 @@ R_OBJS = \ raw_as_char.o OBJECTS = $(ARGON2_OBJS) $(R_OBJS) - all: $(SHLIB) - $(SHLIB): $(OBJECTS) - clean: rm -rf *.o *.so *.dll