diff --git a/libxcrypt-4.1.1_to_master.patch b/libxcrypt-4.1.1_to_master.patch deleted file mode 100644 index 21db174..0000000 --- a/libxcrypt-4.1.1_to_master.patch +++ /dev/null @@ -1,2808 +0,0 @@ -From 0e5a38cde2ede896e4dca6d85f133d9e23ec72cc Mon Sep 17 00:00:00 2001 -From: =?UTF-8?q?Bj=C3=B6rn=20Esser?= -Date: Wed, 1 Aug 2018 11:51:23 +0200 -Subject: [PATCH 01/10] Bump tarball version to 4.1.2 and update NEWS. - ---- - NEWS | 2 ++ - configure.ac | 2 +- - 2 files changed, 3 insertions(+), 1 deletion(-) - -diff --git a/NEWS b/NEWS -index 0288c44..40effdc 100644 ---- a/NEWS -+++ b/NEWS -@@ -3,6 +3,8 @@ libxcrypt NEWS -- history of user-visible changes. - Please send bug reports, questions and suggestions to - . - -+Version 4.1.2 -+ - Version 4.1.1 - * --enable-hashes now supports additional groups of hashing methods: - 'freebsd', 'netbsd', 'openbsd', 'osx', and 'solaris', which select -diff --git a/configure.ac b/configure.ac -index a22a592..8940e2d 100644 ---- a/configure.ac -+++ b/configure.ac -@@ -1,7 +1,7 @@ - # Process this file with autoconf to produce a configure script. - m4_include([m4/zw_automodern.m4]) - AC_INIT([xcrypt], -- [4.1.1], -+ [4.1.2], - [https://github.com/besser82/libxcrypt/issues], - [libxcrypt], - [https://github.com/besser82/libxcrypt]) - -From 7281ceb60e404e8734784670490aaf7d95ffb970 Mon Sep 17 00:00:00 2001 -From: =?UTF-8?q?Bj=C3=B6rn=20Esser?= -Date: Thu, 2 Aug 2018 09:44:07 +0200 -Subject: [PATCH 02/10] Use valgrind memcheck if available to test for memory - leaks. - ---- - .travis.yml | 5 +- - Makefile.am | 11 +- - NEWS | 1 + - configure.ac | 13 +- - m4/ax_valgrind_check.m4 | 239 ++++++++++++++++++ - test-symbols-compat => test-symbols-compat.sh | 0 - ...symbols-renames => test-symbols-renames.sh | 0 - test-symbols-static => test-symbols-static.sh | 0 - 8 files changed, 261 insertions(+), 8 deletions(-) - create mode 100644 m4/ax_valgrind_check.m4 - rename test-symbols-compat => test-symbols-compat.sh (100%) - rename test-symbols-renames => test-symbols-renames.sh (100%) - rename test-symbols-static => test-symbols-static.sh (100%) - -diff --git a/.travis.yml b/.travis.yml -index db45ded..1f8e224 100644 ---- a/.travis.yml -+++ b/.travis.yml -@@ -155,7 +155,7 @@ before_install: - - docker exec -t buildenv /bin/sh -c 'for i in `seq 0 99`; do dnf makecache && i= && break || sleep 1; done; [ -z "$i" ]' - - docker exec -t buildenv /bin/sh -c 'for i in `seq 0 99`; do dnf -y upgrade && i= && break || sleep 1; done; [ -z "$i" ]' - - docker exec -t buildenv /bin/sh -c 'for i in `seq 0 99`; do dnf -y groups install buildsys-build && i= && break || sleep 1; done; [ -z "$i" ]' -- - docker exec -t buildenv /bin/sh -c 'for i in `seq 0 99`; do dnf -y install libtool && i= && break || sleep 1; done; [ -z "$i" ]' -+ - docker exec -t buildenv /bin/sh -c 'for i in `seq 0 99`; do dnf -y install libtool valgrind && i= && break || sleep 1; done; [ -z "$i" ]' - - if [[ "$CC" == "clang" ]] ; then docker exec -t buildenv /bin/sh -c 'for i in `seq 0 99`; do dnf -y install clang && i= && break || sleep 1; done; [ -z "$i" ]' ; fi - - if [[ "$CODECOV" == "1" ]] ; then docker exec -t buildenv /bin/sh -c 'for i in `seq 0 99`; do dnf -y install '/usr/bin/git' '/usr/bin/lcov' '/usr/bin/pip3' && i= && break || sleep 1; done; [ -z "$i" ]' ; fi - - if [[ "$CODECOV" == "1" ]] ; then docker exec -t buildenv /bin/sh -c "pip3 install codecov" ; fi -@@ -178,6 +178,7 @@ script: - - docker exec -t buildenv /bin/sh -c "make -C /opt/libxcrypt -j$((`nproc --all` * 2))" - - docker exec -t buildenv /bin/sh -c "make -C /opt/libxcrypt install" - - docker exec -t buildenv /bin/sh -c "(make -C /opt/libxcrypt -j$((`nproc --all` * 2)) check || (cat /opt/libxcrypt/test-suite.log && exit 1))" -+ - docker exec -t buildenv /bin/sh -c "(make -C /opt/libxcrypt -j$((`nproc --all` * 2)) check-valgrind-memcheck || (cat /opt/libxcrypt/test-suite-memcheck.log && exit 1))" - - after_success: -- - if [[ "$CODECOV" == "1" ]] ; then docker exec -t buildenv /bin/sh -c "make -C /opt/libxcrypt check && cd /opt/libxcrypt && lcov --directory . --capture --output-file all_coverage.info && lcov --remove all_coverage.info '/usr/*' '*test*' > coverage.info && rm all_coverage.info && codecov -X gcov" ; fi -+ - if [[ "$CODECOV" == "1" ]] ; then docker exec -t buildenv /bin/sh -c "cd /opt/libxcrypt && lcov --directory . --capture --output-file all_coverage.info && lcov --remove all_coverage.info '/usr/*' '*test*' > coverage.info && rm all_coverage.info && codecov -X gcov" ; fi -diff --git a/Makefile.am b/Makefile.am -index 201dea5..874db12 100644 ---- a/Makefile.am -+++ b/Makefile.am -@@ -9,6 +9,9 @@ ACLOCAL_AMFLAGS = -I m4 - - AM_CFLAGS = $(WARN_CFLAGS) - -+@VALGRIND_CHECK_RULES@ -+TEST_EXTENSIONS = .sh -+ - EXTRA_DIST = \ - LICENSING THANKS \ - libcrypt.map.in libcrypt.minver \ -@@ -158,15 +161,15 @@ endif - - TESTS = $(check_PROGRAMS) - if ENABLE_STATIC --TESTS += test-symbols-static -+TESTS += test-symbols-static.sh - if HAVE_CPP_dD --TESTS += test-symbols-renames -+TESTS += test-symbols-renames.sh - endif - endif - if ENABLE_OBSOLETE_API --TESTS += test-symbols-compat -+TESTS += test-symbols-compat.sh - endif --EXTRA_DIST += test-symbols-static test-symbols-compat test-symbols-renames -+EXTRA_DIST += test-symbols-static.sh test-symbols-compat.sh test-symbols-renames.sh - - AM_TESTS_ENVIRONMENT = \ - lib_la="./libcrypt.la"; lib_map="$(srcdir)/libcrypt.map.in"; \ -diff --git a/NEWS b/NEWS -index 40effdc..77b556f 100644 ---- a/NEWS -+++ b/NEWS -@@ -4,6 +4,7 @@ Please send bug reports, questions and suggestions to - . - - Version 4.1.2 -+* Add optional 'check-valgrind' target to the Makefile. - - Version 4.1.1 - * --enable-hashes now supports additional groups of hashing methods: -diff --git a/configure.ac b/configure.ac -index 8940e2d..9ea30f6 100644 ---- a/configure.ac -+++ b/configure.ac -@@ -51,7 +51,6 @@ AC_C_BIGENDIAN( - AC_DEFINE([IS_BIGENDIAN], 0, - [Define to 0 if system's architecture is little-endian.]) - ) -- - # One of the test scripts needs to use -dD. - AC_CACHE_CHECK([whether the preprocessor ($CPP) supports -dD], - [ac_cv_prog_cc_dD], -@@ -151,8 +150,18 @@ AC_CHECK_FUNCS_ONCE([ - syscall - ]) - --# Configure options. -+# Disable valgrind tools for checking multithreaded -+# programs, as we don't use them in checks. -+AX_VALGRIND_DFLT([drd], [off]) -+AX_VALGRIND_DFLT([helgrind], [off]) -+ -+# Valgrind's sgcheck is b0rk3n upstream. -+AX_VALGRIND_DFLT([sgcheck], [off]) - -+# Add a target to run testsuite with valgrind. -+AX_VALGRIND_CHECK() -+ -+# Configure options. - AC_ARG_ENABLE([obsolete-api], - AS_HELP_STRING( - [--enable-obsolete-api[=ARG]], -diff --git a/m4/ax_valgrind_check.m4 b/m4/ax_valgrind_check.m4 -new file mode 100644 -index 0000000..7033798 ---- /dev/null -+++ b/m4/ax_valgrind_check.m4 -@@ -0,0 +1,239 @@ -+# =========================================================================== -+# https://www.gnu.org/software/autoconf-archive/ax_valgrind_check.html -+# =========================================================================== -+# -+# SYNOPSIS -+# -+# AX_VALGRIND_DFLT(memcheck|helgrind|drd|sgcheck, on|off) -+# AX_VALGRIND_CHECK() -+# -+# DESCRIPTION -+# -+# AX_VALGRIND_CHECK checks whether Valgrind is present and, if so, allows -+# running `make check` under a variety of Valgrind tools to check for -+# memory and threading errors. -+# -+# Defines VALGRIND_CHECK_RULES which should be substituted in your -+# Makefile; and $enable_valgrind which can be used in subsequent configure -+# output. VALGRIND_ENABLED is defined and substituted, and corresponds to -+# the value of the --enable-valgrind option, which defaults to being -+# enabled if Valgrind is installed and disabled otherwise. Individual -+# Valgrind tools can be disabled via --disable-valgrind-, the -+# default is configurable via the AX_VALGRIND_DFLT command or is to use -+# all commands not disabled via AX_VALGRIND_DFLT. All AX_VALGRIND_DFLT -+# calls must be made before the call to AX_VALGRIND_CHECK. -+# -+# If unit tests are written using a shell script and automake's -+# LOG_COMPILER system, the $(VALGRIND) variable can be used within the -+# shell scripts to enable Valgrind, as described here: -+# -+# https://www.gnu.org/software/gnulib/manual/html_node/Running-self_002dtests-under-valgrind.html -+# -+# Usage example: -+# -+# configure.ac: -+# -+# AX_VALGRIND_DFLT([sgcheck], [off]) -+# AX_VALGRIND_CHECK -+# -+# in each Makefile.am with tests: -+# -+# @VALGRIND_CHECK_RULES@ -+# VALGRIND_SUPPRESSIONS_FILES = my-project.supp -+# EXTRA_DIST = my-project.supp -+# -+# This results in a "check-valgrind" rule being added. Running `make -+# check-valgrind` in that directory will recursively run the module's test -+# suite (`make check`) once for each of the available Valgrind tools (out -+# of memcheck, helgrind and drd) while the sgcheck will be skipped unless -+# enabled again on the commandline with --enable-valgrind-sgcheck. The -+# results for each check will be output to test-suite-$toolname.log. The -+# target will succeed if there are zero errors and fail otherwise. -+# -+# Alternatively, a "check-valgrind-$TOOL" rule will be added, for $TOOL in -+# memcheck, helgrind, drd and sgcheck. These are useful because often only -+# some of those tools can be ran cleanly on a codebase. -+# -+# The macro supports running with and without libtool. -+# -+# LICENSE -+# -+# Copyright (c) 2014, 2015, 2016 Philip Withnall -+# -+# Copying and distribution of this file, with or without modification, are -+# permitted in any medium without royalty provided the copyright notice -+# and this notice are preserved. This file is offered as-is, without any -+# warranty. -+ -+#serial 17 -+ -+dnl Configured tools -+m4_define([valgrind_tool_list], [[memcheck], [helgrind], [drd], [sgcheck]]) -+m4_set_add_all([valgrind_exp_tool_set], [sgcheck]) -+m4_foreach([vgtool], [valgrind_tool_list], -+ [m4_define([en_dflt_valgrind_]vgtool, [on])]) -+ -+AC_DEFUN([AX_VALGRIND_DFLT],[ -+ m4_define([en_dflt_valgrind_$1], [$2]) -+])dnl -+ -+AM_EXTRA_RECURSIVE_TARGETS([check-valgrind]) -+m4_foreach([vgtool], [valgrind_tool_list], -+ [AM_EXTRA_RECURSIVE_TARGETS([check-valgrind-]vgtool)]) -+ -+AC_DEFUN([AX_VALGRIND_CHECK],[ -+ dnl Check for --enable-valgrind -+ AC_ARG_ENABLE([valgrind], -+ [AS_HELP_STRING([--enable-valgrind], [Whether to enable Valgrind on the unit tests])], -+ [enable_valgrind=$enableval],[enable_valgrind=]) -+ -+ AS_IF([test "$enable_valgrind" != "no"],[ -+ # Check for Valgrind. -+ AC_CHECK_PROG([VALGRIND],[valgrind],[valgrind]) -+ AS_IF([test "$VALGRIND" = ""],[ -+ AS_IF([test "$enable_valgrind" = "yes"],[ -+ AC_MSG_ERROR([Could not find valgrind; either install it or reconfigure with --disable-valgrind]) -+ ],[ -+ enable_valgrind=no -+ ]) -+ ],[ -+ enable_valgrind=yes -+ ]) -+ ]) -+ -+ AM_CONDITIONAL([VALGRIND_ENABLED],[test "$enable_valgrind" = "yes"]) -+ AC_SUBST([VALGRIND_ENABLED],[$enable_valgrind]) -+ -+ # Check for Valgrind tools we care about. -+ [valgrind_enabled_tools=] -+ m4_foreach([vgtool],[valgrind_tool_list],[ -+ AC_ARG_ENABLE([valgrind-]vgtool, -+ m4_if(m4_defn([en_dflt_valgrind_]vgtool),[off],dnl -+[AS_HELP_STRING([--enable-valgrind-]vgtool, [Whether to use ]vgtool[ during the Valgrind tests])],dnl -+[AS_HELP_STRING([--disable-valgrind-]vgtool, [Whether to skip ]vgtool[ during the Valgrind tests])]), -+ [enable_valgrind_]vgtool[=$enableval], -+ [enable_valgrind_]vgtool[=]) -+ AS_IF([test "$enable_valgrind" = "no"],[ -+ enable_valgrind_]vgtool[=no], -+ [test "$enable_valgrind_]vgtool[" ]dnl -+m4_if(m4_defn([en_dflt_valgrind_]vgtool), [off], [= "yes"], [!= "no"]),[ -+ AC_CACHE_CHECK([for Valgrind tool ]vgtool, -+ [ax_cv_valgrind_tool_]vgtool,[ -+ ax_cv_valgrind_tool_]vgtool[=no -+ m4_set_contains([valgrind_exp_tool_set],vgtool, -+ [m4_define([vgtoolx],[exp-]vgtool)], -+ [m4_define([vgtoolx],vgtool)]) -+ AS_IF([`$VALGRIND --tool=]vgtoolx[ --help >/dev/null 2>&1`],[ -+ ax_cv_valgrind_tool_]vgtool[=yes -+ ]) -+ ]) -+ AS_IF([test "$ax_cv_valgrind_tool_]vgtool[" = "no"],[ -+ AS_IF([test "$enable_valgrind_]vgtool[" = "yes"],[ -+ AC_MSG_ERROR([Valgrind does not support ]vgtool[; reconfigure with --disable-valgrind-]vgtool) -+ ],[ -+ enable_valgrind_]vgtool[=no -+ ]) -+ ],[ -+ enable_valgrind_]vgtool[=yes -+ ]) -+ ]) -+ AS_IF([test "$enable_valgrind_]vgtool[" = "yes"],[ -+ valgrind_enabled_tools="$valgrind_enabled_tools ]m4_bpatsubst(vgtool,[^exp-])[" -+ ]) -+ AC_SUBST([ENABLE_VALGRIND_]vgtool,[$enable_valgrind_]vgtool) -+ ]) -+ AC_SUBST([valgrind_tools],["]m4_join([ ], valgrind_tool_list)["]) -+ AC_SUBST([valgrind_enabled_tools],[$valgrind_enabled_tools]) -+ -+[VALGRIND_CHECK_RULES=' -+# Valgrind check -+# -+# Optional: -+# - VALGRIND_SUPPRESSIONS_FILES: Space-separated list of Valgrind suppressions -+# files to load. (Default: empty) -+# - VALGRIND_FLAGS: General flags to pass to all Valgrind tools. -+# (Default: --num-callers=30) -+# - VALGRIND_$toolname_FLAGS: Flags to pass to Valgrind $toolname (one of: -+# memcheck, helgrind, drd, sgcheck). (Default: various) -+ -+# Optional variables -+VALGRIND_SUPPRESSIONS ?= $(addprefix --suppressions=,$(VALGRIND_SUPPRESSIONS_FILES)) -+VALGRIND_FLAGS ?= --num-callers=30 -+VALGRIND_memcheck_FLAGS ?= --leak-check=full --show-reachable=no -+VALGRIND_helgrind_FLAGS ?= --history-level=approx -+VALGRIND_drd_FLAGS ?= -+VALGRIND_sgcheck_FLAGS ?= -+ -+# Internal use -+valgrind_log_files = $(addprefix test-suite-,$(addsuffix .log,$(valgrind_tools))) -+ -+valgrind_memcheck_flags = --tool=memcheck $(VALGRIND_memcheck_FLAGS) -+valgrind_helgrind_flags = --tool=helgrind $(VALGRIND_helgrind_FLAGS) -+valgrind_drd_flags = --tool=drd $(VALGRIND_drd_FLAGS) -+valgrind_sgcheck_flags = --tool=exp-sgcheck $(VALGRIND_sgcheck_FLAGS) -+ -+valgrind_quiet = $(valgrind_quiet_$(V)) -+valgrind_quiet_ = $(valgrind_quiet_$(AM_DEFAULT_VERBOSITY)) -+valgrind_quiet_0 = --quiet -+valgrind_v_use = $(valgrind_v_use_$(V)) -+valgrind_v_use_ = $(valgrind_v_use_$(AM_DEFAULT_VERBOSITY)) -+valgrind_v_use_0 = @echo " USE " $(patsubst check-valgrind-%-am,%,$''@):; -+ -+# Support running with and without libtool. -+ifneq ($(LIBTOOL),) -+valgrind_lt = $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=execute -+else -+valgrind_lt = -+endif -+ -+# Use recursive makes in order to ignore errors during check -+check-valgrind-am: -+ifeq ($(VALGRIND_ENABLED),yes) -+ $(A''M_V_at)$(MAKE) $(AM_MAKEFLAGS) -k \ -+ $(foreach tool, $(valgrind_enabled_tools), check-valgrind-$(tool)) -+else -+ @echo "Need to reconfigure with --enable-valgrind" -+endif -+ -+# Valgrind running -+VALGRIND_TESTS_ENVIRONMENT = \ -+ $(TESTS_ENVIRONMENT) \ -+ env VALGRIND=$(VALGRIND) \ -+ G_SLICE=always-malloc,debug-blocks \ -+ G_DEBUG=fatal-warnings,fatal-criticals,gc-friendly -+ -+VALGRIND_LOG_COMPILER = \ -+ $(valgrind_lt) \ -+ $(VALGRIND) $(VALGRIND_SUPPRESSIONS) --error-exitcode=1 $(VALGRIND_FLAGS) -+ -+define valgrind_tool_rule -+check-valgrind-$(1)-am: -+ifeq ($$(VALGRIND_ENABLED)-$$(ENABLE_VALGRIND_$(1)),yes-yes) -+ifneq ($$(TESTS),) -+ $$(valgrind_v_use)$$(MAKE) check-TESTS \ -+ TESTS_ENVIRONMENT="$$(VALGRIND_TESTS_ENVIRONMENT)" \ -+ LOG_COMPILER="$$(VALGRIND_LOG_COMPILER)" \ -+ LOG_FLAGS="$$(valgrind_$(1)_flags)" \ -+ TEST_SUITE_LOG=test-suite-$(1).log -+endif -+else ifeq ($$(VALGRIND_ENABLED),yes) -+ @echo "Need to reconfigure with --enable-valgrind-$(1)" -+else -+ @echo "Need to reconfigure with --enable-valgrind" -+endif -+endef -+ -+$(foreach tool,$(valgrind_tools),$(eval $(call valgrind_tool_rule,$(tool)))) -+ -+A''M_DISTCHECK_CONFIGURE_FLAGS ?= -+A''M_DISTCHECK_CONFIGURE_FLAGS += --disable-valgrind -+ -+MOSTLYCLEANFILES ?= -+MOSTLYCLEANFILES += $(valgrind_log_files) -+ -+.PHONY: check-valgrind $(add-prefix check-valgrind-,$(valgrind_tools)) -+'] -+ -+ AC_SUBST([VALGRIND_CHECK_RULES]) -+ m4_ifdef([_AM_SUBST_NOTMAKE], [_AM_SUBST_NOTMAKE([VALGRIND_CHECK_RULES])]) -+]) -diff --git a/test-symbols-compat b/test-symbols-compat.sh -similarity index 100% -rename from test-symbols-compat -rename to test-symbols-compat.sh -diff --git a/test-symbols-renames b/test-symbols-renames.sh -similarity index 100% -rename from test-symbols-renames -rename to test-symbols-renames.sh -diff --git a/test-symbols-static b/test-symbols-static.sh -similarity index 100% -rename from test-symbols-static -rename to test-symbols-static.sh - -From 307c223a0f8c7b52678bf3fed59685932ec57c18 Mon Sep 17 00:00:00 2001 -From: =?UTF-8?q?Bj=C3=B6rn=20Esser?= -Date: Sat, 14 Jul 2018 20:36:30 +0200 -Subject: [PATCH 03/10] Replace crypt-sha256.c with an implementation in the - Public Domain. - -This implementation is based on the SHA256-based Unix crypt -implementation. Released into the Public Domain [1] by -Ulrich Drepper . - -This file is a modified except from [2], lines 648 up to 909. - -[1] https://www.akkadia.org/drepper/sha-crypt.html -[2] https://www.akkadia.org/drepper/SHA-crypt.txt ---- - crypt-sha256.c | 351 +++++++++++++++++++++++++------------------------ - 1 file changed, 176 insertions(+), 175 deletions(-) - -diff --git a/crypt-sha256.c b/crypt-sha256.c -index e8d3808..c2954a4 100644 ---- a/crypt-sha256.c -+++ b/crypt-sha256.c -@@ -1,20 +1,17 @@ --/* One way encryption based on SHA256 sum. -- -- Copyright (C) 2007-2017 Free Software Foundation, Inc. -- -- This library is free software; you can redistribute it and/or -- modify it under the terms of the GNU Lesser General Public License -- as published by the Free Software Foundation; either version 2.1 of -- the License, or (at your option) any later version. -- -- This library is distributed in the hope that it will be useful, -- but WITHOUT ANY WARRANTY; without even the implied warranty of -- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -- GNU Lesser General Public License for more details. -- -- You should have received a copy of the GNU Lesser General Public -- License along with this library; if not, see -- . */ -+/* One way encryption based on the SHA256-based Unix crypt implementation. -+ * -+ * Written by Ulrich Drepper in 2007 [1]. -+ * To the extent possible under law, Ulrich Drepper has waived all -+ * copyright and related or neighboring rights to this work. -+ * -+ * See https://creativecommons.org/publicdomain/zero/1.0/ for further -+ * details. -+ * -+ * This file is an except from [2], lines 648 up to 909. -+ * -+ * [1] https://www.akkadia.org/drepper/sha-crypt.html -+ * [2] https://www.akkadia.org/drepper/SHA-crypt.txt -+ */ - - #include "crypt-port.h" - #include "crypt-private.h" -@@ -42,35 +39,8 @@ static const char sha256_rounds_prefix[] = "rounds="; - /* Maximum number of rounds. */ - #define ROUNDS_MAX 999999999 - --/* The maximum possible length of a SHA256-hashed password string, -- including the terminating NUL character. Prefix (including its NUL) -- + rounds tag ("rounds=$" = "rounds=\0") + strlen(ROUNDS_MAX) -- + salt (up to SALT_LEN_MAX chars) + '$' + hash (43 chars). */ -- --#define LENGTH_OF_NUMBER(n) (sizeof #n - 1) -- --#define SHA256_HASH_LENGTH \ -- (sizeof (sha256_salt_prefix) + sizeof (sha256_rounds_prefix) + \ -- LENGTH_OF_NUMBER (ROUNDS_MAX) + SALT_LEN_MAX + 1 + 43) -- --static_assert (SHA256_HASH_LENGTH <= CRYPT_OUTPUT_SIZE, -- "CRYPT_OUTPUT_SIZE is too small for SHA256"); -- --/* A sha256_buffer holds all of the sensitive intermediate data. */ --struct sha256_buffer --{ -- struct sha256_ctx ctx; -- uint8_t result[32]; -- uint8_t p_bytes[32]; -- uint8_t s_bytes[32]; --}; -- --static_assert (sizeof (struct sha256_buffer) <= ALG_SPECIFIC_SIZE, -- "ALG_SPECIFIC_SIZE is too small for SHA256"); -- -- - /* Table with characters for base64 transformation. */ --static const char b64t[] = -+static const char b64t[64] = - "./0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz"; - - /* Subroutine of _xcrypt_crypt_sha256_rn: Feed CTX with LEN bytes of a -@@ -86,30 +56,23 @@ sha256_process_recycled_bytes (unsigned char block[32], size_t len, - sha256_process_bytes (block, cnt, ctx); - } - --void --crypt_sha256_rn (const char *phrase, size_t phr_size, -- const char *setting, size_t ARG_UNUSED (set_size), -- uint8_t *output, size_t out_size, -- void *scratch, size_t scr_size) -+static char * -+sha256_crypt_r (const char *key, const char *salt, char *buffer, int buflen) - { -- /* This shouldn't ever happen, but... */ -- if (out_size < SHA256_HASH_LENGTH -- || scr_size < sizeof (struct sha256_buffer)) -- { -- errno = ERANGE; -- return; -- } -- -- struct sha256_buffer *buf = scratch; -- struct sha256_ctx *ctx = &buf->ctx; -- uint8_t *result = buf->result; -- uint8_t *p_bytes = buf->p_bytes; -- uint8_t *s_bytes = buf->s_bytes; -- char *cp = (char *)output; -- const char *salt = setting; -- -- size_t salt_size; -+ unsigned char alt_result[32] -+ __attribute__ ((__aligned__ (__alignof__ (uint32_t)))); -+ unsigned char temp_result[32] -+ __attribute__ ((__aligned__ (__alignof__ (uint32_t)))); -+ struct sha256_ctx ctx; -+ struct sha256_ctx alt_ctx; -+ size_t salt_len; -+ size_t key_len; - size_t cnt; -+ char *cp; -+ char *copied_key = NULL; -+ char *copied_salt = NULL; -+ char *p_bytes; -+ char *s_bytes; - /* Default number of rounds. */ - size_t rounds = ROUNDS_DEFAULT; - bool rounds_custom = false; -@@ -124,176 +87,214 @@ crypt_sha256_rn (const char *phrase, size_t phr_size, - == 0) - { - const char *num = salt + sizeof (sha256_rounds_prefix) - 1; -- /* Do not allow an explicit setting of zero rounds, nor of the -- default number of rounds, nor leading zeroes on the rounds. */ -- if (!(*num >= '1' && *num <= '9')) -- { -- errno = EINVAL; -- return; -- } -- -- errno = 0; - char *endp; -- rounds = strtoul (num, &endp, 10); -- if (endp == num || *endp != '$' -- || rounds < ROUNDS_MIN -- || rounds > ROUNDS_MAX -- || errno) -+ unsigned long int srounds = strtoul (num, &endp, 10); -+ if (*endp == '$') - { -- errno = EINVAL; -- return; -+ salt = endp + 1; -+ rounds = MAX (ROUNDS_MIN, MIN (srounds, ROUNDS_MAX)); -+ rounds_custom = true; - } -- salt = endp + 1; -- rounds_custom = true; - } - -- salt_size = strspn (salt, b64t); -- if (salt[salt_size] && salt[salt_size] != '$') -+ salt_len = MIN (strcspn (salt, "$"), SALT_LEN_MAX); -+ key_len = strlen (key); -+ -+ if ((key - (char *) 0) % __alignof__ (uint32_t) != 0) - { -- errno = EINVAL; -- return; -+ char *tmp = (char *) alloca (key_len + __alignof__ (uint32_t)); -+ key = copied_key = -+ memcpy (tmp + __alignof__ (uint32_t) -+ - (tmp - (char *) 0) % __alignof__ (uint32_t), -+ key, key_len); - } -- if (salt_size > SALT_LEN_MAX) -- salt_size = SALT_LEN_MAX; - -- /* Compute alternate SHA256 sum with input PHRASE, SALT, and PHRASE. The -- final result will be added to the first context. */ -- sha256_init_ctx (ctx); -+ if ((salt - (char *) 0) % __alignof__ (uint32_t) != 0) -+ { -+ char *tmp = (char *) alloca (salt_len + __alignof__ (uint32_t)); -+ salt = copied_salt = -+ memcpy (tmp + __alignof__ (uint32_t) -+ - (tmp - (char *) 0) % __alignof__ (uint32_t), -+ salt, salt_len); -+ } - -- /* Add phrase. */ -- sha256_process_bytes (phrase, phr_size, ctx); -+ /* Prepare for the real work. */ -+ sha256_init_ctx (&ctx); - -- /* Add salt. */ -- sha256_process_bytes (salt, salt_size, ctx); -+ /* Add the key string. */ -+ sha256_process_bytes (key, key_len, &ctx); - -- /* Add phrase again. */ -- sha256_process_bytes (phrase, phr_size, ctx); -+ /* The last part is the salt string. This must be at most 16 -+ characters and it ends at the first `$' character (for -+ compatibility with existing implementations). */ -+ sha256_process_bytes (salt, salt_len, &ctx); - -- /* Now get result of this (32 bytes). */ -- sha256_finish_ctx (ctx, result); -+ /* Compute alternate SHA256 sum with input KEY, SALT, and KEY. The -+ final result will be added to the first context. */ -+ sha256_init_ctx (&alt_ctx); - -- /* Prepare for the real work. */ -- sha256_init_ctx (ctx); -+ /* Add key. */ -+ sha256_process_bytes (key, key_len, &alt_ctx); - -- /* Add the phrase string. */ -- sha256_process_bytes (phrase, phr_size, ctx); -+ /* Add salt. */ -+ sha256_process_bytes (salt, salt_len, &alt_ctx); - -- /* The last part is the salt string. This must be at most 8 -- characters and it ends at the first `$' character (for -- compatibility with existing implementations). */ -- sha256_process_bytes (salt, salt_size, ctx); -+ /* Add key again. */ -+ sha256_process_bytes (key, key_len, &alt_ctx); -+ -+ /* Now get result of this (32 bytes) and add it to the other -+ context. */ -+ sha256_finish_ctx (&alt_ctx, alt_result); - -- /* Add for any character in the phrase one byte of the alternate sum. */ -- for (cnt = phr_size; cnt > 32; cnt -= 32) -- sha256_process_bytes (result, 32, ctx); -- sha256_process_bytes (result, cnt, ctx); -+ /* Add for any character in the key one byte of the alternate sum. */ -+ for (cnt = key_len; cnt > 32; cnt -= 32) -+ sha256_process_bytes (alt_result, 32, &ctx); -+ sha256_process_bytes (alt_result, cnt, &ctx); - -- /* Take the binary representation of the length of the phrase and for every -- 1 add the alternate sum, for every 0 the phrase. */ -- for (cnt = phr_size; cnt > 0; cnt >>= 1) -+ /* Take the binary representation of the length of the key and for every -+ 1 add the alternate sum, for every 0 the key. */ -+ for (cnt = key_len; cnt > 0; cnt >>= 1) - if ((cnt & 1) != 0) -- sha256_process_bytes (result, 32, ctx); -+ sha256_process_bytes (alt_result, 32, &ctx); - else -- sha256_process_bytes (phrase, phr_size, ctx); -+ sha256_process_bytes (key, key_len, &ctx); - - /* Create intermediate result. */ -- sha256_finish_ctx (ctx, result); -+ sha256_finish_ctx (&ctx, alt_result); - - /* Start computation of P byte sequence. */ -- sha256_init_ctx (ctx); -+ sha256_init_ctx (&alt_ctx); - - /* For every character in the password add the entire password. */ -- for (cnt = 0; cnt < phr_size; ++cnt) -- sha256_process_bytes (phrase, phr_size, ctx); -+ for (cnt = 0; cnt < key_len; ++cnt) -+ sha256_process_bytes (key, key_len, &alt_ctx); - - /* Finish the digest. */ -- sha256_finish_ctx (ctx, p_bytes); -+ sha256_finish_ctx (&alt_ctx, temp_result); -+ -+ /* Create byte sequence P. */ -+ cp = p_bytes = alloca (key_len); -+ for (cnt = key_len; cnt >= 32; cnt -= 32) -+ cp = mempcpy (cp, temp_result, 32); -+ memcpy (cp, temp_result, cnt); - - /* Start computation of S byte sequence. */ -- sha256_init_ctx (ctx); -+ sha256_init_ctx (&alt_ctx); - - /* For every character in the password add the entire password. */ -- for (cnt = 0; cnt < (size_t) 16 + (size_t) result[0]; ++cnt) -- sha256_process_bytes (salt, salt_size, ctx); -+ for (cnt = 0; cnt < 16 + alt_result[0]; ++cnt) -+ sha256_process_bytes (salt, salt_len, &alt_ctx); - - /* Finish the digest. */ -- sha256_finish_ctx (ctx, s_bytes); -+ sha256_finish_ctx (&alt_ctx, temp_result); -+ -+ /* Create byte sequence S. */ -+ cp = s_bytes = alloca (salt_len); -+ for (cnt = salt_len; cnt >= 32; cnt -= 32) -+ cp = mempcpy (cp, temp_result, 32); -+ memcpy (cp, temp_result, cnt); - - /* Repeatedly run the collected hash value through SHA256 to burn - CPU cycles. */ - for (cnt = 0; cnt < rounds; ++cnt) - { - /* New context. */ -- sha256_init_ctx (ctx); -+ sha256_init_ctx (&ctx); - -- /* Add phrase or last result. */ -+ /* Add key or last result. */ - if ((cnt & 1) != 0) -- sha256_process_recycled_bytes (p_bytes, phr_size, ctx); -+ sha256_process_bytes (p_bytes, key_len, &ctx); - else -- sha256_process_bytes (result, 32, ctx); -+ sha256_process_bytes (alt_result, 32, &ctx); - - /* Add salt for numbers not divisible by 3. */ - if (cnt % 3 != 0) -- sha256_process_recycled_bytes (s_bytes, salt_size, ctx); -+ sha256_process_bytes (s_bytes, salt_len, &ctx); - -- /* Add phrase for numbers not divisible by 7. */ -+ /* Add key for numbers not divisible by 7. */ - if (cnt % 7 != 0) -- sha256_process_recycled_bytes (p_bytes, phr_size, ctx); -+ sha256_process_bytes (p_bytes, key_len, &ctx); - -- /* Add phrase or last result. */ -+ /* Add key or last result. */ - if ((cnt & 1) != 0) -- sha256_process_bytes (result, 32, ctx); -+ sha256_process_bytes (alt_result, 32, &ctx); - else -- sha256_process_recycled_bytes (p_bytes, phr_size, ctx); -+ sha256_process_bytes (p_bytes, key_len, &ctx); - - /* Create intermediate result. */ -- sha256_finish_ctx (ctx, result); -+ sha256_finish_ctx (&ctx, alt_result); - } - -- /* Now we can construct the result string. It consists of four -- parts, one of which is optional. We already know that there -- is sufficient space at CP for the longest possible result string. */ -- memcpy (cp, sha256_salt_prefix, sizeof (sha256_salt_prefix) - 1); -- cp += sizeof (sha256_salt_prefix) - 1; -+ /* Now we can construct the result string. It consists of three -+ parts. */ -+ cp = stpncpy (buffer, sha256_salt_prefix, MAX (0, buflen)); -+ buflen -= sizeof (sha256_salt_prefix) - 1; - - if (rounds_custom) - { -- int n = snprintf (cp, -- SHA256_HASH_LENGTH - (sizeof (sha256_salt_prefix) - 1), -- "%s%zu$", sha256_rounds_prefix, rounds); -+ int n = snprintf (cp, MAX (0, buflen), "%s%zu$", -+ sha256_rounds_prefix, rounds); - cp += n; -+ buflen -= n; - } - -- memcpy (cp, salt, salt_size); -- cp += salt_size; -- *cp++ = '$'; -- --#define b64_from_24bit(B2, B1, B0, N) \ -- do { \ -- unsigned int w = ((((unsigned int)(B2)) << 16) | \ -- (((unsigned int)(B1)) << 8) | \ -- ((unsigned int)(B0))); \ -- int n = (N); \ -- while (n-- > 0) \ -- { \ -- *cp++ = b64t[w & 0x3f]; \ -- w >>= 6; \ -- } \ -+ cp = stpncpy (cp, salt, MIN ((size_t) MAX (0, buflen), salt_len)); -+ buflen -= MIN ((size_t) MAX (0, buflen), salt_len); -+ -+ if (buflen > 0) -+ { -+ *cp++ = '$'; -+ --buflen; -+ } -+ -+#define b64_from_24bit(B2, B1, B0, N) \ -+ do { \ -+ unsigned int w = ((B2) << 16) | ((B1) << 8) | (B0); \ -+ int n = (N); \ -+ while (n-- > 0 && buflen > 0) \ -+ { \ -+ *cp++ = b64t[w & 0x3f]; \ -+ --buflen; \ -+ w >>= 6; \ -+ } \ - } while (0) - -- b64_from_24bit (result[0], result[10], result[20], 4); -- b64_from_24bit (result[21], result[1], result[11], 4); -- b64_from_24bit (result[12], result[22], result[2], 4); -- b64_from_24bit (result[3], result[13], result[23], 4); -- b64_from_24bit (result[24], result[4], result[14], 4); -- b64_from_24bit (result[15], result[25], result[5], 4); -- b64_from_24bit (result[6], result[16], result[26], 4); -- b64_from_24bit (result[27], result[7], result[17], 4); -- b64_from_24bit (result[18], result[28], result[8], 4); -- b64_from_24bit (result[9], result[19], result[29], 4); -- b64_from_24bit (0, result[31], result[30], 3); -- -- *cp = '\0'; -+ b64_from_24bit (alt_result[0], alt_result[10], alt_result[20], 4); -+ b64_from_24bit (alt_result[21], alt_result[1], alt_result[11], 4); -+ b64_from_24bit (alt_result[12], alt_result[22], alt_result[2], 4); -+ b64_from_24bit (alt_result[3], alt_result[13], alt_result[23], 4); -+ b64_from_24bit (alt_result[24], alt_result[4], alt_result[14], 4); -+ b64_from_24bit (alt_result[15], alt_result[25], alt_result[5], 4); -+ b64_from_24bit (alt_result[6], alt_result[16], alt_result[26], 4); -+ b64_from_24bit (alt_result[27], alt_result[7], alt_result[17], 4); -+ b64_from_24bit (alt_result[18], alt_result[28], alt_result[8], 4); -+ b64_from_24bit (alt_result[9], alt_result[19], alt_result[29], 4); -+ b64_from_24bit (0, alt_result[31], alt_result[30], 3); -+ if (buflen <= 0) -+ { -+ errno = ERANGE; -+ buffer = NULL; -+ } -+ else -+ *cp = '\0'; /* Terminate the string. */ -+ -+ /* Clear the buffer for the intermediate result so that people -+ attaching to processes or reading core dumps cannot get any -+ information. We do it in this way to clear correct_words[] -+ inside the SHA256 implementation as well. */ -+ sha256_init_ctx (&ctx); -+ sha256_finish_ctx (&ctx, alt_result); -+ memset (temp_result, '\0', sizeof (temp_result)); -+ memset (p_bytes, '\0', key_len); -+ memset (s_bytes, '\0', salt_len); -+ memset (&ctx, '\0', sizeof (ctx)); -+ memset (&alt_ctx, '\0', sizeof (alt_ctx)); -+ if (copied_key != NULL) -+ memset (copied_key, '\0', key_len); -+ if (copied_salt != NULL) -+ memset (copied_salt, '\0', salt_len); -+ -+ return buffer; - } - - void - -From 40a0d88687d7944ae618b1f507e6a0adc532399c Mon Sep 17 00:00:00 2001 -From: =?UTF-8?q?Bj=C3=B6rn=20Esser?= -Date: Sat, 14 Jul 2018 21:00:10 +0200 -Subject: [PATCH 04/10] crypt-sha256.c: Apply previous commits from Zack - Weinberg - -This patch summarizes the changes from: - - * 4a1152b4f9bc900d0488b473e20daed95025f4b0 - * ccc833b4b2c60cefd74cb91a05f1ce7628179657 - * 118abc2c5c08542fe528a1193328b161a756db90 - * 9483c648978378a9cd128382049a88055d5b2a61 - * a67c7cd73c19592315ae184fe8dee155ef6ebd31 - * 4856729bd75c78e4e1e4e35ab5afd7cef6c66afc - * a2d558581c3cd9b3d62f916825405cebd708f268 - * b46a39a57e4801f5c41b1bac207239b6ed8e31a5 - * cbdf27e254b0a113f0bea87071177f083e3f2545 - * 00ec9369ac4875a8e3903d6e41ae785bbc8e8b26 - * 114d4200eaa572525089795cf7990c3dafd5028c - * ed4be6afa7b34fe0d827cc3f7f9608de0d9325cd - * a7f9df50cecec46bb8176382faa685ce35ca72be - * 15d1e3bf3d259ea262f3d34e8c225a3abfabaa09 ---- - crypt-sha256.c | 326 ++++++++++++++++++++++++------------------------- - 1 file changed, 162 insertions(+), 164 deletions(-) - -diff --git a/crypt-sha256.c b/crypt-sha256.c -index c2954a4..e036a18 100644 ---- a/crypt-sha256.c -+++ b/crypt-sha256.c -@@ -1,13 +1,15 @@ - /* One way encryption based on the SHA256-based Unix crypt implementation. - * - * Written by Ulrich Drepper in 2007 [1]. -- * To the extent possible under law, Ulrich Drepper has waived all -+ * Modified by Zack Weinberg in 2017, 2018. -+ * Composed by Björn Esser in 2018. -+ * To the extent possible under law, the named authors have waived all - * copyright and related or neighboring rights to this work. - * - * See https://creativecommons.org/publicdomain/zero/1.0/ for further - * details. - * -- * This file is an except from [2], lines 648 up to 909. -+ * This file is a modified except from [2], lines 648 up to 909. - * - * [1] https://www.akkadia.org/drepper/sha-crypt.html - * [2] https://www.akkadia.org/drepper/SHA-crypt.txt -@@ -39,8 +41,35 @@ static const char sha256_rounds_prefix[] = "rounds="; - /* Maximum number of rounds. */ - #define ROUNDS_MAX 999999999 - -+/* The maximum possible length of a SHA256-hashed password string, -+ including the terminating NUL character. Prefix (including its NUL) -+ + rounds tag ("rounds=$" = "rounds=\0") + strlen(ROUNDS_MAX) -+ + salt (up to SALT_LEN_MAX chars) + '$' + hash (43 chars). */ -+ -+#define LENGTH_OF_NUMBER(n) (sizeof #n - 1) -+ -+#define SHA256_HASH_LENGTH \ -+ (sizeof (sha256_salt_prefix) + sizeof (sha256_rounds_prefix) + \ -+ LENGTH_OF_NUMBER (ROUNDS_MAX) + SALT_LEN_MAX + 1 + 43) -+ -+static_assert (SHA256_HASH_LENGTH <= CRYPT_OUTPUT_SIZE, -+ "CRYPT_OUTPUT_SIZE is too small for SHA256"); -+ -+/* A sha256_buffer holds all of the sensitive intermediate data. */ -+struct sha256_buffer -+{ -+ struct sha256_ctx ctx; -+ uint8_t result[32]; -+ uint8_t p_bytes[32]; -+ uint8_t s_bytes[32]; -+}; -+ -+static_assert (sizeof (struct sha256_buffer) <= ALG_SPECIFIC_SIZE, -+ "ALG_SPECIFIC_SIZE is too small for SHA256"); -+ -+ - /* Table with characters for base64 transformation. */ --static const char b64t[64] = -+static const char b64t[] = - "./0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz"; - - /* Subroutine of _xcrypt_crypt_sha256_rn: Feed CTX with LEN bytes of a -@@ -56,23 +85,30 @@ sha256_process_recycled_bytes (unsigned char block[32], size_t len, - sha256_process_bytes (block, cnt, ctx); - } - --static char * --sha256_crypt_r (const char *key, const char *salt, char *buffer, int buflen) -+void -+crypt_sha256_rn (const char *phrase, size_t phr_size, -+ const char *setting, size_t ARG_UNUSED (set_size), -+ uint8_t *output, size_t out_size, -+ void *scratch, size_t scr_size) - { -- unsigned char alt_result[32] -- __attribute__ ((__aligned__ (__alignof__ (uint32_t)))); -- unsigned char temp_result[32] -- __attribute__ ((__aligned__ (__alignof__ (uint32_t)))); -- struct sha256_ctx ctx; -- struct sha256_ctx alt_ctx; -- size_t salt_len; -- size_t key_len; -+ /* This shouldn't ever happen, but... */ -+ if (out_size < SHA256_HASH_LENGTH -+ || scr_size < sizeof (struct sha256_buffer)) -+ { -+ errno = ERANGE; -+ return; -+ } -+ -+ struct sha256_buffer *buf = scratch; -+ struct sha256_ctx *ctx = &buf->ctx; -+ uint8_t *result = buf->result; -+ uint8_t *p_bytes = buf->p_bytes; -+ uint8_t *s_bytes = buf->s_bytes; -+ char *cp = (char *)output; -+ const char *salt = setting; -+ -+ size_t salt_size; - size_t cnt; -- char *cp; -- char *copied_key = NULL; -- char *copied_salt = NULL; -- char *p_bytes; -- char *s_bytes; - /* Default number of rounds. */ - size_t rounds = ROUNDS_DEFAULT; - bool rounds_custom = false; -@@ -87,214 +123,176 @@ sha256_crypt_r (const char *key, const char *salt, char *buffer, int buflen) - == 0) - { - const char *num = salt + sizeof (sha256_rounds_prefix) - 1; -- char *endp; -- unsigned long int srounds = strtoul (num, &endp, 10); -- if (*endp == '$') -+ /* Do not allow an explicit setting of zero rounds, nor of the -+ default number of rounds, nor leading zeroes on the rounds. */ -+ if (!(*num >= '1' && *num <= '9')) - { -- salt = endp + 1; -- rounds = MAX (ROUNDS_MIN, MIN (srounds, ROUNDS_MAX)); -- rounds_custom = true; -+ errno = EINVAL; -+ return; - } -- } -- -- salt_len = MIN (strcspn (salt, "$"), SALT_LEN_MAX); -- key_len = strlen (key); - -- if ((key - (char *) 0) % __alignof__ (uint32_t) != 0) -- { -- char *tmp = (char *) alloca (key_len + __alignof__ (uint32_t)); -- key = copied_key = -- memcpy (tmp + __alignof__ (uint32_t) -- - (tmp - (char *) 0) % __alignof__ (uint32_t), -- key, key_len); -+ errno = 0; -+ char *endp; -+ rounds = strtoul (num, &endp, 10); -+ if (endp == num || *endp != '$' -+ || rounds < ROUNDS_MIN -+ || rounds > ROUNDS_MAX -+ || errno) -+ { -+ errno = EINVAL; -+ return; -+ } -+ salt = endp + 1; -+ rounds_custom = true; - } - -- if ((salt - (char *) 0) % __alignof__ (uint32_t) != 0) -+ salt_size = strspn (salt, b64t); -+ if (salt[salt_size] && salt[salt_size] != '$') - { -- char *tmp = (char *) alloca (salt_len + __alignof__ (uint32_t)); -- salt = copied_salt = -- memcpy (tmp + __alignof__ (uint32_t) -- - (tmp - (char *) 0) % __alignof__ (uint32_t), -- salt, salt_len); -+ errno = EINVAL; -+ return; - } -+ if (salt_size > SALT_LEN_MAX) -+ salt_size = SALT_LEN_MAX; - -- /* Prepare for the real work. */ -- sha256_init_ctx (&ctx); -+ /* Compute alternate SHA256 sum with input PHRASE, SALT, and PHRASE. The -+ final result will be added to the first context. */ -+ sha256_init_ctx (ctx); - -- /* Add the key string. */ -- sha256_process_bytes (key, key_len, &ctx); -+ /* Add phrase. */ -+ sha256_process_bytes (phrase, phr_size, ctx); - -- /* The last part is the salt string. This must be at most 16 -- characters and it ends at the first `$' character (for -- compatibility with existing implementations). */ -- sha256_process_bytes (salt, salt_len, &ctx); -+ /* Add salt. */ -+ sha256_process_bytes (salt, salt_size, ctx); - -- /* Compute alternate SHA256 sum with input KEY, SALT, and KEY. The -- final result will be added to the first context. */ -- sha256_init_ctx (&alt_ctx); -+ /* Add phrase again. */ -+ sha256_process_bytes (phrase, phr_size, ctx); - -- /* Add key. */ -- sha256_process_bytes (key, key_len, &alt_ctx); -+ /* Now get result of this (32 bytes). */ -+ sha256_finish_ctx (ctx, result); - -- /* Add salt. */ -- sha256_process_bytes (salt, salt_len, &alt_ctx); -+ /* Prepare for the real work. */ -+ sha256_init_ctx (ctx); - -- /* Add key again. */ -- sha256_process_bytes (key, key_len, &alt_ctx); -+ /* Add the phrase string. */ -+ sha256_process_bytes (phrase, phr_size, ctx); - -- /* Now get result of this (32 bytes) and add it to the other -- context. */ -- sha256_finish_ctx (&alt_ctx, alt_result); -+ /* The last part is the salt string. This must be at most 8 -+ characters and it ends at the first `$' character (for -+ compatibility with existing implementations). */ -+ sha256_process_bytes (salt, salt_size, ctx); - -- /* Add for any character in the key one byte of the alternate sum. */ -- for (cnt = key_len; cnt > 32; cnt -= 32) -- sha256_process_bytes (alt_result, 32, &ctx); -- sha256_process_bytes (alt_result, cnt, &ctx); -+ /* Add for any character in the phrase one byte of the alternate sum. */ -+ for (cnt = phr_size; cnt > 32; cnt -= 32) -+ sha256_process_bytes (result, 32, ctx); -+ sha256_process_bytes (result, cnt, ctx); - -- /* Take the binary representation of the length of the key and for every -- 1 add the alternate sum, for every 0 the key. */ -- for (cnt = key_len; cnt > 0; cnt >>= 1) -+ /* Take the binary representation of the length of the phrase and for every -+ 1 add the alternate sum, for every 0 the phrase. */ -+ for (cnt = phr_size; cnt > 0; cnt >>= 1) - if ((cnt & 1) != 0) -- sha256_process_bytes (alt_result, 32, &ctx); -+ sha256_process_bytes (result, 32, ctx); - else -- sha256_process_bytes (key, key_len, &ctx); -+ sha256_process_bytes (phrase, phr_size, ctx); - - /* Create intermediate result. */ -- sha256_finish_ctx (&ctx, alt_result); -+ sha256_finish_ctx (ctx, result); - - /* Start computation of P byte sequence. */ -- sha256_init_ctx (&alt_ctx); -+ sha256_init_ctx (ctx); - - /* For every character in the password add the entire password. */ -- for (cnt = 0; cnt < key_len; ++cnt) -- sha256_process_bytes (key, key_len, &alt_ctx); -+ for (cnt = 0; cnt < phr_size; ++cnt) -+ sha256_process_bytes (phrase, phr_size, ctx); - - /* Finish the digest. */ -- sha256_finish_ctx (&alt_ctx, temp_result); -- -- /* Create byte sequence P. */ -- cp = p_bytes = alloca (key_len); -- for (cnt = key_len; cnt >= 32; cnt -= 32) -- cp = mempcpy (cp, temp_result, 32); -- memcpy (cp, temp_result, cnt); -+ sha256_finish_ctx (ctx, p_bytes); - - /* Start computation of S byte sequence. */ -- sha256_init_ctx (&alt_ctx); -+ sha256_init_ctx (ctx); - - /* For every character in the password add the entire password. */ -- for (cnt = 0; cnt < 16 + alt_result[0]; ++cnt) -- sha256_process_bytes (salt, salt_len, &alt_ctx); -+ for (cnt = 0; cnt < (size_t) 16 + (size_t) result[0]; ++cnt) -+ sha256_process_bytes (salt, salt_size, ctx); - - /* Finish the digest. */ -- sha256_finish_ctx (&alt_ctx, temp_result); -- -- /* Create byte sequence S. */ -- cp = s_bytes = alloca (salt_len); -- for (cnt = salt_len; cnt >= 32; cnt -= 32) -- cp = mempcpy (cp, temp_result, 32); -- memcpy (cp, temp_result, cnt); -+ sha256_finish_ctx (ctx, s_bytes); - - /* Repeatedly run the collected hash value through SHA256 to burn - CPU cycles. */ - for (cnt = 0; cnt < rounds; ++cnt) - { - /* New context. */ -- sha256_init_ctx (&ctx); -+ sha256_init_ctx (ctx); - -- /* Add key or last result. */ -+ /* Add phrase or last result. */ - if ((cnt & 1) != 0) -- sha256_process_bytes (p_bytes, key_len, &ctx); -+ sha256_process_recycled_bytes (p_bytes, phr_size, ctx); - else -- sha256_process_bytes (alt_result, 32, &ctx); -+ sha256_process_bytes (result, 32, ctx); - - /* Add salt for numbers not divisible by 3. */ - if (cnt % 3 != 0) -- sha256_process_bytes (s_bytes, salt_len, &ctx); -+ sha256_process_recycled_bytes (s_bytes, salt_size, ctx); - -- /* Add key for numbers not divisible by 7. */ -+ /* Add phrase for numbers not divisible by 7. */ - if (cnt % 7 != 0) -- sha256_process_bytes (p_bytes, key_len, &ctx); -+ sha256_process_recycled_bytes (p_bytes, phr_size, ctx); - -- /* Add key or last result. */ -+ /* Add phrase or last result. */ - if ((cnt & 1) != 0) -- sha256_process_bytes (alt_result, 32, &ctx); -+ sha256_process_bytes (result, 32, ctx); - else -- sha256_process_bytes (p_bytes, key_len, &ctx); -+ sha256_process_recycled_bytes (p_bytes, phr_size, ctx); - - /* Create intermediate result. */ -- sha256_finish_ctx (&ctx, alt_result); -+ sha256_finish_ctx (ctx, result); - } - -- /* Now we can construct the result string. It consists of three -- parts. */ -- cp = stpncpy (buffer, sha256_salt_prefix, MAX (0, buflen)); -- buflen -= sizeof (sha256_salt_prefix) - 1; -+ /* Now we can construct the result string. It consists of four -+ parts, one of which is optional. We already know that there -+ is sufficient space at CP for the longest possible result string. */ -+ memcpy (cp, sha256_salt_prefix, sizeof (sha256_salt_prefix) - 1); -+ cp += sizeof (sha256_salt_prefix) - 1; - - if (rounds_custom) - { -- int n = snprintf (cp, MAX (0, buflen), "%s%zu$", -- sha256_rounds_prefix, rounds); -+ int n = snprintf (cp, -+ SHA256_HASH_LENGTH - (sizeof (sha256_salt_prefix) - 1), -+ "%s%zu$", sha256_rounds_prefix, rounds); - cp += n; -- buflen -= n; -- } -- -- cp = stpncpy (cp, salt, MIN ((size_t) MAX (0, buflen), salt_len)); -- buflen -= MIN ((size_t) MAX (0, buflen), salt_len); -- -- if (buflen > 0) -- { -- *cp++ = '$'; -- --buflen; - } - --#define b64_from_24bit(B2, B1, B0, N) \ -- do { \ -- unsigned int w = ((B2) << 16) | ((B1) << 8) | (B0); \ -- int n = (N); \ -- while (n-- > 0 && buflen > 0) \ -- { \ -- *cp++ = b64t[w & 0x3f]; \ -- --buflen; \ -- w >>= 6; \ -- } \ -+ memcpy (cp, salt, salt_size); -+ cp += salt_size; -+ *cp++ = '$'; -+ -+#define b64_from_24bit(B2, B1, B0, N) \ -+ do { \ -+ unsigned int w = ((((unsigned int)(B2)) << 16) | \ -+ (((unsigned int)(B1)) << 8) | \ -+ ((unsigned int)(B0))); \ -+ int n = (N); \ -+ while (n-- > 0) \ -+ { \ -+ *cp++ = b64t[w & 0x3f]; \ -+ w >>= 6; \ -+ } \ - } while (0) - -- b64_from_24bit (alt_result[0], alt_result[10], alt_result[20], 4); -- b64_from_24bit (alt_result[21], alt_result[1], alt_result[11], 4); -- b64_from_24bit (alt_result[12], alt_result[22], alt_result[2], 4); -- b64_from_24bit (alt_result[3], alt_result[13], alt_result[23], 4); -- b64_from_24bit (alt_result[24], alt_result[4], alt_result[14], 4); -- b64_from_24bit (alt_result[15], alt_result[25], alt_result[5], 4); -- b64_from_24bit (alt_result[6], alt_result[16], alt_result[26], 4); -- b64_from_24bit (alt_result[27], alt_result[7], alt_result[17], 4); -- b64_from_24bit (alt_result[18], alt_result[28], alt_result[8], 4); -- b64_from_24bit (alt_result[9], alt_result[19], alt_result[29], 4); -- b64_from_24bit (0, alt_result[31], alt_result[30], 3); -- if (buflen <= 0) -- { -- errno = ERANGE; -- buffer = NULL; -- } -- else -- *cp = '\0'; /* Terminate the string. */ -- -- /* Clear the buffer for the intermediate result so that people -- attaching to processes or reading core dumps cannot get any -- information. We do it in this way to clear correct_words[] -- inside the SHA256 implementation as well. */ -- sha256_init_ctx (&ctx); -- sha256_finish_ctx (&ctx, alt_result); -- memset (temp_result, '\0', sizeof (temp_result)); -- memset (p_bytes, '\0', key_len); -- memset (s_bytes, '\0', salt_len); -- memset (&ctx, '\0', sizeof (ctx)); -- memset (&alt_ctx, '\0', sizeof (alt_ctx)); -- if (copied_key != NULL) -- memset (copied_key, '\0', key_len); -- if (copied_salt != NULL) -- memset (copied_salt, '\0', salt_len); -- -- return buffer; -+ b64_from_24bit (result[0], result[10], result[20], 4); -+ b64_from_24bit (result[21], result[1], result[11], 4); -+ b64_from_24bit (result[12], result[22], result[2], 4); -+ b64_from_24bit (result[3], result[13], result[23], 4); -+ b64_from_24bit (result[24], result[4], result[14], 4); -+ b64_from_24bit (result[15], result[25], result[5], 4); -+ b64_from_24bit (result[6], result[16], result[26], 4); -+ b64_from_24bit (result[27], result[7], result[17], 4); -+ b64_from_24bit (result[18], result[28], result[8], 4); -+ b64_from_24bit (result[9], result[19], result[29], 4); -+ b64_from_24bit (0, result[31], result[30], 3); -+ -+ *cp = '\0'; - } - - void - -From 989f1faae098a9345855bf733b8f35f92cefcf23 Mon Sep 17 00:00:00 2001 -From: =?UTF-8?q?Bj=C3=B6rn=20Esser?= -Date: Sat, 14 Jul 2018 21:40:34 +0200 -Subject: [PATCH 05/10] Replace crypt-sha512.c with an implementation in the - Public Domain. - -This implementation is based on the SHA512-based Unix crypt -implementation. Released into the Public Domain [1] by -Ulrich Drepper . - -This file is a modified except from [2], lines 1403 up to 1676. - -[1] https://www.akkadia.org/drepper/sha-crypt.html -[2] https://www.akkadia.org/drepper/SHA-crypt.txt ---- - crypt-sha512.c | 383 ++++++++++++++++++++++++------------------------- - 1 file changed, 191 insertions(+), 192 deletions(-) - -diff --git a/crypt-sha512.c b/crypt-sha512.c -index 955a27b..f3798a0 100644 ---- a/crypt-sha512.c -+++ b/crypt-sha512.c -@@ -1,20 +1,17 @@ --/* One way encryption based on SHA512 sum. -- -- Copyright (C) 2007-2017 Free Software Foundation, Inc. -- -- This library is free software; you can redistribute it and/or -- modify it under the terms of the GNU Lesser General Public License -- as published by the Free Software Foundation; either version 2.1 of -- the License, or (at your option) any later version. -- -- This library is distributed in the hope that it will be useful, -- but WITHOUT ANY WARRANTY; without even the implied warranty of -- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -- GNU Lesser General Public License for more details. -- -- You should have received a copy of the GNU Lesser General Public -- License along with this library; if not, see -- . */ -+/* One way encryption based on the SHA512-based Unix crypt implementation. -+ * -+ * Written by Ulrich Drepper in 2007 [1]. -+ * To the extent possible under law, Ulrich Drepper has waived all -+ * copyright and related or neighboring rights to this work. -+ * -+ * See https://creativecommons.org/publicdomain/zero/1.0/ for further -+ * details. -+ * -+ * This file is a modified except from [2], lines 1403 up to 1676. -+ * -+ * [1] https://www.akkadia.org/drepper/sha-crypt.html -+ * [2] https://www.akkadia.org/drepper/SHA-crypt.txt -+ */ - - #include "crypt-port.h" - #include "crypt-private.h" -@@ -42,36 +39,9 @@ static const char sha512_rounds_prefix[] = "rounds="; - /* Maximum number of rounds. */ - #define ROUNDS_MAX 999999999 - --/* The maximum possible length of a SHA512-hashed password string, -- including the terminating NUL character. Prefix (including its NUL) -- + rounds tag ("rounds=$" = "rounds=\0") + strlen(ROUNDS_MAX) -- + salt (up to SALT_LEN_MAX chars) + '$' + hash (86 chars). */ -- --#define LENGTH_OF_NUMBER(n) (sizeof #n - 1) -- --#define SHA512_HASH_LENGTH \ -- (sizeof (sha512_salt_prefix) + sizeof (sha512_rounds_prefix) + \ -- LENGTH_OF_NUMBER (ROUNDS_MAX) + SALT_LEN_MAX + 1 + 86) -- --static_assert (SHA512_HASH_LENGTH <= CRYPT_OUTPUT_SIZE, -- "CRYPT_OUTPUT_SIZE is too small for SHA512"); -- --/* A sha512_buffer holds all of the sensitive intermediate data. */ --struct sha512_buffer --{ -- struct sha512_ctx ctx; -- uint8_t result[64]; -- uint8_t p_bytes[64]; -- uint8_t s_bytes[64]; --}; -- --static_assert (sizeof (struct sha512_buffer) <= ALG_SPECIFIC_SIZE, -- "ALG_SPECIFIC_SIZE is too small for SHA512"); -- -- - /* Table with characters for base64 transformation. */ --static const char b64t[] = -- "./0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz"; -+static const char b64t[64] = -+"./0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz"; - - /* Subroutine of _xcrypt_crypt_sha512_rn: Feed CTX with LEN bytes of a - virtual byte sequence consisting of BLOCK repeated over and over -@@ -86,30 +56,23 @@ sha512_process_recycled_bytes (unsigned char block[64], size_t len, - sha512_process_bytes (block, cnt, ctx); - } - --void --crypt_sha512_rn (const char *phrase, size_t phr_size, -- const char *setting, size_t ARG_UNUSED (set_size), -- uint8_t *output, size_t out_size, -- void *scratch, size_t scr_size) -+static char * -+sha512_crypt_r (const char *key, const char *salt, char *buffer, int buflen) - { -- /* This shouldn't ever happen, but... */ -- if (out_size < SHA512_HASH_LENGTH -- || scr_size < sizeof (struct sha512_buffer)) -- { -- errno = ERANGE; -- return; -- } -- -- struct sha512_buffer *buf = scratch; -- struct sha512_ctx *ctx = &buf->ctx; -- uint8_t *result = buf->result; -- uint8_t *p_bytes = buf->p_bytes; -- uint8_t *s_bytes = buf->s_bytes; -- char *cp = (char *)output; -- const char *salt = setting; -- -- size_t salt_size; -+ unsigned char alt_result[64] -+ __attribute__ ((__aligned__ (__alignof__ (uint64_t)))); -+ unsigned char temp_result[64] -+ __attribute__ ((__aligned__ (__alignof__ (uint64_t)))); -+ struct sha512_ctx ctx; -+ struct sha512_ctx alt_ctx; -+ size_t salt_len; -+ size_t key_len; - size_t cnt; -+ char *cp; -+ char *copied_key = NULL; -+ char *copied_salt = NULL; -+ char *p_bytes; -+ char *s_bytes; - /* Default number of rounds. */ - size_t rounds = ROUNDS_DEFAULT; - bool rounds_custom = false; -@@ -124,191 +87,227 @@ crypt_sha512_rn (const char *phrase, size_t phr_size, - == 0) - { - const char *num = salt + sizeof (sha512_rounds_prefix) - 1; -- /* Do not allow an explicit setting of zero rounds, nor of the -- default number of rounds, nor leading zeroes on the rounds. */ -- if (!(*num >= '1' && *num <= '9')) -- { -- errno = EINVAL; -- return; -- } -- -- errno = 0; - char *endp; -- rounds = strtoul (num, &endp, 10); -- if (endp == num || *endp != '$' -- || rounds < ROUNDS_MIN -- || rounds > ROUNDS_MAX -- || errno) -- { -- errno = EINVAL; -- return; -- } -- salt = endp + 1; -- rounds_custom = true; -+ unsigned long int srounds = strtoul (num, &endp, 10); -+ if (*endp == '$') -+ { -+ salt = endp + 1; -+ rounds = MAX (ROUNDS_MIN, MIN (srounds, ROUNDS_MAX)); -+ rounds_custom = true; -+ } -+ } -+ -+ salt_len = MIN (strcspn (salt, "$"), SALT_LEN_MAX); -+ key_len = strlen (key); -+ -+ if ((key - (char *) 0) % __alignof__ (uint64_t) != 0) -+ { -+ char *tmp = (char *) alloca (key_len + __alignof__ (uint64_t)); -+ key = copied_key = -+ memcpy (tmp + __alignof__ (uint64_t) -+ - (tmp - (char *) 0) % __alignof__ (uint64_t), -+ key, key_len); - } - -- salt_size = strspn (salt, b64t); -- if (salt[salt_size] && salt[salt_size] != '$') -+ if ((salt - (char *) 0) % __alignof__ (uint64_t) != 0) - { -- errno = EINVAL; -- return; -+ char *tmp = (char *) alloca (salt_len + __alignof__ (uint64_t)); -+ salt = copied_salt = -+ memcpy (tmp + __alignof__ (uint64_t) -+ - (tmp - (char *) 0) % __alignof__ (uint64_t), -+ salt, salt_len); - } -- if (salt_size > SALT_LEN_MAX) -- salt_size = SALT_LEN_MAX; -- phr_size = strlen (phrase); - -- /* Compute alternate SHA512 sum with input PHRASE, SALT, and PHRASE. The -+ /* Prepare for the real work. */ -+ sha512_init_ctx (&ctx); -+ -+ /* Add the key string. */ -+ sha512_process_bytes (key, key_len, &ctx); -+ -+ /* The last part is the salt string. This must be at most 16 -+ characters and it ends at the first `$' character (for -+ compatibility with existing implementations). */ -+ sha512_process_bytes (salt, salt_len, &ctx); -+ -+ -+ /* Compute alternate SHA512 sum with input KEY, SALT, and KEY. The - final result will be added to the first context. */ -- sha512_init_ctx (ctx); -+ sha512_init_ctx (&alt_ctx); - -- /* Add phrase. */ -- sha512_process_bytes (phrase, phr_size, ctx); -+ /* Add key. */ -+ sha512_process_bytes (key, key_len, &alt_ctx); - - /* Add salt. */ -- sha512_process_bytes (salt, salt_size, ctx); -+ sha512_process_bytes (salt, salt_len, &alt_ctx); - -- /* Add phrase again. */ -- sha512_process_bytes (phrase, phr_size, ctx); -+ /* Add key again. */ -+ sha512_process_bytes (key, key_len, &alt_ctx); - - /* Now get result of this (64 bytes) and add it to the other - context. */ -- sha512_finish_ctx (ctx, result); -- -- /* Prepare for the real work. */ -- sha512_init_ctx (ctx); -+ sha512_finish_ctx (&alt_ctx, alt_result); - -- /* Add the phrase string. */ -- sha512_process_bytes (phrase, phr_size, ctx); -- -- /* The last part is the salt string. This must be at most 8 -- characters and it ends at the first `$' character (for -- compatibility with existing implementations). */ -- sha512_process_bytes (salt, salt_size, ctx); -+ /* Add for any character in the key one byte of the alternate sum. */ -+ for (cnt = key_len; cnt > 64; cnt -= 64) -+ sha512_process_bytes (alt_result, 64, &ctx); -+ sha512_process_bytes (alt_result, cnt, &ctx); - -- /* Add for any character in the phrase one byte of the alternate sum. */ -- for (cnt = phr_size; cnt > 64; cnt -= 64) -- sha512_process_bytes (result, 64, ctx); -- sha512_process_bytes (result, cnt, ctx); -- -- /* Take the binary representation of the length of the phrase and for every -- 1 add the alternate sum, for every 0 the phrase. */ -- for (cnt = phr_size; cnt > 0; cnt >>= 1) -+ /* Take the binary representation of the length of the key and for every -+ 1 add the alternate sum, for every 0 the key. */ -+ for (cnt = key_len; cnt > 0; cnt >>= 1) - if ((cnt & 1) != 0) -- sha512_process_bytes (result, 64, ctx); -+ sha512_process_bytes (alt_result, 64, &ctx); - else -- sha512_process_bytes (phrase, phr_size, ctx); -+ sha512_process_bytes (key, key_len, &ctx); - - /* Create intermediate result. */ -- sha512_finish_ctx (ctx, result); -+ sha512_finish_ctx (&ctx, alt_result); - - /* Start computation of P byte sequence. */ -- sha512_init_ctx (ctx); -+ sha512_init_ctx (&alt_ctx); - - /* For every character in the password add the entire password. */ -- for (cnt = 0; cnt < phr_size; ++cnt) -- sha512_process_bytes (phrase, phr_size, ctx); -+ for (cnt = 0; cnt < key_len; ++cnt) -+ sha512_process_bytes (key, key_len, &alt_ctx); - - /* Finish the digest. */ -- sha512_finish_ctx (ctx, p_bytes); -+ sha512_finish_ctx (&alt_ctx, temp_result); -+ -+ /* Create byte sequence P. */ -+ cp = p_bytes = alloca (key_len); -+ for (cnt = key_len; cnt >= 64; cnt -= 64) -+ cp = mempcpy (cp, temp_result, 64); -+ memcpy (cp, temp_result, cnt); - - /* Start computation of S byte sequence. */ -- sha512_init_ctx (ctx); -+ sha512_init_ctx (&alt_ctx); - - /* For every character in the password add the entire password. */ -- for (cnt = 0; cnt < (size_t) 16 + (size_t) result[0]; ++cnt) -- sha512_process_bytes (salt, salt_size, ctx); -+ for (cnt = 0; cnt < 16 + alt_result[0]; ++cnt) -+ sha512_process_bytes (salt, salt_len, &alt_ctx); - - /* Finish the digest. */ -- sha512_finish_ctx (ctx, s_bytes); -+ sha512_finish_ctx (&alt_ctx, temp_result); -+ -+ /* Create byte sequence S. */ -+ cp = s_bytes = alloca (salt_len); -+ for (cnt = salt_len; cnt >= 64; cnt -= 64) -+ cp = mempcpy (cp, temp_result, 64); -+ memcpy (cp, temp_result, cnt); - - /* Repeatedly run the collected hash value through SHA512 to burn - CPU cycles. */ - for (cnt = 0; cnt < rounds; ++cnt) - { - /* New context. */ -- sha512_init_ctx (ctx); -+ sha512_init_ctx (&ctx); - -- /* Add phrase or last result. */ -+ /* Add key or last result. */ - if ((cnt & 1) != 0) -- sha512_process_recycled_bytes (p_bytes, phr_size, ctx); -+ sha512_process_bytes (p_bytes, key_len, &ctx); - else -- sha512_process_bytes (result, 64, ctx); -+ sha512_process_bytes (alt_result, 64, &ctx); - - /* Add salt for numbers not divisible by 3. */ - if (cnt % 3 != 0) -- sha512_process_recycled_bytes (s_bytes, salt_size, ctx); -+ sha512_process_bytes (s_bytes, salt_len, &ctx); - -- /* Add phrase for numbers not divisible by 7. */ -+ /* Add key for numbers not divisible by 7. */ - if (cnt % 7 != 0) -- sha512_process_recycled_bytes (p_bytes, phr_size, ctx); -+ sha512_process_bytes (p_bytes, key_len, &ctx); - -- /* Add phrase or last result. */ -+ /* Add key or last result. */ - if ((cnt & 1) != 0) -- sha512_process_bytes (result, 64, ctx); -+ sha512_process_bytes (alt_result, 64, &ctx); - else -- sha512_process_recycled_bytes (p_bytes, phr_size, ctx); -+ sha512_process_bytes (p_bytes, key_len, &ctx); - - /* Create intermediate result. */ -- sha512_finish_ctx (ctx, result); -+ sha512_finish_ctx (&ctx, alt_result); - } - -- /* Now we can construct the result string. It consists of four -- parts, one of which is optional. We already know that buflen is -- at least sha512_hash_length, therefore none of the string bashing -- below can overflow the buffer. */ -- -- memcpy (cp, sha512_salt_prefix, sizeof (sha512_salt_prefix) - 1); -- cp += sizeof (sha512_salt_prefix) - 1; -+ /* Now we can construct the result string. It consists of three -+ parts. */ -+ cp = __stpncpy (buffer, sha512_salt_prefix, MAX (0, buflen)); -+ buflen -= sizeof (sha512_salt_prefix) - 1; - - if (rounds_custom) - { -- int n = snprintf (cp, -- SHA512_HASH_LENGTH - (sizeof (sha512_salt_prefix) - 1), -- "%s%zu$", sha512_rounds_prefix, rounds); -+ int n = snprintf (cp, MAX (0, buflen), "%s%zu$", -+ sha512_rounds_prefix, rounds); - cp += n; -+ buflen -= n; - } - -- memcpy (cp, salt, salt_size); -- cp += salt_size; -- *cp++ = '$'; -- --#define b64_from_24bit(B2, B1, B0, N) \ -- do { \ -- unsigned int w = ((((unsigned int)(B2)) << 16) | \ -- (((unsigned int)(B1)) << 8) | \ -- ((unsigned int)(B0))); \ -- int n = (N); \ -- while (n-- > 0) \ -- { \ -- *cp++ = b64t[w & 0x3f]; \ -- w >>= 6; \ -- } \ -+ cp = __stpncpy (cp, salt, MIN ((size_t) MAX (0, buflen), salt_len)); -+ buflen -= MIN ((size_t) MAX (0, buflen), salt_len); -+ -+ if (buflen > 0) -+ { -+ *cp++ = '$'; -+ --buflen; -+ } -+ -+#define b64_from_24bit(B2, B1, B0, N) \ -+ do { \ -+ unsigned int w = ((B2) << 16) | ((B1) << 8) | (B0); \ -+ int n = (N); \ -+ while (n-- > 0 && buflen > 0) \ -+ { \ -+ *cp++ = b64t[w & 0x3f]; \ -+ --buflen; \ -+ w >>= 6; \ -+ } \ - } while (0) - -- b64_from_24bit (result[0], result[21], result[42], 4); -- b64_from_24bit (result[22], result[43], result[1], 4); -- b64_from_24bit (result[44], result[2], result[23], 4); -- b64_from_24bit (result[3], result[24], result[45], 4); -- b64_from_24bit (result[25], result[46], result[4], 4); -- b64_from_24bit (result[47], result[5], result[26], 4); -- b64_from_24bit (result[6], result[27], result[48], 4); -- b64_from_24bit (result[28], result[49], result[7], 4); -- b64_from_24bit (result[50], result[8], result[29], 4); -- b64_from_24bit (result[9], result[30], result[51], 4); -- b64_from_24bit (result[31], result[52], result[10], 4); -- b64_from_24bit (result[53], result[11], result[32], 4); -- b64_from_24bit (result[12], result[33], result[54], 4); -- b64_from_24bit (result[34], result[55], result[13], 4); -- b64_from_24bit (result[56], result[14], result[35], 4); -- b64_from_24bit (result[15], result[36], result[57], 4); -- b64_from_24bit (result[37], result[58], result[16], 4); -- b64_from_24bit (result[59], result[17], result[38], 4); -- b64_from_24bit (result[18], result[39], result[60], 4); -- b64_from_24bit (result[40], result[61], result[19], 4); -- b64_from_24bit (result[62], result[20], result[41], 4); -- b64_from_24bit (0, 0, result[63], 2); -- -- *cp = '\0'; -+ b64_from_24bit (alt_result[0], alt_result[21], alt_result[42], 4); -+ b64_from_24bit (alt_result[22], alt_result[43], alt_result[1], 4); -+ b64_from_24bit (alt_result[44], alt_result[2], alt_result[23], 4); -+ b64_from_24bit (alt_result[3], alt_result[24], alt_result[45], 4); -+ b64_from_24bit (alt_result[25], alt_result[46], alt_result[4], 4); -+ b64_from_24bit (alt_result[47], alt_result[5], alt_result[26], 4); -+ b64_from_24bit (alt_result[6], alt_result[27], alt_result[48], 4); -+ b64_from_24bit (alt_result[28], alt_result[49], alt_result[7], 4); -+ b64_from_24bit (alt_result[50], alt_result[8], alt_result[29], 4); -+ b64_from_24bit (alt_result[9], alt_result[30], alt_result[51], 4); -+ b64_from_24bit (alt_result[31], alt_result[52], alt_result[10], 4); -+ b64_from_24bit (alt_result[53], alt_result[11], alt_result[32], 4); -+ b64_from_24bit (alt_result[12], alt_result[33], alt_result[54], 4); -+ b64_from_24bit (alt_result[34], alt_result[55], alt_result[13], 4); -+ b64_from_24bit (alt_result[56], alt_result[14], alt_result[35], 4); -+ b64_from_24bit (alt_result[15], alt_result[36], alt_result[57], 4); -+ b64_from_24bit (alt_result[37], alt_result[58], alt_result[16], 4); -+ b64_from_24bit (alt_result[59], alt_result[17], alt_result[38], 4); -+ b64_from_24bit (alt_result[18], alt_result[39], alt_result[60], 4); -+ b64_from_24bit (alt_result[40], alt_result[61], alt_result[19], 4); -+ b64_from_24bit (alt_result[62], alt_result[20], alt_result[41], 4); -+ b64_from_24bit (0, 0, alt_result[63], 2); -+ -+ if (buflen <= 0) -+ { -+ errno = ERANGE; -+ buffer = NULL; -+ } -+ else -+ *cp = '\0'; /* Terminate the string. */ -+ -+ /* Clear the buffer for the intermediate result so that people -+ attaching to processes or reading core dumps cannot get any -+ information. We do it in this way to clear correct_words[] -+ inside the SHA512 implementation as well. */ -+ sha512_init_ctx (&ctx); -+ sha512_finish_ctx (&ctx, alt_result); -+ memset (temp_result, '\0', sizeof (temp_result)); -+ memset (p_bytes, '\0', key_len); -+ memset (s_bytes, '\0', salt_len); -+ memset (&ctx, '\0', sizeof (ctx)); -+ memset (&alt_ctx, '\0', sizeof (alt_ctx)); -+ if (copied_key != NULL) -+ memset (copied_key, '\0', key_len); -+ if (copied_salt != NULL) -+ memset (copied_salt, '\0', salt_len); -+ -+ return buffer; - } - - void - -From 16abeb10230f3762c2c820b43bdb262013f2e17a Mon Sep 17 00:00:00 2001 -From: =?UTF-8?q?Bj=C3=B6rn=20Esser?= -Date: Sat, 14 Jul 2018 21:44:21 +0200 -Subject: [PATCH 06/10] crypt-sha512.c: Apply previous commits from Zack - Weinberg - -This patch summarizes the changes from: - - * 4a1152b4f9bc900d0488b473e20daed95025f4b0 - * ccc833b4b2c60cefd74cb91a05f1ce7628179657 - * 118abc2c5c08542fe528a1193328b161a756db90 - * 9483c648978378a9cd128382049a88055d5b2a61 - * 4856729bd75c78e4e1e4e35ab5afd7cef6c66afc - * a2d558581c3cd9b3d62f916825405cebd708f268 - * b46a39a57e4801f5c41b1bac207239b6ed8e31a5 - * cbdf27e254b0a113f0bea87071177f083e3f2545 - * 00ec9369ac4875a8e3903d6e41ae785bbc8e8b26 - * 114d4200eaa572525089795cf7990c3dafd5028c - * ed4be6afa7b34fe0d827cc3f7f9608de0d9325cd - * a7f9df50cecec46bb8176382faa685ce35ca72be - * 15d1e3bf3d259ea262f3d34e8c225a3abfabaa09 ---- - crypt-sha512.c | 356 ++++++++++++++++++++++++------------------------- - 1 file changed, 178 insertions(+), 178 deletions(-) - -diff --git a/crypt-sha512.c b/crypt-sha512.c -index f3798a0..39ec0b5 100644 ---- a/crypt-sha512.c -+++ b/crypt-sha512.c -@@ -1,7 +1,9 @@ - /* One way encryption based on the SHA512-based Unix crypt implementation. - * - * Written by Ulrich Drepper in 2007 [1]. -- * To the extent possible under law, Ulrich Drepper has waived all -+ * Modified by Zack Weinberg in 2017, 2018. -+ * Composed by Björn Esser in 2018. -+ * To the extent possible under law, the named authors have waived all - * copyright and related or neighboring rights to this work. - * - * See https://creativecommons.org/publicdomain/zero/1.0/ for further -@@ -39,9 +41,36 @@ static const char sha512_rounds_prefix[] = "rounds="; - /* Maximum number of rounds. */ - #define ROUNDS_MAX 999999999 - -+/* The maximum possible length of a SHA512-hashed password string, -+ including the terminating NUL character. Prefix (including its NUL) -+ + rounds tag ("rounds=$" = "rounds=\0") + strlen(ROUNDS_MAX) -+ + salt (up to SALT_LEN_MAX chars) + '$' + hash (86 chars). */ -+ -+#define LENGTH_OF_NUMBER(n) (sizeof #n - 1) -+ -+#define SHA512_HASH_LENGTH \ -+ (sizeof (sha512_salt_prefix) + sizeof (sha512_rounds_prefix) + \ -+ LENGTH_OF_NUMBER (ROUNDS_MAX) + SALT_LEN_MAX + 1 + 86) -+ -+static_assert (SHA512_HASH_LENGTH <= CRYPT_OUTPUT_SIZE, -+ "CRYPT_OUTPUT_SIZE is too small for SHA512"); -+ -+/* A sha512_buffer holds all of the sensitive intermediate data. */ -+struct sha512_buffer -+{ -+ struct sha512_ctx ctx; -+ uint8_t result[64]; -+ uint8_t p_bytes[64]; -+ uint8_t s_bytes[64]; -+}; -+ -+static_assert (sizeof (struct sha512_buffer) <= ALG_SPECIFIC_SIZE, -+ "ALG_SPECIFIC_SIZE is too small for SHA512"); -+ -+ - /* Table with characters for base64 transformation. */ --static const char b64t[64] = --"./0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz"; -+static const char b64t[] = -+ "./0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz"; - - /* Subroutine of _xcrypt_crypt_sha512_rn: Feed CTX with LEN bytes of a - virtual byte sequence consisting of BLOCK repeated over and over -@@ -56,23 +85,30 @@ sha512_process_recycled_bytes (unsigned char block[64], size_t len, - sha512_process_bytes (block, cnt, ctx); - } - --static char * --sha512_crypt_r (const char *key, const char *salt, char *buffer, int buflen) -+void -+crypt_sha512_rn (const char *phrase, size_t phr_size, -+ const char *setting, size_t ARG_UNUSED (set_size), -+ uint8_t *output, size_t out_size, -+ void *scratch, size_t scr_size) - { -- unsigned char alt_result[64] -- __attribute__ ((__aligned__ (__alignof__ (uint64_t)))); -- unsigned char temp_result[64] -- __attribute__ ((__aligned__ (__alignof__ (uint64_t)))); -- struct sha512_ctx ctx; -- struct sha512_ctx alt_ctx; -- size_t salt_len; -- size_t key_len; -+ /* This shouldn't ever happen, but... */ -+ if (out_size < SHA512_HASH_LENGTH -+ || scr_size < sizeof (struct sha512_buffer)) -+ { -+ errno = ERANGE; -+ return; -+ } -+ -+ struct sha512_buffer *buf = scratch; -+ struct sha512_ctx *ctx = &buf->ctx; -+ uint8_t *result = buf->result; -+ uint8_t *p_bytes = buf->p_bytes; -+ uint8_t *s_bytes = buf->s_bytes; -+ char *cp = (char *)output; -+ const char *salt = setting; -+ -+ size_t salt_size; - size_t cnt; -- char *cp; -- char *copied_key = NULL; -- char *copied_salt = NULL; -- char *p_bytes; -- char *s_bytes; - /* Default number of rounds. */ - size_t rounds = ROUNDS_DEFAULT; - bool rounds_custom = false; -@@ -87,227 +123,191 @@ sha512_crypt_r (const char *key, const char *salt, char *buffer, int buflen) - == 0) - { - const char *num = salt + sizeof (sha512_rounds_prefix) - 1; -+ /* Do not allow an explicit setting of zero rounds, nor of the -+ default number of rounds, nor leading zeroes on the rounds. */ -+ if (!(*num >= '1' && *num <= '9')) -+ { -+ errno = EINVAL; -+ return; -+ } -+ -+ errno = 0; - char *endp; -- unsigned long int srounds = strtoul (num, &endp, 10); -- if (*endp == '$') -- { -- salt = endp + 1; -- rounds = MAX (ROUNDS_MIN, MIN (srounds, ROUNDS_MAX)); -- rounds_custom = true; -- } -+ rounds = strtoul (num, &endp, 10); -+ if (endp == num || *endp != '$' -+ || rounds < ROUNDS_MIN -+ || rounds > ROUNDS_MAX -+ || errno) -+ { -+ errno = EINVAL; -+ return; -+ } -+ salt = endp + 1; -+ rounds_custom = true; - } - -- salt_len = MIN (strcspn (salt, "$"), SALT_LEN_MAX); -- key_len = strlen (key); -- -- if ((key - (char *) 0) % __alignof__ (uint64_t) != 0) -+ salt_size = strspn (salt, b64t); -+ if (salt[salt_size] && salt[salt_size] != '$') - { -- char *tmp = (char *) alloca (key_len + __alignof__ (uint64_t)); -- key = copied_key = -- memcpy (tmp + __alignof__ (uint64_t) -- - (tmp - (char *) 0) % __alignof__ (uint64_t), -- key, key_len); -+ errno = EINVAL; -+ return; - } -+ if (salt_size > SALT_LEN_MAX) -+ salt_size = SALT_LEN_MAX; -+ phr_size = strlen (phrase); - -- if ((salt - (char *) 0) % __alignof__ (uint64_t) != 0) -- { -- char *tmp = (char *) alloca (salt_len + __alignof__ (uint64_t)); -- salt = copied_salt = -- memcpy (tmp + __alignof__ (uint64_t) -- - (tmp - (char *) 0) % __alignof__ (uint64_t), -- salt, salt_len); -- } -- -- /* Prepare for the real work. */ -- sha512_init_ctx (&ctx); -- -- /* Add the key string. */ -- sha512_process_bytes (key, key_len, &ctx); -- -- /* The last part is the salt string. This must be at most 16 -- characters and it ends at the first `$' character (for -- compatibility with existing implementations). */ -- sha512_process_bytes (salt, salt_len, &ctx); -- -- -- /* Compute alternate SHA512 sum with input KEY, SALT, and KEY. The -+ /* Compute alternate SHA512 sum with input PHRASE, SALT, and PHRASE. The - final result will be added to the first context. */ -- sha512_init_ctx (&alt_ctx); -+ sha512_init_ctx (ctx); - -- /* Add key. */ -- sha512_process_bytes (key, key_len, &alt_ctx); -+ /* Add phrase. */ -+ sha512_process_bytes (phrase, phr_size, ctx); - - /* Add salt. */ -- sha512_process_bytes (salt, salt_len, &alt_ctx); -+ sha512_process_bytes (salt, salt_size, ctx); - -- /* Add key again. */ -- sha512_process_bytes (key, key_len, &alt_ctx); -+ /* Add phrase again. */ -+ sha512_process_bytes (phrase, phr_size, ctx); - - /* Now get result of this (64 bytes) and add it to the other - context. */ -- sha512_finish_ctx (&alt_ctx, alt_result); -+ sha512_finish_ctx (ctx, result); -+ -+ /* Prepare for the real work. */ -+ sha512_init_ctx (ctx); -+ -+ /* Add the phrase string. */ -+ sha512_process_bytes (phrase, phr_size, ctx); -+ -+ /* The last part is the salt string. This must be at most 8 -+ characters and it ends at the first `$' character (for -+ compatibility with existing implementations). */ -+ sha512_process_bytes (salt, salt_size, ctx); - -- /* Add for any character in the key one byte of the alternate sum. */ -- for (cnt = key_len; cnt > 64; cnt -= 64) -- sha512_process_bytes (alt_result, 64, &ctx); -- sha512_process_bytes (alt_result, cnt, &ctx); -+ /* Add for any character in the phrase one byte of the alternate sum. */ -+ for (cnt = phr_size; cnt > 64; cnt -= 64) -+ sha512_process_bytes (result, 64, ctx); -+ sha512_process_bytes (result, cnt, ctx); - -- /* Take the binary representation of the length of the key and for every -- 1 add the alternate sum, for every 0 the key. */ -- for (cnt = key_len; cnt > 0; cnt >>= 1) -+ /* Take the binary representation of the length of the phrase and for every -+ 1 add the alternate sum, for every 0 the phrase. */ -+ for (cnt = phr_size; cnt > 0; cnt >>= 1) - if ((cnt & 1) != 0) -- sha512_process_bytes (alt_result, 64, &ctx); -+ sha512_process_bytes (result, 64, ctx); - else -- sha512_process_bytes (key, key_len, &ctx); -+ sha512_process_bytes (phrase, phr_size, ctx); - - /* Create intermediate result. */ -- sha512_finish_ctx (&ctx, alt_result); -+ sha512_finish_ctx (ctx, result); - - /* Start computation of P byte sequence. */ -- sha512_init_ctx (&alt_ctx); -+ sha512_init_ctx (ctx); - - /* For every character in the password add the entire password. */ -- for (cnt = 0; cnt < key_len; ++cnt) -- sha512_process_bytes (key, key_len, &alt_ctx); -+ for (cnt = 0; cnt < phr_size; ++cnt) -+ sha512_process_bytes (phrase, phr_size, ctx); - - /* Finish the digest. */ -- sha512_finish_ctx (&alt_ctx, temp_result); -- -- /* Create byte sequence P. */ -- cp = p_bytes = alloca (key_len); -- for (cnt = key_len; cnt >= 64; cnt -= 64) -- cp = mempcpy (cp, temp_result, 64); -- memcpy (cp, temp_result, cnt); -+ sha512_finish_ctx (ctx, p_bytes); - - /* Start computation of S byte sequence. */ -- sha512_init_ctx (&alt_ctx); -+ sha512_init_ctx (ctx); - - /* For every character in the password add the entire password. */ -- for (cnt = 0; cnt < 16 + alt_result[0]; ++cnt) -- sha512_process_bytes (salt, salt_len, &alt_ctx); -+ for (cnt = 0; cnt < (size_t) 16 + (size_t) result[0]; ++cnt) -+ sha512_process_bytes (salt, salt_size, ctx); - - /* Finish the digest. */ -- sha512_finish_ctx (&alt_ctx, temp_result); -- -- /* Create byte sequence S. */ -- cp = s_bytes = alloca (salt_len); -- for (cnt = salt_len; cnt >= 64; cnt -= 64) -- cp = mempcpy (cp, temp_result, 64); -- memcpy (cp, temp_result, cnt); -+ sha512_finish_ctx (ctx, s_bytes); - - /* Repeatedly run the collected hash value through SHA512 to burn - CPU cycles. */ - for (cnt = 0; cnt < rounds; ++cnt) - { - /* New context. */ -- sha512_init_ctx (&ctx); -+ sha512_init_ctx (ctx); - -- /* Add key or last result. */ -+ /* Add phrase or last result. */ - if ((cnt & 1) != 0) -- sha512_process_bytes (p_bytes, key_len, &ctx); -+ sha512_process_recycled_bytes (p_bytes, phr_size, ctx); - else -- sha512_process_bytes (alt_result, 64, &ctx); -+ sha512_process_bytes (result, 64, ctx); - - /* Add salt for numbers not divisible by 3. */ - if (cnt % 3 != 0) -- sha512_process_bytes (s_bytes, salt_len, &ctx); -+ sha512_process_recycled_bytes (s_bytes, salt_size, ctx); - -- /* Add key for numbers not divisible by 7. */ -+ /* Add phrase for numbers not divisible by 7. */ - if (cnt % 7 != 0) -- sha512_process_bytes (p_bytes, key_len, &ctx); -+ sha512_process_recycled_bytes (p_bytes, phr_size, ctx); - -- /* Add key or last result. */ -+ /* Add phrase or last result. */ - if ((cnt & 1) != 0) -- sha512_process_bytes (alt_result, 64, &ctx); -+ sha512_process_bytes (result, 64, ctx); - else -- sha512_process_bytes (p_bytes, key_len, &ctx); -+ sha512_process_recycled_bytes (p_bytes, phr_size, ctx); - - /* Create intermediate result. */ -- sha512_finish_ctx (&ctx, alt_result); -+ sha512_finish_ctx (ctx, result); - } - -- /* Now we can construct the result string. It consists of three -- parts. */ -- cp = __stpncpy (buffer, sha512_salt_prefix, MAX (0, buflen)); -- buflen -= sizeof (sha512_salt_prefix) - 1; -+ /* Now we can construct the result string. It consists of four -+ parts, one of which is optional. We already know that buflen is -+ at least sha512_hash_length, therefore none of the string bashing -+ below can overflow the buffer. */ -+ -+ memcpy (cp, sha512_salt_prefix, sizeof (sha512_salt_prefix) - 1); -+ cp += sizeof (sha512_salt_prefix) - 1; - - if (rounds_custom) - { -- int n = snprintf (cp, MAX (0, buflen), "%s%zu$", -- sha512_rounds_prefix, rounds); -+ int n = snprintf (cp, -+ SHA512_HASH_LENGTH - (sizeof (sha512_salt_prefix) - 1), -+ "%s%zu$", sha512_rounds_prefix, rounds); - cp += n; -- buflen -= n; -- } -- -- cp = __stpncpy (cp, salt, MIN ((size_t) MAX (0, buflen), salt_len)); -- buflen -= MIN ((size_t) MAX (0, buflen), salt_len); -- -- if (buflen > 0) -- { -- *cp++ = '$'; -- --buflen; - } - --#define b64_from_24bit(B2, B1, B0, N) \ -- do { \ -- unsigned int w = ((B2) << 16) | ((B1) << 8) | (B0); \ -- int n = (N); \ -- while (n-- > 0 && buflen > 0) \ -- { \ -- *cp++ = b64t[w & 0x3f]; \ -- --buflen; \ -- w >>= 6; \ -- } \ -+ memcpy (cp, salt, salt_size); -+ cp += salt_size; -+ *cp++ = '$'; -+ -+#define b64_from_24bit(B2, B1, B0, N) \ -+ do { \ -+ unsigned int w = ((((unsigned int)(B2)) << 16) | \ -+ (((unsigned int)(B1)) << 8) | \ -+ ((unsigned int)(B0))); \ -+ int n = (N); \ -+ while (n-- > 0) \ -+ { \ -+ *cp++ = b64t[w & 0x3f]; \ -+ w >>= 6; \ -+ } \ - } while (0) - -- b64_from_24bit (alt_result[0], alt_result[21], alt_result[42], 4); -- b64_from_24bit (alt_result[22], alt_result[43], alt_result[1], 4); -- b64_from_24bit (alt_result[44], alt_result[2], alt_result[23], 4); -- b64_from_24bit (alt_result[3], alt_result[24], alt_result[45], 4); -- b64_from_24bit (alt_result[25], alt_result[46], alt_result[4], 4); -- b64_from_24bit (alt_result[47], alt_result[5], alt_result[26], 4); -- b64_from_24bit (alt_result[6], alt_result[27], alt_result[48], 4); -- b64_from_24bit (alt_result[28], alt_result[49], alt_result[7], 4); -- b64_from_24bit (alt_result[50], alt_result[8], alt_result[29], 4); -- b64_from_24bit (alt_result[9], alt_result[30], alt_result[51], 4); -- b64_from_24bit (alt_result[31], alt_result[52], alt_result[10], 4); -- b64_from_24bit (alt_result[53], alt_result[11], alt_result[32], 4); -- b64_from_24bit (alt_result[12], alt_result[33], alt_result[54], 4); -- b64_from_24bit (alt_result[34], alt_result[55], alt_result[13], 4); -- b64_from_24bit (alt_result[56], alt_result[14], alt_result[35], 4); -- b64_from_24bit (alt_result[15], alt_result[36], alt_result[57], 4); -- b64_from_24bit (alt_result[37], alt_result[58], alt_result[16], 4); -- b64_from_24bit (alt_result[59], alt_result[17], alt_result[38], 4); -- b64_from_24bit (alt_result[18], alt_result[39], alt_result[60], 4); -- b64_from_24bit (alt_result[40], alt_result[61], alt_result[19], 4); -- b64_from_24bit (alt_result[62], alt_result[20], alt_result[41], 4); -- b64_from_24bit (0, 0, alt_result[63], 2); -- -- if (buflen <= 0) -- { -- errno = ERANGE; -- buffer = NULL; -- } -- else -- *cp = '\0'; /* Terminate the string. */ -- -- /* Clear the buffer for the intermediate result so that people -- attaching to processes or reading core dumps cannot get any -- information. We do it in this way to clear correct_words[] -- inside the SHA512 implementation as well. */ -- sha512_init_ctx (&ctx); -- sha512_finish_ctx (&ctx, alt_result); -- memset (temp_result, '\0', sizeof (temp_result)); -- memset (p_bytes, '\0', key_len); -- memset (s_bytes, '\0', salt_len); -- memset (&ctx, '\0', sizeof (ctx)); -- memset (&alt_ctx, '\0', sizeof (alt_ctx)); -- if (copied_key != NULL) -- memset (copied_key, '\0', key_len); -- if (copied_salt != NULL) -- memset (copied_salt, '\0', salt_len); -- -- return buffer; -+ b64_from_24bit (result[0], result[21], result[42], 4); -+ b64_from_24bit (result[22], result[43], result[1], 4); -+ b64_from_24bit (result[44], result[2], result[23], 4); -+ b64_from_24bit (result[3], result[24], result[45], 4); -+ b64_from_24bit (result[25], result[46], result[4], 4); -+ b64_from_24bit (result[47], result[5], result[26], 4); -+ b64_from_24bit (result[6], result[27], result[48], 4); -+ b64_from_24bit (result[28], result[49], result[7], 4); -+ b64_from_24bit (result[50], result[8], result[29], 4); -+ b64_from_24bit (result[9], result[30], result[51], 4); -+ b64_from_24bit (result[31], result[52], result[10], 4); -+ b64_from_24bit (result[53], result[11], result[32], 4); -+ b64_from_24bit (result[12], result[33], result[54], 4); -+ b64_from_24bit (result[34], result[55], result[13], 4); -+ b64_from_24bit (result[56], result[14], result[35], 4); -+ b64_from_24bit (result[15], result[36], result[57], 4); -+ b64_from_24bit (result[37], result[58], result[16], 4); -+ b64_from_24bit (result[59], result[17], result[38], 4); -+ b64_from_24bit (result[18], result[39], result[60], 4); -+ b64_from_24bit (result[40], result[61], result[19], 4); -+ b64_from_24bit (result[62], result[20], result[41], 4); -+ b64_from_24bit (0, 0, result[63], 2); -+ -+ *cp = '\0'; - } - - void - -From c76847e3be40c4ac0d78bc8518502418c6207144 Mon Sep 17 00:00:00 2001 -From: =?UTF-8?q?Bj=C3=B6rn=20Esser?= -Date: Wed, 1 Aug 2018 19:34:53 +0200 -Subject: [PATCH 07/10] Update LICENSING and NEWS for changes in previous - commits. - -crypt-sha{256,512}.c have been replaced with an implementation -in the Public Domain. ---- - LICENSING | 7 +++++-- - NEWS | 2 ++ - 2 files changed, 7 insertions(+), 2 deletions(-) - -diff --git a/LICENSING b/LICENSING -index b9df920..3efbed0 100644 ---- a/LICENSING -+++ b/LICENSING -@@ -14,14 +14,17 @@ source tree. For specific licensing terms consult the files themselves. - * Copyright Free Software Foundation, Inc.; LGPL (v2.1 or later): - crypt-base.h, crypt-obsolete.h, crypt-private.h - alg-md5.h, alg-md5.c, crypt-md5.c, -- alg-sha256.h, alg-sha256.c, crypt-sha256.c, -- alg-sha512.h, alg-sha512.c, crypt-sha256.c, -+ alg-sha256.h, alg-sha256.c, -+ alg-sha512.h, alg-sha512.c, - test-crypt-badsalt, test-crypt-nonnull - - * Copyright David Burren et al.; 3-clause BSD: - alg-des.h, alg-des.c, alg-des-tables.c, - crypt-des.c, crypt-des-obsolete.c, gen-des-tables.c - -+ * Public domain, written by Ulrich Drepper et al.: -+ crypt-sha256.c, crypt-sha512.c -+ - * Public domain, written by Solar Designer et al.: - alg-md4.h, alg-md4.c, crypt-bcrypt.c, crypt-gensalt.c, test-crypt-bcrypt.c - -diff --git a/NEWS b/NEWS -index 77b556f..8acf032 100644 ---- a/NEWS -+++ b/NEWS -@@ -5,6 +5,8 @@ Please send bug reports, questions and suggestions to - - Version 4.1.2 - * Add optional 'check-valgrind' target to the Makefile. -+* Replace crypt-sha{256,512}.c with an implementation in the Public -+ Domain. - - Version 4.1.1 - * --enable-hashes now supports additional groups of hashing methods: - -From cc1806e214b89403152c2c53932d8d0b8aeb1e91 Mon Sep 17 00:00:00 2001 -From: =?UTF-8?q?Bj=C3=B6rn=20Esser?= -Date: Sat, 4 Aug 2018 13:02:03 +0200 -Subject: [PATCH 08/10] Add alias man-pages for other crypt functions. - ---- - Makefile.am | 3 ++- - crypt.3 | 1 + - crypt.5 | 2 ++ - crypt_gensalt.3 | 2 ++ - crypt_r.3 | 1 + - crypt_ra.3 | 1 + - 6 files changed, 9 insertions(+), 1 deletion(-) - create mode 100644 crypt.3 - create mode 100644 crypt_r.3 - create mode 100644 crypt_ra.3 - -diff --git a/Makefile.am b/Makefile.am -index 874db12..41ca783 100644 ---- a/Makefile.am -+++ b/Makefile.am -@@ -18,7 +18,8 @@ EXTRA_DIST = \ - gen-map.awk gen-vers.awk gen-crypt-h.awk \ - gen-hashes.awk sel-hashes.awk hashes.lst - --notrans_dist_man3_MANS = crypt_rn.3 crypt_gensalt.3 -+notrans_dist_man3_MANS = crypt.3 crypt_r.3 crypt_ra.3 \ -+ crypt_rn.3 crypt_gensalt.3 - notrans_dist_man5_MANS = crypt.5 - - nodist_include_HEADERS = crypt.h -diff --git a/crypt.3 b/crypt.3 -new file mode 100644 -index 0000000..430e48f ---- /dev/null -+++ b/crypt.3 -@@ -0,0 +1 @@ -+.so man3/crypt_rn.3 -diff --git a/crypt.5 b/crypt.5 -index 5db9c92..7fe4609 100644 ---- a/crypt.5 -+++ b/crypt.5 -@@ -279,6 +279,8 @@ that will work on an old operating system that supports nothing else. - .hash "$3$" "\e$3\e$\e$[0-9a-f]{32}" unlimited 8 256 256 0 1 - .SH SEE ALSO - .BR crypt (3), -+.BR crypt_r (3), -+.BR crypt_ra (3), - .BR crypt_rn (3), - .BR crypt_gensalt (3), - .BR getpwent (3), -diff --git a/crypt_gensalt.3 b/crypt_gensalt.3 -index ebfff28..3109740 100644 ---- a/crypt_gensalt.3 -+++ b/crypt_gensalt.3 -@@ -223,6 +223,8 @@ T} Thread safety MT-Safe - .SH SEE ALSO - .ad l - .BR crypt (3), -+.BR crypt_r (3), -+.BR crypt_ra (3), - .BR crypt_rn (3), - .BR getpass (3), - .BR getpwent (3), -diff --git a/crypt_r.3 b/crypt_r.3 -new file mode 100644 -index 0000000..430e48f ---- /dev/null -+++ b/crypt_r.3 -@@ -0,0 +1 @@ -+.so man3/crypt_rn.3 -diff --git a/crypt_ra.3 b/crypt_ra.3 -new file mode 100644 -index 0000000..430e48f ---- /dev/null -+++ b/crypt_ra.3 -@@ -0,0 +1 @@ -+.so man3/crypt_rn.3 - -From 6679d3427645da43140e5c5297f46985590b8e08 Mon Sep 17 00:00:00 2001 -From: =?UTF-8?q?Bj=C3=B6rn=20Esser?= -Date: Sat, 4 Aug 2018 20:45:42 +0200 -Subject: [PATCH 09/10] Update NEWS. - ---- - NEWS | 1 + - 1 file changed, 1 insertion(+) - -diff --git a/NEWS b/NEWS -index 8acf032..7e1d526 100644 ---- a/NEWS -+++ b/NEWS -@@ -7,6 +7,7 @@ Version 4.1.2 - * Add optional 'check-valgrind' target to the Makefile. - * Replace crypt-sha{256,512}.c with an implementation in the Public - Domain. -+* Add alias man-pages for other crypt functions. - - Version 4.1.1 - * --enable-hashes now supports additional groups of hashing methods: - -From 8596e298f761c32cecff45424f5242cd14269292 Mon Sep 17 00:00:00 2001 -From: Zack Weinberg -Date: Tue, 7 Aug 2018 21:35:12 -0400 -Subject: [PATCH 10/10] Add configure option --disable-failure-tokens. - -When this option is given, crypt and crypt_r will return NULL on -failure, instead of a special "failure token" string that isn't the -hash of any passphrase. This was the historical behavior of glibc, -FreeBSD libc, and several other implementations. ---- - NEWS | 8 ++++++ - configure.ac | 20 +++++++++++++ - crypt.c | 4 +++ - crypt_rn.3 | 35 +++++++++++++---------- - test-badsalt.c | 18 +++++++++++- - test-crypt-badargs.c | 68 +++++++++++++++++++++++++------------------- - test-crypt-bcrypt.c | 6 +++- - 7 files changed, 112 insertions(+), 47 deletions(-) - -diff --git a/NEWS b/NEWS -index 7e1d526..de91957 100644 ---- a/NEWS -+++ b/NEWS -@@ -8,6 +8,14 @@ Version 4.1.2 - * Replace crypt-sha{256,512}.c with an implementation in the Public - Domain. - * Add alias man-pages for other crypt functions. -+* Add configure option --disable-failure-tokens, which causes crypt -+ and crypt_r to return NULL on failure, as crypt_rn and crypt_ra do, -+ instead of a special "failure token". Using this option improves -+ compatibility with programs written on the assumption that, like -+ most C library functions, crypt and crypt_r will return NULL on -+ failure; but it breaks compatibility with programs that assume these -+ functions never return NULL. We're not sure which type of program -+ is more common. Please let us know if you encounter either. - - Version 4.1.1 - * --enable-hashes now supports additional groups of hashing methods: -diff --git a/configure.ac b/configure.ac -index 9ea30f6..84d3ad9 100644 ---- a/configure.ac -+++ b/configure.ac -@@ -162,6 +162,26 @@ AX_VALGRIND_DFLT([sgcheck], [off]) - AX_VALGRIND_CHECK() - - # Configure options. -+AC_ARG_ENABLE([failure-tokens], -+ AS_HELP_STRING( -+ [--disable-failure-tokens], -+ [Make crypt and crypt_r return NULL on failure, instead of a -+ special "failure token" string that isn't the hash of any -+ passphrase. This matches the behavior of several other -+ crypt implementations, but will break programs that assume these -+ functions never return NULL. crypt_rn and crypt_ra are not affected -+ by this option, and will always return NULL on failure.] -+ ), -+ [case "$enableval" in -+ yes) enable_failure_tokens=1;; -+ no) enable_failure_tokens=0;; -+ *) AC_MSG_ERROR([bad value ${enableval} for --enable-failure-tokens]);; -+ esac], -+ [enable_failure_tokens=1]) -+AC_DEFINE_UNQUOTED([ENABLE_FAILURE_TOKENS], [$enable_failure_tokens], -+ [Define to 1 if crypt and crypt_r should return a "failure token" on -+ failure, or 0 if they should return NULL.]) -+ - AC_ARG_ENABLE([obsolete-api], - AS_HELP_STRING( - [--enable-obsolete-api[=ARG]], -diff --git a/crypt.c b/crypt.c -index 9a3e192..839763a 100644 ---- a/crypt.c -+++ b/crypt.c -@@ -235,7 +235,11 @@ crypt_r (const char *phrase, const char *setting, struct crypt_data *data) - { - make_failure_token (setting, data->output, sizeof data->output); - do_crypt (phrase, setting, data); -+#if ENABLE_FAILURE_TOKENS - return data->output; -+#else -+ return data->output[0] == '*' ? 0 : data->output; -+#endif - } - SYMVER_crypt_r; - #endif -diff --git a/crypt_rn.3 b/crypt_rn.3 -index 24da44c..d021c4e 100644 ---- a/crypt_rn.3 -+++ b/crypt_rn.3 -@@ -204,17 +204,31 @@ multiple threads simultaneously, as long as a separate - object is used for each thread. - .PP - Upon error, --.B crypt --and --.B crypt_r --return a pointer to an -+.BR crypt_r ", " crypt_rn ", and " crypt_ra -+write an - .I invalid --hashed passphrase. -+hashed passphrase to the -+.I output -+field of their -+.I crypt_data -+object, and -+.B crypt -+writes an invalid hash to its static storage area. - This string will be shorter than 13 characters, - will begin with a \(oq\fB*\fR\(cq, - and will not compare equal to - .IR setting . --(This peculiar behavior is for compatibility -+.PP -+Upon error, -+.BR crypt_rn " and " crypt_ra -+return a null pointer. -+.BR crypt_r " and " crypt -+may also return a null pointer, -+or they may return a pointer to the invalid hash, -+depending on how -+.I libcrypt -+was configured. -+(The option to return the invalid hash is for compatibility - with old applications that assume that - .B crypt - cannot return a null pointer. -@@ -222,15 +236,6 @@ See - .B "PORTABILITY NOTES" - below.) - .PP --.B crypt_rn --and --.B crypt_ra --also write an invalid hashed passphrase to the --.I output --field of their --.I crypt_data --object when they fail, but they return a null pointer. --.PP - All four functions set - .I errno - when they fail. -diff --git a/test-badsalt.c b/test-badsalt.c -index b274337..3d2e47a 100644 ---- a/test-badsalt.c -+++ b/test-badsalt.c -@@ -222,12 +222,28 @@ check_crypt (const char *label, const char *fn, - const char *retval, const char *setting, - bool expected_to_succeed) - { -- /* crypt/crypt_r should never return null */ -+#if ENABLE_FAILURE_TOKENS -+ /* crypt/crypt_r never return null when failure tokens are enabled */ - if (!retval) - { - printf ("FAIL: %s/%s/%s: returned NULL\n", label, setting, fn); - return false; - } -+#else -+ if (expected_to_succeed && !retval) -+ { -+ printf ("FAIL: %s/%s/%s: returned NULL\n", label, setting, fn); -+ return false; -+ } -+ else if (!expected_to_succeed && retval) -+ { -+ printf ("FAIL: %s/%s/%s: returned %p, should be NULL\n", -+ label, setting, fn, (const void *)retval); -+ return false; -+ } -+ else if (!expected_to_succeed && !retval) -+ return true; -+#endif - if (!check_results (label, fn, retval, setting, - expected_to_succeed)) - return false; -diff --git a/test-crypt-badargs.c b/test-crypt-badargs.c -index 0e6af16..6be24a9 100644 ---- a/test-crypt-badargs.c -+++ b/test-crypt-badargs.c -@@ -169,6 +169,14 @@ test_crypt_ra (const char *tag, - check (tag, expect, got); - } - -+#if ENABLE_FAILURE_TOKENS -+# define FT0 "*0" -+# define FT1 "*1" -+#else -+# define FT0 0 -+# define FT1 0 -+#endif -+ - /* PAGE should point to PAGESIZE bytes of read-write memory followed - by another PAGESIZE bytes of inaccessible memory. */ - -@@ -187,55 +195,55 @@ do_tests(char *page, size_t pagesize) - size_t i; - - /* When SETTING is null, it shouldn't matter what PHRASE is. */ -- expect_no_fault ("0.0.crypt", 0, 0, "*0", test_crypt); -- expect_no_fault ("0.0.crypt_r", 0, 0, "*0", test_crypt_r); -+ expect_no_fault ("0.0.crypt", 0, 0, FT0, test_crypt); -+ expect_no_fault ("0.0.crypt_r", 0, 0, FT0, test_crypt_r); - expect_no_fault ("0.0.crypt_rn", 0, 0, 0, test_crypt_rn); - expect_no_fault ("0.0.crypt_ra", 0, 0, 0, test_crypt_ra); - -- expect_no_fault ("''.0.crypt", "", 0, "*0", test_crypt); -- expect_no_fault ("''.0.crypt_r", "", 0, "*0", test_crypt_r); -+ expect_no_fault ("''.0.crypt", "", 0, FT0, test_crypt); -+ expect_no_fault ("''.0.crypt_r", "", 0, FT0, test_crypt_r); - expect_no_fault ("''.0.crypt_rn", "", 0, 0, test_crypt_rn); - expect_no_fault ("''.0.crypt_ra", "", 0, 0, test_crypt_ra); - -- expect_no_fault ("ph.0.crypt", phrase, 0, "*0", test_crypt); -- expect_no_fault ("ph.0.crypt_r", phrase, 0, "*0", test_crypt_r); -+ expect_no_fault ("ph.0.crypt", phrase, 0, FT0, test_crypt); -+ expect_no_fault ("ph.0.crypt_r", phrase, 0, FT0, test_crypt_r); - expect_no_fault ("ph.0.crypt_rn", phrase, 0, 0, test_crypt_rn); - expect_no_fault ("ph.0.crypt_ra", phrase, 0, 0, test_crypt_ra); - -- expect_no_fault ("p1.0.crypt", p1, 0, "*0", test_crypt); -- expect_no_fault ("p1.0.crypt_r", p1, 0, "*0", test_crypt_r); -+ expect_no_fault ("p1.0.crypt", p1, 0, FT0, test_crypt); -+ expect_no_fault ("p1.0.crypt_r", p1, 0, FT0, test_crypt_r); - expect_no_fault ("p1.0.crypt_rn", p1, 0, 0, test_crypt_rn); - expect_no_fault ("p1.0.crypt_ra", p1, 0, 0, test_crypt_ra); - -- expect_no_fault ("p2.0.crypt", p2, 0, "*0", test_crypt); -- expect_no_fault ("p2.0.crypt_r", p2, 0, "*0", test_crypt_r); -+ expect_no_fault ("p2.0.crypt", p2, 0, FT0, test_crypt); -+ expect_no_fault ("p2.0.crypt_r", p2, 0, FT0, test_crypt_r); - expect_no_fault ("p2.0.crypt_rn", p2, 0, 0, test_crypt_rn); - expect_no_fault ("p2.0.crypt_ra", p2, 0, 0, test_crypt_ra); - - /* Conversely, when PHRASE is null, - it shouldn't matter what SETTING is... */ -- expect_no_fault ("0.''.crypt", 0, "", "*0", test_crypt); -- expect_no_fault ("0.''.crypt_r", 0, "", "*0", test_crypt_r); -+ expect_no_fault ("0.''.crypt", 0, "", FT0, test_crypt); -+ expect_no_fault ("0.''.crypt_r", 0, "", FT0, test_crypt_r); - expect_no_fault ("0.''.crypt_rn", 0, "", 0, test_crypt_rn); - expect_no_fault ("0.''.crypt_ra", 0, "", 0, test_crypt_ra); - -- expect_no_fault ("0.'*'.crypt", 0, "*", "*0", test_crypt); -- expect_no_fault ("0.'*'.crypt_r", 0, "*", "*0", test_crypt_r); -+ expect_no_fault ("0.'*'.crypt", 0, "*", FT0, test_crypt); -+ expect_no_fault ("0.'*'.crypt_r", 0, "*", FT0, test_crypt_r); - expect_no_fault ("0.'*'.crypt_rn", 0, "*", 0, test_crypt_rn); - expect_no_fault ("0.'*'.crypt_ra", 0, "*", 0, test_crypt_ra); - -- expect_no_fault ("0.'*0'.crypt", 0, "*0", "*1", test_crypt); -- expect_no_fault ("0.'*0'.crypt_r", 0, "*0", "*1", test_crypt_r); -+ expect_no_fault ("0.'*0'.crypt", 0, "*0", FT1, test_crypt); -+ expect_no_fault ("0.'*0'.crypt_r", 0, "*0", FT1, test_crypt_r); - expect_no_fault ("0.'*0'.crypt_rn", 0, "*0", 0, test_crypt_rn); - expect_no_fault ("0.'*0'.crypt_ra", 0, "*0", 0, test_crypt_ra); - -- expect_no_fault ("0.'*1'.crypt", 0, "*1", "*0", test_crypt); -- expect_no_fault ("0.'*1'.crypt_r", 0, "*1", "*0", test_crypt_r); -+ expect_no_fault ("0.'*1'.crypt", 0, "*1", FT0, test_crypt); -+ expect_no_fault ("0.'*1'.crypt_r", 0, "*1", FT0, test_crypt_r); - expect_no_fault ("0.'*1'.crypt_rn", 0, "*1", 0, test_crypt_rn); - expect_no_fault ("0.'*1'.crypt_ra", 0, "*1", 0, test_crypt_ra); - -- expect_no_fault ("0.p1.crypt", 0, p1, "*0", test_crypt); -- expect_no_fault ("0.p1.crypt_r", 0, p1, "*0", test_crypt_r); -+ expect_no_fault ("0.p1.crypt", 0, p1, FT0, test_crypt); -+ expect_no_fault ("0.p1.crypt_r", 0, p1, FT0, test_crypt_r); - expect_no_fault ("0.p1.crypt_rn", 0, p1, 0, test_crypt_rn); - expect_no_fault ("0.p1.crypt_ra", 0, p1, 0, test_crypt_ra); - -@@ -245,8 +253,8 @@ do_tests(char *page, size_t pagesize) - bug, but it's impractical to fix without breaking the property - that 'crypt' _never_ creates a failure token that is equal to the - setting string, which is more important than this corner case. */ -- expect_a_fault ("0.p2.crypt", 0, p2, "*0", test_crypt); -- expect_a_fault ("0.p2.crypt_r", 0, p2, "*0", test_crypt_r); -+ expect_a_fault ("0.p2.crypt", 0, p2, FT0, test_crypt); -+ expect_a_fault ("0.p2.crypt_r", 0, p2, FT0, test_crypt_r); - expect_a_fault ("0.p2.crypt_rn", 0, p2, 0, test_crypt_rn); - expect_a_fault ("0.p2.crypt_ra", 0, p2, 0, test_crypt_ra); - -@@ -257,9 +265,9 @@ do_tests(char *page, size_t pagesize) - strcpy (page, "p1.'"); - strcat (page, settings[i]); - strcat (page, "'.crypt"); -- expect_a_fault (page, p1, settings[i], "*0", test_crypt); -+ expect_a_fault (page, p1, settings[i], FT0, test_crypt); - strcat (page, "_r"); -- expect_a_fault (page, p1, settings[i], "*0", test_crypt_r); -+ expect_a_fault (page, p1, settings[i], FT0, test_crypt_r); - strcat (page, "n"); - expect_a_fault (page, p1, settings[i], 0, test_crypt_rn); - page [strlen (page) - 1] = 'a'; -@@ -268,9 +276,9 @@ do_tests(char *page, size_t pagesize) - strcpy (page, "p2.'"); - strcat (page, settings[i]); - strcat (page, "'.crypt"); -- expect_a_fault (page, p2, settings[i], "*0", test_crypt); -+ expect_a_fault (page, p2, settings[i], FT0, test_crypt); - strcat (page, "_r"); -- expect_a_fault (page, p2, settings[i], "*0", test_crypt_r); -+ expect_a_fault (page, p2, settings[i], FT0, test_crypt_r); - strcat (page, "n"); - expect_a_fault (page, p2, settings[i], 0, test_crypt_rn); - page [strlen (page) - 1] = 'a'; -@@ -279,8 +287,8 @@ do_tests(char *page, size_t pagesize) - - /* Conversely, when PHRASE is valid, passing an invalid string as SETTING - should crash reliably. */ -- expect_a_fault ("ph.p2.crypt", phrase, p2, "*0", test_crypt); -- expect_a_fault ("ph.p2.crypt_r", phrase, p2, "*0", test_crypt_r); -+ expect_a_fault ("ph.p2.crypt", phrase, p2, FT0, test_crypt); -+ expect_a_fault ("ph.p2.crypt_r", phrase, p2, FT0, test_crypt_r); - expect_a_fault ("ph.p2.crypt_rn", phrase, p2, 0, test_crypt_rn); - expect_a_fault ("ph.p2.crypt_ra", phrase, p2, 0, test_crypt_ra); - -@@ -292,9 +300,9 @@ do_tests(char *page, size_t pagesize) - strcpy (page, "ph.'"); - strcat (page, settings[i]); - strcat (page, ".crypt"); -- expect_a_fault (page, phrase, p1, "*0", test_crypt); -+ expect_a_fault (page, phrase, p1, FT0, test_crypt); - strcat (page, "_r"); -- expect_a_fault (page, phrase, p1, "*0", test_crypt_r); -+ expect_a_fault (page, phrase, p1, FT0, test_crypt_r); - strcat (page, "n"); - expect_a_fault (page, phrase, p1, 0, test_crypt_rn); - page [strlen (page) - 1] = 'a'; -diff --git a/test-crypt-bcrypt.c b/test-crypt-bcrypt.c -index c984e4d..bf149b4 100644 ---- a/test-crypt-bcrypt.c -+++ b/test-crypt-bcrypt.c -@@ -194,8 +194,12 @@ main (void) - errno = 0; - p = crypt (key, setting); - errnm = errno; -+#if ENABLE_FAILURE_TOKENS - match = strcmp (p, hash); -- if ((!ok && !errno) || strcmp (p, hash)) -+#else -+ match = (ok ? strcmp (p, hash) : p != 0); -+#endif -+ if ((!ok && !errno) || match) - { - printf ("FAIL: %d/crypt.1: key=%s setting=%s: xhash=%s xerr=%d, " - "p=%s match=%d err=%s\n", diff --git a/libxcrypt.spec b/libxcrypt.spec index 38d0c11..7d2e121 100644 --- a/libxcrypt.spec +++ b/libxcrypt.spec @@ -18,8 +18,8 @@ Name: libxcrypt -Version: 4.1.1 -Release: 4%{?dist} +Version: 4.1.2 +Release: 1%{?dist} Summary: Extended crypt library for DES, MD5, Blowfish and others # For explicit license breakdown, see the @@ -28,8 +28,6 @@ License: LGPLv2+ and BSD and Public Domain URL: https://github.com/besser82/%{name} Source0: %{url}/archive/v%{version}.tar.gz#/%{name}-%{version}.tar.gz -Patch0: %{url}/compare/v4.1.1...develop.patch#/%{name}-4.1.1_to_master.patch - BuildRequires: fipscheck BuildRequires: libtool @@ -183,6 +181,9 @@ is highly discouraged. %changelog +* Fri Aug 24 2018 Björn Esser - 4.1.2-1 +- New upstream release + * Wed Aug 08 2018 Björn Esser - 4.1.1-4 - Move *.3 manpages to devel subpackage (#1613762) - Add needed Conflicts: man-pages < 4.15-3 diff --git a/sources b/sources index 8659c8b..000125a 100644 --- a/sources +++ b/sources @@ -1 +1 @@ -SHA512 (libxcrypt-4.1.1.tar.gz) = 64f9453ffd0128e65dbafb981e5ee0e20eb1dcabae6290053a9ad30a071e37c8f970c83d2c58c61bddc7f3793af2e32344260cbfc9a69af8beca0b1650e44dff +SHA512 (libxcrypt-4.1.2.tar.gz) = 8be5e3214822d24eba468e01d74d6a809c7317a8503613fb8d515abb120357387286fd0bc9a92023dc9acb7d784442353e6f47d4f49b872b9c9e6cde1f402095