Latest update.
This commit is contained in:
@@ -9,6 +9,12 @@
|
|||||||
|
|
||||||
Changes between 1.1.1 and 3.0.0 [xx XXX xxxx]
|
Changes between 1.1.1 and 3.0.0 [xx XXX xxxx]
|
||||||
|
|
||||||
|
*) Change the default RSA, DSA and DH size to 2048 bit instead of 1024.
|
||||||
|
This changes the size when using the genpkey app when no size is given. It
|
||||||
|
fixes an omission in earlier changes that changed all RSA, DSA and DH
|
||||||
|
generation apps to use 2048 bits by default.
|
||||||
|
[Kurt Roeckx]
|
||||||
|
|
||||||
*) Added command 'openssl kdf' that uses the EVP_KDF API.
|
*) Added command 'openssl kdf' that uses the EVP_KDF API.
|
||||||
[Shane Lontis]
|
[Shane Lontis]
|
||||||
|
|
||||||
|
|||||||
@@ -13,7 +13,8 @@ require platform::BASE;
|
|||||||
use configdata;
|
use configdata;
|
||||||
|
|
||||||
sub binext { $target{exe_extension} || '' }
|
sub binext { $target{exe_extension} || '' }
|
||||||
sub dsoext { $target{dso_extension} || '.so' }
|
sub dsoext { $target{dso_extension} || platform->shlibextsimple()
|
||||||
|
|| '.so' }
|
||||||
# Because these are also used in scripts and not just Makefile, we must
|
# Because these are also used in scripts and not just Makefile, we must
|
||||||
# convert $(SHLIB_VERSION_NUMBER) to the actual number.
|
# convert $(SHLIB_VERSION_NUMBER) to the actual number.
|
||||||
sub shlibext { (my $x = $target{shared_extension}
|
sub shlibext { (my $x = $target{shared_extension}
|
||||||
|
|||||||
@@ -33,9 +33,10 @@ my %shared_info;
|
|||||||
%{$shared_info{'gnu-shared'}},
|
%{$shared_info{'gnu-shared'}},
|
||||||
shared_defflag => '-Wl,--version-script=',
|
shared_defflag => '-Wl,--version-script=',
|
||||||
dso_ldflags =>
|
dso_ldflags =>
|
||||||
$disabled{asan} && $disabled{msan} && $disabled{ubsan}
|
(grep /(?:^|\s)-fsanitize/,
|
||||||
? '-z defs'
|
@{$config{CFLAGS}}, @{$config{cflags}})
|
||||||
: '',
|
? ''
|
||||||
|
: '-z defs',
|
||||||
};
|
};
|
||||||
},
|
},
|
||||||
'bsd-gcc-shared' => sub { return $shared_info{'linux-shared'}; },
|
'bsd-gcc-shared' => sub { return $shared_info{'linux-shared'}; },
|
||||||
|
|||||||
@@ -206,6 +206,7 @@ AS={- $config{AS} -}
|
|||||||
ASFLAGS={- join(' ', @{$config{ASFLAGS}}) -}
|
ASFLAGS={- join(' ', @{$config{ASFLAGS}}) -}
|
||||||
|
|
||||||
RC={- $config{RC} -}
|
RC={- $config{RC} -}
|
||||||
|
RCFLAGS={- join(' ', @{$config{RCFLAGS}}) -}
|
||||||
|
|
||||||
ECHO="$(PERL)" "$(SRCDIR)\util\echo.pl"
|
ECHO="$(PERL)" "$(SRCDIR)\util\echo.pl"
|
||||||
|
|
||||||
@@ -630,7 +631,7 @@ EOF
|
|||||||
my $res = platform->res($args{obj});
|
my $res = platform->res($args{obj});
|
||||||
return <<"EOF";
|
return <<"EOF";
|
||||||
$res: $deps
|
$res: $deps
|
||||||
\$(RC) \$(RCOUTFLAG)\$\@ $srcs
|
\$(RC) \$(RCFLAGS) \$(RCOUTFLAG)\$\@ $srcs
|
||||||
EOF
|
EOF
|
||||||
}
|
}
|
||||||
my $obj = platform->obj($args{obj});
|
my $obj = platform->obj($args{obj});
|
||||||
|
|||||||
@@ -345,9 +345,9 @@ my @disablables = (
|
|||||||
"cast",
|
"cast",
|
||||||
"chacha",
|
"chacha",
|
||||||
"cmac",
|
"cmac",
|
||||||
|
"cmp",
|
||||||
"cms",
|
"cms",
|
||||||
"comp",
|
"comp",
|
||||||
"crmf",
|
|
||||||
"crypto-mdebug",
|
"crypto-mdebug",
|
||||||
"crypto-mdebug-backtrace",
|
"crypto-mdebug-backtrace",
|
||||||
"ct",
|
"ct",
|
||||||
@@ -433,6 +433,14 @@ foreach my $proto ((@tls, @dtls))
|
|||||||
push(@disablables, "$proto-method") unless $proto eq "tls1_3";
|
push(@disablables, "$proto-method") unless $proto eq "tls1_3";
|
||||||
}
|
}
|
||||||
|
|
||||||
|
# Internal disablables, for aliasing purposes. They serve no special
|
||||||
|
# purpose here, but allow scripts to get to know them through configdata.pm,
|
||||||
|
# where these are merged with @disablables.
|
||||||
|
# The actual aliasing mechanism is done via %disable_cascades
|
||||||
|
my @disablables_int = qw(
|
||||||
|
crmf
|
||||||
|
);
|
||||||
|
|
||||||
my %deprecated_disablables = (
|
my %deprecated_disablables = (
|
||||||
"ssl2" => undef,
|
"ssl2" => undef,
|
||||||
"buf-freelists" => undef,
|
"buf-freelists" => undef,
|
||||||
@@ -534,6 +542,8 @@ my @disable_cascades = (
|
|||||||
|
|
||||||
sub { $disabled{cmac}; } => [ "siv" ],
|
sub { $disabled{cmac}; } => [ "siv" ],
|
||||||
"legacy" => [ "md2" ],
|
"legacy" => [ "md2" ],
|
||||||
|
|
||||||
|
"cmp" => [ "crmf" ],
|
||||||
);
|
);
|
||||||
|
|
||||||
# Avoid protocol support holes. Also disable all versions below N, if version
|
# Avoid protocol support holes. Also disable all versions below N, if version
|
||||||
@@ -594,7 +604,7 @@ my %user = (
|
|||||||
PERL => env('PERL') || ($^O ne "VMS" ? $^X : "perl"),
|
PERL => env('PERL') || ($^O ne "VMS" ? $^X : "perl"),
|
||||||
RANLIB => env('RANLIB'),
|
RANLIB => env('RANLIB'),
|
||||||
RC => env('RC') || env('WINDRES'),
|
RC => env('RC') || env('WINDRES'),
|
||||||
RCFLAGS => [],
|
RCFLAGS => [ env('RCFLAGS') || () ],
|
||||||
RM => undef,
|
RM => undef,
|
||||||
);
|
);
|
||||||
# Info about what "make variables" may be prefixed with the cross compiler
|
# Info about what "make variables" may be prefixed with the cross compiler
|
||||||
@@ -611,6 +621,7 @@ my %useradd = (
|
|||||||
CXXFLAGS => [],
|
CXXFLAGS => [],
|
||||||
LDFLAGS => [],
|
LDFLAGS => [],
|
||||||
LDLIBS => [],
|
LDLIBS => [],
|
||||||
|
RCFLAGS => [],
|
||||||
);
|
);
|
||||||
|
|
||||||
my %user_synonyms = (
|
my %user_synonyms = (
|
||||||
@@ -1110,44 +1121,6 @@ foreach (keys %target_attr_translate) {
|
|||||||
|
|
||||||
%target = ( %{$table{DEFAULTS}}, %target );
|
%target = ( %{$table{DEFAULTS}}, %target );
|
||||||
|
|
||||||
# Make the flags to build DSOs the same as for shared libraries unless they
|
|
||||||
# are already defined
|
|
||||||
$target{module_cflags} = $target{shared_cflag} unless defined $target{module_cflags};
|
|
||||||
$target{module_cxxflags} = $target{shared_cxxflag} unless defined $target{module_cxxflags};
|
|
||||||
$target{module_ldflags} = $target{shared_ldflag} unless defined $target{module_ldflags};
|
|
||||||
{
|
|
||||||
my $shared_info_pl =
|
|
||||||
catfile(dirname($0), "Configurations", "shared-info.pl");
|
|
||||||
my %shared_info = read_eval_file($shared_info_pl);
|
|
||||||
push @{$target{_conf_fname_int}}, $shared_info_pl;
|
|
||||||
my $si = $target{shared_target};
|
|
||||||
while (ref $si ne "HASH") {
|
|
||||||
last if ! defined $si;
|
|
||||||
if (ref $si eq "CODE") {
|
|
||||||
$si = $si->();
|
|
||||||
} else {
|
|
||||||
$si = $shared_info{$si};
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
# Some of the 'shared_target' values don't have any entried in
|
|
||||||
# %shared_info. That's perfectly fine, AS LONG AS the build file
|
|
||||||
# template knows how to handle this. That is currently the case for
|
|
||||||
# Windows and VMS.
|
|
||||||
if (defined $si) {
|
|
||||||
# Just as above, copy certain shared_* attributes to the corresponding
|
|
||||||
# module_ attribute unless the latter is already defined
|
|
||||||
$si->{module_cflags} = $si->{shared_cflag} unless defined $si->{module_cflags};
|
|
||||||
$si->{module_cxxflags} = $si->{shared_cxxflag} unless defined $si->{module_cxxflags};
|
|
||||||
$si->{module_ldflags} = $si->{shared_ldflag} unless defined $si->{module_ldflags};
|
|
||||||
foreach (sort keys %$si) {
|
|
||||||
$target{$_} = defined $target{$_}
|
|
||||||
? add($si->{$_})->($target{$_})
|
|
||||||
: $si->{$_};
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
my %conf_files = map { $_ => 1 } (@{$target{_conf_fname_int}});
|
my %conf_files = map { $_ => 1 } (@{$target{_conf_fname_int}});
|
||||||
$config{conf_files} = [ sort keys %conf_files ];
|
$config{conf_files} = [ sort keys %conf_files ];
|
||||||
|
|
||||||
@@ -1687,7 +1660,48 @@ unless ($disabled{ktls}) {
|
|||||||
|
|
||||||
push @{$config{openssl_other_defines}}, "OPENSSL_NO_KTLS" if ($disabled{ktls});
|
push @{$config{openssl_other_defines}}, "OPENSSL_NO_KTLS" if ($disabled{ktls});
|
||||||
|
|
||||||
# ALL MODIFICATIONS TO %config and %target MUST BE DONE FROM HERE ON
|
# Get the extra flags used when building shared libraries and modules. We
|
||||||
|
# do this late because some of them depend on %disabled.
|
||||||
|
|
||||||
|
# Make the flags to build DSOs the same as for shared libraries unless they
|
||||||
|
# are already defined
|
||||||
|
$target{module_cflags} = $target{shared_cflag} unless defined $target{module_cflags};
|
||||||
|
$target{module_cxxflags} = $target{shared_cxxflag} unless defined $target{module_cxxflags};
|
||||||
|
$target{module_ldflags} = $target{shared_ldflag} unless defined $target{module_ldflags};
|
||||||
|
{
|
||||||
|
my $shared_info_pl =
|
||||||
|
catfile(dirname($0), "Configurations", "shared-info.pl");
|
||||||
|
my %shared_info = read_eval_file($shared_info_pl);
|
||||||
|
push @{$target{_conf_fname_int}}, $shared_info_pl;
|
||||||
|
my $si = $target{shared_target};
|
||||||
|
while (ref $si ne "HASH") {
|
||||||
|
last if ! defined $si;
|
||||||
|
if (ref $si eq "CODE") {
|
||||||
|
$si = $si->();
|
||||||
|
} else {
|
||||||
|
$si = $shared_info{$si};
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
# Some of the 'shared_target' values don't have any entries in
|
||||||
|
# %shared_info. That's perfectly fine, AS LONG AS the build file
|
||||||
|
# template knows how to handle this. That is currently the case for
|
||||||
|
# Windows and VMS.
|
||||||
|
if (defined $si) {
|
||||||
|
# Just as above, copy certain shared_* attributes to the corresponding
|
||||||
|
# module_ attribute unless the latter is already defined
|
||||||
|
$si->{module_cflags} = $si->{shared_cflag} unless defined $si->{module_cflags};
|
||||||
|
$si->{module_cxxflags} = $si->{shared_cxxflag} unless defined $si->{module_cxxflags};
|
||||||
|
$si->{module_ldflags} = $si->{shared_ldflag} unless defined $si->{module_ldflags};
|
||||||
|
foreach (sort keys %$si) {
|
||||||
|
$target{$_} = defined $target{$_}
|
||||||
|
? add($si->{$_})->($target{$_})
|
||||||
|
: $si->{$_};
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
# ALL MODIFICATIONS TO %disabled, %config and %target MUST BE DONE FROM HERE ON
|
||||||
|
|
||||||
# If we use the unified build, collect information from build.info files
|
# If we use the unified build, collect information from build.info files
|
||||||
my %unified_info = ();
|
my %unified_info = ();
|
||||||
@@ -2411,7 +2425,7 @@ use warnings;
|
|||||||
use Exporter;
|
use Exporter;
|
||||||
#use vars qw(\@ISA \@EXPORT);
|
#use vars qw(\@ISA \@EXPORT);
|
||||||
our \@ISA = qw(Exporter);
|
our \@ISA = qw(Exporter);
|
||||||
our \@EXPORT = qw(\%config \%target \%disabled \%withargs \%unified_info \@disablables);
|
our \@EXPORT = qw(\%config \%target \%disabled \%withargs \%unified_info \@disablables \@disablables_int);
|
||||||
|
|
||||||
EOF
|
EOF
|
||||||
print OUT "our %config = (\n";
|
print OUT "our %config = (\n";
|
||||||
@@ -2472,6 +2486,15 @@ foreach (@disablables) {
|
|||||||
print OUT <<"EOF";
|
print OUT <<"EOF";
|
||||||
);
|
);
|
||||||
|
|
||||||
|
EOF
|
||||||
|
print OUT "# The following come from Configure's @disablables_int\n";
|
||||||
|
print OUT "our \@disablables_int = (\n";
|
||||||
|
foreach (@disablables_int) {
|
||||||
|
print OUT " ", quotify("perl", $_), ",\n";
|
||||||
|
}
|
||||||
|
print OUT <<"EOF";
|
||||||
|
);
|
||||||
|
|
||||||
EOF
|
EOF
|
||||||
print OUT "our \%disabled = (\n";
|
print OUT "our \%disabled = (\n";
|
||||||
foreach (sort keys %disabled) {
|
foreach (sort keys %disabled) {
|
||||||
|
|||||||
@@ -23,6 +23,7 @@
|
|||||||
* NOTES.WIN (any supported Windows)
|
* NOTES.WIN (any supported Windows)
|
||||||
* NOTES.DJGPP (DOS platform with DJGPP)
|
* NOTES.DJGPP (DOS platform with DJGPP)
|
||||||
* NOTES.ANDROID (obviously Android [NDK])
|
* NOTES.ANDROID (obviously Android [NDK])
|
||||||
|
* NOTES.VALGRIND (testing with Valgrind)
|
||||||
|
|
||||||
Notational conventions in this document
|
Notational conventions in this document
|
||||||
---------------------------------------
|
---------------------------------------
|
||||||
|
|||||||
+1
-1
@@ -78,7 +78,7 @@
|
|||||||
---------------------------------
|
---------------------------------
|
||||||
|
|
||||||
There are a number of ways to install a perl module. In all
|
There are a number of ways to install a perl module. In all
|
||||||
descriptions below, Text::Template will server as an example.
|
descriptions below, Text::Template will serve as an example.
|
||||||
|
|
||||||
1. for Linux users, the easiest is to install with the use of your
|
1. for Linux users, the easiest is to install with the use of your
|
||||||
favorite package manager. Usually, all you need to do is search
|
favorite package manager. Usually, all you need to do is search
|
||||||
|
|||||||
@@ -0,0 +1,70 @@
|
|||||||
|
|
||||||
|
NOTES FOR VALGRIND
|
||||||
|
==================
|
||||||
|
|
||||||
|
Valgrind is a test harness that includes many tools such as memcheck,
|
||||||
|
which is commonly used to check for memory leaks, etc. The default tool
|
||||||
|
run by Valgrind is memcheck. There are other tools available, but this
|
||||||
|
will focus on memcheck.
|
||||||
|
|
||||||
|
Valgrind runs programs in a virtual machine, this means OpenSSL unit
|
||||||
|
tests run under Valgrind will take longer than normal.
|
||||||
|
|
||||||
|
Requirements
|
||||||
|
------------
|
||||||
|
|
||||||
|
1. Platform supported by Valgrind
|
||||||
|
See: http://valgrind.org/info/platforms.html
|
||||||
|
2. Valgrind installed on the platform
|
||||||
|
See: http://valgrind.org/downloads/current.html
|
||||||
|
3. OpensSSL compiled
|
||||||
|
See: INSTALL
|
||||||
|
|
||||||
|
Running Tests
|
||||||
|
-------------
|
||||||
|
|
||||||
|
Test behavior can be modified by adjusting environment variables.
|
||||||
|
|
||||||
|
EXE_SHELL
|
||||||
|
|
||||||
|
This variable is used to specify the shell used to execute OpenSSL test
|
||||||
|
programs. The default program (util/shlib_wrap.sh) initializes the
|
||||||
|
environment to allow programs to find shared libraries. The variable can
|
||||||
|
be modified to specify a different executable environment.
|
||||||
|
|
||||||
|
EXE_SHELL="`/bin/pwd`/util/shlib_wrap.sh valgrind --error-exitcode=1 --leak-check=full -q"
|
||||||
|
|
||||||
|
This will start up Valgrind with the default checker (memcheck).
|
||||||
|
The --error-exitcode=1 option specifies that Valgrind should exit with an
|
||||||
|
error code of 1 when memory leaks occur.
|
||||||
|
The --leak-check=full option specifies extensive memory checking.
|
||||||
|
The -q option prints only error messages.
|
||||||
|
Additional Valgrind options may be added to the EXE_SHELL variable.
|
||||||
|
|
||||||
|
OPENSSL_ia32cap
|
||||||
|
|
||||||
|
This variable controls the processor-specific code on Intel processors.
|
||||||
|
By default, OpenSSL will attempt to figure out the capabilities of a
|
||||||
|
processor, and use it to its fullest capability. This variable can be
|
||||||
|
used to control what capabilities OpenSSL uses.
|
||||||
|
|
||||||
|
As of valgrind-3.15.0 on Linux/x86_64, instructions up to AVX2 are
|
||||||
|
supported. Setting the following disables instructions beyond AVX2:
|
||||||
|
|
||||||
|
OPENSSL_ia32cap=":0"
|
||||||
|
|
||||||
|
This variable may need to be set to something different based on the
|
||||||
|
processor and Valgrind version you are running tests on. More information
|
||||||
|
may be found in docs/man3/OPENSSL_ia32cap.pod.
|
||||||
|
|
||||||
|
Additional variables (i.e. VERBOSE and TESTS) are described in the
|
||||||
|
INSTALL file in the root of the OpenSSL source tree.
|
||||||
|
|
||||||
|
Example command line:
|
||||||
|
|
||||||
|
make test EXE_SHELL="`/bin/pwd`/util/shlib_wrap.sh valgrind --error-exitcode=1 --leak-check=full -q" OPENSSL_ia32cap=":0"
|
||||||
|
|
||||||
|
If an error occurs, you can then run the specific test via the TESTS
|
||||||
|
variable with the VERBOSE option to gather additional information.
|
||||||
|
|
||||||
|
make test VERBOSE=1 TESTS=test_test EXE_SHELL="`/bin/pwd`/util/shlib_wrap.sh valgrind --error-exitcode=1 --leak-check=full -q" OPENSSL_ia32cap=":0"
|
||||||
@@ -640,6 +640,7 @@ int cms_main(int argc, char **argv)
|
|||||||
goto opthelp;
|
goto opthelp;
|
||||||
}
|
}
|
||||||
} else if (!operation) {
|
} else if (!operation) {
|
||||||
|
BIO_printf(bio_err, "No operation option (-encrypt|-decrypt|-sign|-verify|...) specified.\n");
|
||||||
goto opthelp;
|
goto opthelp;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
+16
-4
@@ -25,12 +25,15 @@ NON_EMPTY_TRANSLATION_UNIT
|
|||||||
# include <openssl/x509.h>
|
# include <openssl/x509.h>
|
||||||
# include <openssl/pem.h>
|
# include <openssl/pem.h>
|
||||||
|
|
||||||
|
static int verbose = 0;
|
||||||
|
|
||||||
static int dsa_cb(int p, int n, BN_GENCB *cb);
|
static int dsa_cb(int p, int n, BN_GENCB *cb);
|
||||||
|
|
||||||
typedef enum OPTION_choice {
|
typedef enum OPTION_choice {
|
||||||
OPT_ERR = -1, OPT_EOF = 0, OPT_HELP,
|
OPT_ERR = -1, OPT_EOF = 0, OPT_HELP,
|
||||||
OPT_INFORM, OPT_OUTFORM, OPT_IN, OPT_OUT, OPT_TEXT, OPT_C,
|
OPT_INFORM, OPT_OUTFORM, OPT_IN, OPT_OUT, OPT_TEXT, OPT_C,
|
||||||
OPT_NOOUT, OPT_GENKEY, OPT_ENGINE, OPT_R_ENUM
|
OPT_NOOUT, OPT_GENKEY, OPT_ENGINE, OPT_VERBOSE,
|
||||||
|
OPT_R_ENUM
|
||||||
} OPTION_CHOICE;
|
} OPTION_CHOICE;
|
||||||
|
|
||||||
const OPTIONS dsaparam_options[] = {
|
const OPTIONS dsaparam_options[] = {
|
||||||
@@ -47,6 +50,7 @@ const OPTIONS dsaparam_options[] = {
|
|||||||
# ifndef OPENSSL_NO_ENGINE
|
# ifndef OPENSSL_NO_ENGINE
|
||||||
{"engine", OPT_ENGINE, 's', "Use engine e, possibly a hardware device"},
|
{"engine", OPT_ENGINE, 's', "Use engine e, possibly a hardware device"},
|
||||||
# endif
|
# endif
|
||||||
|
{"verbose", OPT_VERBOSE, '-', "Verbose output"},
|
||||||
{NULL}
|
{NULL}
|
||||||
};
|
};
|
||||||
|
|
||||||
@@ -107,6 +111,9 @@ int dsaparam_main(int argc, char **argv)
|
|||||||
case OPT_NOOUT:
|
case OPT_NOOUT:
|
||||||
noout = 1;
|
noout = 1;
|
||||||
break;
|
break;
|
||||||
|
case OPT_VERBOSE:
|
||||||
|
verbose = 1;
|
||||||
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
argc = opt_num_rest();
|
argc = opt_num_rest();
|
||||||
@@ -145,9 +152,11 @@ int dsaparam_main(int argc, char **argv)
|
|||||||
BIO_printf(bio_err, "Error allocating DSA object\n");
|
BIO_printf(bio_err, "Error allocating DSA object\n");
|
||||||
goto end;
|
goto end;
|
||||||
}
|
}
|
||||||
BIO_printf(bio_err, "Generating DSA parameters, %d bit long prime\n",
|
if (verbose) {
|
||||||
num);
|
BIO_printf(bio_err, "Generating DSA parameters, %d bit long prime\n",
|
||||||
BIO_printf(bio_err, "This could take some time\n");
|
num);
|
||||||
|
BIO_printf(bio_err, "This could take some time\n");
|
||||||
|
}
|
||||||
if (!DSA_generate_parameters_ex(dsa, num, NULL, 0, NULL, NULL, cb)) {
|
if (!DSA_generate_parameters_ex(dsa, num, NULL, 0, NULL, NULL, cb)) {
|
||||||
ERR_print_errors(bio_err);
|
ERR_print_errors(bio_err);
|
||||||
BIO_printf(bio_err, "Error, DSA key generation failed\n");
|
BIO_printf(bio_err, "Error, DSA key generation failed\n");
|
||||||
@@ -251,6 +260,9 @@ static int dsa_cb(int p, int n, BN_GENCB *cb)
|
|||||||
static const char symbols[] = ".+*\n";
|
static const char symbols[] = ".+*\n";
|
||||||
char c = (p >= 0 && (size_t)p < sizeof(symbols) - 1) ? symbols[p] : '?';
|
char c = (p >= 0 && (size_t)p < sizeof(symbols) - 1) ? symbols[p] : '?';
|
||||||
|
|
||||||
|
if (!verbose)
|
||||||
|
return 1;
|
||||||
|
|
||||||
BIO_write(BN_GENCB_get_arg(cb), &c, 1);
|
BIO_write(BN_GENCB_get_arg(cb), &c, 1);
|
||||||
(void)BIO_flush(BN_GENCB_get_arg(cb));
|
(void)BIO_flush(BN_GENCB_get_arg(cb));
|
||||||
return 1;
|
return 1;
|
||||||
|
|||||||
+8
-3
@@ -27,7 +27,7 @@ NON_EMPTY_TRANSLATION_UNIT
|
|||||||
|
|
||||||
typedef enum OPTION_choice {
|
typedef enum OPTION_choice {
|
||||||
OPT_ERR = -1, OPT_EOF = 0, OPT_HELP,
|
OPT_ERR = -1, OPT_EOF = 0, OPT_HELP,
|
||||||
OPT_OUT, OPT_PASSOUT, OPT_ENGINE, OPT_CIPHER,
|
OPT_OUT, OPT_PASSOUT, OPT_ENGINE, OPT_CIPHER, OPT_VERBOSE,
|
||||||
OPT_R_ENUM
|
OPT_R_ENUM
|
||||||
} OPTION_CHOICE;
|
} OPTION_CHOICE;
|
||||||
|
|
||||||
@@ -42,6 +42,7 @@ const OPTIONS gendsa_options[] = {
|
|||||||
# ifndef OPENSSL_NO_ENGINE
|
# ifndef OPENSSL_NO_ENGINE
|
||||||
{"engine", OPT_ENGINE, 's', "Use engine, possibly a hardware device"},
|
{"engine", OPT_ENGINE, 's', "Use engine, possibly a hardware device"},
|
||||||
# endif
|
# endif
|
||||||
|
{"verbose", OPT_VERBOSE, '-', "Verbose output"},
|
||||||
{NULL}
|
{NULL}
|
||||||
};
|
};
|
||||||
|
|
||||||
@@ -54,7 +55,7 @@ int gendsa_main(int argc, char **argv)
|
|||||||
char *dsaparams = NULL;
|
char *dsaparams = NULL;
|
||||||
char *outfile = NULL, *passoutarg = NULL, *passout = NULL, *prog;
|
char *outfile = NULL, *passoutarg = NULL, *passout = NULL, *prog;
|
||||||
OPTION_CHOICE o;
|
OPTION_CHOICE o;
|
||||||
int ret = 1, private = 0;
|
int ret = 1, private = 0, verbose = 0;
|
||||||
const BIGNUM *p = NULL;
|
const BIGNUM *p = NULL;
|
||||||
|
|
||||||
prog = opt_init(argc, argv, gendsa_options);
|
prog = opt_init(argc, argv, gendsa_options);
|
||||||
@@ -86,6 +87,9 @@ int gendsa_main(int argc, char **argv)
|
|||||||
if (!opt_cipher(opt_unknown(), &enc))
|
if (!opt_cipher(opt_unknown(), &enc))
|
||||||
goto end;
|
goto end;
|
||||||
break;
|
break;
|
||||||
|
case OPT_VERBOSE:
|
||||||
|
verbose = 1;
|
||||||
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
argc = opt_num_rest();
|
argc = opt_num_rest();
|
||||||
@@ -124,7 +128,8 @@ int gendsa_main(int argc, char **argv)
|
|||||||
" Your key size is %d! Larger key size may behave not as expected.\n",
|
" Your key size is %d! Larger key size may behave not as expected.\n",
|
||||||
OPENSSL_DSA_MAX_MODULUS_BITS, BN_num_bits(p));
|
OPENSSL_DSA_MAX_MODULUS_BITS, BN_num_bits(p));
|
||||||
|
|
||||||
BIO_printf(bio_err, "Generating DSA key, %d bits\n", BN_num_bits(p));
|
if (verbose)
|
||||||
|
BIO_printf(bio_err, "Generating DSA key, %d bits\n", BN_num_bits(p));
|
||||||
if (!DSA_generate_key(dsa))
|
if (!DSA_generate_key(dsa))
|
||||||
goto end;
|
goto end;
|
||||||
|
|
||||||
|
|||||||
+14
-4
@@ -30,12 +30,14 @@ NON_EMPTY_TRANSLATION_UNIT
|
|||||||
# define DEFBITS 2048
|
# define DEFBITS 2048
|
||||||
# define DEFPRIMES 2
|
# define DEFPRIMES 2
|
||||||
|
|
||||||
|
static int verbose = 0;
|
||||||
|
|
||||||
static int genrsa_cb(int p, int n, BN_GENCB *cb);
|
static int genrsa_cb(int p, int n, BN_GENCB *cb);
|
||||||
|
|
||||||
typedef enum OPTION_choice {
|
typedef enum OPTION_choice {
|
||||||
OPT_ERR = -1, OPT_EOF = 0, OPT_HELP,
|
OPT_ERR = -1, OPT_EOF = 0, OPT_HELP,
|
||||||
OPT_3, OPT_F4, OPT_ENGINE,
|
OPT_3, OPT_F4, OPT_ENGINE,
|
||||||
OPT_OUT, OPT_PASSOUT, OPT_CIPHER, OPT_PRIMES,
|
OPT_OUT, OPT_PASSOUT, OPT_CIPHER, OPT_PRIMES, OPT_VERBOSE,
|
||||||
OPT_R_ENUM
|
OPT_R_ENUM
|
||||||
} OPTION_CHOICE;
|
} OPTION_CHOICE;
|
||||||
|
|
||||||
@@ -52,6 +54,7 @@ const OPTIONS genrsa_options[] = {
|
|||||||
{"engine", OPT_ENGINE, 's', "Use engine, possibly a hardware device"},
|
{"engine", OPT_ENGINE, 's', "Use engine, possibly a hardware device"},
|
||||||
# endif
|
# endif
|
||||||
{"primes", OPT_PRIMES, 'p', "Specify number of primes"},
|
{"primes", OPT_PRIMES, 'p', "Specify number of primes"},
|
||||||
|
{"verbose", OPT_VERBOSE, '-', "Verbose output"},
|
||||||
{NULL}
|
{NULL}
|
||||||
};
|
};
|
||||||
|
|
||||||
@@ -115,6 +118,9 @@ opthelp:
|
|||||||
if (!opt_int(opt_arg(), &primes))
|
if (!opt_int(opt_arg(), &primes))
|
||||||
goto end;
|
goto end;
|
||||||
break;
|
break;
|
||||||
|
case OPT_VERBOSE:
|
||||||
|
verbose = 1;
|
||||||
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
argc = opt_num_rest();
|
argc = opt_num_rest();
|
||||||
@@ -143,8 +149,9 @@ opthelp:
|
|||||||
if (out == NULL)
|
if (out == NULL)
|
||||||
goto end;
|
goto end;
|
||||||
|
|
||||||
BIO_printf(bio_err, "Generating RSA private key, %d bit long modulus (%d primes)\n",
|
if (verbose)
|
||||||
num, primes);
|
BIO_printf(bio_err, "Generating RSA private key, %d bit long modulus (%d primes)\n",
|
||||||
|
num, primes);
|
||||||
rsa = eng ? RSA_new_method(eng) : RSA_new();
|
rsa = eng ? RSA_new_method(eng) : RSA_new();
|
||||||
if (rsa == NULL)
|
if (rsa == NULL)
|
||||||
goto end;
|
goto end;
|
||||||
@@ -156,7 +163,7 @@ opthelp:
|
|||||||
RSA_get0_key(rsa, NULL, &e, NULL);
|
RSA_get0_key(rsa, NULL, &e, NULL);
|
||||||
hexe = BN_bn2hex(e);
|
hexe = BN_bn2hex(e);
|
||||||
dece = BN_bn2dec(e);
|
dece = BN_bn2dec(e);
|
||||||
if (hexe && dece) {
|
if (hexe && dece && verbose) {
|
||||||
BIO_printf(bio_err, "e is %s (0x%s)\n", dece, hexe);
|
BIO_printf(bio_err, "e is %s (0x%s)\n", dece, hexe);
|
||||||
}
|
}
|
||||||
OPENSSL_free(hexe);
|
OPENSSL_free(hexe);
|
||||||
@@ -186,6 +193,9 @@ static int genrsa_cb(int p, int n, BN_GENCB *cb)
|
|||||||
{
|
{
|
||||||
char c = '*';
|
char c = '*';
|
||||||
|
|
||||||
|
if (!verbose)
|
||||||
|
return 1;
|
||||||
|
|
||||||
if (p == 0)
|
if (p == 0)
|
||||||
c = '.';
|
c = '.';
|
||||||
if (p == 1)
|
if (p == 1)
|
||||||
|
|||||||
+1
-2
@@ -42,8 +42,7 @@ int info_main(int argc, char **argv)
|
|||||||
prog = opt_init(argc, argv, info_options);
|
prog = opt_init(argc, argv, info_options);
|
||||||
while ((o = opt_next()) != OPT_EOF) {
|
while ((o = opt_next()) != OPT_EOF) {
|
||||||
switch (o) {
|
switch (o) {
|
||||||
case OPT_EOF:
|
default:
|
||||||
case OPT_ERR:
|
|
||||||
opthelp:
|
opthelp:
|
||||||
BIO_printf(bio_err, "%s: Use -help for summary.\n", prog);
|
BIO_printf(bio_err, "%s: Use -help for summary.\n", prog);
|
||||||
goto end;
|
goto end;
|
||||||
|
|||||||
+3
-3
@@ -31,7 +31,7 @@ NON_EMPTY_TRANSLATION_UNIT
|
|||||||
typedef enum OPTION_choice {
|
typedef enum OPTION_choice {
|
||||||
OPT_ERR = -1, OPT_EOF = 0, OPT_HELP,
|
OPT_ERR = -1, OPT_EOF = 0, OPT_HELP,
|
||||||
OPT_ENGINE, OPT_IN, OPT_OUT, OPT_ASN1PARSE, OPT_HEXDUMP,
|
OPT_ENGINE, OPT_IN, OPT_OUT, OPT_ASN1PARSE, OPT_HEXDUMP,
|
||||||
OPT_RAW, OPT_OAEP, OPT_SSL, OPT_PKCS, OPT_X931,
|
OPT_RSA_RAW, OPT_OAEP, OPT_SSL, OPT_PKCS, OPT_X931,
|
||||||
OPT_SIGN, OPT_VERIFY, OPT_REV, OPT_ENCRYPT, OPT_DECRYPT,
|
OPT_SIGN, OPT_VERIFY, OPT_REV, OPT_ENCRYPT, OPT_DECRYPT,
|
||||||
OPT_PUBIN, OPT_CERTIN, OPT_INKEY, OPT_PASSIN, OPT_KEYFORM,
|
OPT_PUBIN, OPT_CERTIN, OPT_INKEY, OPT_PASSIN, OPT_KEYFORM,
|
||||||
OPT_R_ENUM
|
OPT_R_ENUM
|
||||||
@@ -46,7 +46,7 @@ const OPTIONS rsautl_options[] = {
|
|||||||
{"pubin", OPT_PUBIN, '-', "Input is an RSA public"},
|
{"pubin", OPT_PUBIN, '-', "Input is an RSA public"},
|
||||||
{"certin", OPT_CERTIN, '-', "Input is a cert carrying an RSA public key"},
|
{"certin", OPT_CERTIN, '-', "Input is a cert carrying an RSA public key"},
|
||||||
{"ssl", OPT_SSL, '-', "Use SSL v2 padding"},
|
{"ssl", OPT_SSL, '-', "Use SSL v2 padding"},
|
||||||
{"raw", OPT_RAW, '-', "Use no padding"},
|
{"raw", OPT_RSA_RAW, '-', "Use no padding"},
|
||||||
{"pkcs", OPT_PKCS, '-', "Use PKCS#1 v1.5 padding (default)"},
|
{"pkcs", OPT_PKCS, '-', "Use PKCS#1 v1.5 padding (default)"},
|
||||||
{"oaep", OPT_OAEP, '-', "Use PKCS#1 OAEP"},
|
{"oaep", OPT_OAEP, '-', "Use PKCS#1 OAEP"},
|
||||||
{"sign", OPT_SIGN, '-', "Sign with private key"},
|
{"sign", OPT_SIGN, '-', "Sign with private key"},
|
||||||
@@ -112,7 +112,7 @@ int rsautl_main(int argc, char **argv)
|
|||||||
case OPT_HEXDUMP:
|
case OPT_HEXDUMP:
|
||||||
hexdump = 1;
|
hexdump = 1;
|
||||||
break;
|
break;
|
||||||
case OPT_RAW:
|
case OPT_RSA_RAW:
|
||||||
pad = RSA_NO_PADDING;
|
pad = RSA_NO_PADDING;
|
||||||
break;
|
break;
|
||||||
case OPT_OAEP:
|
case OPT_OAEP:
|
||||||
|
|||||||
+11
-2
@@ -123,6 +123,8 @@ static SSL_SESSION *psksess = NULL;
|
|||||||
static char *psk_identity = "Client_identity";
|
static char *psk_identity = "Client_identity";
|
||||||
char *psk_key = NULL; /* by default PSK is not used */
|
char *psk_key = NULL; /* by default PSK is not used */
|
||||||
|
|
||||||
|
static char http_server_binmode = 0; /* for now: 0/1 = default/binary */
|
||||||
|
|
||||||
#ifndef OPENSSL_NO_PSK
|
#ifndef OPENSSL_NO_PSK
|
||||||
static unsigned int psk_server_cb(SSL *ssl, const char *identity,
|
static unsigned int psk_server_cb(SSL *ssl, const char *identity,
|
||||||
unsigned char *psk,
|
unsigned char *psk,
|
||||||
@@ -752,6 +754,7 @@ typedef enum OPTION_choice {
|
|||||||
OPT_SRTP_PROFILES, OPT_KEYMATEXPORT, OPT_KEYMATEXPORTLEN,
|
OPT_SRTP_PROFILES, OPT_KEYMATEXPORT, OPT_KEYMATEXPORTLEN,
|
||||||
OPT_KEYLOG_FILE, OPT_MAX_EARLY, OPT_RECV_MAX_EARLY, OPT_EARLY_DATA,
|
OPT_KEYLOG_FILE, OPT_MAX_EARLY, OPT_RECV_MAX_EARLY, OPT_EARLY_DATA,
|
||||||
OPT_S_NUM_TICKETS, OPT_ANTI_REPLAY, OPT_NO_ANTI_REPLAY, OPT_SCTP_LABEL_BUG,
|
OPT_S_NUM_TICKETS, OPT_ANTI_REPLAY, OPT_NO_ANTI_REPLAY, OPT_SCTP_LABEL_BUG,
|
||||||
|
OPT_HTTP_SERVER_BINMODE,
|
||||||
OPT_R_ENUM,
|
OPT_R_ENUM,
|
||||||
OPT_S_ENUM,
|
OPT_S_ENUM,
|
||||||
OPT_V_ENUM,
|
OPT_V_ENUM,
|
||||||
@@ -966,6 +969,7 @@ const OPTIONS s_server_options[] = {
|
|||||||
"The number of TLSv1.3 session tickets that a server will automatically issue" },
|
"The number of TLSv1.3 session tickets that a server will automatically issue" },
|
||||||
{"anti_replay", OPT_ANTI_REPLAY, '-', "Switch on anti-replay protection (default)"},
|
{"anti_replay", OPT_ANTI_REPLAY, '-', "Switch on anti-replay protection (default)"},
|
||||||
{"no_anti_replay", OPT_NO_ANTI_REPLAY, '-', "Switch off anti-replay protection"},
|
{"no_anti_replay", OPT_NO_ANTI_REPLAY, '-', "Switch off anti-replay protection"},
|
||||||
|
{"http_server_binmode", OPT_HTTP_SERVER_BINMODE, '-', "opening files in binary mode when acting as http server (-WWW and -HTTP)"},
|
||||||
{NULL, OPT_EOF, 0, NULL}
|
{NULL, OPT_EOF, 0, NULL}
|
||||||
};
|
};
|
||||||
|
|
||||||
@@ -1595,6 +1599,9 @@ int s_server_main(int argc, char *argv[])
|
|||||||
if (max_early_data == -1)
|
if (max_early_data == -1)
|
||||||
max_early_data = SSL3_RT_MAX_PLAIN_LENGTH;
|
max_early_data = SSL3_RT_MAX_PLAIN_LENGTH;
|
||||||
break;
|
break;
|
||||||
|
case OPT_HTTP_SERVER_BINMODE:
|
||||||
|
http_server_binmode = 1;
|
||||||
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
argc = opt_num_rest();
|
argc = opt_num_rest();
|
||||||
@@ -2956,6 +2963,7 @@ static int www_body(int s, int stype, int prot, unsigned char *context)
|
|||||||
#endif
|
#endif
|
||||||
int width;
|
int width;
|
||||||
fd_set readfds;
|
fd_set readfds;
|
||||||
|
const char *opmode;
|
||||||
|
|
||||||
/* Set width for a select call if needed */
|
/* Set width for a select call if needed */
|
||||||
width = s + 1;
|
width = s + 1;
|
||||||
@@ -3249,9 +3257,10 @@ static int www_body(int s, int stype, int prot, unsigned char *context)
|
|||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
if ((file = BIO_new_file(p, "r")) == NULL) {
|
opmode = (http_server_binmode == 1) ? "rb" : "r";
|
||||||
|
if ((file = BIO_new_file(p, opmode)) == NULL) {
|
||||||
BIO_puts(io, text);
|
BIO_puts(io, text);
|
||||||
BIO_printf(io, "Error opening '%s'\r\n", p);
|
BIO_printf(io, "Error opening '%s' mode='%s'\r\n", p, opmode);
|
||||||
ERR_print_errors(io);
|
ERR_print_errors(io);
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|||||||
+10
-15
@@ -122,35 +122,30 @@ opthelp:
|
|||||||
if (!dirty)
|
if (!dirty)
|
||||||
version = 1;
|
version = 1;
|
||||||
|
|
||||||
if (version) {
|
if (version)
|
||||||
if (strcmp(OpenSSL_version(OPENSSL_FULL_VERSION_STRING),
|
printf("%s (Library: %s)\n",
|
||||||
OPENSSL_FULL_VERSION_STR) == 0)
|
OPENSSL_VERSION_TEXT, OpenSSL_version(OPENSSL_VERSION));
|
||||||
printf("%s\n", OpenSSL_version(OPENSSL_VERSION));
|
|
||||||
else
|
|
||||||
printf("%s (Library: %s)\n",
|
|
||||||
OPENSSL_VERSION_TEXT, OpenSSL_version(OPENSSL_VERSION));
|
|
||||||
}
|
|
||||||
if (date)
|
if (date)
|
||||||
printf("%s\n", OpenSSL_version(OPENSSL_BUILT_ON));
|
printf("%s\n", OpenSSL_version(OPENSSL_BUILT_ON));
|
||||||
if (platform)
|
if (platform)
|
||||||
printf("%s\n", OpenSSL_version(OPENSSL_PLATFORM));
|
printf("%s\n", OpenSSL_version(OPENSSL_PLATFORM));
|
||||||
if (options) {
|
if (options) {
|
||||||
printf("options: ");
|
printf("options: ");
|
||||||
printf("%s ", BN_options());
|
printf(" %s", BN_options());
|
||||||
#ifndef OPENSSL_NO_MD2
|
#ifndef OPENSSL_NO_MD2
|
||||||
printf("%s ", MD2_options());
|
printf(" %s", MD2_options());
|
||||||
#endif
|
#endif
|
||||||
#ifndef OPENSSL_NO_RC4
|
#ifndef OPENSSL_NO_RC4
|
||||||
printf("%s ", RC4_options());
|
printf(" %s", RC4_options());
|
||||||
#endif
|
#endif
|
||||||
#ifndef OPENSSL_NO_DES
|
#ifndef OPENSSL_NO_DES
|
||||||
printf("%s ", DES_options());
|
printf(" %s", DES_options());
|
||||||
#endif
|
#endif
|
||||||
#ifndef OPENSSL_NO_IDEA
|
#ifndef OPENSSL_NO_IDEA
|
||||||
printf("%s ", IDEA_options());
|
printf(" %s", IDEA_options());
|
||||||
#endif
|
#endif
|
||||||
#ifndef OPENSSL_NO_BF
|
#ifndef OPENSSL_NO_BF
|
||||||
printf("%s ", BF_options());
|
printf(" %s", BF_options());
|
||||||
#endif
|
#endif
|
||||||
printf("\n");
|
printf("\n");
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -217,7 +217,7 @@ int PKCS5_v2_scrypt_keyivgen(EVP_CIPHER_CTX *ctx, const char *pass,
|
|||||||
uint64_t p, r, N;
|
uint64_t p, r, N;
|
||||||
size_t saltlen;
|
size_t saltlen;
|
||||||
size_t keylen = 0;
|
size_t keylen = 0;
|
||||||
int rv = 0;
|
int t, rv = 0;
|
||||||
SCRYPT_PARAMS *sparam = NULL;
|
SCRYPT_PARAMS *sparam = NULL;
|
||||||
|
|
||||||
if (EVP_CIPHER_CTX_cipher(ctx) == NULL) {
|
if (EVP_CIPHER_CTX_cipher(ctx) == NULL) {
|
||||||
@@ -234,7 +234,12 @@ int PKCS5_v2_scrypt_keyivgen(EVP_CIPHER_CTX *ctx, const char *pass,
|
|||||||
goto err;
|
goto err;
|
||||||
}
|
}
|
||||||
|
|
||||||
keylen = EVP_CIPHER_CTX_key_length(ctx);
|
t = EVP_CIPHER_CTX_key_length(ctx);
|
||||||
|
if (t < 0) {
|
||||||
|
EVPerr(EVP_F_PKCS5_V2_SCRYPT_KEYIVGEN, EVP_R_INVALID_KEY_LENGTH);
|
||||||
|
goto err;
|
||||||
|
}
|
||||||
|
keylen = t;
|
||||||
|
|
||||||
/* Now check the parameters of sparam */
|
/* Now check the parameters of sparam */
|
||||||
|
|
||||||
|
|||||||
@@ -0,0 +1,44 @@
|
|||||||
|
/*
|
||||||
|
* Copyright 2019 The OpenSSL Project Authors. All Rights Reserved.
|
||||||
|
*
|
||||||
|
* Licensed under the Apache License 2.0 (the "License"). You may not use
|
||||||
|
* this file except in compliance with the License. You can obtain a copy
|
||||||
|
* in the file LICENSE in the source distribution or at
|
||||||
|
* https://www.openssl.org/source/license.html
|
||||||
|
*/
|
||||||
|
|
||||||
|
#include <stddef.h>
|
||||||
|
#include "internal/cryptlib.h"
|
||||||
|
|
||||||
|
const void *ossl_bsearch(const void *key, const void *base, int num,
|
||||||
|
int size, int (*cmp) (const void *, const void *),
|
||||||
|
int flags)
|
||||||
|
{
|
||||||
|
const char *base_ = base;
|
||||||
|
int l, h, i = 0, c = 0;
|
||||||
|
const char *p = NULL;
|
||||||
|
|
||||||
|
if (num == 0)
|
||||||
|
return NULL;
|
||||||
|
l = 0;
|
||||||
|
h = num;
|
||||||
|
while (l < h) {
|
||||||
|
i = (l + h) / 2;
|
||||||
|
p = &(base_[i * size]);
|
||||||
|
c = (*cmp) (key, p);
|
||||||
|
if (c < 0)
|
||||||
|
h = i;
|
||||||
|
else if (c > 0)
|
||||||
|
l = i + 1;
|
||||||
|
else
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
if (c != 0 && !(flags & OSSL_BSEARCH_VALUE_ON_NOMATCH))
|
||||||
|
p = NULL;
|
||||||
|
else if (c == 0 && (flags & OSSL_BSEARCH_FIRST_VALUE_ON_MATCH)) {
|
||||||
|
while (i > 0 && (*cmp) (key, &(base_[(i - 1) * size])) == 0)
|
||||||
|
i--;
|
||||||
|
p = &(base_[i * size]);
|
||||||
|
}
|
||||||
|
return p;
|
||||||
|
}
|
||||||
+3
-3
@@ -10,7 +10,7 @@ SUBDIRS=objects buffer bio stack lhash rand evp asn1 pem x509 x509v3 conf \
|
|||||||
LIBS=../libcrypto
|
LIBS=../libcrypto
|
||||||
# The Core
|
# The Core
|
||||||
SOURCE[../libcrypto]=provider_core.c provider_predefined.c provider_conf.c \
|
SOURCE[../libcrypto]=provider_core.c provider_predefined.c provider_conf.c \
|
||||||
core_fetch.c
|
core_fetch.c core_namemap.c
|
||||||
|
|
||||||
# Central utilities
|
# Central utilities
|
||||||
SOURCE[../libcrypto]=\
|
SOURCE[../libcrypto]=\
|
||||||
@@ -18,12 +18,12 @@ SOURCE[../libcrypto]=\
|
|||||||
ebcdic.c uid.c o_time.c o_str.c o_dir.c o_fopen.c ctype.c \
|
ebcdic.c uid.c o_time.c o_str.c o_dir.c o_fopen.c ctype.c \
|
||||||
threads_pthread.c threads_win.c threads_none.c getenv.c \
|
threads_pthread.c threads_win.c threads_none.c getenv.c \
|
||||||
o_init.c o_fips.c mem_sec.c init.c context.c sparse_array.c \
|
o_init.c o_fips.c mem_sec.c init.c context.c sparse_array.c \
|
||||||
trace.c provider.c params.c \
|
trace.c provider.c params.c bsearch.c \
|
||||||
{- $target{cpuid_asm_src} -} {- $target{uplink_aux_src} -}
|
{- $target{cpuid_asm_src} -} {- $target{uplink_aux_src} -}
|
||||||
|
|
||||||
# FIPS module
|
# FIPS module
|
||||||
SOURCE[../providers/fips]=\
|
SOURCE[../providers/fips]=\
|
||||||
cryptlib.c mem.c mem_clr.c params.c
|
cryptlib.c mem.c mem_clr.c params.c bsearch.c
|
||||||
|
|
||||||
|
|
||||||
DEPEND[cversion.o]=buildinf.h
|
DEPEND[cversion.o]=buildinf.h
|
||||||
|
|||||||
+194
-22
@@ -10,38 +10,106 @@
|
|||||||
#include "internal/cryptlib.h"
|
#include "internal/cryptlib.h"
|
||||||
#include "internal/thread_once.h"
|
#include "internal/thread_once.h"
|
||||||
|
|
||||||
|
struct openssl_ctx_onfree_list_st {
|
||||||
|
openssl_ctx_onfree_fn *fn;
|
||||||
|
struct openssl_ctx_onfree_list_st *next;
|
||||||
|
};
|
||||||
|
|
||||||
struct openssl_ctx_st {
|
struct openssl_ctx_st {
|
||||||
CRYPTO_RWLOCK *lock;
|
CRYPTO_RWLOCK *lock;
|
||||||
CRYPTO_EX_DATA data;
|
CRYPTO_EX_DATA data;
|
||||||
|
|
||||||
|
/*
|
||||||
|
* For most data in the OPENSSL_CTX we just use ex_data to store it. But
|
||||||
|
* that doesn't work for ex_data itself - so we store that directly.
|
||||||
|
*/
|
||||||
|
OSSL_EX_DATA_GLOBAL global;
|
||||||
|
|
||||||
|
/* Map internal static indexes to dynamically created indexes */
|
||||||
|
int dyn_indexes[OPENSSL_CTX_MAX_INDEXES];
|
||||||
|
|
||||||
|
CRYPTO_RWLOCK *oncelock;
|
||||||
|
int run_once_done[OPENSSL_CTX_MAX_RUN_ONCE];
|
||||||
|
int run_once_ret[OPENSSL_CTX_MAX_RUN_ONCE];
|
||||||
|
struct openssl_ctx_onfree_list_st *onfreelist;
|
||||||
};
|
};
|
||||||
|
|
||||||
static OPENSSL_CTX default_context;
|
#ifndef FIPS_MODE
|
||||||
|
static OPENSSL_CTX default_context_int;
|
||||||
|
#endif
|
||||||
|
|
||||||
|
/* Always points at default_context_int if it has been initialised */
|
||||||
|
static OPENSSL_CTX *default_context = NULL;
|
||||||
|
|
||||||
static int context_init(OPENSSL_CTX *ctx)
|
static int context_init(OPENSSL_CTX *ctx)
|
||||||
{
|
{
|
||||||
return (ctx->lock = CRYPTO_THREAD_lock_new()) != NULL
|
size_t i;
|
||||||
&& CRYPTO_new_ex_data(CRYPTO_EX_INDEX_OPENSSL_CTX, NULL,
|
|
||||||
&ctx->data);
|
ctx->lock = CRYPTO_THREAD_lock_new();
|
||||||
|
if (ctx->lock == NULL)
|
||||||
|
return 0;
|
||||||
|
|
||||||
|
ctx->oncelock = CRYPTO_THREAD_lock_new();
|
||||||
|
if (ctx->oncelock == NULL)
|
||||||
|
goto err;
|
||||||
|
|
||||||
|
for (i = 0; i < OPENSSL_CTX_MAX_INDEXES; i++)
|
||||||
|
ctx->dyn_indexes[i] = -1;
|
||||||
|
|
||||||
|
if (!do_ex_data_init(ctx))
|
||||||
|
goto err;
|
||||||
|
|
||||||
|
if (!crypto_new_ex_data_ex(ctx, CRYPTO_EX_INDEX_OPENSSL_CTX, NULL,
|
||||||
|
&ctx->data)) {
|
||||||
|
crypto_cleanup_all_ex_data_int(ctx);
|
||||||
|
goto err;
|
||||||
|
}
|
||||||
|
|
||||||
|
return 1;
|
||||||
|
err:
|
||||||
|
CRYPTO_THREAD_lock_free(ctx->oncelock);
|
||||||
|
CRYPTO_THREAD_lock_free(ctx->lock);
|
||||||
|
ctx->lock = NULL;
|
||||||
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
static int context_deinit(OPENSSL_CTX *ctx)
|
static int context_deinit(OPENSSL_CTX *ctx)
|
||||||
{
|
{
|
||||||
|
struct openssl_ctx_onfree_list_st *tmp, *onfree;
|
||||||
|
|
||||||
|
if (ctx == NULL)
|
||||||
|
return 1;
|
||||||
|
|
||||||
|
onfree = ctx->onfreelist;
|
||||||
|
while (onfree != NULL) {
|
||||||
|
onfree->fn(ctx);
|
||||||
|
tmp = onfree;
|
||||||
|
onfree = onfree->next;
|
||||||
|
OPENSSL_free(tmp);
|
||||||
|
}
|
||||||
CRYPTO_free_ex_data(CRYPTO_EX_INDEX_OPENSSL_CTX, NULL, &ctx->data);
|
CRYPTO_free_ex_data(CRYPTO_EX_INDEX_OPENSSL_CTX, NULL, &ctx->data);
|
||||||
|
crypto_cleanup_all_ex_data_int(ctx);
|
||||||
|
CRYPTO_THREAD_lock_free(ctx->oncelock);
|
||||||
CRYPTO_THREAD_lock_free(ctx->lock);
|
CRYPTO_THREAD_lock_free(ctx->lock);
|
||||||
|
ctx->lock = NULL;
|
||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
static CRYPTO_ONCE default_context_init = CRYPTO_ONCE_STATIC_INIT;
|
#ifndef FIPS_MODE
|
||||||
static void do_default_context_deinit(void)
|
void openssl_ctx_default_deinit(void)
|
||||||
{
|
{
|
||||||
context_deinit(&default_context);
|
context_deinit(default_context);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static CRYPTO_ONCE default_context_init = CRYPTO_ONCE_STATIC_INIT;
|
||||||
DEFINE_RUN_ONCE_STATIC(do_default_context_init)
|
DEFINE_RUN_ONCE_STATIC(do_default_context_init)
|
||||||
{
|
{
|
||||||
return OPENSSL_init_crypto(0, NULL)
|
if (context_init(&default_context_int))
|
||||||
&& context_init(&default_context)
|
default_context = &default_context_int;
|
||||||
&& OPENSSL_atexit(do_default_context_deinit);
|
|
||||||
|
return 1;
|
||||||
}
|
}
|
||||||
|
#endif
|
||||||
|
|
||||||
OPENSSL_CTX *OPENSSL_CTX_new(void)
|
OPENSSL_CTX *OPENSSL_CTX_new(void)
|
||||||
{
|
{
|
||||||
@@ -66,7 +134,7 @@ static void openssl_ctx_generic_new(void *parent_ign, void *ptr_ign,
|
|||||||
long argl_ign, void *argp)
|
long argl_ign, void *argp)
|
||||||
{
|
{
|
||||||
const OPENSSL_CTX_METHOD *meth = argp;
|
const OPENSSL_CTX_METHOD *meth = argp;
|
||||||
void *ptr = meth->new_func();
|
void *ptr = meth->new_func(crypto_ex_data_get_openssl_ctx(ad));
|
||||||
|
|
||||||
if (ptr != NULL)
|
if (ptr != NULL)
|
||||||
CRYPTO_set_ex_data(ad, index, ptr);
|
CRYPTO_set_ex_data(ad, index, ptr);
|
||||||
@@ -79,32 +147,136 @@ static void openssl_ctx_generic_free(void *parent_ign, void *ptr,
|
|||||||
|
|
||||||
meth->free_func(ptr);
|
meth->free_func(ptr);
|
||||||
}
|
}
|
||||||
int openssl_ctx_new_index(const OPENSSL_CTX_METHOD *meth)
|
|
||||||
{
|
|
||||||
return CRYPTO_get_ex_new_index(CRYPTO_EX_INDEX_OPENSSL_CTX, 0, (void *)meth,
|
|
||||||
openssl_ctx_generic_new, NULL,
|
|
||||||
openssl_ctx_generic_free);
|
|
||||||
}
|
|
||||||
|
|
||||||
void *openssl_ctx_get_data(OPENSSL_CTX *ctx, int index)
|
/* Non-static so we can use it in context_internal_test */
|
||||||
|
static int openssl_ctx_init_index(OPENSSL_CTX *ctx, int static_index,
|
||||||
|
const OPENSSL_CTX_METHOD *meth)
|
||||||
{
|
{
|
||||||
void *data = NULL;
|
int idx;
|
||||||
|
|
||||||
|
#ifndef FIPS_MODE
|
||||||
if (ctx == NULL) {
|
if (ctx == NULL) {
|
||||||
if (!RUN_ONCE(&default_context_init, do_default_context_init))
|
if (!RUN_ONCE(&default_context_init, do_default_context_init))
|
||||||
return 0;
|
return 0;
|
||||||
ctx = &default_context;
|
ctx = default_context;
|
||||||
}
|
}
|
||||||
|
#endif
|
||||||
|
if (ctx == NULL)
|
||||||
|
return 0;
|
||||||
|
|
||||||
|
idx = crypto_get_ex_new_index_ex(ctx, CRYPTO_EX_INDEX_OPENSSL_CTX, 0,
|
||||||
|
(void *)meth,
|
||||||
|
openssl_ctx_generic_new,
|
||||||
|
NULL, openssl_ctx_generic_free);
|
||||||
|
if (idx < 0)
|
||||||
|
return 0;
|
||||||
|
|
||||||
|
ctx->dyn_indexes[static_index] = idx;
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
void *openssl_ctx_get_data(OPENSSL_CTX *ctx, int index,
|
||||||
|
const OPENSSL_CTX_METHOD *meth)
|
||||||
|
{
|
||||||
|
void *data = NULL;
|
||||||
|
|
||||||
|
#ifndef FIPS_MODE
|
||||||
|
if (ctx == NULL) {
|
||||||
|
if (!RUN_ONCE(&default_context_init, do_default_context_init))
|
||||||
|
return NULL;
|
||||||
|
ctx = default_context;
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
if (ctx == NULL)
|
||||||
|
return NULL;
|
||||||
|
|
||||||
CRYPTO_THREAD_read_lock(ctx->lock);
|
CRYPTO_THREAD_read_lock(ctx->lock);
|
||||||
|
|
||||||
|
if (ctx->dyn_indexes[index] == -1
|
||||||
|
&& !openssl_ctx_init_index(ctx, index, meth)) {
|
||||||
|
CRYPTO_THREAD_unlock(ctx->lock);
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
|
|
||||||
/* The alloc call ensures there's a value there */
|
/* The alloc call ensures there's a value there */
|
||||||
if (CRYPTO_alloc_ex_data(CRYPTO_EX_INDEX_OPENSSL_CTX, NULL,
|
if (CRYPTO_alloc_ex_data(CRYPTO_EX_INDEX_OPENSSL_CTX, NULL,
|
||||||
&ctx->data, index))
|
&ctx->data, ctx->dyn_indexes[index]))
|
||||||
data = CRYPTO_get_ex_data(&ctx->data, index);
|
data = CRYPTO_get_ex_data(&ctx->data, ctx->dyn_indexes[index]);
|
||||||
|
|
||||||
CRYPTO_THREAD_unlock(ctx->lock);
|
CRYPTO_THREAD_unlock(ctx->lock);
|
||||||
|
|
||||||
return data;
|
return data;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
OSSL_EX_DATA_GLOBAL *openssl_ctx_get_ex_data_global(OPENSSL_CTX *ctx)
|
||||||
|
{
|
||||||
|
/*
|
||||||
|
* The default context code is not needed in FIPS_MODE and ctx should never
|
||||||
|
* be NULL in the FIPS provider. However we compile this code out to ensure
|
||||||
|
* we fail immediately if ctx == NULL in FIPS_MODE
|
||||||
|
*/
|
||||||
|
#ifndef FIPS_MODE
|
||||||
|
if (ctx == NULL) {
|
||||||
|
if (!RUN_ONCE(&default_context_init, do_default_context_init))
|
||||||
|
return NULL;
|
||||||
|
ctx = default_context;
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
if (ctx == NULL)
|
||||||
|
return NULL;
|
||||||
|
return &ctx->global;
|
||||||
|
}
|
||||||
|
|
||||||
|
int openssl_ctx_run_once(OPENSSL_CTX *ctx, unsigned int idx,
|
||||||
|
openssl_ctx_run_once_fn run_once_fn)
|
||||||
|
{
|
||||||
|
int done = 0, ret = 0;
|
||||||
|
|
||||||
|
#ifndef FIPS_MODE
|
||||||
|
if (ctx == NULL) {
|
||||||
|
if (!RUN_ONCE(&default_context_init, do_default_context_init))
|
||||||
|
return 0;
|
||||||
|
ctx = default_context;
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
if (ctx == NULL)
|
||||||
|
return 0;
|
||||||
|
|
||||||
|
CRYPTO_THREAD_read_lock(ctx->oncelock);
|
||||||
|
done = ctx->run_once_done[idx];
|
||||||
|
if (done)
|
||||||
|
ret = ctx->run_once_ret[idx];
|
||||||
|
CRYPTO_THREAD_unlock(ctx->oncelock);
|
||||||
|
|
||||||
|
if (done)
|
||||||
|
return ret;
|
||||||
|
|
||||||
|
CRYPTO_THREAD_write_lock(ctx->oncelock);
|
||||||
|
if (ctx->run_once_done[idx]) {
|
||||||
|
ret = ctx->run_once_ret[idx];
|
||||||
|
CRYPTO_THREAD_unlock(ctx->oncelock);
|
||||||
|
return ret;
|
||||||
|
}
|
||||||
|
|
||||||
|
ret = run_once_fn(ctx);
|
||||||
|
ctx->run_once_done[idx] = 1;
|
||||||
|
ctx->run_once_ret[idx] = ret;
|
||||||
|
CRYPTO_THREAD_unlock(ctx->oncelock);
|
||||||
|
|
||||||
|
return ret;
|
||||||
|
}
|
||||||
|
|
||||||
|
int openssl_ctx_onfree(OPENSSL_CTX *ctx, openssl_ctx_onfree_fn onfreefn)
|
||||||
|
{
|
||||||
|
struct openssl_ctx_onfree_list_st *newonfree
|
||||||
|
= OPENSSL_malloc(sizeof(*newonfree));
|
||||||
|
|
||||||
|
if (newonfree == NULL)
|
||||||
|
return 0;
|
||||||
|
|
||||||
|
newonfree->fn = onfreefn;
|
||||||
|
newonfree->next = ctx->onfreelist;
|
||||||
|
ctx->onfreelist = newonfree;
|
||||||
|
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
+10
-9
@@ -56,14 +56,14 @@ static int ossl_method_construct_this(OSSL_PROVIDER *provider, void *cbdata)
|
|||||||
* If we haven't been told not to store,
|
* If we haven't been told not to store,
|
||||||
* add to the global store
|
* add to the global store
|
||||||
*/
|
*/
|
||||||
data->mcm->put(data->libctx, NULL,
|
data->mcm->put(data->libctx, NULL, method,
|
||||||
thismap->property_definition,
|
thismap->algorithm_name,
|
||||||
method, data->mcm_data);
|
thismap->property_definition, data->mcm_data);
|
||||||
}
|
}
|
||||||
|
|
||||||
data->mcm->put(data->libctx, data->store,
|
data->mcm->put(data->libctx, data->store, method,
|
||||||
thismap->property_definition,
|
thismap->algorithm_name, thismap->property_definition,
|
||||||
method, data->mcm_data);
|
data->mcm_data);
|
||||||
|
|
||||||
/* refcnt-- because we're dropping the reference */
|
/* refcnt-- because we're dropping the reference */
|
||||||
data->mcm->destruct(method, data->mcm_data);
|
data->mcm->destruct(method, data->mcm_data);
|
||||||
@@ -79,14 +79,15 @@ void *ossl_method_construct(OPENSSL_CTX *libctx, int operation_id,
|
|||||||
{
|
{
|
||||||
void *method = NULL;
|
void *method = NULL;
|
||||||
|
|
||||||
if ((method = mcm->get(libctx, NULL, propquery, mcm_data)) == NULL) {
|
if ((method =
|
||||||
|
mcm->get(libctx, NULL, name, propquery, mcm_data)) == NULL) {
|
||||||
struct construct_data_st cbdata;
|
struct construct_data_st cbdata;
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* We have a temporary store to be able to easily search among new
|
* We have a temporary store to be able to easily search among new
|
||||||
* items, or items that should find themselves in the global store.
|
* items, or items that should find themselves in the global store.
|
||||||
*/
|
*/
|
||||||
if ((cbdata.store = mcm->alloc_tmp_store()) == NULL)
|
if ((cbdata.store = mcm->alloc_tmp_store(libctx)) == NULL)
|
||||||
goto fin;
|
goto fin;
|
||||||
|
|
||||||
cbdata.libctx = libctx;
|
cbdata.libctx = libctx;
|
||||||
@@ -97,7 +98,7 @@ void *ossl_method_construct(OPENSSL_CTX *libctx, int operation_id,
|
|||||||
ossl_provider_forall_loaded(libctx, ossl_method_construct_this,
|
ossl_provider_forall_loaded(libctx, ossl_method_construct_this,
|
||||||
&cbdata);
|
&cbdata);
|
||||||
|
|
||||||
method = mcm->get(libctx, cbdata.store, propquery, mcm_data);
|
method = mcm->get(libctx, cbdata.store, name, propquery, mcm_data);
|
||||||
mcm->dealloc_tmp_store(cbdata.store);
|
mcm->dealloc_tmp_store(cbdata.store);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -0,0 +1,211 @@
|
|||||||
|
/*
|
||||||
|
* Copyright 2019 The OpenSSL Project Authors. All Rights Reserved.
|
||||||
|
*
|
||||||
|
* Licensed under the Apache License 2.0 (the "License"). You may not use
|
||||||
|
* this file except in compliance with the License. You can obtain a copy
|
||||||
|
* in the file LICENSE in the source distribution or at
|
||||||
|
* https://www.openssl.org/source/license.html
|
||||||
|
*/
|
||||||
|
|
||||||
|
#include "internal/namemap.h"
|
||||||
|
#include <openssl/lhash.h>
|
||||||
|
#include <openssl/safestack.h>
|
||||||
|
|
||||||
|
/* The namemap entry */
|
||||||
|
typedef struct {
|
||||||
|
int number;
|
||||||
|
const char *name;
|
||||||
|
char body[1]; /* Sized appropriately to contain the name */
|
||||||
|
} NAMEMAP_ENTRY;
|
||||||
|
|
||||||
|
DEFINE_LHASH_OF(NAMEMAP_ENTRY);
|
||||||
|
DEFINE_STACK_OF(NAMEMAP_ENTRY)
|
||||||
|
|
||||||
|
/* The namemap, which provides for bidirectional indexing */
|
||||||
|
|
||||||
|
struct ossl_namemap_st {
|
||||||
|
/* Flags */
|
||||||
|
unsigned int stored:1; /* If 1, it's stored in a library context */
|
||||||
|
|
||||||
|
CRYPTO_RWLOCK *lock;
|
||||||
|
LHASH_OF(NAMEMAP_ENTRY) *namenum; /* Name->number mapping */
|
||||||
|
STACK_OF(NAMEMAP_ENTRY) *numname; /* Number->name mapping */
|
||||||
|
};
|
||||||
|
|
||||||
|
/* LHASH callbacks */
|
||||||
|
|
||||||
|
static unsigned long namemap_hash(const NAMEMAP_ENTRY *n)
|
||||||
|
{
|
||||||
|
return OPENSSL_LH_strhash(n->name);
|
||||||
|
}
|
||||||
|
|
||||||
|
static int namemap_cmp(const NAMEMAP_ENTRY *a, const NAMEMAP_ENTRY *b)
|
||||||
|
{
|
||||||
|
return strcmp(a->name, b->name);
|
||||||
|
}
|
||||||
|
|
||||||
|
static void namemap_free(NAMEMAP_ENTRY *n)
|
||||||
|
{
|
||||||
|
OPENSSL_free(n);
|
||||||
|
}
|
||||||
|
|
||||||
|
/* OPENSSL_CTX_METHOD functions for a namemap stored in a library context */
|
||||||
|
|
||||||
|
static void *stored_namemap_new(OPENSSL_CTX *libctx)
|
||||||
|
{
|
||||||
|
OSSL_NAMEMAP *namemap = ossl_namemap_new();
|
||||||
|
|
||||||
|
if (namemap != NULL)
|
||||||
|
namemap->stored = 1;
|
||||||
|
|
||||||
|
return namemap;
|
||||||
|
}
|
||||||
|
|
||||||
|
static void stored_namemap_free(void *vnamemap)
|
||||||
|
{
|
||||||
|
OSSL_NAMEMAP *namemap = vnamemap;
|
||||||
|
|
||||||
|
/* Pretend it isn't stored, or ossl_namemap_free() will do nothing */
|
||||||
|
namemap->stored = 0;
|
||||||
|
ossl_namemap_free(namemap);
|
||||||
|
}
|
||||||
|
|
||||||
|
static const OPENSSL_CTX_METHOD stored_namemap_method = {
|
||||||
|
stored_namemap_new,
|
||||||
|
stored_namemap_free,
|
||||||
|
};
|
||||||
|
|
||||||
|
/* API functions */
|
||||||
|
|
||||||
|
OSSL_NAMEMAP *ossl_namemap_stored(OPENSSL_CTX *libctx)
|
||||||
|
{
|
||||||
|
return openssl_ctx_get_data(libctx, OPENSSL_CTX_NAMEMAP_INDEX,
|
||||||
|
&stored_namemap_method);
|
||||||
|
}
|
||||||
|
|
||||||
|
OSSL_NAMEMAP *ossl_namemap_new(void)
|
||||||
|
{
|
||||||
|
OSSL_NAMEMAP *namemap;
|
||||||
|
|
||||||
|
if ((namemap = OPENSSL_zalloc(sizeof(*namemap))) != NULL
|
||||||
|
&& (namemap->lock = CRYPTO_THREAD_lock_new()) != NULL
|
||||||
|
&& (namemap->numname = sk_NAMEMAP_ENTRY_new_null()) != NULL
|
||||||
|
&& (namemap->namenum =
|
||||||
|
lh_NAMEMAP_ENTRY_new(namemap_hash, namemap_cmp)) != NULL) {
|
||||||
|
return namemap;
|
||||||
|
}
|
||||||
|
|
||||||
|
ossl_namemap_free(namemap);
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
|
|
||||||
|
void ossl_namemap_free(OSSL_NAMEMAP *namemap)
|
||||||
|
{
|
||||||
|
if (namemap == NULL || namemap->stored)
|
||||||
|
return;
|
||||||
|
|
||||||
|
/* The elements will be freed by sk_NAMEMAP_ENTRY_pop_free() */
|
||||||
|
lh_NAMEMAP_ENTRY_free(namemap->namenum);
|
||||||
|
|
||||||
|
sk_NAMEMAP_ENTRY_pop_free(namemap->numname, namemap_free);
|
||||||
|
|
||||||
|
CRYPTO_THREAD_lock_free(namemap->lock);
|
||||||
|
OPENSSL_free(namemap);
|
||||||
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
* TODO(3.0) It isn't currently possible to have a default namemap in the
|
||||||
|
* FIPS module because if init and cleanup constraints, so we currently
|
||||||
|
* disable the code that would allow it when FIPS_MODE is defined.
|
||||||
|
*/
|
||||||
|
|
||||||
|
const char *ossl_namemap_name(const OSSL_NAMEMAP *namemap, int number)
|
||||||
|
{
|
||||||
|
NAMEMAP_ENTRY *entry;
|
||||||
|
|
||||||
|
#ifndef FIPS_MODE
|
||||||
|
if (namemap == NULL)
|
||||||
|
namemap = ossl_namemap_stored(NULL);
|
||||||
|
#endif
|
||||||
|
|
||||||
|
if (namemap == NULL || number == 0)
|
||||||
|
return NULL;
|
||||||
|
|
||||||
|
CRYPTO_THREAD_read_lock(namemap->lock);
|
||||||
|
entry = sk_NAMEMAP_ENTRY_value(namemap->numname, number);
|
||||||
|
CRYPTO_THREAD_unlock(namemap->lock);
|
||||||
|
|
||||||
|
if (entry != NULL)
|
||||||
|
return entry->name;
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
|
|
||||||
|
int ossl_namemap_number(const OSSL_NAMEMAP *namemap, const char *name)
|
||||||
|
{
|
||||||
|
NAMEMAP_ENTRY *entry, template;
|
||||||
|
|
||||||
|
#ifndef FIPS_MODE
|
||||||
|
if (namemap == NULL)
|
||||||
|
namemap = ossl_namemap_stored(NULL);
|
||||||
|
#endif
|
||||||
|
|
||||||
|
if (namemap == NULL)
|
||||||
|
return 0;
|
||||||
|
|
||||||
|
template.name = name;
|
||||||
|
CRYPTO_THREAD_read_lock(namemap->lock);
|
||||||
|
entry = lh_NAMEMAP_ENTRY_retrieve(namemap->namenum, &template);
|
||||||
|
CRYPTO_THREAD_unlock(namemap->lock);
|
||||||
|
|
||||||
|
if (entry == NULL)
|
||||||
|
return 0;
|
||||||
|
|
||||||
|
return entry->number;
|
||||||
|
}
|
||||||
|
|
||||||
|
int ossl_namemap_add(OSSL_NAMEMAP *namemap, const char *name)
|
||||||
|
{
|
||||||
|
NAMEMAP_ENTRY *entry;
|
||||||
|
int number;
|
||||||
|
|
||||||
|
#ifndef FIPS_MODE
|
||||||
|
if (namemap == NULL)
|
||||||
|
namemap = ossl_namemap_stored(NULL);
|
||||||
|
#endif
|
||||||
|
|
||||||
|
if (name == NULL || namemap == NULL)
|
||||||
|
return 0;
|
||||||
|
|
||||||
|
if ((number = ossl_namemap_number(namemap, name)) != 0)
|
||||||
|
return number; /* Pretend success */
|
||||||
|
|
||||||
|
if ((entry = OPENSSL_zalloc(sizeof(*entry) + strlen(name))) == NULL)
|
||||||
|
goto err;
|
||||||
|
|
||||||
|
strcpy(entry->body, name);
|
||||||
|
entry->name = entry->body;
|
||||||
|
|
||||||
|
CRYPTO_THREAD_write_lock(namemap->lock);
|
||||||
|
|
||||||
|
entry->number = sk_NAMEMAP_ENTRY_push(namemap->numname, entry);
|
||||||
|
|
||||||
|
if (entry->number == 0)
|
||||||
|
goto err;
|
||||||
|
|
||||||
|
(void)lh_NAMEMAP_ENTRY_insert(namemap->namenum, entry);
|
||||||
|
if (lh_NAMEMAP_ENTRY_error(namemap->namenum))
|
||||||
|
goto err;
|
||||||
|
|
||||||
|
CRYPTO_THREAD_unlock(namemap->lock);
|
||||||
|
|
||||||
|
return entry->number;
|
||||||
|
|
||||||
|
err:
|
||||||
|
if (entry != NULL) {
|
||||||
|
if (entry->number != 0)
|
||||||
|
(void)sk_NAMEMAP_ENTRY_pop(namemap->numname);
|
||||||
|
lh_NAMEMAP_ENTRY_delete(namemap->namenum, entry);
|
||||||
|
CRYPTO_THREAD_unlock(namemap->lock);
|
||||||
|
}
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
+6
-2
@@ -21,9 +21,13 @@ static const ERR_STRING_DATA CRYPTO_str_functs[] = {
|
|||||||
"CRYPTO_free_ex_data"},
|
"CRYPTO_free_ex_data"},
|
||||||
{ERR_PACK(ERR_LIB_CRYPTO, CRYPTO_F_CRYPTO_GET_EX_NEW_INDEX, 0),
|
{ERR_PACK(ERR_LIB_CRYPTO, CRYPTO_F_CRYPTO_GET_EX_NEW_INDEX, 0),
|
||||||
"CRYPTO_get_ex_new_index"},
|
"CRYPTO_get_ex_new_index"},
|
||||||
|
{ERR_PACK(ERR_LIB_CRYPTO, CRYPTO_F_CRYPTO_GET_EX_NEW_INDEX_EX, 0),
|
||||||
|
"CRYPTO_get_ex_new_index_ex"},
|
||||||
{ERR_PACK(ERR_LIB_CRYPTO, CRYPTO_F_CRYPTO_MEMDUP, 0), "CRYPTO_memdup"},
|
{ERR_PACK(ERR_LIB_CRYPTO, CRYPTO_F_CRYPTO_MEMDUP, 0), "CRYPTO_memdup"},
|
||||||
{ERR_PACK(ERR_LIB_CRYPTO, CRYPTO_F_CRYPTO_NEW_EX_DATA, 0),
|
{ERR_PACK(ERR_LIB_CRYPTO, CRYPTO_F_CRYPTO_NEW_EX_DATA, 0),
|
||||||
"CRYPTO_new_ex_data"},
|
"CRYPTO_new_ex_data"},
|
||||||
|
{ERR_PACK(ERR_LIB_CRYPTO, CRYPTO_F_CRYPTO_NEW_EX_DATA_EX, 0),
|
||||||
|
"crypto_new_ex_data_ex"},
|
||||||
{ERR_PACK(ERR_LIB_CRYPTO, CRYPTO_F_CRYPTO_OCB128_COPY_CTX, 0),
|
{ERR_PACK(ERR_LIB_CRYPTO, CRYPTO_F_CRYPTO_OCB128_COPY_CTX, 0),
|
||||||
"CRYPTO_ocb128_copy_ctx"},
|
"CRYPTO_ocb128_copy_ctx"},
|
||||||
{ERR_PACK(ERR_LIB_CRYPTO, CRYPTO_F_CRYPTO_OCB128_INIT, 0),
|
{ERR_PACK(ERR_LIB_CRYPTO, CRYPTO_F_CRYPTO_OCB128_INIT, 0),
|
||||||
@@ -46,10 +50,10 @@ static const ERR_STRING_DATA CRYPTO_str_functs[] = {
|
|||||||
{ERR_PACK(ERR_LIB_CRYPTO, CRYPTO_F_OPENSSL_SK_DEEP_COPY, 0),
|
{ERR_PACK(ERR_LIB_CRYPTO, CRYPTO_F_OPENSSL_SK_DEEP_COPY, 0),
|
||||||
"OPENSSL_sk_deep_copy"},
|
"OPENSSL_sk_deep_copy"},
|
||||||
{ERR_PACK(ERR_LIB_CRYPTO, CRYPTO_F_OPENSSL_SK_DUP, 0), "OPENSSL_sk_dup"},
|
{ERR_PACK(ERR_LIB_CRYPTO, CRYPTO_F_OPENSSL_SK_DUP, 0), "OPENSSL_sk_dup"},
|
||||||
{ERR_PACK(ERR_LIB_CRYPTO, CRYPTO_F_OSSL_PROVIDER_ADD_BUILTIN, 0),
|
|
||||||
"OSSL_PROVIDER_add_builtin"},
|
|
||||||
{ERR_PACK(ERR_LIB_CRYPTO, CRYPTO_F_OSSL_PROVIDER_ACTIVATE, 0),
|
{ERR_PACK(ERR_LIB_CRYPTO, CRYPTO_F_OSSL_PROVIDER_ACTIVATE, 0),
|
||||||
"ossl_provider_activate"},
|
"ossl_provider_activate"},
|
||||||
|
{ERR_PACK(ERR_LIB_CRYPTO, CRYPTO_F_OSSL_PROVIDER_ADD_BUILTIN, 0),
|
||||||
|
"OSSL_PROVIDER_add_builtin"},
|
||||||
{ERR_PACK(ERR_LIB_CRYPTO, CRYPTO_F_OSSL_PROVIDER_ADD_PARAMETER, 0),
|
{ERR_PACK(ERR_LIB_CRYPTO, CRYPTO_F_OSSL_PROVIDER_ADD_PARAMETER, 0),
|
||||||
"ossl_provider_add_parameter"},
|
"ossl_provider_add_parameter"},
|
||||||
{ERR_PACK(ERR_LIB_CRYPTO, CRYPTO_F_OSSL_PROVIDER_NEW, 0),
|
{ERR_PACK(ERR_LIB_CRYPTO, CRYPTO_F_OSSL_PROVIDER_NEW, 0),
|
||||||
|
|||||||
@@ -54,7 +54,7 @@ static int pkey_dh_init(EVP_PKEY_CTX *ctx)
|
|||||||
DHerr(DH_F_PKEY_DH_INIT, ERR_R_MALLOC_FAILURE);
|
DHerr(DH_F_PKEY_DH_INIT, ERR_R_MALLOC_FAILURE);
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
dctx->prime_len = 1024;
|
dctx->prime_len = 2048;
|
||||||
dctx->subprime_len = -1;
|
dctx->subprime_len = -1;
|
||||||
dctx->generator = 2;
|
dctx->generator = 2;
|
||||||
dctx->kdf_type = EVP_PKEY_DH_KDF_NONE;
|
dctx->kdf_type = EVP_PKEY_DH_KDF_NONE;
|
||||||
|
|||||||
@@ -190,6 +190,12 @@ static int dsa_sign_setup(DSA *dsa, BN_CTX *ctx_in,
|
|||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/* Reject obviously invalid parameters */
|
||||||
|
if (BN_is_zero(dsa->p) || BN_is_zero(dsa->q) || BN_is_zero(dsa->g)) {
|
||||||
|
DSAerr(DSA_F_DSA_SIGN_SETUP, DSA_R_INVALID_PARAMETERS);
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
k = BN_new();
|
k = BN_new();
|
||||||
l = BN_new();
|
l = BN_new();
|
||||||
if (k == NULL || l == NULL)
|
if (k == NULL || l == NULL)
|
||||||
|
|||||||
@@ -20,8 +20,8 @@
|
|||||||
|
|
||||||
typedef struct {
|
typedef struct {
|
||||||
/* Parameter gen parameters */
|
/* Parameter gen parameters */
|
||||||
int nbits; /* size of p in bits (default: 1024) */
|
int nbits; /* size of p in bits (default: 2048) */
|
||||||
int qbits; /* size of q in bits (default: 160) */
|
int qbits; /* size of q in bits (default: 224) */
|
||||||
const EVP_MD *pmd; /* MD for parameter generation */
|
const EVP_MD *pmd; /* MD for parameter generation */
|
||||||
/* Keygen callback info */
|
/* Keygen callback info */
|
||||||
int gentmp[2];
|
int gentmp[2];
|
||||||
@@ -35,8 +35,8 @@ static int pkey_dsa_init(EVP_PKEY_CTX *ctx)
|
|||||||
|
|
||||||
if (dctx == NULL)
|
if (dctx == NULL)
|
||||||
return 0;
|
return 0;
|
||||||
dctx->nbits = 1024;
|
dctx->nbits = 2048;
|
||||||
dctx->qbits = 160;
|
dctx->qbits = 224;
|
||||||
dctx->pmd = NULL;
|
dctx->pmd = NULL;
|
||||||
dctx->md = NULL;
|
dctx->md = NULL;
|
||||||
|
|
||||||
@@ -138,7 +138,11 @@ static int pkey_dsa_ctrl(EVP_PKEY_CTX *ctx, int type, int p1, void *p2)
|
|||||||
EVP_MD_type((const EVP_MD *)p2) != NID_sha224 &&
|
EVP_MD_type((const EVP_MD *)p2) != NID_sha224 &&
|
||||||
EVP_MD_type((const EVP_MD *)p2) != NID_sha256 &&
|
EVP_MD_type((const EVP_MD *)p2) != NID_sha256 &&
|
||||||
EVP_MD_type((const EVP_MD *)p2) != NID_sha384 &&
|
EVP_MD_type((const EVP_MD *)p2) != NID_sha384 &&
|
||||||
EVP_MD_type((const EVP_MD *)p2) != NID_sha512) {
|
EVP_MD_type((const EVP_MD *)p2) != NID_sha512 &&
|
||||||
|
EVP_MD_type((const EVP_MD *)p2) != NID_sha3_224 &&
|
||||||
|
EVP_MD_type((const EVP_MD *)p2) != NID_sha3_256 &&
|
||||||
|
EVP_MD_type((const EVP_MD *)p2) != NID_sha3_384 &&
|
||||||
|
EVP_MD_type((const EVP_MD *)p2) != NID_sha3_512) {
|
||||||
DSAerr(DSA_F_PKEY_DSA_CTRL, DSA_R_INVALID_DIGEST_TYPE);
|
DSAerr(DSA_F_PKEY_DSA_CTRL, DSA_R_INVALID_DIGEST_TYPE);
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -323,7 +323,11 @@ static int pkey_ec_ctrl(EVP_PKEY_CTX *ctx, int type, int p1, void *p2)
|
|||||||
EVP_MD_type((const EVP_MD *)p2) != NID_sha224 &&
|
EVP_MD_type((const EVP_MD *)p2) != NID_sha224 &&
|
||||||
EVP_MD_type((const EVP_MD *)p2) != NID_sha256 &&
|
EVP_MD_type((const EVP_MD *)p2) != NID_sha256 &&
|
||||||
EVP_MD_type((const EVP_MD *)p2) != NID_sha384 &&
|
EVP_MD_type((const EVP_MD *)p2) != NID_sha384 &&
|
||||||
EVP_MD_type((const EVP_MD *)p2) != NID_sha512) {
|
EVP_MD_type((const EVP_MD *)p2) != NID_sha512 &&
|
||||||
|
EVP_MD_type((const EVP_MD *)p2) != NID_sha3_224 &&
|
||||||
|
EVP_MD_type((const EVP_MD *)p2) != NID_sha3_256 &&
|
||||||
|
EVP_MD_type((const EVP_MD *)p2) != NID_sha3_384 &&
|
||||||
|
EVP_MD_type((const EVP_MD *)p2) != NID_sha3_512) {
|
||||||
ECerr(EC_F_PKEY_EC_CTRL, EC_R_INVALID_DIGEST_TYPE);
|
ECerr(EC_F_PKEY_EC_CTRL, EC_R_INVALID_DIGEST_TYPE);
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|||||||
+15
-49
@@ -1,5 +1,5 @@
|
|||||||
/*
|
/*
|
||||||
* Copyright 2015-2018 The OpenSSL Project Authors. All Rights Reserved.
|
* Copyright 2015-2019 The OpenSSL Project Authors. All Rights Reserved.
|
||||||
*
|
*
|
||||||
* Licensed under the Apache License 2.0 (the "License"). You may not use
|
* Licensed under the Apache License 2.0 (the "License"). You may not use
|
||||||
* this file except in compliance with the License. You can obtain a copy
|
* this file except in compliance with the License. You can obtain a copy
|
||||||
@@ -10,62 +10,28 @@
|
|||||||
#include <string.h>
|
#include <string.h>
|
||||||
#include <openssl/ec.h>
|
#include <openssl/ec.h>
|
||||||
#include <openssl/evp.h>
|
#include <openssl/evp.h>
|
||||||
|
#include <openssl/kdf.h>
|
||||||
#include "ec_lcl.h"
|
#include "ec_lcl.h"
|
||||||
|
|
||||||
/* Key derivation function from X9.63/SECG */
|
/* Key derivation function from X9.63/SECG */
|
||||||
/* Way more than we will ever need */
|
|
||||||
#define ECDH_KDF_MAX (1 << 30)
|
|
||||||
|
|
||||||
int ecdh_KDF_X9_63(unsigned char *out, size_t outlen,
|
int ecdh_KDF_X9_63(unsigned char *out, size_t outlen,
|
||||||
const unsigned char *Z, size_t Zlen,
|
const unsigned char *Z, size_t Zlen,
|
||||||
const unsigned char *sinfo, size_t sinfolen,
|
const unsigned char *sinfo, size_t sinfolen,
|
||||||
const EVP_MD *md)
|
const EVP_MD *md)
|
||||||
{
|
{
|
||||||
EVP_MD_CTX *mctx = NULL;
|
int ret;
|
||||||
int rv = 0;
|
EVP_KDF_CTX *kctx = NULL;
|
||||||
unsigned int i;
|
|
||||||
size_t mdlen;
|
kctx = EVP_KDF_CTX_new(EVP_get_kdfbyname(SN_x963kdf));
|
||||||
unsigned char ctr[4];
|
ret =
|
||||||
if (sinfolen > ECDH_KDF_MAX || outlen > ECDH_KDF_MAX
|
kctx != NULL
|
||||||
|| Zlen > ECDH_KDF_MAX)
|
&& EVP_KDF_ctrl(kctx, EVP_KDF_CTRL_SET_MD, md) > 0
|
||||||
return 0;
|
&& EVP_KDF_ctrl(kctx, EVP_KDF_CTRL_SET_KEY, Z, Zlen) > 0
|
||||||
mctx = EVP_MD_CTX_new();
|
&& EVP_KDF_ctrl(kctx, EVP_KDF_CTRL_SET_SHARED_INFO, sinfo, sinfolen) > 0
|
||||||
if (mctx == NULL)
|
&& EVP_KDF_derive(kctx, out, outlen) > 0;
|
||||||
return 0;
|
|
||||||
mdlen = EVP_MD_size(md);
|
EVP_KDF_CTX_free(kctx);
|
||||||
for (i = 1;; i++) {
|
return ret;
|
||||||
unsigned char mtmp[EVP_MAX_MD_SIZE];
|
|
||||||
if (!EVP_DigestInit_ex(mctx, md, NULL))
|
|
||||||
goto err;
|
|
||||||
ctr[3] = i & 0xFF;
|
|
||||||
ctr[2] = (i >> 8) & 0xFF;
|
|
||||||
ctr[1] = (i >> 16) & 0xFF;
|
|
||||||
ctr[0] = (i >> 24) & 0xFF;
|
|
||||||
if (!EVP_DigestUpdate(mctx, Z, Zlen))
|
|
||||||
goto err;
|
|
||||||
if (!EVP_DigestUpdate(mctx, ctr, sizeof(ctr)))
|
|
||||||
goto err;
|
|
||||||
if (!EVP_DigestUpdate(mctx, sinfo, sinfolen))
|
|
||||||
goto err;
|
|
||||||
if (outlen >= mdlen) {
|
|
||||||
if (!EVP_DigestFinal(mctx, out, NULL))
|
|
||||||
goto err;
|
|
||||||
outlen -= mdlen;
|
|
||||||
if (outlen == 0)
|
|
||||||
break;
|
|
||||||
out += mdlen;
|
|
||||||
} else {
|
|
||||||
if (!EVP_DigestFinal(mctx, mtmp, NULL))
|
|
||||||
goto err;
|
|
||||||
memcpy(out, mtmp, outlen);
|
|
||||||
OPENSSL_cleanse(mtmp, mdlen);
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
rv = 1;
|
|
||||||
err:
|
|
||||||
EVP_MD_CTX_free(mctx);
|
|
||||||
return rv;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/*-
|
/*-
|
||||||
|
|||||||
@@ -189,12 +189,15 @@ typedef struct {
|
|||||||
static int test_rc4_init_key(EVP_CIPHER_CTX *ctx, const unsigned char *key,
|
static int test_rc4_init_key(EVP_CIPHER_CTX *ctx, const unsigned char *key,
|
||||||
const unsigned char *iv, int enc)
|
const unsigned char *iv, int enc)
|
||||||
{
|
{
|
||||||
|
const int n = EVP_CIPHER_CTX_key_length(ctx);
|
||||||
|
|
||||||
# ifdef TEST_ENG_OPENSSL_RC4_P_INIT
|
# ifdef TEST_ENG_OPENSSL_RC4_P_INIT
|
||||||
fprintf(stderr, "(TEST_ENG_OPENSSL_RC4) test_init_key() called\n");
|
fprintf(stderr, "(TEST_ENG_OPENSSL_RC4) test_init_key() called\n");
|
||||||
# endif
|
# endif
|
||||||
memcpy(&test(ctx)->key[0], key, EVP_CIPHER_CTX_key_length(ctx));
|
if (n <= 0)
|
||||||
RC4_set_key(&test(ctx)->ks, EVP_CIPHER_CTX_key_length(ctx),
|
return n;
|
||||||
test(ctx)->key);
|
memcpy(&test(ctx)->key[0], key, n);
|
||||||
|
RC4_set_key(&test(ctx)->ks, n, test(ctx)->key);
|
||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -92,7 +92,7 @@ int err_load_crypto_strings_int(void)
|
|||||||
# ifndef OPENSSL_NO_CMS
|
# ifndef OPENSSL_NO_CMS
|
||||||
ERR_load_CMS_strings() == 0 ||
|
ERR_load_CMS_strings() == 0 ||
|
||||||
# endif
|
# endif
|
||||||
# ifndef OPENSSL_NO_CMP
|
# ifndef OPENSSL_NO_CRMF
|
||||||
ERR_load_CRMF_strings() == 0 ||
|
ERR_load_CRMF_strings() == 0 ||
|
||||||
# endif
|
# endif
|
||||||
# ifndef OPENSSL_NO_CT
|
# ifndef OPENSSL_NO_CT
|
||||||
|
|||||||
@@ -374,8 +374,10 @@ CRYPTO_F_CMAC_CTX_NEW:120:CMAC_CTX_new
|
|||||||
CRYPTO_F_CRYPTO_DUP_EX_DATA:110:CRYPTO_dup_ex_data
|
CRYPTO_F_CRYPTO_DUP_EX_DATA:110:CRYPTO_dup_ex_data
|
||||||
CRYPTO_F_CRYPTO_FREE_EX_DATA:111:CRYPTO_free_ex_data
|
CRYPTO_F_CRYPTO_FREE_EX_DATA:111:CRYPTO_free_ex_data
|
||||||
CRYPTO_F_CRYPTO_GET_EX_NEW_INDEX:100:CRYPTO_get_ex_new_index
|
CRYPTO_F_CRYPTO_GET_EX_NEW_INDEX:100:CRYPTO_get_ex_new_index
|
||||||
|
CRYPTO_F_CRYPTO_GET_EX_NEW_INDEX_EX:141:crypto_get_ex_new_index_ex
|
||||||
CRYPTO_F_CRYPTO_MEMDUP:115:CRYPTO_memdup
|
CRYPTO_F_CRYPTO_MEMDUP:115:CRYPTO_memdup
|
||||||
CRYPTO_F_CRYPTO_NEW_EX_DATA:112:CRYPTO_new_ex_data
|
CRYPTO_F_CRYPTO_NEW_EX_DATA:112:CRYPTO_new_ex_data
|
||||||
|
CRYPTO_F_CRYPTO_NEW_EX_DATA_EX:142:crypto_new_ex_data_ex
|
||||||
CRYPTO_F_CRYPTO_OCB128_COPY_CTX:121:CRYPTO_ocb128_copy_ctx
|
CRYPTO_F_CRYPTO_OCB128_COPY_CTX:121:CRYPTO_ocb128_copy_ctx
|
||||||
CRYPTO_F_CRYPTO_OCB128_INIT:122:CRYPTO_ocb128_init
|
CRYPTO_F_CRYPTO_OCB128_INIT:122:CRYPTO_ocb128_init
|
||||||
CRYPTO_F_CRYPTO_SET_EX_DATA:102:CRYPTO_set_ex_data
|
CRYPTO_F_CRYPTO_SET_EX_DATA:102:CRYPTO_set_ex_data
|
||||||
@@ -800,6 +802,7 @@ EVP_F_EVP_ENCRYPTFINAL_EX:127:EVP_EncryptFinal_ex
|
|||||||
EVP_F_EVP_ENCRYPTUPDATE:167:EVP_EncryptUpdate
|
EVP_F_EVP_ENCRYPTUPDATE:167:EVP_EncryptUpdate
|
||||||
EVP_F_EVP_KDF_CTRL:224:EVP_KDF_ctrl
|
EVP_F_EVP_KDF_CTRL:224:EVP_KDF_ctrl
|
||||||
EVP_F_EVP_KDF_CTRL_STR:225:EVP_KDF_ctrl_str
|
EVP_F_EVP_KDF_CTRL_STR:225:EVP_KDF_ctrl_str
|
||||||
|
EVP_F_EVP_KDF_CTX_NEW:240:EVP_KDF_CTX_new
|
||||||
EVP_F_EVP_KDF_CTX_NEW_ID:226:EVP_KDF_CTX_new_id
|
EVP_F_EVP_KDF_CTX_NEW_ID:226:EVP_KDF_CTX_new_id
|
||||||
EVP_F_EVP_MAC_CTRL:209:EVP_MAC_ctrl
|
EVP_F_EVP_MAC_CTRL:209:EVP_MAC_ctrl
|
||||||
EVP_F_EVP_MAC_CTRL_STR:210:EVP_MAC_ctrl_str
|
EVP_F_EVP_MAC_CTRL_STR:210:EVP_MAC_ctrl_str
|
||||||
@@ -922,6 +925,7 @@ KDF_F_SSKDF_MAC2CTRL:136:sskdf_mac2ctrl
|
|||||||
KDF_F_SSKDF_NEW:137:sskdf_new
|
KDF_F_SSKDF_NEW:137:sskdf_new
|
||||||
KDF_F_SSKDF_SIZE:138:sskdf_size
|
KDF_F_SSKDF_SIZE:138:sskdf_size
|
||||||
KDF_F_TLS1_PRF_ALG:111:tls1_prf_alg
|
KDF_F_TLS1_PRF_ALG:111:tls1_prf_alg
|
||||||
|
KDF_F_X963KDF_DERIVE:139:x963kdf_derive
|
||||||
OBJ_F_OBJ_ADD_OBJECT:105:OBJ_add_object
|
OBJ_F_OBJ_ADD_OBJECT:105:OBJ_add_object
|
||||||
OBJ_F_OBJ_ADD_SIGID:107:OBJ_add_sigid
|
OBJ_F_OBJ_ADD_SIGID:107:OBJ_add_sigid
|
||||||
OBJ_F_OBJ_CREATE:100:OBJ_create
|
OBJ_F_OBJ_CREATE:100:OBJ_create
|
||||||
@@ -1434,6 +1438,7 @@ SSL_F_SSL_RENEGOTIATE:516:SSL_renegotiate
|
|||||||
SSL_F_SSL_RENEGOTIATE_ABBREVIATED:546:SSL_renegotiate_abbreviated
|
SSL_F_SSL_RENEGOTIATE_ABBREVIATED:546:SSL_renegotiate_abbreviated
|
||||||
SSL_F_SSL_SCAN_CLIENTHELLO_TLSEXT:320:*
|
SSL_F_SSL_SCAN_CLIENTHELLO_TLSEXT:320:*
|
||||||
SSL_F_SSL_SCAN_SERVERHELLO_TLSEXT:321:*
|
SSL_F_SSL_SCAN_SERVERHELLO_TLSEXT:321:*
|
||||||
|
SSL_F_SSL_SENDFILE:639:SSL_sendfile
|
||||||
SSL_F_SSL_SESSION_DUP:348:ssl_session_dup
|
SSL_F_SSL_SESSION_DUP:348:ssl_session_dup
|
||||||
SSL_F_SSL_SESSION_NEW:189:SSL_SESSION_new
|
SSL_F_SSL_SESSION_NEW:189:SSL_SESSION_new
|
||||||
SSL_F_SSL_SESSION_PRINT_FP:190:SSL_SESSION_print_fp
|
SSL_F_SSL_SESSION_PRINT_FP:190:SSL_SESSION_print_fp
|
||||||
@@ -2396,6 +2401,7 @@ EVP_R_INPUT_NOT_INITIALIZED:111:input not initialized
|
|||||||
EVP_R_INVALID_CUSTOM_LENGTH:185:invalid custom length
|
EVP_R_INVALID_CUSTOM_LENGTH:185:invalid custom length
|
||||||
EVP_R_INVALID_DIGEST:152:invalid digest
|
EVP_R_INVALID_DIGEST:152:invalid digest
|
||||||
EVP_R_INVALID_FIPS_MODE:168:invalid fips mode
|
EVP_R_INVALID_FIPS_MODE:168:invalid fips mode
|
||||||
|
EVP_R_INVALID_IV_LENGTH:194:invalid iv length
|
||||||
EVP_R_INVALID_KEY:163:invalid key
|
EVP_R_INVALID_KEY:163:invalid key
|
||||||
EVP_R_INVALID_KEY_LENGTH:130:invalid key length
|
EVP_R_INVALID_KEY_LENGTH:130:invalid key length
|
||||||
EVP_R_INVALID_OPERATION:148:invalid operation
|
EVP_R_INVALID_OPERATION:148:invalid operation
|
||||||
@@ -2459,6 +2465,7 @@ KDF_R_MISSING_SEED:106:missing seed
|
|||||||
KDF_R_MISSING_SESSION_ID:113:missing session id
|
KDF_R_MISSING_SESSION_ID:113:missing session id
|
||||||
KDF_R_MISSING_TYPE:114:missing type
|
KDF_R_MISSING_TYPE:114:missing type
|
||||||
KDF_R_MISSING_XCGHASH:115:missing xcghash
|
KDF_R_MISSING_XCGHASH:115:missing xcghash
|
||||||
|
KDF_R_NOT_SUPPORTED:118:not supported
|
||||||
KDF_R_UNKNOWN_PARAMETER_TYPE:103:unknown parameter type
|
KDF_R_UNKNOWN_PARAMETER_TYPE:103:unknown parameter type
|
||||||
KDF_R_UNSUPPORTED_MAC_TYPE:117:unsupported mac type
|
KDF_R_UNSUPPORTED_MAC_TYPE:117:unsupported mac type
|
||||||
KDF_R_VALUE_ERROR:108:value error
|
KDF_R_VALUE_ERROR:108:value error
|
||||||
|
|||||||
@@ -10,7 +10,7 @@ SOURCE[../../libcrypto]=\
|
|||||||
bio_md.c bio_b64.c bio_enc.c evp_err.c e_null.c \
|
bio_md.c bio_b64.c bio_enc.c evp_err.c e_null.c \
|
||||||
c_allc.c c_alld.c evp_lib.c bio_ok.c \
|
c_allc.c c_alld.c evp_lib.c bio_ok.c \
|
||||||
evp_pkey.c kdf_lib.c evp_pbe.c p5_crpt.c p5_crpt2.c pbe_scrypt.c \
|
evp_pkey.c kdf_lib.c evp_pbe.c p5_crpt.c p5_crpt2.c pbe_scrypt.c \
|
||||||
pkey_kdf.c \
|
pkey_kdf.c c_allkdf.c \
|
||||||
e_old.c pmeth_lib.c pmeth_fn.c pmeth_gn.c m_sigver.c \
|
e_old.c pmeth_lib.c pmeth_fn.c pmeth_gn.c m_sigver.c \
|
||||||
e_aes_cbc_hmac_sha1.c e_aes_cbc_hmac_sha256.c e_rc4_hmac_md5.c \
|
e_aes_cbc_hmac_sha1.c e_aes_cbc_hmac_sha256.c e_rc4_hmac_md5.c \
|
||||||
e_chacha20_poly1305.c cmeth_lib.c \
|
e_chacha20_poly1305.c cmeth_lib.c \
|
||||||
|
|||||||
@@ -0,0 +1,24 @@
|
|||||||
|
/*
|
||||||
|
* Copyright 2019 The OpenSSL Project Authors. All Rights Reserved.
|
||||||
|
*
|
||||||
|
* Licensed under the Apache License 2.0 (the "License"). You may not use
|
||||||
|
* this file except in compliance with the License. You can obtain a copy
|
||||||
|
* in the file LICENSE in the source distribution or at
|
||||||
|
* https://www.openssl.org/source/license.html
|
||||||
|
*/
|
||||||
|
|
||||||
|
#include <openssl/evp.h>
|
||||||
|
#include "internal/evp_int.h"
|
||||||
|
|
||||||
|
void openssl_add_all_kdfs_int(void)
|
||||||
|
{
|
||||||
|
EVP_add_kdf(&pbkdf2_kdf_meth);
|
||||||
|
#ifndef OPENSSL_NO_SCRYPT
|
||||||
|
EVP_add_kdf(&scrypt_kdf_meth);
|
||||||
|
#endif
|
||||||
|
EVP_add_kdf(&tls1_prf_kdf_meth);
|
||||||
|
EVP_add_kdf(&hkdf_kdf_meth);
|
||||||
|
EVP_add_kdf(&sshkdf_kdf_meth);
|
||||||
|
EVP_add_kdf(&ss_kdf_meth);
|
||||||
|
EVP_add_kdf(&x963_kdf_meth);
|
||||||
|
}
|
||||||
+23
-14
@@ -172,7 +172,7 @@ int EVP_DigestInit_ex(EVP_MD_CTX *ctx, const EVP_MD *type, ENGINE *impl)
|
|||||||
|
|
||||||
ctx->digest = type;
|
ctx->digest = type;
|
||||||
if (ctx->provctx == NULL) {
|
if (ctx->provctx == NULL) {
|
||||||
ctx->provctx = ctx->digest->newctx();
|
ctx->provctx = ctx->digest->newctx(ossl_provider_ctx(type->prov));
|
||||||
if (ctx->provctx == NULL) {
|
if (ctx->provctx == NULL) {
|
||||||
EVPerr(EVP_F_EVP_DIGESTINIT_EX, EVP_R_INITIALIZATION_ERROR);
|
EVPerr(EVP_F_EVP_DIGESTINIT_EX, EVP_R_INITIALIZATION_ERROR);
|
||||||
return 0;
|
return 0;
|
||||||
@@ -494,13 +494,14 @@ int EVP_MD_CTX_ctrl(EVP_MD_CTX *ctx, int cmd, int p1, void *p2)
|
|||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
static void *evp_md_from_dispatch(int mdtype, const OSSL_DISPATCH *fns,
|
static void *evp_md_from_dispatch(const OSSL_DISPATCH *fns,
|
||||||
OSSL_PROVIDER *prov)
|
OSSL_PROVIDER *prov)
|
||||||
{
|
{
|
||||||
EVP_MD *md = NULL;
|
EVP_MD *md = NULL;
|
||||||
int fncnt = 0;
|
int fncnt = 0;
|
||||||
|
|
||||||
if ((md = EVP_MD_meth_new(mdtype, NID_undef)) == NULL)
|
/* EVP_MD_fetch() will set the legacy NID if available */
|
||||||
|
if ((md = EVP_MD_meth_new(NID_undef, NID_undef)) == NULL)
|
||||||
return NULL;
|
return NULL;
|
||||||
|
|
||||||
for (; fns->function_id != 0; fns++) {
|
for (; fns->function_id != 0; fns++) {
|
||||||
@@ -587,17 +588,25 @@ static void evp_md_free(void *md)
|
|||||||
EVP_MD_meth_free(md);
|
EVP_MD_meth_free(md);
|
||||||
}
|
}
|
||||||
|
|
||||||
static int evp_md_nid(void *vmd)
|
|
||||||
{
|
|
||||||
EVP_MD *md = vmd;
|
|
||||||
|
|
||||||
return md->type;
|
|
||||||
}
|
|
||||||
|
|
||||||
EVP_MD *EVP_MD_fetch(OPENSSL_CTX *ctx, const char *algorithm,
|
EVP_MD *EVP_MD_fetch(OPENSSL_CTX *ctx, const char *algorithm,
|
||||||
const char *properties)
|
const char *properties)
|
||||||
{
|
{
|
||||||
return evp_generic_fetch(ctx, OSSL_OP_DIGEST, algorithm, properties,
|
EVP_MD *md =
|
||||||
evp_md_from_dispatch, evp_md_upref,
|
evp_generic_fetch(ctx, OSSL_OP_DIGEST, algorithm, properties,
|
||||||
evp_md_free, evp_md_nid);
|
evp_md_from_dispatch, evp_md_upref,
|
||||||
|
evp_md_free);
|
||||||
|
|
||||||
|
#ifndef FIPS_MODE
|
||||||
|
/* TODO(3.x) get rid of the need for legacy NIDs */
|
||||||
|
if (md != NULL) {
|
||||||
|
/*
|
||||||
|
* FIPS module note: since internal fetches will be entirely
|
||||||
|
* provider based, we know that none of its code depends on legacy
|
||||||
|
* NIDs or any functionality that use them.
|
||||||
|
*/
|
||||||
|
md->type = OBJ_sn2nid(algorithm);
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
|
||||||
|
return md;
|
||||||
}
|
}
|
||||||
+22
-17
@@ -15,6 +15,7 @@
|
|||||||
#include <assert.h>
|
#include <assert.h>
|
||||||
#include <openssl/aes.h>
|
#include <openssl/aes.h>
|
||||||
#include "internal/evp_int.h"
|
#include "internal/evp_int.h"
|
||||||
|
#include "internal/cryptlib.h"
|
||||||
#include "modes_lcl.h"
|
#include "modes_lcl.h"
|
||||||
#include <openssl/rand.h>
|
#include <openssl/rand.h>
|
||||||
#include <openssl/cmac.h>
|
#include <openssl/cmac.h>
|
||||||
@@ -22,7 +23,7 @@
|
|||||||
|
|
||||||
typedef struct {
|
typedef struct {
|
||||||
union {
|
union {
|
||||||
double align;
|
OSSL_UNION_ALIGN;
|
||||||
AES_KEY ks;
|
AES_KEY ks;
|
||||||
} ks;
|
} ks;
|
||||||
block128_f block;
|
block128_f block;
|
||||||
@@ -34,7 +35,7 @@ typedef struct {
|
|||||||
|
|
||||||
typedef struct {
|
typedef struct {
|
||||||
union {
|
union {
|
||||||
double align;
|
OSSL_UNION_ALIGN;
|
||||||
AES_KEY ks;
|
AES_KEY ks;
|
||||||
} ks; /* AES key schedule to use */
|
} ks; /* AES key schedule to use */
|
||||||
int key_set; /* Set if key initialised */
|
int key_set; /* Set if key initialised */
|
||||||
@@ -52,7 +53,7 @@ typedef struct {
|
|||||||
|
|
||||||
typedef struct {
|
typedef struct {
|
||||||
union {
|
union {
|
||||||
double align;
|
OSSL_UNION_ALIGN;
|
||||||
AES_KEY ks;
|
AES_KEY ks;
|
||||||
} ks1, ks2; /* AES key schedules to use */
|
} ks1, ks2; /* AES key schedules to use */
|
||||||
XTS128_CONTEXT xts;
|
XTS128_CONTEXT xts;
|
||||||
@@ -64,7 +65,7 @@ typedef struct {
|
|||||||
|
|
||||||
typedef struct {
|
typedef struct {
|
||||||
union {
|
union {
|
||||||
double align;
|
OSSL_UNION_ALIGN;
|
||||||
AES_KEY ks;
|
AES_KEY ks;
|
||||||
} ks; /* AES key schedule to use */
|
} ks; /* AES key schedule to use */
|
||||||
int key_set; /* Set if key initialised */
|
int key_set; /* Set if key initialised */
|
||||||
@@ -80,11 +81,11 @@ typedef struct {
|
|||||||
#ifndef OPENSSL_NO_OCB
|
#ifndef OPENSSL_NO_OCB
|
||||||
typedef struct {
|
typedef struct {
|
||||||
union {
|
union {
|
||||||
double align;
|
OSSL_UNION_ALIGN;
|
||||||
AES_KEY ks;
|
AES_KEY ks;
|
||||||
} ksenc; /* AES key schedule to use for encryption */
|
} ksenc; /* AES key schedule to use for encryption */
|
||||||
union {
|
union {
|
||||||
double align;
|
OSSL_UNION_ALIGN;
|
||||||
AES_KEY ks;
|
AES_KEY ks;
|
||||||
} ksdec; /* AES key schedule to use for decryption */
|
} ksdec; /* AES key schedule to use for decryption */
|
||||||
int key_set; /* Set if key initialised */
|
int key_set; /* Set if key initialised */
|
||||||
@@ -1008,7 +1009,7 @@ const EVP_CIPHER *EVP_aes_##keylen##_##mode(void) \
|
|||||||
|
|
||||||
typedef struct {
|
typedef struct {
|
||||||
union {
|
union {
|
||||||
double align;
|
OSSL_UNION_ALIGN;
|
||||||
/*-
|
/*-
|
||||||
* KM-AES parameter block - begin
|
* KM-AES parameter block - begin
|
||||||
* (see z/Architecture Principles of Operation >= SA22-7832-06)
|
* (see z/Architecture Principles of Operation >= SA22-7832-06)
|
||||||
@@ -1023,7 +1024,7 @@ typedef struct {
|
|||||||
|
|
||||||
typedef struct {
|
typedef struct {
|
||||||
union {
|
union {
|
||||||
double align;
|
OSSL_UNION_ALIGN;
|
||||||
/*-
|
/*-
|
||||||
* KMO-AES parameter block - begin
|
* KMO-AES parameter block - begin
|
||||||
* (see z/Architecture Principles of Operation >= SA22-7832-08)
|
* (see z/Architecture Principles of Operation >= SA22-7832-08)
|
||||||
@@ -1041,7 +1042,7 @@ typedef struct {
|
|||||||
|
|
||||||
typedef struct {
|
typedef struct {
|
||||||
union {
|
union {
|
||||||
double align;
|
OSSL_UNION_ALIGN;
|
||||||
/*-
|
/*-
|
||||||
* KMF-AES parameter block - begin
|
* KMF-AES parameter block - begin
|
||||||
* (see z/Architecture Principles of Operation >= SA22-7832-08)
|
* (see z/Architecture Principles of Operation >= SA22-7832-08)
|
||||||
@@ -1059,7 +1060,7 @@ typedef struct {
|
|||||||
|
|
||||||
typedef struct {
|
typedef struct {
|
||||||
union {
|
union {
|
||||||
double align;
|
OSSL_UNION_ALIGN;
|
||||||
/*-
|
/*-
|
||||||
* KMA-GCM-AES parameter block - begin
|
* KMA-GCM-AES parameter block - begin
|
||||||
* (see z/Architecture Principles of Operation >= SA22-7832-11)
|
* (see z/Architecture Principles of Operation >= SA22-7832-11)
|
||||||
@@ -1108,7 +1109,7 @@ typedef struct {
|
|||||||
|
|
||||||
typedef struct {
|
typedef struct {
|
||||||
union {
|
union {
|
||||||
double align;
|
OSSL_UNION_ALIGN;
|
||||||
/*-
|
/*-
|
||||||
* Padding is chosen so that ccm.kmac_param.k overlaps with key.k and
|
* Padding is chosen so that ccm.kmac_param.k overlaps with key.k and
|
||||||
* ccm.fc with key.k.rounds. Remember that on s390x, an AES_KEY's
|
* ccm.fc with key.k.rounds. Remember that on s390x, an AES_KEY's
|
||||||
@@ -2263,9 +2264,6 @@ static int s390x_aes_ccm_cipher(EVP_CIPHER_CTX *ctx, unsigned char *out,
|
|||||||
if (!cctx->aes.ccm.iv_set)
|
if (!cctx->aes.ccm.iv_set)
|
||||||
return -1;
|
return -1;
|
||||||
|
|
||||||
if (!enc && !cctx->aes.ccm.tag_set)
|
|
||||||
return -1;
|
|
||||||
|
|
||||||
if (out == NULL) {
|
if (out == NULL) {
|
||||||
/* Update(): Pass message length. */
|
/* Update(): Pass message length. */
|
||||||
if (in == NULL) {
|
if (in == NULL) {
|
||||||
@@ -2284,6 +2282,10 @@ static int s390x_aes_ccm_cipher(EVP_CIPHER_CTX *ctx, unsigned char *out,
|
|||||||
return len;
|
return len;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/* The tag must be set before actually decrypting data */
|
||||||
|
if (!enc && !cctx->aes.ccm.tag_set)
|
||||||
|
return -1;
|
||||||
|
|
||||||
/* Update(): Process message. */
|
/* Update(): Process message. */
|
||||||
|
|
||||||
if (!cctx->aes.ccm.len_set) {
|
if (!cctx->aes.ccm.len_set) {
|
||||||
@@ -3791,8 +3793,6 @@ static int aes_ccm_cipher(EVP_CIPHER_CTX *ctx, unsigned char *out,
|
|||||||
if (!cctx->iv_set)
|
if (!cctx->iv_set)
|
||||||
return -1;
|
return -1;
|
||||||
|
|
||||||
if (!EVP_CIPHER_CTX_encrypting(ctx) && !cctx->tag_set)
|
|
||||||
return -1;
|
|
||||||
if (!out) {
|
if (!out) {
|
||||||
if (!in) {
|
if (!in) {
|
||||||
if (CRYPTO_ccm128_setiv(ccm, EVP_CIPHER_CTX_iv_noconst(ctx),
|
if (CRYPTO_ccm128_setiv(ccm, EVP_CIPHER_CTX_iv_noconst(ctx),
|
||||||
@@ -3807,6 +3807,11 @@ static int aes_ccm_cipher(EVP_CIPHER_CTX *ctx, unsigned char *out,
|
|||||||
CRYPTO_ccm128_aad(ccm, in, len);
|
CRYPTO_ccm128_aad(ccm, in, len);
|
||||||
return len;
|
return len;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/* The tag must be set before actually decrypting data */
|
||||||
|
if (!EVP_CIPHER_CTX_encrypting(ctx) && !cctx->tag_set)
|
||||||
|
return -1;
|
||||||
|
|
||||||
/* If not set length yet do it */
|
/* If not set length yet do it */
|
||||||
if (!cctx->len_set) {
|
if (!cctx->len_set) {
|
||||||
if (CRYPTO_ccm128_setiv(ccm, EVP_CIPHER_CTX_iv_noconst(ctx),
|
if (CRYPTO_ccm128_setiv(ccm, EVP_CIPHER_CTX_iv_noconst(ctx),
|
||||||
@@ -3853,7 +3858,7 @@ BLOCK_CIPHER_custom(NID_aes, 128, 1, 12, ccm, CCM,
|
|||||||
|
|
||||||
typedef struct {
|
typedef struct {
|
||||||
union {
|
union {
|
||||||
double align;
|
OSSL_UNION_ALIGN;
|
||||||
AES_KEY ks;
|
AES_KEY ks;
|
||||||
} ks;
|
} ks;
|
||||||
/* Indicates if IV has been set */
|
/* Indicates if IV has been set */
|
||||||
|
|||||||
+3
-3
@@ -1,5 +1,5 @@
|
|||||||
/*
|
/*
|
||||||
* Copyright 2017-2018 The OpenSSL Project Authors. All Rights Reserved.
|
* Copyright 2017-2019 The OpenSSL Project Authors. All Rights Reserved.
|
||||||
* Copyright (c) 2017, Oracle and/or its affiliates. All rights reserved.
|
* Copyright (c) 2017, Oracle and/or its affiliates. All rights reserved.
|
||||||
*
|
*
|
||||||
* Licensed under the Apache License 2.0 (the "License"). You may not use
|
* Licensed under the Apache License 2.0 (the "License"). You may not use
|
||||||
@@ -27,7 +27,7 @@ typedef struct {
|
|||||||
/* ARIA GCM context */
|
/* ARIA GCM context */
|
||||||
typedef struct {
|
typedef struct {
|
||||||
union {
|
union {
|
||||||
double align;
|
OSSL_UNION_ALIGN;
|
||||||
ARIA_KEY ks;
|
ARIA_KEY ks;
|
||||||
} ks; /* ARIA subkey to use */
|
} ks; /* ARIA subkey to use */
|
||||||
int key_set; /* Set if key initialised */
|
int key_set; /* Set if key initialised */
|
||||||
@@ -43,7 +43,7 @@ typedef struct {
|
|||||||
/* ARIA CCM context */
|
/* ARIA CCM context */
|
||||||
typedef struct {
|
typedef struct {
|
||||||
union {
|
union {
|
||||||
double align;
|
OSSL_UNION_ALIGN;
|
||||||
ARIA_KEY ks;
|
ARIA_KEY ks;
|
||||||
} ks; /* ARIA key schedule to use */
|
} ks; /* ARIA key schedule to use */
|
||||||
int key_set; /* Set if key initialised */
|
int key_set; /* Set if key initialised */
|
||||||
|
|||||||
@@ -1,5 +1,5 @@
|
|||||||
/*
|
/*
|
||||||
* Copyright 2015-2018 The OpenSSL Project Authors. All Rights Reserved.
|
* Copyright 2015-2019 The OpenSSL Project Authors. All Rights Reserved.
|
||||||
*
|
*
|
||||||
* Licensed under the Apache License 2.0 (the "License"). You may not use
|
* Licensed under the Apache License 2.0 (the "License"). You may not use
|
||||||
* this file except in compliance with the License. You can obtain a copy
|
* this file except in compliance with the License. You can obtain a copy
|
||||||
@@ -20,7 +20,7 @@
|
|||||||
|
|
||||||
typedef struct {
|
typedef struct {
|
||||||
union {
|
union {
|
||||||
double align; /* this ensures even sizeof(EVP_CHACHA_KEY)%8==0 */
|
OSSL_UNION_ALIGN; /* this ensures even sizeof(EVP_CHACHA_KEY)%8==0 */
|
||||||
unsigned int d[CHACHA_KEY_SIZE / 4];
|
unsigned int d[CHACHA_KEY_SIZE / 4];
|
||||||
} key;
|
} key;
|
||||||
unsigned int counter[CHACHA_CTR_SIZE / 4];
|
unsigned int counter[CHACHA_CTR_SIZE / 4];
|
||||||
|
|||||||
+2
-2
@@ -1,5 +1,5 @@
|
|||||||
/*
|
/*
|
||||||
* Copyright 1995-2018 The OpenSSL Project Authors. All Rights Reserved.
|
* Copyright 1995-2019 The OpenSSL Project Authors. All Rights Reserved.
|
||||||
*
|
*
|
||||||
* Licensed under the Apache License 2.0 (the "License"). You may not use
|
* Licensed under the Apache License 2.0 (the "License"). You may not use
|
||||||
* this file except in compliance with the License. You can obtain a copy
|
* this file except in compliance with the License. You can obtain a copy
|
||||||
@@ -18,7 +18,7 @@
|
|||||||
|
|
||||||
typedef struct {
|
typedef struct {
|
||||||
union {
|
union {
|
||||||
double align;
|
OSSL_UNION_ALIGN;
|
||||||
DES_key_schedule ks;
|
DES_key_schedule ks;
|
||||||
} ks;
|
} ks;
|
||||||
union {
|
union {
|
||||||
|
|||||||
+7
-5
@@ -1,5 +1,5 @@
|
|||||||
/*
|
/*
|
||||||
* Copyright 1995-2018 The OpenSSL Project Authors. All Rights Reserved.
|
* Copyright 1995-2019 The OpenSSL Project Authors. All Rights Reserved.
|
||||||
*
|
*
|
||||||
* Licensed under the Apache License 2.0 (the "License"). You may not use
|
* Licensed under the Apache License 2.0 (the "License"). You may not use
|
||||||
* this file except in compliance with the License. You can obtain a copy
|
* this file except in compliance with the License. You can obtain a copy
|
||||||
@@ -19,7 +19,7 @@
|
|||||||
|
|
||||||
typedef struct {
|
typedef struct {
|
||||||
union {
|
union {
|
||||||
double align;
|
OSSL_UNION_ALIGN;
|
||||||
DES_key_schedule ks[3];
|
DES_key_schedule ks[3];
|
||||||
} ks;
|
} ks;
|
||||||
union {
|
union {
|
||||||
@@ -280,15 +280,17 @@ static int des3_ctrl(EVP_CIPHER_CTX *ctx, int type, int arg, void *ptr)
|
|||||||
{
|
{
|
||||||
|
|
||||||
DES_cblock *deskey = ptr;
|
DES_cblock *deskey = ptr;
|
||||||
|
int kl;
|
||||||
|
|
||||||
switch (type) {
|
switch (type) {
|
||||||
case EVP_CTRL_RAND_KEY:
|
case EVP_CTRL_RAND_KEY:
|
||||||
if (RAND_priv_bytes(ptr, EVP_CIPHER_CTX_key_length(ctx)) <= 0)
|
kl = EVP_CIPHER_CTX_key_length(ctx);
|
||||||
|
if (kl < 0 || RAND_priv_bytes(ptr, kl) <= 0)
|
||||||
return 0;
|
return 0;
|
||||||
DES_set_odd_parity(deskey);
|
DES_set_odd_parity(deskey);
|
||||||
if (EVP_CIPHER_CTX_key_length(ctx) >= 16)
|
if (kl >= 16)
|
||||||
DES_set_odd_parity(deskey + 1);
|
DES_set_odd_parity(deskey + 1);
|
||||||
if (EVP_CIPHER_CTX_key_length(ctx) >= 24)
|
if (kl >= 24)
|
||||||
DES_set_odd_parity(deskey + 2);
|
DES_set_odd_parity(deskey + 2);
|
||||||
return 1;
|
return 1;
|
||||||
|
|
||||||
|
|||||||
+67
-34
@@ -206,7 +206,7 @@ int EVP_CipherInit_ex(EVP_CIPHER_CTX *ctx, const EVP_CIPHER *cipher,
|
|||||||
|
|
||||||
ctx->cipher = cipher;
|
ctx->cipher = cipher;
|
||||||
if (ctx->provctx == NULL) {
|
if (ctx->provctx == NULL) {
|
||||||
ctx->provctx = ctx->cipher->newctx();
|
ctx->provctx = ctx->cipher->newctx(ossl_provider_ctx(cipher->prov));
|
||||||
if (ctx->provctx == NULL) {
|
if (ctx->provctx == NULL) {
|
||||||
EVPerr(EVP_F_EVP_CIPHERINIT_EX, EVP_R_INITIALIZATION_ERROR);
|
EVPerr(EVP_F_EVP_CIPHERINIT_EX, EVP_R_INITIALIZATION_ERROR);
|
||||||
return 0;
|
return 0;
|
||||||
@@ -338,6 +338,9 @@ int EVP_CipherInit_ex(EVP_CIPHER_CTX *ctx, const EVP_CIPHER *cipher,
|
|||||||
#ifndef OPENSSL_NO_ENGINE
|
#ifndef OPENSSL_NO_ENGINE
|
||||||
skip_to_init:
|
skip_to_init:
|
||||||
#endif
|
#endif
|
||||||
|
if (ctx->cipher == NULL)
|
||||||
|
return 0;
|
||||||
|
|
||||||
/* we assume block size is a power of 2 in *cryptUpdate */
|
/* we assume block size is a power of 2 in *cryptUpdate */
|
||||||
OPENSSL_assert(ctx->cipher->block_size == 1
|
OPENSSL_assert(ctx->cipher->block_size == 1
|
||||||
|| ctx->cipher->block_size == 8
|
|| ctx->cipher->block_size == 8
|
||||||
@@ -492,11 +495,6 @@ static int evp_EncryptDecryptUpdate(EVP_CIPHER_CTX *ctx,
|
|||||||
|
|
||||||
bl = ctx->cipher->block_size;
|
bl = ctx->cipher->block_size;
|
||||||
|
|
||||||
if (inl <= 0) {
|
|
||||||
*outl = 0;
|
|
||||||
return inl == 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (ctx->cipher->flags & EVP_CIPH_FLAG_CUSTOM_CIPHER) {
|
if (ctx->cipher->flags & EVP_CIPH_FLAG_CUSTOM_CIPHER) {
|
||||||
/* If block size > 1 then the cipher will have to do this check */
|
/* If block size > 1 then the cipher will have to do this check */
|
||||||
if (bl == 1 && is_partially_overlapping(out, in, cmpl)) {
|
if (bl == 1 && is_partially_overlapping(out, in, cmpl)) {
|
||||||
@@ -512,6 +510,10 @@ static int evp_EncryptDecryptUpdate(EVP_CIPHER_CTX *ctx,
|
|||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (inl <= 0) {
|
||||||
|
*outl = 0;
|
||||||
|
return inl == 0;
|
||||||
|
}
|
||||||
if (is_partially_overlapping(out + ctx->buf_len, in, cmpl)) {
|
if (is_partially_overlapping(out + ctx->buf_len, in, cmpl)) {
|
||||||
EVPerr(EVP_F_EVP_ENCRYPTDECRYPTUPDATE, EVP_R_PARTIALLY_OVERLAPPING);
|
EVPerr(EVP_F_EVP_ENCRYPTDECRYPTUPDATE, EVP_R_PARTIALLY_OVERLAPPING);
|
||||||
return 0;
|
return 0;
|
||||||
@@ -587,11 +589,14 @@ int EVP_EncryptUpdate(EVP_CIPHER_CTX *ctx, unsigned char *out, int *outl,
|
|||||||
inl + (blocksize == 1 ? 0 : blocksize), in,
|
inl + (blocksize == 1 ? 0 : blocksize), in,
|
||||||
(size_t)inl);
|
(size_t)inl);
|
||||||
|
|
||||||
if (soutl > INT_MAX) {
|
if (ret) {
|
||||||
EVPerr(EVP_F_EVP_ENCRYPTUPDATE, EVP_R_UPDATE_ERROR);
|
if (soutl > INT_MAX) {
|
||||||
return 0;
|
EVPerr(EVP_F_EVP_ENCRYPTUPDATE, EVP_R_UPDATE_ERROR);
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
*outl = soutl;
|
||||||
}
|
}
|
||||||
*outl = soutl;
|
|
||||||
return ret;
|
return ret;
|
||||||
|
|
||||||
/* TODO(3.0): Remove legacy code below */
|
/* TODO(3.0): Remove legacy code below */
|
||||||
@@ -620,7 +625,11 @@ int EVP_EncryptFinal_ex(EVP_CIPHER_CTX *ctx, unsigned char *out, int *outl)
|
|||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (ctx->cipher == NULL || ctx->cipher->prov == NULL)
|
if (ctx->cipher == NULL) {
|
||||||
|
EVPerr(EVP_F_EVP_ENCRYPTFINAL_EX, EVP_R_NO_CIPHER_SET);
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
if (ctx->cipher->prov == NULL)
|
||||||
goto legacy;
|
goto legacy;
|
||||||
|
|
||||||
blocksize = EVP_CIPHER_CTX_block_size(ctx);
|
blocksize = EVP_CIPHER_CTX_block_size(ctx);
|
||||||
@@ -633,11 +642,13 @@ int EVP_EncryptFinal_ex(EVP_CIPHER_CTX *ctx, unsigned char *out, int *outl)
|
|||||||
ret = ctx->cipher->cfinal(ctx->provctx, out, &soutl,
|
ret = ctx->cipher->cfinal(ctx->provctx, out, &soutl,
|
||||||
blocksize == 1 ? 0 : blocksize);
|
blocksize == 1 ? 0 : blocksize);
|
||||||
|
|
||||||
if (soutl > INT_MAX) {
|
if (ret) {
|
||||||
EVPerr(EVP_F_EVP_ENCRYPTFINAL_EX, EVP_R_FINAL_ERROR);
|
if (soutl > INT_MAX) {
|
||||||
return 0;
|
EVPerr(EVP_F_EVP_ENCRYPTFINAL_EX, EVP_R_FINAL_ERROR);
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
*outl = soutl;
|
||||||
}
|
}
|
||||||
*outl = soutl;
|
|
||||||
|
|
||||||
return ret;
|
return ret;
|
||||||
|
|
||||||
@@ -695,7 +706,11 @@ int EVP_DecryptUpdate(EVP_CIPHER_CTX *ctx, unsigned char *out, int *outl,
|
|||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (ctx->cipher == NULL || ctx->cipher->prov == NULL)
|
if (ctx->cipher == NULL) {
|
||||||
|
EVPerr(EVP_F_EVP_DECRYPTUPDATE, EVP_R_NO_CIPHER_SET);
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
if (ctx->cipher->prov == NULL)
|
||||||
goto legacy;
|
goto legacy;
|
||||||
|
|
||||||
blocksize = EVP_CIPHER_CTX_block_size(ctx);
|
blocksize = EVP_CIPHER_CTX_block_size(ctx);
|
||||||
@@ -726,11 +741,6 @@ int EVP_DecryptUpdate(EVP_CIPHER_CTX *ctx, unsigned char *out, int *outl,
|
|||||||
if (EVP_CIPHER_CTX_test_flags(ctx, EVP_CIPH_FLAG_LENGTH_BITS))
|
if (EVP_CIPHER_CTX_test_flags(ctx, EVP_CIPH_FLAG_LENGTH_BITS))
|
||||||
cmpl = (cmpl + 7) / 8;
|
cmpl = (cmpl + 7) / 8;
|
||||||
|
|
||||||
if (inl <= 0) {
|
|
||||||
*outl = 0;
|
|
||||||
return inl == 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (ctx->cipher->flags & EVP_CIPH_FLAG_CUSTOM_CIPHER) {
|
if (ctx->cipher->flags & EVP_CIPH_FLAG_CUSTOM_CIPHER) {
|
||||||
if (b == 1 && is_partially_overlapping(out, in, cmpl)) {
|
if (b == 1 && is_partially_overlapping(out, in, cmpl)) {
|
||||||
EVPerr(EVP_F_EVP_DECRYPTUPDATE, EVP_R_PARTIALLY_OVERLAPPING);
|
EVPerr(EVP_F_EVP_DECRYPTUPDATE, EVP_R_PARTIALLY_OVERLAPPING);
|
||||||
@@ -746,6 +756,11 @@ int EVP_DecryptUpdate(EVP_CIPHER_CTX *ctx, unsigned char *out, int *outl,
|
|||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (inl <= 0) {
|
||||||
|
*outl = 0;
|
||||||
|
return inl == 0;
|
||||||
|
}
|
||||||
|
|
||||||
if (ctx->flags & EVP_CIPH_NO_PADDING)
|
if (ctx->flags & EVP_CIPH_NO_PADDING)
|
||||||
return evp_EncryptDecryptUpdate(ctx, out, outl, in, inl);
|
return evp_EncryptDecryptUpdate(ctx, out, outl, in, inl);
|
||||||
|
|
||||||
@@ -832,6 +847,10 @@ int EVP_DecryptFinal_ex(EVP_CIPHER_CTX *ctx, unsigned char *out, int *outl)
|
|||||||
legacy:
|
legacy:
|
||||||
|
|
||||||
*outl = 0;
|
*outl = 0;
|
||||||
|
if (ctx->cipher == NULL) {
|
||||||
|
EVPerr(EVP_F_EVP_DECRYPTFINAL_EX, EVP_R_NO_CIPHER_SET);
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
if (ctx->cipher->flags & EVP_CIPH_FLAG_CUSTOM_CIPHER) {
|
if (ctx->cipher->flags & EVP_CIPH_FLAG_CUSTOM_CIPHER) {
|
||||||
i = ctx->cipher->do_cipher(ctx, out, NULL, 0);
|
i = ctx->cipher->do_cipher(ctx, out, NULL, 0);
|
||||||
@@ -949,9 +968,11 @@ int EVP_CIPHER_CTX_ctrl(EVP_CIPHER_CTX *ctx, int type, int arg, void *ptr)
|
|||||||
|
|
||||||
int EVP_CIPHER_CTX_rand_key(EVP_CIPHER_CTX *ctx, unsigned char *key)
|
int EVP_CIPHER_CTX_rand_key(EVP_CIPHER_CTX *ctx, unsigned char *key)
|
||||||
{
|
{
|
||||||
|
int kl;
|
||||||
if (ctx->cipher->flags & EVP_CIPH_RAND_KEY)
|
if (ctx->cipher->flags & EVP_CIPH_RAND_KEY)
|
||||||
return EVP_CIPHER_CTX_ctrl(ctx, EVP_CTRL_RAND_KEY, 0, key);
|
return EVP_CIPHER_CTX_ctrl(ctx, EVP_CTRL_RAND_KEY, 0, key);
|
||||||
if (RAND_priv_bytes(key, EVP_CIPHER_CTX_key_length(ctx)) <= 0)
|
kl = EVP_CIPHER_CTX_key_length(ctx);
|
||||||
|
if (kl <= 0 || RAND_priv_bytes(key, kl) <= 0)
|
||||||
return 0;
|
return 0;
|
||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
@@ -1022,13 +1043,17 @@ int EVP_CIPHER_CTX_copy(EVP_CIPHER_CTX *out, const EVP_CIPHER_CTX *in)
|
|||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
static void *evp_cipher_from_dispatch(int nid, const OSSL_DISPATCH *fns,
|
static void *evp_cipher_from_dispatch(const OSSL_DISPATCH *fns,
|
||||||
OSSL_PROVIDER *prov)
|
OSSL_PROVIDER *prov)
|
||||||
{
|
{
|
||||||
EVP_CIPHER *cipher = NULL;
|
EVP_CIPHER *cipher = NULL;
|
||||||
int fnciphcnt = 0, fnctxcnt = 0;
|
int fnciphcnt = 0, fnctxcnt = 0;
|
||||||
|
|
||||||
if ((cipher = EVP_CIPHER_meth_new(nid, 0, 0)) == NULL)
|
/*
|
||||||
|
* The legacy NID is set by EVP_CIPHER_fetch() if the name exists in
|
||||||
|
* the object database.
|
||||||
|
*/
|
||||||
|
if ((cipher = EVP_CIPHER_meth_new(0, 0, 0)) == NULL)
|
||||||
return NULL;
|
return NULL;
|
||||||
|
|
||||||
for (; fns->function_id != 0; fns++) {
|
for (; fns->function_id != 0; fns++) {
|
||||||
@@ -1145,17 +1170,25 @@ static void evp_cipher_free(void *cipher)
|
|||||||
EVP_CIPHER_meth_free(cipher);
|
EVP_CIPHER_meth_free(cipher);
|
||||||
}
|
}
|
||||||
|
|
||||||
static int evp_cipher_nid(void *vcipher)
|
|
||||||
{
|
|
||||||
EVP_CIPHER *cipher = vcipher;
|
|
||||||
|
|
||||||
return cipher->nid;
|
|
||||||
}
|
|
||||||
|
|
||||||
EVP_CIPHER *EVP_CIPHER_fetch(OPENSSL_CTX *ctx, const char *algorithm,
|
EVP_CIPHER *EVP_CIPHER_fetch(OPENSSL_CTX *ctx, const char *algorithm,
|
||||||
const char *properties)
|
const char *properties)
|
||||||
{
|
{
|
||||||
return evp_generic_fetch(ctx, OSSL_OP_CIPHER, algorithm, properties,
|
EVP_CIPHER *cipher =
|
||||||
evp_cipher_from_dispatch, evp_cipher_upref,
|
evp_generic_fetch(ctx, OSSL_OP_CIPHER, algorithm, properties,
|
||||||
evp_cipher_free, evp_cipher_nid);
|
evp_cipher_from_dispatch, evp_cipher_upref,
|
||||||
|
evp_cipher_free);
|
||||||
|
|
||||||
|
#ifndef FIPS_MODE
|
||||||
|
/* TODO(3.x) get rid of the need for legacy NIDs */
|
||||||
|
if (cipher != NULL) {
|
||||||
|
/*
|
||||||
|
* FIPS module note: since internal fetches will be entirely
|
||||||
|
* provider based, we know that none of its code depends on legacy
|
||||||
|
* NIDs or any functionality that use them.
|
||||||
|
*/
|
||||||
|
cipher->nid = OBJ_sn2nid(algorithm);
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
|
||||||
|
return cipher;
|
||||||
}
|
}
|
||||||
@@ -74,6 +74,7 @@ static const ERR_STRING_DATA EVP_str_functs[] = {
|
|||||||
{ERR_PACK(ERR_LIB_EVP, EVP_F_EVP_ENCRYPTUPDATE, 0), "EVP_EncryptUpdate"},
|
{ERR_PACK(ERR_LIB_EVP, EVP_F_EVP_ENCRYPTUPDATE, 0), "EVP_EncryptUpdate"},
|
||||||
{ERR_PACK(ERR_LIB_EVP, EVP_F_EVP_KDF_CTRL, 0), "EVP_KDF_ctrl"},
|
{ERR_PACK(ERR_LIB_EVP, EVP_F_EVP_KDF_CTRL, 0), "EVP_KDF_ctrl"},
|
||||||
{ERR_PACK(ERR_LIB_EVP, EVP_F_EVP_KDF_CTRL_STR, 0), "EVP_KDF_ctrl_str"},
|
{ERR_PACK(ERR_LIB_EVP, EVP_F_EVP_KDF_CTRL_STR, 0), "EVP_KDF_ctrl_str"},
|
||||||
|
{ERR_PACK(ERR_LIB_EVP, EVP_F_EVP_KDF_CTX_NEW, 0), "EVP_KDF_CTX_new"},
|
||||||
{ERR_PACK(ERR_LIB_EVP, EVP_F_EVP_KDF_CTX_NEW_ID, 0), "EVP_KDF_CTX_new_id"},
|
{ERR_PACK(ERR_LIB_EVP, EVP_F_EVP_KDF_CTX_NEW_ID, 0), "EVP_KDF_CTX_new_id"},
|
||||||
{ERR_PACK(ERR_LIB_EVP, EVP_F_EVP_MAC_CTRL, 0), "EVP_MAC_ctrl"},
|
{ERR_PACK(ERR_LIB_EVP, EVP_F_EVP_MAC_CTRL, 0), "EVP_MAC_ctrl"},
|
||||||
{ERR_PACK(ERR_LIB_EVP, EVP_F_EVP_MAC_CTRL_STR, 0), "EVP_MAC_ctrl_str"},
|
{ERR_PACK(ERR_LIB_EVP, EVP_F_EVP_MAC_CTRL_STR, 0), "EVP_MAC_ctrl_str"},
|
||||||
@@ -248,6 +249,7 @@ static const ERR_STRING_DATA EVP_str_reasons[] = {
|
|||||||
"invalid custom length"},
|
"invalid custom length"},
|
||||||
{ERR_PACK(ERR_LIB_EVP, 0, EVP_R_INVALID_DIGEST), "invalid digest"},
|
{ERR_PACK(ERR_LIB_EVP, 0, EVP_R_INVALID_DIGEST), "invalid digest"},
|
||||||
{ERR_PACK(ERR_LIB_EVP, 0, EVP_R_INVALID_FIPS_MODE), "invalid fips mode"},
|
{ERR_PACK(ERR_LIB_EVP, 0, EVP_R_INVALID_FIPS_MODE), "invalid fips mode"},
|
||||||
|
{ERR_PACK(ERR_LIB_EVP, 0, EVP_R_INVALID_IV_LENGTH), "invalid iv length"},
|
||||||
{ERR_PACK(ERR_LIB_EVP, 0, EVP_R_INVALID_KEY), "invalid key"},
|
{ERR_PACK(ERR_LIB_EVP, 0, EVP_R_INVALID_KEY), "invalid key"},
|
||||||
{ERR_PACK(ERR_LIB_EVP, 0, EVP_R_INVALID_KEY_LENGTH), "invalid key length"},
|
{ERR_PACK(ERR_LIB_EVP, 0, EVP_R_INVALID_KEY_LENGTH), "invalid key length"},
|
||||||
{ERR_PACK(ERR_LIB_EVP, 0, EVP_R_INVALID_OPERATION), "invalid operation"},
|
{ERR_PACK(ERR_LIB_EVP, 0, EVP_R_INVALID_OPERATION), "invalid operation"},
|
||||||
|
|||||||
+40
-76
@@ -13,23 +13,20 @@
|
|||||||
#include <openssl/core.h>
|
#include <openssl/core.h>
|
||||||
#include "internal/cryptlib.h"
|
#include "internal/cryptlib.h"
|
||||||
#include "internal/thread_once.h"
|
#include "internal/thread_once.h"
|
||||||
#include "internal/asn1_int.h"
|
|
||||||
#include "internal/property.h"
|
#include "internal/property.h"
|
||||||
#include "internal/core.h"
|
#include "internal/core.h"
|
||||||
|
#include "internal/namemap.h"
|
||||||
#include "internal/evp_int.h" /* evp_locl.h needs it */
|
#include "internal/evp_int.h" /* evp_locl.h needs it */
|
||||||
#include "evp_locl.h"
|
#include "evp_locl.h"
|
||||||
|
|
||||||
/* The OpenSSL library context index for the default method store */
|
|
||||||
static int default_method_store_index = -1;
|
|
||||||
|
|
||||||
static void default_method_store_free(void *vstore)
|
static void default_method_store_free(void *vstore)
|
||||||
{
|
{
|
||||||
ossl_method_store_free(vstore);
|
ossl_method_store_free(vstore);
|
||||||
}
|
}
|
||||||
|
|
||||||
static void *default_method_store_new(void)
|
static void *default_method_store_new(OPENSSL_CTX *ctx)
|
||||||
{
|
{
|
||||||
return ossl_method_store_new();
|
return ossl_method_store_new(ctx);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@@ -38,39 +35,23 @@ static const OPENSSL_CTX_METHOD default_method_store_method = {
|
|||||||
default_method_store_free,
|
default_method_store_free,
|
||||||
};
|
};
|
||||||
|
|
||||||
static int default_method_store_init(void)
|
|
||||||
{
|
|
||||||
default_method_store_index =
|
|
||||||
openssl_ctx_new_index(&default_method_store_method);
|
|
||||||
|
|
||||||
return default_method_store_index != -1;
|
|
||||||
}
|
|
||||||
|
|
||||||
static CRYPTO_ONCE default_method_store_init_flag = CRYPTO_ONCE_STATIC_INIT;
|
|
||||||
DEFINE_RUN_ONCE_STATIC(do_default_method_store_init)
|
|
||||||
{
|
|
||||||
return OPENSSL_init_crypto(0, NULL)
|
|
||||||
&& default_method_store_init();
|
|
||||||
}
|
|
||||||
|
|
||||||
/* Data to be passed through ossl_method_construct() */
|
/* Data to be passed through ossl_method_construct() */
|
||||||
struct method_data_st {
|
struct method_data_st {
|
||||||
|
OPENSSL_CTX *libctx;
|
||||||
const char *name;
|
const char *name;
|
||||||
int nid;
|
int id;
|
||||||
OSSL_METHOD_CONSTRUCT_METHOD *mcm;
|
OSSL_METHOD_CONSTRUCT_METHOD *mcm;
|
||||||
void *(*method_from_dispatch)(int nid, const OSSL_DISPATCH *,
|
void *(*method_from_dispatch)(const OSSL_DISPATCH *, OSSL_PROVIDER *);
|
||||||
OSSL_PROVIDER *);
|
|
||||||
int (*refcnt_up_method)(void *method);
|
int (*refcnt_up_method)(void *method);
|
||||||
void (*destruct_method)(void *method);
|
void (*destruct_method)(void *method);
|
||||||
int (*nid_method)(void *method);
|
|
||||||
};
|
};
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Generic routines to fetch / create EVP methods with ossl_method_construct()
|
* Generic routines to fetch / create EVP methods with ossl_method_construct()
|
||||||
*/
|
*/
|
||||||
static void *alloc_tmp_method_store(void)
|
static void *alloc_tmp_method_store(OPENSSL_CTX *ctx)
|
||||||
{
|
{
|
||||||
return ossl_method_store_new();
|
return ossl_method_store_new(ctx);
|
||||||
}
|
}
|
||||||
|
|
||||||
static void dealloc_tmp_method_store(void *store)
|
static void dealloc_tmp_method_store(void *store)
|
||||||
@@ -81,23 +62,28 @@ static void *alloc_tmp_method_store(void)
|
|||||||
|
|
||||||
static OSSL_METHOD_STORE *get_default_method_store(OPENSSL_CTX *libctx)
|
static OSSL_METHOD_STORE *get_default_method_store(OPENSSL_CTX *libctx)
|
||||||
{
|
{
|
||||||
if (!RUN_ONCE(&default_method_store_init_flag,
|
return openssl_ctx_get_data(libctx, OPENSSL_CTX_DEFAULT_METHOD_STORE_INDEX,
|
||||||
do_default_method_store_init))
|
&default_method_store_method);
|
||||||
return NULL;
|
|
||||||
return openssl_ctx_get_data(libctx, default_method_store_index);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
static void *get_method_from_store(OPENSSL_CTX *libctx, void *store,
|
static void *get_method_from_store(OPENSSL_CTX *libctx, void *store,
|
||||||
const char *propquery, void *data)
|
const char *name, const char *propquery,
|
||||||
|
void *data)
|
||||||
{
|
{
|
||||||
struct method_data_st *methdata = data;
|
struct method_data_st *methdata = data;
|
||||||
void *method = NULL;
|
void *method = NULL;
|
||||||
|
OSSL_NAMEMAP *namemap;
|
||||||
|
int id;
|
||||||
|
|
||||||
if (store == NULL
|
if (store == NULL
|
||||||
&& (store = get_default_method_store(libctx)) == NULL)
|
&& (store = get_default_method_store(libctx)) == NULL)
|
||||||
return NULL;
|
return NULL;
|
||||||
|
|
||||||
(void)ossl_method_store_fetch(store, methdata->nid, propquery, &method);
|
if ((namemap = ossl_namemap_stored(libctx)) == NULL
|
||||||
|
|| (id = ossl_namemap_add(namemap, name)) == 0)
|
||||||
|
return NULL;
|
||||||
|
|
||||||
|
(void)ossl_method_store_fetch(store, id, propquery, &method);
|
||||||
|
|
||||||
if (method != NULL
|
if (method != NULL
|
||||||
&& !methdata->refcnt_up_method(method)) {
|
&& !methdata->refcnt_up_method(method)) {
|
||||||
@@ -107,13 +93,15 @@ static void *get_method_from_store(OPENSSL_CTX *libctx, void *store,
|
|||||||
}
|
}
|
||||||
|
|
||||||
static int put_method_in_store(OPENSSL_CTX *libctx, void *store,
|
static int put_method_in_store(OPENSSL_CTX *libctx, void *store,
|
||||||
const char *propdef,
|
void *method, const char *name,
|
||||||
void *method, void *data)
|
const char *propdef, void *data)
|
||||||
{
|
{
|
||||||
struct method_data_st *methdata = data;
|
struct method_data_st *methdata = data;
|
||||||
int nid = methdata->nid_method(method);
|
OSSL_NAMEMAP *namemap;
|
||||||
|
int id;
|
||||||
|
|
||||||
if (nid == NID_undef)
|
if ((namemap = ossl_namemap_stored(methdata->libctx)) == NULL
|
||||||
|
|| (id = ossl_namemap_add(namemap, name)) == 0)
|
||||||
return 0;
|
return 0;
|
||||||
|
|
||||||
if (store == NULL
|
if (store == NULL
|
||||||
@@ -121,41 +109,18 @@ static int put_method_in_store(OPENSSL_CTX *libctx, void *store,
|
|||||||
return 0;
|
return 0;
|
||||||
|
|
||||||
if (methdata->refcnt_up_method(method)
|
if (methdata->refcnt_up_method(method)
|
||||||
&& ossl_method_store_add(store, nid, propdef, method,
|
&& ossl_method_store_add(store, id, propdef, method,
|
||||||
methdata->destruct_method))
|
methdata->destruct_method))
|
||||||
return 1;
|
return 1;
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
static void *construct_method(const char *algorithm_name,
|
static void *construct_method(const char *name, const OSSL_DISPATCH *fns,
|
||||||
const OSSL_DISPATCH *fns, OSSL_PROVIDER *prov,
|
OSSL_PROVIDER *prov, void *data)
|
||||||
void *data)
|
|
||||||
{
|
{
|
||||||
struct method_data_st *methdata = data;
|
struct method_data_st *methdata = data;
|
||||||
void *method = NULL;
|
|
||||||
int nid = OBJ_sn2nid(algorithm_name);
|
|
||||||
|
|
||||||
if (nid == NID_undef) {
|
return methdata->method_from_dispatch(fns, prov);
|
||||||
/* Create a new NID for that name on the fly */
|
|
||||||
ASN1_OBJECT tmpobj;
|
|
||||||
|
|
||||||
/* This is the same as OBJ_create() but without requiring a OID */
|
|
||||||
tmpobj.nid = OBJ_new_nid(1);
|
|
||||||
tmpobj.sn = tmpobj.ln = methdata->name;
|
|
||||||
tmpobj.flags = ASN1_OBJECT_FLAG_DYNAMIC;
|
|
||||||
tmpobj.length = 0;
|
|
||||||
tmpobj.data = NULL;
|
|
||||||
|
|
||||||
nid = OBJ_add_object(&tmpobj);
|
|
||||||
}
|
|
||||||
|
|
||||||
if (nid == NID_undef)
|
|
||||||
return NULL;
|
|
||||||
|
|
||||||
method = methdata->method_from_dispatch(nid, fns, prov);
|
|
||||||
if (method == NULL)
|
|
||||||
return NULL;
|
|
||||||
return method;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
static void destruct_method(void *method, void *data)
|
static void destruct_method(void *method, void *data)
|
||||||
@@ -166,22 +131,22 @@ static void destruct_method(void *method, void *data)
|
|||||||
}
|
}
|
||||||
|
|
||||||
void *evp_generic_fetch(OPENSSL_CTX *libctx, int operation_id,
|
void *evp_generic_fetch(OPENSSL_CTX *libctx, int operation_id,
|
||||||
const char *algorithm, const char *properties,
|
const char *name, const char *properties,
|
||||||
void *(*new_method)(int nid, const OSSL_DISPATCH *fns,
|
void *(*new_method)(const OSSL_DISPATCH *fns,
|
||||||
OSSL_PROVIDER *prov),
|
OSSL_PROVIDER *prov),
|
||||||
int (*upref_method)(void *),
|
int (*upref_method)(void *),
|
||||||
void (*free_method)(void *),
|
void (*free_method)(void *))
|
||||||
int (*nid_method)(void *))
|
|
||||||
{
|
{
|
||||||
OSSL_METHOD_STORE *store = get_default_method_store(libctx);
|
OSSL_METHOD_STORE *store = get_default_method_store(libctx);
|
||||||
int nid = OBJ_sn2nid(algorithm);
|
OSSL_NAMEMAP *namemap = ossl_namemap_stored(libctx);
|
||||||
|
int id;
|
||||||
void *method = NULL;
|
void *method = NULL;
|
||||||
|
|
||||||
if (store == NULL)
|
if (store == NULL || namemap == NULL)
|
||||||
return NULL;
|
return NULL;
|
||||||
|
|
||||||
if (nid == NID_undef
|
if ((id = ossl_namemap_number(namemap, name)) == 0
|
||||||
|| !ossl_method_store_cache_get(store, nid, properties, &method)) {
|
|| !ossl_method_store_cache_get(store, id, properties, &method)) {
|
||||||
OSSL_METHOD_CONSTRUCT_METHOD mcm = {
|
OSSL_METHOD_CONSTRUCT_METHOD mcm = {
|
||||||
alloc_tmp_method_store,
|
alloc_tmp_method_store,
|
||||||
dealloc_tmp_method_store,
|
dealloc_tmp_method_store,
|
||||||
@@ -192,17 +157,16 @@ void *evp_generic_fetch(OPENSSL_CTX *libctx, int operation_id,
|
|||||||
};
|
};
|
||||||
struct method_data_st mcmdata;
|
struct method_data_st mcmdata;
|
||||||
|
|
||||||
mcmdata.nid = nid;
|
|
||||||
mcmdata.mcm = &mcm;
|
mcmdata.mcm = &mcm;
|
||||||
|
mcmdata.libctx = libctx;
|
||||||
mcmdata.method_from_dispatch = new_method;
|
mcmdata.method_from_dispatch = new_method;
|
||||||
mcmdata.destruct_method = free_method;
|
mcmdata.destruct_method = free_method;
|
||||||
mcmdata.refcnt_up_method = upref_method;
|
mcmdata.refcnt_up_method = upref_method;
|
||||||
mcmdata.destruct_method = free_method;
|
mcmdata.destruct_method = free_method;
|
||||||
mcmdata.nid_method = nid_method;
|
method = ossl_method_construct(libctx, operation_id, name,
|
||||||
method = ossl_method_construct(libctx, operation_id, algorithm,
|
|
||||||
properties, 0 /* !force_cache */,
|
properties, 0 /* !force_cache */,
|
||||||
&mcm, &mcmdata);
|
&mcm, &mcmdata);
|
||||||
ossl_method_store_cache_set(store, nid, properties, method);
|
ossl_method_store_cache_set(store, id, properties, method);
|
||||||
} else {
|
} else {
|
||||||
upref_method(method);
|
upref_method(method);
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -232,8 +232,14 @@ int EVP_Cipher(EVP_CIPHER_CTX *ctx, unsigned char *out,
|
|||||||
const unsigned char *in, unsigned int inl)
|
const unsigned char *in, unsigned int inl)
|
||||||
{
|
{
|
||||||
if (ctx->cipher->prov != NULL) {
|
if (ctx->cipher->prov != NULL) {
|
||||||
|
size_t outl = 0; /* ignored */
|
||||||
|
int blocksize = EVP_CIPHER_CTX_block_size(ctx);
|
||||||
|
|
||||||
if (ctx->cipher->ccipher != NULL)
|
if (ctx->cipher->ccipher != NULL)
|
||||||
return ctx->cipher->ccipher(ctx->provctx, out, in, (size_t)inl);
|
return
|
||||||
|
ctx->cipher->ccipher(ctx->provctx, out, &outl,
|
||||||
|
inl + (blocksize == 1 ? 0 : blocksize),
|
||||||
|
in, (size_t)inl);
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -56,7 +56,7 @@ struct evp_mac_ctx_st {
|
|||||||
} /* EVP_MAC_CTX */;
|
} /* EVP_MAC_CTX */;
|
||||||
|
|
||||||
struct evp_kdf_ctx_st {
|
struct evp_kdf_ctx_st {
|
||||||
const EVP_KDF_METHOD *kmeth;
|
const EVP_KDF *meth; /* Method structure */
|
||||||
EVP_KDF_IMPL *impl; /* Algorithm-specific data */
|
EVP_KDF_IMPL *impl; /* Algorithm-specific data */
|
||||||
} /* EVP_KDF_CTX */ ;
|
} /* EVP_KDF_CTX */ ;
|
||||||
|
|
||||||
@@ -91,8 +91,7 @@ int is_partially_overlapping(const void *ptr1, const void *ptr2, int len);
|
|||||||
|
|
||||||
void *evp_generic_fetch(OPENSSL_CTX *ctx, int operation_id,
|
void *evp_generic_fetch(OPENSSL_CTX *ctx, int operation_id,
|
||||||
const char *algorithm, const char *properties,
|
const char *algorithm, const char *properties,
|
||||||
void *(*new_method)(int nid, const OSSL_DISPATCH *fns,
|
void *(*new_method)(const OSSL_DISPATCH *fns,
|
||||||
OSSL_PROVIDER *prov),
|
OSSL_PROVIDER *prov),
|
||||||
int (*upref_method)(void *),
|
int (*upref_method)(void *),
|
||||||
void (*free_method)(void *),
|
void (*free_method)(void *));
|
||||||
int (*nid_method)(void *));
|
|
||||||
+33
-65
@@ -1,6 +1,6 @@
|
|||||||
/*
|
/*
|
||||||
* Copyright 2018 The OpenSSL Project Authors. All Rights Reserved.
|
* Copyright 2018-2019 The OpenSSL Project Authors. All Rights Reserved.
|
||||||
* Copyright (c) 2018, Oracle and/or its affiliates. All rights reserved.
|
* Copyright (c) 2018-2019, Oracle and/or its affiliates. All rights reserved.
|
||||||
*
|
*
|
||||||
* Licensed under the Apache License 2.0 (the "License"). You may not use
|
* Licensed under the Apache License 2.0 (the "License"). You may not use
|
||||||
* this file except in compliance with the License. You can obtain a copy
|
* this file except in compliance with the License. You can obtain a copy
|
||||||
@@ -20,70 +20,39 @@
|
|||||||
#include "internal/numbers.h"
|
#include "internal/numbers.h"
|
||||||
#include "evp_locl.h"
|
#include "evp_locl.h"
|
||||||
|
|
||||||
typedef int sk_cmp_fn_type(const char *const *a, const char *const *b);
|
EVP_KDF_CTX *EVP_KDF_CTX_new(const EVP_KDF *kdf)
|
||||||
|
|
||||||
/* This array needs to be in order of NIDs */
|
|
||||||
static const EVP_KDF_METHOD *standard_methods[] = {
|
|
||||||
&pbkdf2_kdf_meth,
|
|
||||||
#ifndef OPENSSL_NO_SCRYPT
|
|
||||||
&scrypt_kdf_meth,
|
|
||||||
#endif
|
|
||||||
&tls1_prf_kdf_meth,
|
|
||||||
&hkdf_kdf_meth,
|
|
||||||
&sshkdf_kdf_meth,
|
|
||||||
&ss_kdf_meth
|
|
||||||
};
|
|
||||||
|
|
||||||
DECLARE_OBJ_BSEARCH_CMP_FN(const EVP_KDF_METHOD *, const EVP_KDF_METHOD *,
|
|
||||||
kmeth);
|
|
||||||
|
|
||||||
static int kmeth_cmp(const EVP_KDF_METHOD *const *a,
|
|
||||||
const EVP_KDF_METHOD *const *b)
|
|
||||||
{
|
{
|
||||||
return ((*a)->type - (*b)->type);
|
EVP_KDF_CTX *ctx = NULL;
|
||||||
}
|
|
||||||
|
|
||||||
IMPLEMENT_OBJ_BSEARCH_CMP_FN(const EVP_KDF_METHOD *, const EVP_KDF_METHOD *,
|
if (kdf == NULL)
|
||||||
kmeth);
|
|
||||||
|
|
||||||
static const EVP_KDF_METHOD *kdf_meth_find(int type)
|
|
||||||
{
|
|
||||||
EVP_KDF_METHOD tmp;
|
|
||||||
const EVP_KDF_METHOD *t = &tmp, **ret;
|
|
||||||
|
|
||||||
tmp.type = type;
|
|
||||||
ret = OBJ_bsearch_kmeth(&t, standard_methods,
|
|
||||||
OSSL_NELEM(standard_methods));
|
|
||||||
if (ret == NULL || *ret == NULL)
|
|
||||||
return NULL;
|
return NULL;
|
||||||
|
|
||||||
return *ret;
|
ctx = OPENSSL_zalloc(sizeof(EVP_KDF_CTX));
|
||||||
|
if (ctx == NULL || (ctx->impl = kdf->new()) == NULL) {
|
||||||
|
EVPerr(EVP_F_EVP_KDF_CTX_NEW, ERR_R_MALLOC_FAILURE);
|
||||||
|
OPENSSL_free(ctx);
|
||||||
|
ctx = NULL;
|
||||||
|
} else {
|
||||||
|
ctx->meth = kdf;
|
||||||
|
}
|
||||||
|
return ctx;
|
||||||
}
|
}
|
||||||
|
|
||||||
EVP_KDF_CTX *EVP_KDF_CTX_new_id(int id)
|
EVP_KDF_CTX *EVP_KDF_CTX_new_id(int id)
|
||||||
{
|
{
|
||||||
EVP_KDF_CTX *ret;
|
const EVP_KDF *kdf = EVP_get_kdfbynid(id);
|
||||||
const EVP_KDF_METHOD *kmeth;
|
|
||||||
|
|
||||||
kmeth = kdf_meth_find(id);
|
return EVP_KDF_CTX_new(kdf);
|
||||||
if (kmeth == NULL) {
|
}
|
||||||
EVPerr(EVP_F_EVP_KDF_CTX_NEW_ID, EVP_R_UNSUPPORTED_ALGORITHM);
|
|
||||||
return NULL;
|
|
||||||
}
|
|
||||||
|
|
||||||
ret = OPENSSL_zalloc(sizeof(*ret));
|
int EVP_KDF_nid(const EVP_KDF *kdf)
|
||||||
if (ret == NULL) {
|
{
|
||||||
EVPerr(EVP_F_EVP_KDF_CTX_NEW_ID, ERR_R_MALLOC_FAILURE);
|
return kdf->type;
|
||||||
return NULL;
|
}
|
||||||
}
|
|
||||||
|
|
||||||
if (kmeth->new != NULL && (ret->impl = kmeth->new()) == NULL) {
|
const EVP_KDF *EVP_KDF_CTX_kdf(EVP_KDF_CTX *ctx)
|
||||||
EVP_KDF_CTX_free(ret);
|
{
|
||||||
return NULL;
|
return ctx->meth;
|
||||||
}
|
|
||||||
|
|
||||||
ret->kmeth = kmeth;
|
|
||||||
return ret;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void EVP_KDF_CTX_free(EVP_KDF_CTX *ctx)
|
void EVP_KDF_CTX_free(EVP_KDF_CTX *ctx)
|
||||||
@@ -91,7 +60,7 @@ void EVP_KDF_CTX_free(EVP_KDF_CTX *ctx)
|
|||||||
if (ctx == NULL)
|
if (ctx == NULL)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
ctx->kmeth->free(ctx->impl);
|
ctx->meth->free(ctx->impl);
|
||||||
OPENSSL_free(ctx);
|
OPENSSL_free(ctx);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -100,8 +69,8 @@ void EVP_KDF_reset(EVP_KDF_CTX *ctx)
|
|||||||
if (ctx == NULL)
|
if (ctx == NULL)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
if (ctx->kmeth->reset != NULL)
|
if (ctx->meth->reset != NULL)
|
||||||
ctx->kmeth->reset(ctx->impl);
|
ctx->meth->reset(ctx->impl);
|
||||||
}
|
}
|
||||||
|
|
||||||
int EVP_KDF_ctrl(EVP_KDF_CTX *ctx, int cmd, ...)
|
int EVP_KDF_ctrl(EVP_KDF_CTX *ctx, int cmd, ...)
|
||||||
@@ -124,7 +93,7 @@ int EVP_KDF_vctrl(EVP_KDF_CTX *ctx, int cmd, va_list args)
|
|||||||
if (ctx == NULL)
|
if (ctx == NULL)
|
||||||
return 0;
|
return 0;
|
||||||
|
|
||||||
return ctx->kmeth->ctrl(ctx->impl, cmd, args);
|
return ctx->meth->ctrl(ctx->impl, cmd, args);
|
||||||
}
|
}
|
||||||
|
|
||||||
int EVP_KDF_ctrl_str(EVP_KDF_CTX *ctx, const char *type, const char *value)
|
int EVP_KDF_ctrl_str(EVP_KDF_CTX *ctx, const char *type, const char *value)
|
||||||
@@ -134,12 +103,12 @@ int EVP_KDF_ctrl_str(EVP_KDF_CTX *ctx, const char *type, const char *value)
|
|||||||
if (ctx == NULL)
|
if (ctx == NULL)
|
||||||
return 0;
|
return 0;
|
||||||
|
|
||||||
if (ctx->kmeth->ctrl_str == NULL) {
|
if (ctx->meth->ctrl_str == NULL) {
|
||||||
EVPerr(EVP_F_EVP_KDF_CTRL_STR, EVP_R_COMMAND_NOT_SUPPORTED);
|
EVPerr(EVP_F_EVP_KDF_CTRL_STR, EVP_R_COMMAND_NOT_SUPPORTED);
|
||||||
return -2;
|
return -2;
|
||||||
}
|
}
|
||||||
|
|
||||||
ret = ctx->kmeth->ctrl_str(ctx->impl, type, value);
|
ret = ctx->meth->ctrl_str(ctx->impl, type, value);
|
||||||
if (ret == -2)
|
if (ret == -2)
|
||||||
EVPerr(EVP_F_EVP_KDF_CTRL_STR, EVP_R_COMMAND_NOT_SUPPORTED);
|
EVPerr(EVP_F_EVP_KDF_CTRL_STR, EVP_R_COMMAND_NOT_SUPPORTED);
|
||||||
|
|
||||||
@@ -151,10 +120,10 @@ size_t EVP_KDF_size(EVP_KDF_CTX *ctx)
|
|||||||
if (ctx == NULL)
|
if (ctx == NULL)
|
||||||
return 0;
|
return 0;
|
||||||
|
|
||||||
if (ctx->kmeth->size == NULL)
|
if (ctx->meth->size == NULL)
|
||||||
return SIZE_MAX;
|
return SIZE_MAX;
|
||||||
|
|
||||||
return ctx->kmeth->size(ctx->impl);
|
return ctx->meth->size(ctx->impl);
|
||||||
}
|
}
|
||||||
|
|
||||||
int EVP_KDF_derive(EVP_KDF_CTX *ctx, unsigned char *key, size_t keylen)
|
int EVP_KDF_derive(EVP_KDF_CTX *ctx, unsigned char *key, size_t keylen)
|
||||||
@@ -162,6 +131,5 @@ int EVP_KDF_derive(EVP_KDF_CTX *ctx, unsigned char *key, size_t keylen)
|
|||||||
if (ctx == NULL)
|
if (ctx == NULL)
|
||||||
return 0;
|
return 0;
|
||||||
|
|
||||||
return ctx->kmeth->derive(ctx->impl, key, keylen);
|
return ctx->meth->derive(ctx->impl, key, keylen);
|
||||||
}
|
}
|
||||||
|
|
||||||
+32
-1
@@ -10,6 +10,7 @@
|
|||||||
#include <stdio.h>
|
#include <stdio.h>
|
||||||
#include "internal/cryptlib.h"
|
#include "internal/cryptlib.h"
|
||||||
#include <openssl/evp.h>
|
#include <openssl/evp.h>
|
||||||
|
#include <openssl/kdf.h>
|
||||||
#include "internal/objects.h"
|
#include "internal/objects.h"
|
||||||
#include <openssl/x509.h>
|
#include <openssl/x509.h>
|
||||||
#include "internal/evp_int.h"
|
#include "internal/evp_int.h"
|
||||||
@@ -71,6 +72,23 @@ int EVP_add_mac(const EVP_MAC *m)
|
|||||||
return r;
|
return r;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/* TODO(3.0) Is this needed after changing to providers? */
|
||||||
|
int EVP_add_kdf(const EVP_KDF *k)
|
||||||
|
{
|
||||||
|
int r;
|
||||||
|
|
||||||
|
if (k == NULL)
|
||||||
|
return 0;
|
||||||
|
|
||||||
|
r = OBJ_NAME_add(OBJ_nid2sn(k->type), OBJ_NAME_TYPE_KDF_METH,
|
||||||
|
(const char *)k);
|
||||||
|
if (r == 0)
|
||||||
|
return 0;
|
||||||
|
r = OBJ_NAME_add(OBJ_nid2ln(k->type), OBJ_NAME_TYPE_KDF_METH,
|
||||||
|
(const char *)k);
|
||||||
|
return r;
|
||||||
|
}
|
||||||
|
|
||||||
const EVP_CIPHER *EVP_get_cipherbyname(const char *name)
|
const EVP_CIPHER *EVP_get_cipherbyname(const char *name)
|
||||||
{
|
{
|
||||||
const EVP_CIPHER *cp;
|
const EVP_CIPHER *cp;
|
||||||
@@ -104,9 +122,22 @@ const EVP_MAC *EVP_get_macbyname(const char *name)
|
|||||||
return mp;
|
return mp;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/* TODO(3.0) Is this API needed after implementing providers? */
|
||||||
|
const EVP_KDF *EVP_get_kdfbyname(const char *name)
|
||||||
|
{
|
||||||
|
const EVP_KDF *kdf;
|
||||||
|
|
||||||
|
if (!OPENSSL_init_crypto(OPENSSL_INIT_ADD_ALL_KDFS, NULL))
|
||||||
|
return NULL;
|
||||||
|
|
||||||
|
kdf = (const EVP_KDF *)OBJ_NAME_get(name, OBJ_NAME_TYPE_KDF_METH);
|
||||||
|
return kdf;
|
||||||
|
}
|
||||||
|
|
||||||
void evp_cleanup_int(void)
|
void evp_cleanup_int(void)
|
||||||
{
|
{
|
||||||
OBJ_NAME_cleanup(OBJ_NAME_TYPE_MAC_METH);
|
OBJ_NAME_cleanup(OBJ_NAME_TYPE_MAC_METH);
|
||||||
|
OBJ_NAME_cleanup(OBJ_NAME_TYPE_KDF_METH);
|
||||||
OBJ_NAME_cleanup(OBJ_NAME_TYPE_CIPHER_METH);
|
OBJ_NAME_cleanup(OBJ_NAME_TYPE_CIPHER_METH);
|
||||||
OBJ_NAME_cleanup(OBJ_NAME_TYPE_MD_METH);
|
OBJ_NAME_cleanup(OBJ_NAME_TYPE_MD_METH);
|
||||||
/*
|
/*
|
||||||
@@ -207,6 +238,7 @@ void EVP_MD_do_all_sorted(void (*fn) (const EVP_MD *md,
|
|||||||
OBJ_NAME_do_all_sorted(OBJ_NAME_TYPE_MD_METH, do_all_md_fn, &dc);
|
OBJ_NAME_do_all_sorted(OBJ_NAME_TYPE_MD_METH, do_all_md_fn, &dc);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/* TODO(3.0) Are these do_all API's needed for MAC? */
|
||||||
struct doall_mac {
|
struct doall_mac {
|
||||||
void *arg;
|
void *arg;
|
||||||
void (*fn) (const EVP_MAC *ciph,
|
void (*fn) (const EVP_MAC *ciph,
|
||||||
@@ -250,4 +282,3 @@ void EVP_MAC_do_all_sorted(void (*fn)
|
|||||||
dc.arg = arg;
|
dc.arg = arg;
|
||||||
OBJ_NAME_do_all_sorted(OBJ_NAME_TYPE_MAC_METH, do_all_mac_fn, &dc);
|
OBJ_NAME_do_all_sorted(OBJ_NAME_TYPE_MAC_METH, do_all_mac_fn, &dc);
|
||||||
}
|
}
|
||||||
|
|
||||||
+14
-6
@@ -28,7 +28,7 @@ int PKCS5_PBE_keyivgen(EVP_CIPHER_CTX *cctx, const char *pass, int passlen,
|
|||||||
EVP_MD_CTX *ctx;
|
EVP_MD_CTX *ctx;
|
||||||
unsigned char md_tmp[EVP_MAX_MD_SIZE];
|
unsigned char md_tmp[EVP_MAX_MD_SIZE];
|
||||||
unsigned char key[EVP_MAX_KEY_LENGTH], iv[EVP_MAX_IV_LENGTH];
|
unsigned char key[EVP_MAX_KEY_LENGTH], iv[EVP_MAX_IV_LENGTH];
|
||||||
int i;
|
int i, ivl, kl;
|
||||||
PBEPARAM *pbe;
|
PBEPARAM *pbe;
|
||||||
int saltlen, iter;
|
int saltlen, iter;
|
||||||
unsigned char *salt;
|
unsigned char *salt;
|
||||||
@@ -48,6 +48,17 @@ int PKCS5_PBE_keyivgen(EVP_CIPHER_CTX *cctx, const char *pass, int passlen,
|
|||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
ivl = EVP_CIPHER_iv_length(cipher);
|
||||||
|
if (ivl < 0 || ivl > 16) {
|
||||||
|
EVPerr(EVP_F_PKCS5_PBE_KEYIVGEN, EVP_R_INVALID_IV_LENGTH);
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
kl = EVP_CIPHER_key_length(cipher);
|
||||||
|
if (kl < 0 || kl > (int)sizeof(md_tmp)) {
|
||||||
|
EVPerr(EVP_F_PKCS5_PBE_KEYIVGEN, EVP_R_INVALID_KEY_LENGTH);
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
if (!pbe->iter)
|
if (!pbe->iter)
|
||||||
iter = 1;
|
iter = 1;
|
||||||
else
|
else
|
||||||
@@ -86,11 +97,8 @@ int PKCS5_PBE_keyivgen(EVP_CIPHER_CTX *cctx, const char *pass, int passlen,
|
|||||||
if (!EVP_DigestFinal_ex(ctx, md_tmp, NULL))
|
if (!EVP_DigestFinal_ex(ctx, md_tmp, NULL))
|
||||||
goto err;
|
goto err;
|
||||||
}
|
}
|
||||||
OPENSSL_assert(EVP_CIPHER_key_length(cipher) <= (int)sizeof(md_tmp));
|
memcpy(key, md_tmp, kl);
|
||||||
memcpy(key, md_tmp, EVP_CIPHER_key_length(cipher));
|
memcpy(iv, md_tmp + (16 - ivl), ivl);
|
||||||
OPENSSL_assert(EVP_CIPHER_iv_length(cipher) <= 16);
|
|
||||||
memcpy(iv, md_tmp + (16 - EVP_CIPHER_iv_length(cipher)),
|
|
||||||
EVP_CIPHER_iv_length(cipher));
|
|
||||||
if (!EVP_CipherInit_ex(cctx, cipher, NULL, key, iv, en_de))
|
if (!EVP_CipherInit_ex(cctx, cipher, NULL, key, iv, en_de))
|
||||||
goto err;
|
goto err;
|
||||||
OPENSSL_cleanse(md_tmp, EVP_MAX_MD_SIZE);
|
OPENSSL_cleanse(md_tmp, EVP_MAX_MD_SIZE);
|
||||||
|
|||||||
@@ -134,7 +134,7 @@ int PKCS5_v2_PBKDF2_keyivgen(EVP_CIPHER_CTX *ctx, const char *pass,
|
|||||||
const EVP_CIPHER *c, const EVP_MD *md, int en_de)
|
const EVP_CIPHER *c, const EVP_MD *md, int en_de)
|
||||||
{
|
{
|
||||||
unsigned char *salt, key[EVP_MAX_KEY_LENGTH];
|
unsigned char *salt, key[EVP_MAX_KEY_LENGTH];
|
||||||
int saltlen, iter;
|
int saltlen, iter, t;
|
||||||
int rv = 0;
|
int rv = 0;
|
||||||
unsigned int keylen = 0;
|
unsigned int keylen = 0;
|
||||||
int prf_nid, hmac_md_nid;
|
int prf_nid, hmac_md_nid;
|
||||||
@@ -157,7 +157,12 @@ int PKCS5_v2_PBKDF2_keyivgen(EVP_CIPHER_CTX *ctx, const char *pass,
|
|||||||
goto err;
|
goto err;
|
||||||
}
|
}
|
||||||
|
|
||||||
keylen = EVP_CIPHER_CTX_key_length(ctx);
|
t = EVP_CIPHER_CTX_key_length(ctx);
|
||||||
|
if (t < 0) {
|
||||||
|
EVPerr(EVP_F_PKCS5_V2_PBKDF2_KEYIVGEN, EVP_R_INVALID_KEY_LENGTH);
|
||||||
|
goto err;
|
||||||
|
}
|
||||||
|
keylen = t;
|
||||||
|
|
||||||
/* Now check the parameters of the kdf */
|
/* Now check the parameters of the kdf */
|
||||||
|
|
||||||
|
|||||||
+99
-65
@@ -10,58 +10,33 @@
|
|||||||
#include "internal/cryptlib_int.h"
|
#include "internal/cryptlib_int.h"
|
||||||
#include "internal/thread_once.h"
|
#include "internal/thread_once.h"
|
||||||
|
|
||||||
/*
|
int do_ex_data_init(OPENSSL_CTX *ctx)
|
||||||
* Each structure type (sometimes called a class), that supports
|
|
||||||
* exdata has a stack of callbacks for each instance.
|
|
||||||
*/
|
|
||||||
struct ex_callback_st {
|
|
||||||
long argl; /* Arbitrary long */
|
|
||||||
void *argp; /* Arbitrary void * */
|
|
||||||
CRYPTO_EX_new *new_func;
|
|
||||||
CRYPTO_EX_free *free_func;
|
|
||||||
CRYPTO_EX_dup *dup_func;
|
|
||||||
};
|
|
||||||
|
|
||||||
/*
|
|
||||||
* The state for each class. This could just be a typedef, but
|
|
||||||
* a structure allows future changes.
|
|
||||||
*/
|
|
||||||
typedef struct ex_callbacks_st {
|
|
||||||
STACK_OF(EX_CALLBACK) *meth;
|
|
||||||
} EX_CALLBACKS;
|
|
||||||
|
|
||||||
static EX_CALLBACKS ex_data[CRYPTO_EX_INDEX__COUNT];
|
|
||||||
|
|
||||||
static CRYPTO_RWLOCK *ex_data_lock = NULL;
|
|
||||||
static CRYPTO_ONCE ex_data_init = CRYPTO_ONCE_STATIC_INIT;
|
|
||||||
|
|
||||||
DEFINE_RUN_ONCE_STATIC(do_ex_data_init)
|
|
||||||
{
|
{
|
||||||
if (!OPENSSL_init_crypto(0, NULL))
|
OSSL_EX_DATA_GLOBAL *global = openssl_ctx_get_ex_data_global(ctx);
|
||||||
|
|
||||||
|
if (global == NULL)
|
||||||
return 0;
|
return 0;
|
||||||
ex_data_lock = CRYPTO_THREAD_lock_new();
|
|
||||||
return ex_data_lock != NULL;
|
global->ex_data_lock = CRYPTO_THREAD_lock_new();
|
||||||
|
return global->ex_data_lock != NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Return the EX_CALLBACKS from the |ex_data| array that corresponds to
|
* Return the EX_CALLBACKS from the |ex_data| array that corresponds to
|
||||||
* a given class. On success, *holds the lock.*
|
* a given class. On success, *holds the lock.*
|
||||||
*/
|
*/
|
||||||
static EX_CALLBACKS *get_and_lock(int class_index)
|
static EX_CALLBACKS *get_and_lock(OPENSSL_CTX *ctx, int class_index)
|
||||||
{
|
{
|
||||||
EX_CALLBACKS *ip;
|
EX_CALLBACKS *ip;
|
||||||
|
OSSL_EX_DATA_GLOBAL *global = NULL;
|
||||||
|
|
||||||
if (class_index < 0 || class_index >= CRYPTO_EX_INDEX__COUNT) {
|
if (class_index < 0 || class_index >= CRYPTO_EX_INDEX__COUNT) {
|
||||||
CRYPTOerr(CRYPTO_F_GET_AND_LOCK, ERR_R_PASSED_INVALID_ARGUMENT);
|
CRYPTOerr(CRYPTO_F_GET_AND_LOCK, ERR_R_PASSED_INVALID_ARGUMENT);
|
||||||
return NULL;
|
return NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!RUN_ONCE(&ex_data_init, do_ex_data_init)) {
|
global = openssl_ctx_get_ex_data_global(ctx);
|
||||||
CRYPTOerr(CRYPTO_F_GET_AND_LOCK, ERR_R_MALLOC_FAILURE);
|
if (global->ex_data_lock == NULL) {
|
||||||
return NULL;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (ex_data_lock == NULL) {
|
|
||||||
/*
|
/*
|
||||||
* This can happen in normal operation when using CRYPTO_mem_leaks().
|
* This can happen in normal operation when using CRYPTO_mem_leaks().
|
||||||
* The CRYPTO_mem_leaks() function calls OPENSSL_cleanup() which cleans
|
* The CRYPTO_mem_leaks() function calls OPENSSL_cleanup() which cleans
|
||||||
@@ -74,8 +49,8 @@ static EX_CALLBACKS *get_and_lock(int class_index)
|
|||||||
return NULL;
|
return NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
ip = &ex_data[class_index];
|
ip = &global->ex_data[class_index];
|
||||||
CRYPTO_THREAD_write_lock(ex_data_lock);
|
CRYPTO_THREAD_write_lock(global->ex_data_lock);
|
||||||
return ip;
|
return ip;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -90,19 +65,23 @@ static void cleanup_cb(EX_CALLBACK *funcs)
|
|||||||
* called under potential race-conditions anyway (it's for program shutdown
|
* called under potential race-conditions anyway (it's for program shutdown
|
||||||
* after all).
|
* after all).
|
||||||
*/
|
*/
|
||||||
void crypto_cleanup_all_ex_data_int(void)
|
void crypto_cleanup_all_ex_data_int(OPENSSL_CTX *ctx)
|
||||||
{
|
{
|
||||||
int i;
|
int i;
|
||||||
|
OSSL_EX_DATA_GLOBAL *global = openssl_ctx_get_ex_data_global(ctx);
|
||||||
|
|
||||||
|
if (global == NULL)
|
||||||
|
return;
|
||||||
|
|
||||||
for (i = 0; i < CRYPTO_EX_INDEX__COUNT; ++i) {
|
for (i = 0; i < CRYPTO_EX_INDEX__COUNT; ++i) {
|
||||||
EX_CALLBACKS *ip = &ex_data[i];
|
EX_CALLBACKS *ip = &global->ex_data[i];
|
||||||
|
|
||||||
sk_EX_CALLBACK_pop_free(ip->meth, cleanup_cb);
|
sk_EX_CALLBACK_pop_free(ip->meth, cleanup_cb);
|
||||||
ip->meth = NULL;
|
ip->meth = NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
CRYPTO_THREAD_lock_free(ex_data_lock);
|
CRYPTO_THREAD_lock_free(global->ex_data_lock);
|
||||||
ex_data_lock = NULL;
|
global->ex_data_lock = NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@@ -127,12 +106,17 @@ static int dummy_dup(CRYPTO_EX_DATA *to, const CRYPTO_EX_DATA *from,
|
|||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
int CRYPTO_free_ex_index(int class_index, int idx)
|
int crypto_free_ex_index_ex(OPENSSL_CTX *ctx, int class_index, int idx)
|
||||||
{
|
{
|
||||||
EX_CALLBACKS *ip = get_and_lock(class_index);
|
EX_CALLBACKS *ip = get_and_lock(ctx, class_index);
|
||||||
EX_CALLBACK *a;
|
EX_CALLBACK *a;
|
||||||
int toret = 0;
|
int toret = 0;
|
||||||
|
OSSL_EX_DATA_GLOBAL *global = openssl_ctx_get_ex_data_global(ctx);
|
||||||
|
|
||||||
|
if (global == NULL)
|
||||||
|
return 0;
|
||||||
|
|
||||||
|
ip = get_and_lock(ctx, class_index);
|
||||||
if (ip == NULL)
|
if (ip == NULL)
|
||||||
return 0;
|
return 0;
|
||||||
if (idx < 0 || idx >= sk_EX_CALLBACK_num(ip->meth))
|
if (idx < 0 || idx >= sk_EX_CALLBACK_num(ip->meth))
|
||||||
@@ -145,21 +129,32 @@ int CRYPTO_free_ex_index(int class_index, int idx)
|
|||||||
a->free_func = dummy_free;
|
a->free_func = dummy_free;
|
||||||
toret = 1;
|
toret = 1;
|
||||||
err:
|
err:
|
||||||
CRYPTO_THREAD_unlock(ex_data_lock);
|
CRYPTO_THREAD_unlock(global->ex_data_lock);
|
||||||
return toret;
|
return toret;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
int CRYPTO_free_ex_index(int class_index, int idx)
|
||||||
|
{
|
||||||
|
return crypto_free_ex_index_ex(NULL, class_index, idx);
|
||||||
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Register a new index.
|
* Register a new index.
|
||||||
*/
|
*/
|
||||||
int CRYPTO_get_ex_new_index(int class_index, long argl, void *argp,
|
int crypto_get_ex_new_index_ex(OPENSSL_CTX *ctx, int class_index, long argl,
|
||||||
CRYPTO_EX_new *new_func, CRYPTO_EX_dup *dup_func,
|
void *argp, CRYPTO_EX_new *new_func,
|
||||||
CRYPTO_EX_free *free_func)
|
CRYPTO_EX_dup *dup_func,
|
||||||
|
CRYPTO_EX_free *free_func)
|
||||||
{
|
{
|
||||||
int toret = -1;
|
int toret = -1;
|
||||||
EX_CALLBACK *a;
|
EX_CALLBACK *a;
|
||||||
EX_CALLBACKS *ip = get_and_lock(class_index);
|
EX_CALLBACKS *ip;
|
||||||
|
OSSL_EX_DATA_GLOBAL *global = openssl_ctx_get_ex_data_global(ctx);
|
||||||
|
|
||||||
|
if (global == NULL)
|
||||||
|
return -1;
|
||||||
|
|
||||||
|
ip = get_and_lock(ctx, class_index);
|
||||||
if (ip == NULL)
|
if (ip == NULL)
|
||||||
return -1;
|
return -1;
|
||||||
|
|
||||||
@@ -169,14 +164,14 @@ int CRYPTO_get_ex_new_index(int class_index, long argl, void *argp,
|
|||||||
* "app_data" routines use ex_data index zero. See RT 3710. */
|
* "app_data" routines use ex_data index zero. See RT 3710. */
|
||||||
if (ip->meth == NULL
|
if (ip->meth == NULL
|
||||||
|| !sk_EX_CALLBACK_push(ip->meth, NULL)) {
|
|| !sk_EX_CALLBACK_push(ip->meth, NULL)) {
|
||||||
CRYPTOerr(CRYPTO_F_CRYPTO_GET_EX_NEW_INDEX, ERR_R_MALLOC_FAILURE);
|
CRYPTOerr(CRYPTO_F_CRYPTO_GET_EX_NEW_INDEX_EX, ERR_R_MALLOC_FAILURE);
|
||||||
goto err;
|
goto err;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
a = (EX_CALLBACK *)OPENSSL_malloc(sizeof(*a));
|
a = (EX_CALLBACK *)OPENSSL_malloc(sizeof(*a));
|
||||||
if (a == NULL) {
|
if (a == NULL) {
|
||||||
CRYPTOerr(CRYPTO_F_CRYPTO_GET_EX_NEW_INDEX, ERR_R_MALLOC_FAILURE);
|
CRYPTOerr(CRYPTO_F_CRYPTO_GET_EX_NEW_INDEX_EX, ERR_R_MALLOC_FAILURE);
|
||||||
goto err;
|
goto err;
|
||||||
}
|
}
|
||||||
a->argl = argl;
|
a->argl = argl;
|
||||||
@@ -186,7 +181,7 @@ int CRYPTO_get_ex_new_index(int class_index, long argl, void *argp,
|
|||||||
a->free_func = free_func;
|
a->free_func = free_func;
|
||||||
|
|
||||||
if (!sk_EX_CALLBACK_push(ip->meth, NULL)) {
|
if (!sk_EX_CALLBACK_push(ip->meth, NULL)) {
|
||||||
CRYPTOerr(CRYPTO_F_CRYPTO_GET_EX_NEW_INDEX, ERR_R_MALLOC_FAILURE);
|
CRYPTOerr(CRYPTO_F_CRYPTO_GET_EX_NEW_INDEX_EX, ERR_R_MALLOC_FAILURE);
|
||||||
OPENSSL_free(a);
|
OPENSSL_free(a);
|
||||||
goto err;
|
goto err;
|
||||||
}
|
}
|
||||||
@@ -194,10 +189,18 @@ int CRYPTO_get_ex_new_index(int class_index, long argl, void *argp,
|
|||||||
(void)sk_EX_CALLBACK_set(ip->meth, toret, a);
|
(void)sk_EX_CALLBACK_set(ip->meth, toret, a);
|
||||||
|
|
||||||
err:
|
err:
|
||||||
CRYPTO_THREAD_unlock(ex_data_lock);
|
CRYPTO_THREAD_unlock(global->ex_data_lock);
|
||||||
return toret;
|
return toret;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
int CRYPTO_get_ex_new_index(int class_index, long argl, void *argp,
|
||||||
|
CRYPTO_EX_new *new_func, CRYPTO_EX_dup *dup_func,
|
||||||
|
CRYPTO_EX_free *free_func)
|
||||||
|
{
|
||||||
|
return crypto_get_ex_new_index_ex(NULL, class_index, argl, argp, new_func,
|
||||||
|
dup_func, free_func);
|
||||||
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Initialise a new CRYPTO_EX_DATA for use in a particular class - including
|
* Initialise a new CRYPTO_EX_DATA for use in a particular class - including
|
||||||
* calling new() callbacks for each index in the class used by this variable
|
* calling new() callbacks for each index in the class used by this variable
|
||||||
@@ -205,17 +208,24 @@ int CRYPTO_get_ex_new_index(int class_index, long argl, void *argp,
|
|||||||
* in the lock, then using them outside the lock. Note this only applies
|
* in the lock, then using them outside the lock. Note this only applies
|
||||||
* to the global "ex_data" state (ie. class definitions), not 'ad' itself.
|
* to the global "ex_data" state (ie. class definitions), not 'ad' itself.
|
||||||
*/
|
*/
|
||||||
int CRYPTO_new_ex_data(int class_index, void *obj, CRYPTO_EX_DATA *ad)
|
int crypto_new_ex_data_ex(OPENSSL_CTX *ctx, int class_index, void *obj,
|
||||||
|
CRYPTO_EX_DATA *ad)
|
||||||
{
|
{
|
||||||
int mx, i;
|
int mx, i;
|
||||||
void *ptr;
|
void *ptr;
|
||||||
EX_CALLBACK **storage = NULL;
|
EX_CALLBACK **storage = NULL;
|
||||||
EX_CALLBACK *stack[10];
|
EX_CALLBACK *stack[10];
|
||||||
EX_CALLBACKS *ip = get_and_lock(class_index);
|
EX_CALLBACKS *ip;
|
||||||
|
OSSL_EX_DATA_GLOBAL *global = openssl_ctx_get_ex_data_global(ctx);
|
||||||
|
|
||||||
|
if (global == NULL)
|
||||||
|
return 0;
|
||||||
|
|
||||||
|
ip = get_and_lock(ctx, class_index);
|
||||||
if (ip == NULL)
|
if (ip == NULL)
|
||||||
return 0;
|
return 0;
|
||||||
|
|
||||||
|
ad->ctx = ctx;
|
||||||
ad->sk = NULL;
|
ad->sk = NULL;
|
||||||
|
|
||||||
mx = sk_EX_CALLBACK_num(ip->meth);
|
mx = sk_EX_CALLBACK_num(ip->meth);
|
||||||
@@ -228,10 +238,10 @@ int CRYPTO_new_ex_data(int class_index, void *obj, CRYPTO_EX_DATA *ad)
|
|||||||
for (i = 0; i < mx; i++)
|
for (i = 0; i < mx; i++)
|
||||||
storage[i] = sk_EX_CALLBACK_value(ip->meth, i);
|
storage[i] = sk_EX_CALLBACK_value(ip->meth, i);
|
||||||
}
|
}
|
||||||
CRYPTO_THREAD_unlock(ex_data_lock);
|
CRYPTO_THREAD_unlock(global->ex_data_lock);
|
||||||
|
|
||||||
if (mx > 0 && storage == NULL) {
|
if (mx > 0 && storage == NULL) {
|
||||||
CRYPTOerr(CRYPTO_F_CRYPTO_NEW_EX_DATA, ERR_R_MALLOC_FAILURE);
|
CRYPTOerr(CRYPTO_F_CRYPTO_NEW_EX_DATA_EX, ERR_R_MALLOC_FAILURE);
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
for (i = 0; i < mx; i++) {
|
for (i = 0; i < mx; i++) {
|
||||||
@@ -246,6 +256,11 @@ int CRYPTO_new_ex_data(int class_index, void *obj, CRYPTO_EX_DATA *ad)
|
|||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
int CRYPTO_new_ex_data(int class_index, void *obj, CRYPTO_EX_DATA *ad)
|
||||||
|
{
|
||||||
|
return crypto_new_ex_data_ex(NULL, class_index, obj, ad);
|
||||||
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Duplicate a CRYPTO_EX_DATA variable - including calling dup() callbacks
|
* Duplicate a CRYPTO_EX_DATA variable - including calling dup() callbacks
|
||||||
* for each index in the class used by this variable
|
* for each index in the class used by this variable
|
||||||
@@ -259,11 +274,16 @@ int CRYPTO_dup_ex_data(int class_index, CRYPTO_EX_DATA *to,
|
|||||||
EX_CALLBACK **storage = NULL;
|
EX_CALLBACK **storage = NULL;
|
||||||
EX_CALLBACKS *ip;
|
EX_CALLBACKS *ip;
|
||||||
int toret = 0;
|
int toret = 0;
|
||||||
|
OSSL_EX_DATA_GLOBAL *global = openssl_ctx_get_ex_data_global(from->ctx);
|
||||||
|
|
||||||
|
if (global == NULL)
|
||||||
|
return 0;
|
||||||
|
|
||||||
|
to->ctx = from->ctx;
|
||||||
if (from->sk == NULL)
|
if (from->sk == NULL)
|
||||||
/* Nothing to copy over */
|
/* Nothing to copy over */
|
||||||
return 1;
|
return 1;
|
||||||
if ((ip = get_and_lock(class_index)) == NULL)
|
if ((ip = get_and_lock(from->ctx, class_index)) == NULL)
|
||||||
return 0;
|
return 0;
|
||||||
|
|
||||||
mx = sk_EX_CALLBACK_num(ip->meth);
|
mx = sk_EX_CALLBACK_num(ip->meth);
|
||||||
@@ -279,7 +299,7 @@ int CRYPTO_dup_ex_data(int class_index, CRYPTO_EX_DATA *to,
|
|||||||
for (i = 0; i < mx; i++)
|
for (i = 0; i < mx; i++)
|
||||||
storage[i] = sk_EX_CALLBACK_value(ip->meth, i);
|
storage[i] = sk_EX_CALLBACK_value(ip->meth, i);
|
||||||
}
|
}
|
||||||
CRYPTO_THREAD_unlock(ex_data_lock);
|
CRYPTO_THREAD_unlock(global->ex_data_lock);
|
||||||
|
|
||||||
if (mx == 0)
|
if (mx == 0)
|
||||||
return 1;
|
return 1;
|
||||||
@@ -325,8 +345,12 @@ void CRYPTO_free_ex_data(int class_index, void *obj, CRYPTO_EX_DATA *ad)
|
|||||||
EX_CALLBACK *f;
|
EX_CALLBACK *f;
|
||||||
EX_CALLBACK *stack[10];
|
EX_CALLBACK *stack[10];
|
||||||
EX_CALLBACK **storage = NULL;
|
EX_CALLBACK **storage = NULL;
|
||||||
|
OSSL_EX_DATA_GLOBAL *global;
|
||||||
|
|
||||||
if ((ip = get_and_lock(class_index)) == NULL)
|
if ((ip = get_and_lock(ad->ctx, class_index)) == NULL)
|
||||||
|
goto err;
|
||||||
|
global = openssl_ctx_get_ex_data_global(ad->ctx);
|
||||||
|
if (global == NULL)
|
||||||
goto err;
|
goto err;
|
||||||
|
|
||||||
mx = sk_EX_CALLBACK_num(ip->meth);
|
mx = sk_EX_CALLBACK_num(ip->meth);
|
||||||
@@ -339,15 +363,15 @@ void CRYPTO_free_ex_data(int class_index, void *obj, CRYPTO_EX_DATA *ad)
|
|||||||
for (i = 0; i < mx; i++)
|
for (i = 0; i < mx; i++)
|
||||||
storage[i] = sk_EX_CALLBACK_value(ip->meth, i);
|
storage[i] = sk_EX_CALLBACK_value(ip->meth, i);
|
||||||
}
|
}
|
||||||
CRYPTO_THREAD_unlock(ex_data_lock);
|
CRYPTO_THREAD_unlock(global->ex_data_lock);
|
||||||
|
|
||||||
for (i = 0; i < mx; i++) {
|
for (i = 0; i < mx; i++) {
|
||||||
if (storage != NULL)
|
if (storage != NULL)
|
||||||
f = storage[i];
|
f = storage[i];
|
||||||
else {
|
else {
|
||||||
CRYPTO_THREAD_write_lock(ex_data_lock);
|
CRYPTO_THREAD_write_lock(global->ex_data_lock);
|
||||||
f = sk_EX_CALLBACK_value(ip->meth, i);
|
f = sk_EX_CALLBACK_value(ip->meth, i);
|
||||||
CRYPTO_THREAD_unlock(ex_data_lock);
|
CRYPTO_THREAD_unlock(global->ex_data_lock);
|
||||||
}
|
}
|
||||||
if (f != NULL && f->free_func != NULL) {
|
if (f != NULL && f->free_func != NULL) {
|
||||||
ptr = CRYPTO_get_ex_data(ad, i);
|
ptr = CRYPTO_get_ex_data(ad, i);
|
||||||
@@ -360,6 +384,7 @@ void CRYPTO_free_ex_data(int class_index, void *obj, CRYPTO_EX_DATA *ad)
|
|||||||
err:
|
err:
|
||||||
sk_void_free(ad->sk);
|
sk_void_free(ad->sk);
|
||||||
ad->sk = NULL;
|
ad->sk = NULL;
|
||||||
|
ad->ctx = NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
@@ -372,6 +397,10 @@ int CRYPTO_alloc_ex_data(int class_index, void *obj, CRYPTO_EX_DATA *ad,
|
|||||||
EX_CALLBACK *f;
|
EX_CALLBACK *f;
|
||||||
EX_CALLBACKS *ip;
|
EX_CALLBACKS *ip;
|
||||||
void *curval;
|
void *curval;
|
||||||
|
OSSL_EX_DATA_GLOBAL *global = openssl_ctx_get_ex_data_global(ad->ctx);
|
||||||
|
|
||||||
|
if (global == NULL)
|
||||||
|
return 0;
|
||||||
|
|
||||||
curval = CRYPTO_get_ex_data(ad, idx);
|
curval = CRYPTO_get_ex_data(ad, idx);
|
||||||
|
|
||||||
@@ -379,11 +408,11 @@ int CRYPTO_alloc_ex_data(int class_index, void *obj, CRYPTO_EX_DATA *ad,
|
|||||||
if (curval != NULL)
|
if (curval != NULL)
|
||||||
return 1;
|
return 1;
|
||||||
|
|
||||||
ip = get_and_lock(class_index);
|
ip = get_and_lock(ad->ctx, class_index);
|
||||||
if (ip == NULL)
|
if (ip == NULL)
|
||||||
return 0;
|
return 0;
|
||||||
f = sk_EX_CALLBACK_value(ip->meth, idx);
|
f = sk_EX_CALLBACK_value(ip->meth, idx);
|
||||||
CRYPTO_THREAD_unlock(ex_data_lock);
|
CRYPTO_THREAD_unlock(global->ex_data_lock);
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* This should end up calling CRYPTO_set_ex_data(), which allocates
|
* This should end up calling CRYPTO_set_ex_data(), which allocates
|
||||||
@@ -432,3 +461,8 @@ void *CRYPTO_get_ex_data(const CRYPTO_EX_DATA *ad, int idx)
|
|||||||
return NULL;
|
return NULL;
|
||||||
return sk_void_value(ad->sk, idx);
|
return sk_void_value(ad->sk, idx);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
OPENSSL_CTX *crypto_ex_data_get_openssl_ctx(const CRYPTO_EX_DATA *ad)
|
||||||
|
{
|
||||||
|
return ad->ctx;
|
||||||
|
}
|
||||||
@@ -151,10 +151,11 @@ const EVP_MD *evp_keccak_kmac256(void);
|
|||||||
* object database.
|
* object database.
|
||||||
*/
|
*/
|
||||||
int EVP_add_mac(const EVP_MAC *mac);
|
int EVP_add_mac(const EVP_MAC *mac);
|
||||||
|
int EVP_add_kdf(const EVP_KDF *kdf);
|
||||||
|
|
||||||
/* struct evp_kdf_impl_st is defined by the implementation */
|
/* struct evp_kdf_impl_st is defined by the implementation */
|
||||||
typedef struct evp_kdf_impl_st EVP_KDF_IMPL;
|
typedef struct evp_kdf_impl_st EVP_KDF_IMPL;
|
||||||
typedef struct {
|
struct evp_kdf_st {
|
||||||
int type;
|
int type;
|
||||||
EVP_KDF_IMPL *(*new) (void);
|
EVP_KDF_IMPL *(*new) (void);
|
||||||
void (*free) (EVP_KDF_IMPL *impl);
|
void (*free) (EVP_KDF_IMPL *impl);
|
||||||
@@ -163,14 +164,15 @@ typedef struct {
|
|||||||
int (*ctrl_str) (EVP_KDF_IMPL *impl, const char *type, const char *value);
|
int (*ctrl_str) (EVP_KDF_IMPL *impl, const char *type, const char *value);
|
||||||
size_t (*size) (EVP_KDF_IMPL *impl);
|
size_t (*size) (EVP_KDF_IMPL *impl);
|
||||||
int (*derive) (EVP_KDF_IMPL *impl, unsigned char *key, size_t keylen);
|
int (*derive) (EVP_KDF_IMPL *impl, unsigned char *key, size_t keylen);
|
||||||
} EVP_KDF_METHOD;
|
};
|
||||||
|
|
||||||
extern const EVP_KDF_METHOD pbkdf2_kdf_meth;
|
extern const EVP_KDF pbkdf2_kdf_meth;
|
||||||
extern const EVP_KDF_METHOD scrypt_kdf_meth;
|
extern const EVP_KDF scrypt_kdf_meth;
|
||||||
extern const EVP_KDF_METHOD tls1_prf_kdf_meth;
|
extern const EVP_KDF tls1_prf_kdf_meth;
|
||||||
extern const EVP_KDF_METHOD hkdf_kdf_meth;
|
extern const EVP_KDF hkdf_kdf_meth;
|
||||||
extern const EVP_KDF_METHOD sshkdf_kdf_meth;
|
extern const EVP_KDF sshkdf_kdf_meth;
|
||||||
extern const EVP_KDF_METHOD ss_kdf_meth;
|
extern const EVP_KDF ss_kdf_meth;
|
||||||
|
extern const EVP_KDF x963_kdf_meth;
|
||||||
|
|
||||||
struct evp_md_st {
|
struct evp_md_st {
|
||||||
/* nid */
|
/* nid */
|
||||||
@@ -528,6 +530,7 @@ struct evp_pkey_st {
|
|||||||
void openssl_add_all_ciphers_int(void);
|
void openssl_add_all_ciphers_int(void);
|
||||||
void openssl_add_all_digests_int(void);
|
void openssl_add_all_digests_int(void);
|
||||||
void openssl_add_all_macs_int(void);
|
void openssl_add_all_macs_int(void);
|
||||||
|
void openssl_add_all_kdfs_int(void);
|
||||||
void evp_cleanup_int(void);
|
void evp_cleanup_int(void);
|
||||||
void evp_app_cleanup_int(void);
|
void evp_app_cleanup_int(void);
|
||||||
|
|
||||||
|
|||||||
+43
-3
@@ -293,6 +293,26 @@ DEFINE_RUN_ONCE_STATIC_ALT(ossl_init_no_add_all_macs, ossl_init_add_all_macs)
|
|||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static CRYPTO_ONCE add_all_kdfs = CRYPTO_ONCE_STATIC_INIT;
|
||||||
|
DEFINE_RUN_ONCE_STATIC(ossl_init_add_all_kdfs)
|
||||||
|
{
|
||||||
|
/*
|
||||||
|
* OPENSSL_NO_AUTOALGINIT is provided here to prevent at compile time
|
||||||
|
* pulling in all the macs during static linking
|
||||||
|
*/
|
||||||
|
#ifndef OPENSSL_NO_AUTOALGINIT
|
||||||
|
OSSL_TRACE(INIT, "openssl_add_all_kdfs_int()\n");
|
||||||
|
openssl_add_all_kdfs_int();
|
||||||
|
#endif
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
DEFINE_RUN_ONCE_STATIC_ALT(ossl_init_no_add_all_kdfs, ossl_init_add_all_kdfs)
|
||||||
|
{
|
||||||
|
/* Do nothing */
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
|
||||||
static CRYPTO_ONCE config = CRYPTO_ONCE_STATIC_INIT;
|
static CRYPTO_ONCE config = CRYPTO_ONCE_STATIC_INIT;
|
||||||
static int config_inited = 0;
|
static int config_inited = 0;
|
||||||
static const OPENSSL_INIT_SETTINGS *conf_settings = NULL;
|
static const OPENSSL_INIT_SETTINGS *conf_settings = NULL;
|
||||||
@@ -468,6 +488,11 @@ void OPENSSL_cleanup(void)
|
|||||||
OPENSSL_INIT_STOP *currhandler, *lasthandler;
|
OPENSSL_INIT_STOP *currhandler, *lasthandler;
|
||||||
CRYPTO_THREAD_LOCAL key;
|
CRYPTO_THREAD_LOCAL key;
|
||||||
|
|
||||||
|
/*
|
||||||
|
* TODO(3.0): This function needs looking at with a view to moving most/all
|
||||||
|
* of this into onfree handlers in OPENSSL_CTX.
|
||||||
|
*/
|
||||||
|
|
||||||
/* If we've not been inited then no need to deinit */
|
/* If we've not been inited then no need to deinit */
|
||||||
if (!base_inited)
|
if (!base_inited)
|
||||||
return;
|
return;
|
||||||
@@ -526,7 +551,7 @@ void OPENSSL_cleanup(void)
|
|||||||
* - rand_cleanup_int could call an ENGINE's RAND cleanup function so
|
* - rand_cleanup_int could call an ENGINE's RAND cleanup function so
|
||||||
* must be called before engine_cleanup_int()
|
* must be called before engine_cleanup_int()
|
||||||
* - ENGINEs use CRYPTO_EX_DATA and therefore, must be cleaned up
|
* - ENGINEs use CRYPTO_EX_DATA and therefore, must be cleaned up
|
||||||
* before the ex data handlers are wiped in CRYPTO_cleanup_all_ex_data().
|
* before the ex data handlers are wiped during default openssl_ctx deinit.
|
||||||
* - conf_modules_free_int() can end up in ENGINE code so must be called
|
* - conf_modules_free_int() can end up in ENGINE code so must be called
|
||||||
* before engine_cleanup_int()
|
* before engine_cleanup_int()
|
||||||
* - ENGINEs and additional EVP algorithms might use added OIDs names so
|
* - ENGINEs and additional EVP algorithms might use added OIDs names so
|
||||||
@@ -540,6 +565,7 @@ void OPENSSL_cleanup(void)
|
|||||||
|
|
||||||
OSSL_TRACE(INIT, "OPENSSL_cleanup: conf_modules_free_int()\n");
|
OSSL_TRACE(INIT, "OPENSSL_cleanup: conf_modules_free_int()\n");
|
||||||
conf_modules_free_int();
|
conf_modules_free_int();
|
||||||
|
|
||||||
#ifndef OPENSSL_NO_ENGINE
|
#ifndef OPENSSL_NO_ENGINE
|
||||||
OSSL_TRACE(INIT, "OPENSSL_cleanup: engine_cleanup_int()\n");
|
OSSL_TRACE(INIT, "OPENSSL_cleanup: engine_cleanup_int()\n");
|
||||||
engine_cleanup_int();
|
engine_cleanup_int();
|
||||||
@@ -547,8 +573,8 @@ void OPENSSL_cleanup(void)
|
|||||||
OSSL_TRACE(INIT, "OPENSSL_cleanup: ossl_store_cleanup_int()\n");
|
OSSL_TRACE(INIT, "OPENSSL_cleanup: ossl_store_cleanup_int()\n");
|
||||||
ossl_store_cleanup_int();
|
ossl_store_cleanup_int();
|
||||||
|
|
||||||
OSSL_TRACE(INIT, "OPENSSL_cleanup: crypto_cleanup_all_ex_data_int()\n");
|
OSSL_TRACE(INIT, "OPENSSL_cleanup: openssl_ctx_default_deinit()\n");
|
||||||
crypto_cleanup_all_ex_data_int();
|
openssl_ctx_default_deinit();
|
||||||
|
|
||||||
OSSL_TRACE(INIT, "OPENSSL_cleanup: bio_cleanup()\n");
|
OSSL_TRACE(INIT, "OPENSSL_cleanup: bio_cleanup()\n");
|
||||||
bio_cleanup();
|
bio_cleanup();
|
||||||
@@ -578,6 +604,11 @@ void OPENSSL_cleanup(void)
|
|||||||
*/
|
*/
|
||||||
int OPENSSL_init_crypto(uint64_t opts, const OPENSSL_INIT_SETTINGS *settings)
|
int OPENSSL_init_crypto(uint64_t opts, const OPENSSL_INIT_SETTINGS *settings)
|
||||||
{
|
{
|
||||||
|
/*
|
||||||
|
* TODO(3.0): This function needs looking at with a view to moving most/all
|
||||||
|
* of this into OPENSSL_CTX.
|
||||||
|
*/
|
||||||
|
|
||||||
if (stopped) {
|
if (stopped) {
|
||||||
if (!(opts & OPENSSL_INIT_BASE_ONLY))
|
if (!(opts & OPENSSL_INIT_BASE_ONLY))
|
||||||
CRYPTOerr(CRYPTO_F_OPENSSL_INIT_CRYPTO, ERR_R_INIT_FAIL);
|
CRYPTOerr(CRYPTO_F_OPENSSL_INIT_CRYPTO, ERR_R_INIT_FAIL);
|
||||||
@@ -655,6 +686,15 @@ int OPENSSL_init_crypto(uint64_t opts, const OPENSSL_INIT_SETTINGS *settings)
|
|||||||
&& !RUN_ONCE(&add_all_macs, ossl_init_add_all_macs))
|
&& !RUN_ONCE(&add_all_macs, ossl_init_add_all_macs))
|
||||||
return 0;
|
return 0;
|
||||||
|
|
||||||
|
if ((opts & OPENSSL_INIT_NO_ADD_ALL_KDFS)
|
||||||
|
&& !RUN_ONCE_ALT(&add_all_kdfs, ossl_init_no_add_all_kdfs,
|
||||||
|
ossl_init_add_all_kdfs))
|
||||||
|
return 0;
|
||||||
|
|
||||||
|
if ((opts & OPENSSL_INIT_ADD_ALL_KDFS)
|
||||||
|
&& !RUN_ONCE(&add_all_kdfs, ossl_init_add_all_kdfs))
|
||||||
|
return 0;
|
||||||
|
|
||||||
if ((opts & OPENSSL_INIT_ATFORK)
|
if ((opts & OPENSSL_INIT_ATFORK)
|
||||||
&& !openssl_init_fork_handlers())
|
&& !openssl_init_fork_handlers())
|
||||||
return 0;
|
return 0;
|
||||||
|
|||||||
+1
-1
@@ -229,7 +229,7 @@ static int kdf_hkdf_derive(EVP_KDF_IMPL *impl, unsigned char *key,
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
const EVP_KDF_METHOD hkdf_kdf_meth = {
|
const EVP_KDF hkdf_kdf_meth = {
|
||||||
EVP_KDF_HKDF,
|
EVP_KDF_HKDF,
|
||||||
kdf_hkdf_new,
|
kdf_hkdf_new,
|
||||||
kdf_hkdf_free,
|
kdf_hkdf_free,
|
||||||
|
|||||||
@@ -65,6 +65,7 @@ static const ERR_STRING_DATA KDF_str_functs[] = {
|
|||||||
{ERR_PACK(ERR_LIB_KDF, KDF_F_SSKDF_NEW, 0), "sskdf_new"},
|
{ERR_PACK(ERR_LIB_KDF, KDF_F_SSKDF_NEW, 0), "sskdf_new"},
|
||||||
{ERR_PACK(ERR_LIB_KDF, KDF_F_SSKDF_SIZE, 0), "sskdf_size"},
|
{ERR_PACK(ERR_LIB_KDF, KDF_F_SSKDF_SIZE, 0), "sskdf_size"},
|
||||||
{ERR_PACK(ERR_LIB_KDF, KDF_F_TLS1_PRF_ALG, 0), "tls1_prf_alg"},
|
{ERR_PACK(ERR_LIB_KDF, KDF_F_TLS1_PRF_ALG, 0), "tls1_prf_alg"},
|
||||||
|
{ERR_PACK(ERR_LIB_KDF, KDF_F_X963KDF_DERIVE, 0), "x963kdf_derive"},
|
||||||
{0, NULL}
|
{0, NULL}
|
||||||
};
|
};
|
||||||
|
|
||||||
@@ -84,6 +85,7 @@ static const ERR_STRING_DATA KDF_str_reasons[] = {
|
|||||||
{ERR_PACK(ERR_LIB_KDF, 0, KDF_R_MISSING_SESSION_ID), "missing session id"},
|
{ERR_PACK(ERR_LIB_KDF, 0, KDF_R_MISSING_SESSION_ID), "missing session id"},
|
||||||
{ERR_PACK(ERR_LIB_KDF, 0, KDF_R_MISSING_TYPE), "missing type"},
|
{ERR_PACK(ERR_LIB_KDF, 0, KDF_R_MISSING_TYPE), "missing type"},
|
||||||
{ERR_PACK(ERR_LIB_KDF, 0, KDF_R_MISSING_XCGHASH), "missing xcghash"},
|
{ERR_PACK(ERR_LIB_KDF, 0, KDF_R_MISSING_XCGHASH), "missing xcghash"},
|
||||||
|
{ERR_PACK(ERR_LIB_KDF, 0, KDF_R_NOT_SUPPORTED), "not supported"},
|
||||||
{ERR_PACK(ERR_LIB_KDF, 0, KDF_R_UNKNOWN_PARAMETER_TYPE),
|
{ERR_PACK(ERR_LIB_KDF, 0, KDF_R_UNKNOWN_PARAMETER_TYPE),
|
||||||
"unknown parameter type"},
|
"unknown parameter type"},
|
||||||
{ERR_PACK(ERR_LIB_KDF, 0, KDF_R_UNSUPPORTED_MAC_TYPE),
|
{ERR_PACK(ERR_LIB_KDF, 0, KDF_R_UNSUPPORTED_MAC_TYPE),
|
||||||
|
|||||||
+1
-1
@@ -180,7 +180,7 @@ static int kdf_pbkdf2_derive(EVP_KDF_IMPL *impl, unsigned char *key,
|
|||||||
impl->md, key, keylen);
|
impl->md, key, keylen);
|
||||||
}
|
}
|
||||||
|
|
||||||
const EVP_KDF_METHOD pbkdf2_kdf_meth = {
|
const EVP_KDF pbkdf2_kdf_meth = {
|
||||||
EVP_KDF_PBKDF2,
|
EVP_KDF_PBKDF2,
|
||||||
kdf_pbkdf2_new,
|
kdf_pbkdf2_new,
|
||||||
kdf_pbkdf2_free,
|
kdf_pbkdf2_free,
|
||||||
|
|||||||
+1
-1
@@ -266,7 +266,7 @@ static int kdf_scrypt_derive(EVP_KDF_IMPL *impl, unsigned char *key,
|
|||||||
impl->maxmem_bytes, key, keylen);
|
impl->maxmem_bytes, key, keylen);
|
||||||
}
|
}
|
||||||
|
|
||||||
const EVP_KDF_METHOD scrypt_kdf_meth = {
|
const EVP_KDF scrypt_kdf_meth = {
|
||||||
EVP_KDF_SCRYPT,
|
EVP_KDF_SCRYPT,
|
||||||
kdf_scrypt_new,
|
kdf_scrypt_new,
|
||||||
kdf_scrypt_free,
|
kdf_scrypt_free,
|
||||||
|
|||||||
+4
-1
@@ -125,6 +125,9 @@ static int kdf_sshkdf_ctrl_str(EVP_KDF_IMPL *impl, const char *type,
|
|||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (strcmp(type, "digest") == 0)
|
||||||
|
return kdf_md2ctrl(impl, kdf_sshkdf_ctrl, EVP_KDF_CTRL_SET_MD, value);
|
||||||
|
/* alias, for historical reasons */
|
||||||
if (strcmp(type, "md") == 0)
|
if (strcmp(type, "md") == 0)
|
||||||
return kdf_md2ctrl(impl, kdf_sshkdf_ctrl, EVP_KDF_CTRL_SET_MD, value);
|
return kdf_md2ctrl(impl, kdf_sshkdf_ctrl, EVP_KDF_CTRL_SET_MD, value);
|
||||||
|
|
||||||
@@ -200,7 +203,7 @@ static int kdf_sshkdf_derive(EVP_KDF_IMPL *impl, unsigned char *key,
|
|||||||
impl->type, key, keylen);
|
impl->type, key, keylen);
|
||||||
}
|
}
|
||||||
|
|
||||||
const EVP_KDF_METHOD sshkdf_kdf_meth = {
|
const EVP_KDF sshkdf_kdf_meth = {
|
||||||
EVP_KDF_SSHKDF,
|
EVP_KDF_SSHKDF,
|
||||||
kdf_sshkdf_new,
|
kdf_sshkdf_new,
|
||||||
kdf_sshkdf_free,
|
kdf_sshkdf_free,
|
||||||
|
|||||||
+42
-3
@@ -66,10 +66,16 @@ static const unsigned char kmac_custom_str[] = { 0x4B, 0x44, 0x46 };
|
|||||||
/*
|
/*
|
||||||
* Refer to https://csrc.nist.gov/publications/detail/sp/800-56c/rev-1/final
|
* Refer to https://csrc.nist.gov/publications/detail/sp/800-56c/rev-1/final
|
||||||
* Section 4. One-Step Key Derivation using H(x) = hash(x)
|
* Section 4. One-Step Key Derivation using H(x) = hash(x)
|
||||||
|
* Note: X9.63 also uses this code with the only difference being that the
|
||||||
|
* counter is appended to the secret 'z'.
|
||||||
|
* i.e.
|
||||||
|
* result[i] = Hash(counter || z || info) for One Step OR
|
||||||
|
* result[i] = Hash(z || counter || info) for X9.63.
|
||||||
*/
|
*/
|
||||||
static int SSKDF_hash_kdm(const EVP_MD *kdf_md,
|
static int SSKDF_hash_kdm(const EVP_MD *kdf_md,
|
||||||
const unsigned char *z, size_t z_len,
|
const unsigned char *z, size_t z_len,
|
||||||
const unsigned char *info, size_t info_len,
|
const unsigned char *info, size_t info_len,
|
||||||
|
unsigned int append_ctr,
|
||||||
unsigned char *derived_key, size_t derived_key_len)
|
unsigned char *derived_key, size_t derived_key_len)
|
||||||
{
|
{
|
||||||
int ret = 0, hlen;
|
int ret = 0, hlen;
|
||||||
@@ -104,8 +110,9 @@ static int SSKDF_hash_kdm(const EVP_MD *kdf_md,
|
|||||||
c[3] = (unsigned char)(counter & 0xff);
|
c[3] = (unsigned char)(counter & 0xff);
|
||||||
|
|
||||||
if (!(EVP_MD_CTX_copy_ex(ctx, ctx_init)
|
if (!(EVP_MD_CTX_copy_ex(ctx, ctx_init)
|
||||||
&& EVP_DigestUpdate(ctx, c, sizeof(c))
|
&& (append_ctr || EVP_DigestUpdate(ctx, c, sizeof(c)))
|
||||||
&& EVP_DigestUpdate(ctx, z, z_len)
|
&& EVP_DigestUpdate(ctx, z, z_len)
|
||||||
|
&& (!append_ctr || EVP_DigestUpdate(ctx, c, sizeof(c)))
|
||||||
&& EVP_DigestUpdate(ctx, info, info_len)))
|
&& EVP_DigestUpdate(ctx, info, info_len)))
|
||||||
goto end;
|
goto end;
|
||||||
if (len >= out_len) {
|
if (len >= out_len) {
|
||||||
@@ -468,11 +475,32 @@ static int sskdf_derive(EVP_KDF_IMPL *impl, unsigned char *key, size_t keylen)
|
|||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
return SSKDF_hash_kdm(impl->md, impl->secret, impl->secret_len,
|
return SSKDF_hash_kdm(impl->md, impl->secret, impl->secret_len,
|
||||||
impl->info, impl->info_len, key, keylen);
|
impl->info, impl->info_len, 0, key, keylen);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
const EVP_KDF_METHOD ss_kdf_meth = {
|
static int x963kdf_derive(EVP_KDF_IMPL *impl, unsigned char *key, size_t keylen)
|
||||||
|
{
|
||||||
|
if (impl->secret == NULL) {
|
||||||
|
KDFerr(KDF_F_X963KDF_DERIVE, KDF_R_MISSING_SECRET);
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (impl->mac != NULL) {
|
||||||
|
KDFerr(KDF_F_X963KDF_DERIVE, KDF_R_NOT_SUPPORTED);
|
||||||
|
return 0;
|
||||||
|
} else {
|
||||||
|
/* H(x) = hash */
|
||||||
|
if (impl->md == NULL) {
|
||||||
|
KDFerr(KDF_F_X963KDF_DERIVE, KDF_R_MISSING_MESSAGE_DIGEST);
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
return SSKDF_hash_kdm(impl->md, impl->secret, impl->secret_len,
|
||||||
|
impl->info, impl->info_len, 1, key, keylen);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
const EVP_KDF ss_kdf_meth = {
|
||||||
EVP_KDF_SS,
|
EVP_KDF_SS,
|
||||||
sskdf_new,
|
sskdf_new,
|
||||||
sskdf_free,
|
sskdf_free,
|
||||||
@@ -482,3 +510,14 @@ const EVP_KDF_METHOD ss_kdf_meth = {
|
|||||||
sskdf_size,
|
sskdf_size,
|
||||||
sskdf_derive
|
sskdf_derive
|
||||||
};
|
};
|
||||||
|
|
||||||
|
const EVP_KDF x963_kdf_meth = {
|
||||||
|
EVP_KDF_X963,
|
||||||
|
sskdf_new,
|
||||||
|
sskdf_free,
|
||||||
|
sskdf_reset,
|
||||||
|
sskdf_ctrl,
|
||||||
|
sskdf_ctrl_str,
|
||||||
|
sskdf_size,
|
||||||
|
x963kdf_derive
|
||||||
|
};
|
||||||
@@ -157,7 +157,7 @@ static int kdf_tls1_prf_derive(EVP_KDF_IMPL *impl, unsigned char *key,
|
|||||||
key, keylen);
|
key, keylen);
|
||||||
}
|
}
|
||||||
|
|
||||||
const EVP_KDF_METHOD tls1_prf_kdf_meth = {
|
const EVP_KDF tls1_prf_kdf_meth = {
|
||||||
EVP_KDF_TLS1_PRF,
|
EVP_KDF_TLS1_PRF,
|
||||||
kdf_tls1_prf_new,
|
kdf_tls1_prf_new,
|
||||||
kdf_tls1_prf_free,
|
kdf_tls1_prf_free,
|
||||||
|
|||||||
+1
-1
@@ -33,8 +33,8 @@
|
|||||||
# include <linux/mman.h>
|
# include <linux/mman.h>
|
||||||
# include <errno.h>
|
# include <errno.h>
|
||||||
# endif
|
# endif
|
||||||
|
# include <sys/param.h>
|
||||||
# endif
|
# endif
|
||||||
# include <sys/param.h>
|
|
||||||
# include <sys/stat.h>
|
# include <sys/stat.h>
|
||||||
# include <fcntl.h>
|
# include <fcntl.h>
|
||||||
#endif
|
#endif
|
||||||
|
|||||||
@@ -585,52 +585,32 @@ const void *OBJ_bsearch_(const void *key, const void *base, int num, int size,
|
|||||||
return OBJ_bsearch_ex_(key, base, num, size, cmp, 0);
|
return OBJ_bsearch_ex_(key, base, num, size, cmp, 0);
|
||||||
}
|
}
|
||||||
|
|
||||||
const void *OBJ_bsearch_ex_(const void *key, const void *base_, int num,
|
const void *OBJ_bsearch_ex_(const void *key, const void *base, int num,
|
||||||
int size,
|
int size,
|
||||||
int (*cmp) (const void *, const void *),
|
int (*cmp) (const void *, const void *),
|
||||||
int flags)
|
int flags)
|
||||||
{
|
{
|
||||||
const char *base = base_;
|
const char *p = ossl_bsearch(key, base, num, size, cmp, flags);
|
||||||
int l, h, i = 0, c = 0;
|
|
||||||
const char *p = NULL;
|
|
||||||
|
|
||||||
if (num == 0)
|
|
||||||
return NULL;
|
|
||||||
l = 0;
|
|
||||||
h = num;
|
|
||||||
while (l < h) {
|
|
||||||
i = (l + h) / 2;
|
|
||||||
p = &(base[i * size]);
|
|
||||||
c = (*cmp) (key, p);
|
|
||||||
if (c < 0)
|
|
||||||
h = i;
|
|
||||||
else if (c > 0)
|
|
||||||
l = i + 1;
|
|
||||||
else
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
#ifdef CHARSET_EBCDIC
|
#ifdef CHARSET_EBCDIC
|
||||||
/*
|
/*
|
||||||
* THIS IS A KLUDGE - Because the *_obj is sorted in ASCII order, and I
|
* THIS IS A KLUDGE - Because the *_obj is sorted in ASCII order, and I
|
||||||
* don't have perl (yet), we revert to a *LINEAR* search when the object
|
* don't have perl (yet), we revert to a *LINEAR* search when the object
|
||||||
* wasn't found in the binary search.
|
* wasn't found in the binary search.
|
||||||
*/
|
*/
|
||||||
if (c != 0) {
|
if (p == NULL) {
|
||||||
|
const char *base_ = base;
|
||||||
|
int l, h, i = 0, c = 0;
|
||||||
|
|
||||||
for (i = 0; i < num; ++i) {
|
for (i = 0; i < num; ++i) {
|
||||||
p = &(base[i * size]);
|
p = &(base_[i * size]);
|
||||||
c = (*cmp) (key, p);
|
c = (*cmp) (key, p);
|
||||||
if (c == 0 || (c < 0 && (flags & OBJ_BSEARCH_VALUE_ON_NOMATCH)))
|
if (c == 0
|
||||||
|
|| (c < 0 && (flags & OBJ_BSEARCH_VALUE_ON_NOMATCH)))
|
||||||
return p;
|
return p;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
if (c != 0 && !(flags & OBJ_BSEARCH_VALUE_ON_NOMATCH))
|
|
||||||
p = NULL;
|
|
||||||
else if (c == 0 && (flags & OBJ_BSEARCH_FIRST_VALUE_ON_MATCH)) {
|
|
||||||
while (i > 0 && (*cmp) (key, &(base[(i - 1) * size])) == 0)
|
|
||||||
i--;
|
|
||||||
p = &(base[i * size]);
|
|
||||||
}
|
|
||||||
return p;
|
return p;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -1070,7 +1070,7 @@ static const unsigned char so[7775] = {
|
|||||||
0x2A,0x85,0x03,0x07,0x01,0x01,0x07,0x01, /* [ 7684] OBJ_id_tc26_wrap_gostr3412_2015_magma */
|
0x2A,0x85,0x03,0x07,0x01,0x01,0x07,0x01, /* [ 7684] OBJ_id_tc26_wrap_gostr3412_2015_magma */
|
||||||
0x2A,0x85,0x03,0x07,0x01,0x01,0x07,0x01,0x01, /* [ 7692] OBJ_id_tc26_wrap_gostr3412_2015_magma_kexp15 */
|
0x2A,0x85,0x03,0x07,0x01,0x01,0x07,0x01,0x01, /* [ 7692] OBJ_id_tc26_wrap_gostr3412_2015_magma_kexp15 */
|
||||||
0x2A,0x85,0x03,0x07,0x01,0x01,0x07,0x02, /* [ 7701] OBJ_id_tc26_wrap_gostr3412_2015_kuznyechik */
|
0x2A,0x85,0x03,0x07,0x01,0x01,0x07,0x02, /* [ 7701] OBJ_id_tc26_wrap_gostr3412_2015_kuznyechik */
|
||||||
0x2A,0x85,0x03,0x07,0x01,0x01,0x07,0x01,0x01, /* [ 7709] OBJ_id_tc26_wrap_gostr3412_2015_kuznyechik_kexp15 */
|
0x2A,0x85,0x03,0x07,0x01,0x01,0x07,0x02,0x01, /* [ 7709] OBJ_id_tc26_wrap_gostr3412_2015_kuznyechik_kexp15 */
|
||||||
0x2A,0x85,0x03,0x07,0x01,0x02,0x01,0x01,0x02, /* [ 7718] OBJ_id_tc26_gost_3410_2012_256_paramSetB */
|
0x2A,0x85,0x03,0x07,0x01,0x02,0x01,0x01,0x02, /* [ 7718] OBJ_id_tc26_gost_3410_2012_256_paramSetB */
|
||||||
0x2A,0x85,0x03,0x07,0x01,0x02,0x01,0x01,0x03, /* [ 7727] OBJ_id_tc26_gost_3410_2012_256_paramSetC */
|
0x2A,0x85,0x03,0x07,0x01,0x02,0x01,0x01,0x03, /* [ 7727] OBJ_id_tc26_gost_3410_2012_256_paramSetC */
|
||||||
0x2A,0x85,0x03,0x07,0x01,0x02,0x01,0x01,0x04, /* [ 7736] OBJ_id_tc26_gost_3410_2012_256_paramSetD */
|
0x2A,0x85,0x03,0x07,0x01,0x02,0x01,0x01,0x04, /* [ 7736] OBJ_id_tc26_gost_3410_2012_256_paramSetD */
|
||||||
@@ -1080,7 +1080,7 @@ static const unsigned char so[7775] = {
|
|||||||
0x2A,0x81,0x1C,0xCF,0x55,0x01,0x83,0x75, /* [ 7766] OBJ_SM2_with_SM3 */
|
0x2A,0x81,0x1C,0xCF,0x55,0x01,0x83,0x75, /* [ 7766] OBJ_SM2_with_SM3 */
|
||||||
};
|
};
|
||||||
|
|
||||||
#define NUM_NID 1207
|
#define NUM_NID 1208
|
||||||
static const ASN1_OBJECT nid_objs[NUM_NID] = {
|
static const ASN1_OBJECT nid_objs[NUM_NID] = {
|
||||||
{"UNDEF", "undefined", NID_undef},
|
{"UNDEF", "undefined", NID_undef},
|
||||||
{"rsadsi", "RSA Data Security, Inc.", NID_rsadsi, 6, &so[0]},
|
{"rsadsi", "RSA Data Security, Inc.", NID_rsadsi, 6, &so[0]},
|
||||||
@@ -2288,10 +2288,11 @@ static const ASN1_OBJECT nid_objs[NUM_NID] = {
|
|||||||
{"SSHKDF", "sshkdf", NID_sshkdf},
|
{"SSHKDF", "sshkdf", NID_sshkdf},
|
||||||
{"SM2-SM3", "SM2-with-SM3", NID_SM2_with_SM3, 8, &so[7766]},
|
{"SM2-SM3", "SM2-with-SM3", NID_SM2_with_SM3, 8, &so[7766]},
|
||||||
{"SSKDF", "sskdf", NID_sskdf},
|
{"SSKDF", "sskdf", NID_sskdf},
|
||||||
|
{"X963KDF", "x963kdf", NID_x963kdf},
|
||||||
{"ChaCha20-Poly1305-D", "chacha20-poly1305-draft", NID_chacha20_poly1305_draft},
|
{"ChaCha20-Poly1305-D", "chacha20-poly1305-draft", NID_chacha20_poly1305_draft},
|
||||||
};
|
};
|
||||||
|
|
||||||
#define NUM_SN 1198
|
#define NUM_SN 1199
|
||||||
static const unsigned int sn_objs[NUM_SN] = {
|
static const unsigned int sn_objs[NUM_SN] = {
|
||||||
364, /* "AD_DVCS" */
|
364, /* "AD_DVCS" */
|
||||||
419, /* "AES-128-CBC" */
|
419, /* "AES-128-CBC" */
|
||||||
@@ -2414,7 +2415,7 @@ static const unsigned int sn_objs[NUM_SN] = {
|
|||||||
417, /* "CSPName" */
|
417, /* "CSPName" */
|
||||||
1019, /* "ChaCha20" */
|
1019, /* "ChaCha20" */
|
||||||
1018, /* "ChaCha20-Poly1305" */
|
1018, /* "ChaCha20-Poly1305" */
|
||||||
1206, /* "ChaCha20-Poly1305-D" */
|
1207, /* "ChaCha20-Poly1305-D" */
|
||||||
367, /* "CrlID" */
|
367, /* "CrlID" */
|
||||||
391, /* "DC" */
|
391, /* "DC" */
|
||||||
31, /* "DES-CBC" */
|
31, /* "DES-CBC" */
|
||||||
@@ -2593,6 +2594,7 @@ static const unsigned int sn_objs[NUM_SN] = {
|
|||||||
378, /* "X500algorithms" */
|
378, /* "X500algorithms" */
|
||||||
12, /* "X509" */
|
12, /* "X509" */
|
||||||
184, /* "X9-57" */
|
184, /* "X9-57" */
|
||||||
|
1206, /* "X963KDF" */
|
||||||
185, /* "X9cm" */
|
185, /* "X9cm" */
|
||||||
125, /* "ZLIB" */
|
125, /* "ZLIB" */
|
||||||
478, /* "aRecord" */
|
478, /* "aRecord" */
|
||||||
@@ -3493,7 +3495,7 @@ static const unsigned int sn_objs[NUM_SN] = {
|
|||||||
1093, /* "x509ExtAdmission" */
|
1093, /* "x509ExtAdmission" */
|
||||||
};
|
};
|
||||||
|
|
||||||
#define NUM_LN 1198
|
#define NUM_LN 1199
|
||||||
static const unsigned int ln_objs[NUM_LN] = {
|
static const unsigned int ln_objs[NUM_LN] = {
|
||||||
363, /* "AD Time Stamping" */
|
363, /* "AD Time Stamping" */
|
||||||
405, /* "ANSI X9.62" */
|
405, /* "ANSI X9.62" */
|
||||||
@@ -3878,7 +3880,7 @@ static const unsigned int ln_objs[NUM_LN] = {
|
|||||||
883, /* "certificateRevocationList" */
|
883, /* "certificateRevocationList" */
|
||||||
1019, /* "chacha20" */
|
1019, /* "chacha20" */
|
||||||
1018, /* "chacha20-poly1305" */
|
1018, /* "chacha20-poly1305" */
|
||||||
1206, /* "chacha20-poly1305-draft" */
|
1207, /* "chacha20-poly1305-draft" */
|
||||||
54, /* "challengePassword" */
|
54, /* "challengePassword" */
|
||||||
407, /* "characteristic-two-field" */
|
407, /* "characteristic-two-field" */
|
||||||
395, /* "clearance" */
|
395, /* "clearance" */
|
||||||
@@ -4692,6 +4694,7 @@ static const unsigned int ln_objs[NUM_LN] = {
|
|||||||
503, /* "x500UniqueIdentifier" */
|
503, /* "x500UniqueIdentifier" */
|
||||||
158, /* "x509Certificate" */
|
158, /* "x509Certificate" */
|
||||||
160, /* "x509Crl" */
|
160, /* "x509Crl" */
|
||||||
|
1206, /* "x963kdf" */
|
||||||
125, /* "zlib compression" */
|
125, /* "zlib compression" */
|
||||||
};
|
};
|
||||||
|
|
||||||
@@ -5404,7 +5407,7 @@ static const unsigned int obj_objs[NUM_OBJ] = {
|
|||||||
1177, /* OBJ_id_tc26_cipher_gostr3412_2015_kuznyechik_ctracpkm 1 2 643 7 1 1 5 2 1 */
|
1177, /* OBJ_id_tc26_cipher_gostr3412_2015_kuznyechik_ctracpkm 1 2 643 7 1 1 5 2 1 */
|
||||||
1178, /* OBJ_id_tc26_cipher_gostr3412_2015_kuznyechik_ctracpkm_omac 1 2 643 7 1 1 5 2 2 */
|
1178, /* OBJ_id_tc26_cipher_gostr3412_2015_kuznyechik_ctracpkm_omac 1 2 643 7 1 1 5 2 2 */
|
||||||
1181, /* OBJ_id_tc26_wrap_gostr3412_2015_magma_kexp15 1 2 643 7 1 1 7 1 1 */
|
1181, /* OBJ_id_tc26_wrap_gostr3412_2015_magma_kexp15 1 2 643 7 1 1 7 1 1 */
|
||||||
1183, /* OBJ_id_tc26_wrap_gostr3412_2015_kuznyechik_kexp15 1 2 643 7 1 1 7 1 1 */
|
1183, /* OBJ_id_tc26_wrap_gostr3412_2015_kuznyechik_kexp15 1 2 643 7 1 1 7 2 1 */
|
||||||
1148, /* OBJ_id_tc26_gost_3410_2012_256_paramSetA 1 2 643 7 1 2 1 1 1 */
|
1148, /* OBJ_id_tc26_gost_3410_2012_256_paramSetA 1 2 643 7 1 2 1 1 1 */
|
||||||
1184, /* OBJ_id_tc26_gost_3410_2012_256_paramSetB 1 2 643 7 1 2 1 1 2 */
|
1184, /* OBJ_id_tc26_gost_3410_2012_256_paramSetB 1 2 643 7 1 2 1 1 2 */
|
||||||
1185, /* OBJ_id_tc26_gost_3410_2012_256_paramSetC 1 2 643 7 1 2 1 1 3 */
|
1185, /* OBJ_id_tc26_gost_3410_2012_256_paramSetC 1 2 643 7 1 2 1 1 3 */
|
||||||
|
|||||||
@@ -1203,4 +1203,5 @@ blake2smac 1202
|
|||||||
sshkdf 1203
|
sshkdf 1203
|
||||||
SM2_with_SM3 1204
|
SM2_with_SM3 1204
|
||||||
sskdf 1205
|
sskdf 1205
|
||||||
chacha20_poly1305_draft 1206
|
x963kdf 1206
|
||||||
|
chacha20_poly1305_draft 1207
|
||||||
@@ -1369,7 +1369,7 @@ id-tc26-algorithms 7 : id-tc26-wrap
|
|||||||
id-tc26-wrap 1 : id-tc26-wrap-gostr3412-2015-magma
|
id-tc26-wrap 1 : id-tc26-wrap-gostr3412-2015-magma
|
||||||
id-tc26-wrap-gostr3412-2015-magma 1 : id-tc26-wrap-gostr3412-2015-magma-kexp15
|
id-tc26-wrap-gostr3412-2015-magma 1 : id-tc26-wrap-gostr3412-2015-magma-kexp15
|
||||||
id-tc26-wrap 2 : id-tc26-wrap-gostr3412-2015-kuznyechik
|
id-tc26-wrap 2 : id-tc26-wrap-gostr3412-2015-kuznyechik
|
||||||
id-tc26-wrap-gostr3412-2015-magma 1 : id-tc26-wrap-gostr3412-2015-kuznyechik-kexp15
|
id-tc26-wrap-gostr3412-2015-kuznyechik 1 : id-tc26-wrap-gostr3412-2015-kuznyechik-kexp15
|
||||||
|
|
||||||
id-tc26 2 : id-tc26-constants
|
id-tc26 2 : id-tc26-constants
|
||||||
|
|
||||||
@@ -1618,6 +1618,9 @@ secg-scheme 14 3 : dhSinglePass-cofactorDH-sha512kdf-scheme
|
|||||||
# NID for SSKDF
|
# NID for SSKDF
|
||||||
: SSKDF : sskdf
|
: SSKDF : sskdf
|
||||||
|
|
||||||
|
# NID for X963-2001 KDF
|
||||||
|
: X963KDF : x963kdf
|
||||||
|
|
||||||
# RFC 4556
|
# RFC 4556
|
||||||
1 3 6 1 5 2 3 : id-pkinit
|
1 3 6 1 5 2 3 : id-pkinit
|
||||||
id-pkinit 4 : pkInitClientAuth : PKINIT Client Auth
|
id-pkinit 4 : pkInitClientAuth : PKINIT Client Auth
|
||||||
|
|||||||
+393
-82
@@ -156,12 +156,54 @@ OSSL_PARAM OSSL_PARAM_construct_ulong(const char *key, unsigned long int *buf,
|
|||||||
|
|
||||||
int OSSL_PARAM_get_int32(const OSSL_PARAM *p, int32_t *val)
|
int OSSL_PARAM_get_int32(const OSSL_PARAM *p, int32_t *val)
|
||||||
{
|
{
|
||||||
if (val == NULL || p == NULL || (p->data_type != OSSL_PARAM_INTEGER))
|
int64_t i64;
|
||||||
|
uint32_t u32;
|
||||||
|
uint64_t u64;
|
||||||
|
double d;
|
||||||
|
|
||||||
|
if (val == NULL || p == NULL )
|
||||||
return 0;
|
return 0;
|
||||||
|
|
||||||
if (p->data_size == sizeof(int32_t)) {
|
if (p->data_type == OSSL_PARAM_INTEGER) {
|
||||||
*val = *(const int32_t *)p->data;
|
switch (p->data_size) {
|
||||||
return 1;
|
case sizeof(int32_t):
|
||||||
|
*val = *(const int32_t *)p->data;
|
||||||
|
return 1;
|
||||||
|
case sizeof(int64_t):
|
||||||
|
i64 = *(const int64_t *)p->data;
|
||||||
|
if (i64 >= INT32_MIN && i64 <= INT32_MAX) {
|
||||||
|
*val = (int32_t)i64;
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
} else if (p->data_type == OSSL_PARAM_UNSIGNED_INTEGER) {
|
||||||
|
switch (p->data_size) {
|
||||||
|
case sizeof(uint32_t):
|
||||||
|
u32 = *(const uint32_t *)p->data;
|
||||||
|
if (u32 <= INT32_MAX) {
|
||||||
|
*val = (int32_t)u32;
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
case sizeof(uint64_t):
|
||||||
|
u64 = *(const uint64_t *)p->data;
|
||||||
|
if (u64 <= INT32_MAX) {
|
||||||
|
*val = (int32_t)u64;
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
} else if (p->data_type == OSSL_PARAM_REAL) {
|
||||||
|
switch (p->data_size) {
|
||||||
|
case sizeof(double):
|
||||||
|
d = *(const double *)p->data;
|
||||||
|
if (d >= INT32_MIN && d <= INT32_MAX && d == (int32_t)d) {
|
||||||
|
*val = (int32_t)d;
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
@@ -171,19 +213,35 @@ int OSSL_PARAM_set_int32(const OSSL_PARAM *p, int32_t val)
|
|||||||
if (p == NULL)
|
if (p == NULL)
|
||||||
return 0;
|
return 0;
|
||||||
SET_RETURN_SIZE(p, 0);
|
SET_RETURN_SIZE(p, 0);
|
||||||
if (p->data_type != OSSL_PARAM_INTEGER)
|
if (p->data_type == OSSL_PARAM_INTEGER) {
|
||||||
return 0;
|
SET_RETURN_SIZE(p, sizeof(int32_t)); /* Minimum expected size */
|
||||||
|
switch (p->data_size) {
|
||||||
SET_RETURN_SIZE(p, sizeof(int32_t)); /* Minimum expected size */
|
case sizeof(int32_t):
|
||||||
switch (p->data_size) {
|
*(int32_t *)p->data = val;
|
||||||
case sizeof(int32_t):
|
return 1;
|
||||||
SET_RETURN_SIZE(p, sizeof(int32_t));
|
case sizeof(int64_t):
|
||||||
*(int32_t *)p->data = val;
|
SET_RETURN_SIZE(p, sizeof(int64_t));
|
||||||
return 1;
|
*(int64_t *)p->data = (int64_t)val;
|
||||||
case sizeof(int64_t):
|
return 1;
|
||||||
SET_RETURN_SIZE(p, sizeof(int64_t));
|
}
|
||||||
*(int64_t *)p->data = (int64_t)val;
|
} else if (p->data_type == OSSL_PARAM_UNSIGNED_INTEGER && val >= 0) {
|
||||||
return 1;
|
SET_RETURN_SIZE(p, sizeof(uint32_t)); /* Minimum expected size */
|
||||||
|
switch (p->data_size) {
|
||||||
|
case sizeof(uint32_t):
|
||||||
|
*(uint32_t *)p->data = (uint32_t)val;
|
||||||
|
return 1;
|
||||||
|
case sizeof(uint64_t):
|
||||||
|
SET_RETURN_SIZE(p, sizeof(uint64_t));
|
||||||
|
*(uint64_t *)p->data = (uint64_t)val;
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
} else if (p->data_type == OSSL_PARAM_REAL) {
|
||||||
|
SET_RETURN_SIZE(p, sizeof(double));
|
||||||
|
switch (p->data_size) {
|
||||||
|
case sizeof(double):
|
||||||
|
*(double *)p->data = (double)val;
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
@@ -197,35 +255,96 @@ OSSL_PARAM OSSL_PARAM_construct_int32(const char *key, int32_t *buf,
|
|||||||
|
|
||||||
int OSSL_PARAM_get_uint32(const OSSL_PARAM *p, uint32_t *val)
|
int OSSL_PARAM_get_uint32(const OSSL_PARAM *p, uint32_t *val)
|
||||||
{
|
{
|
||||||
if (val == NULL
|
int32_t i32;
|
||||||
|| p == NULL
|
int64_t i64;
|
||||||
|| (p->data_type != OSSL_PARAM_UNSIGNED_INTEGER))
|
uint64_t u64;
|
||||||
|
double d;
|
||||||
|
|
||||||
|
if (val == NULL || p == NULL)
|
||||||
return 0;
|
return 0;
|
||||||
|
|
||||||
if (p->data_size == sizeof(uint32_t)) {
|
if (p->data_type == OSSL_PARAM_UNSIGNED_INTEGER) {
|
||||||
*val = *(const uint32_t *)p->data;
|
switch (p->data_size) {
|
||||||
return 1;
|
case sizeof(uint32_t):
|
||||||
|
*val = *(const uint32_t *)p->data;
|
||||||
|
return 1;
|
||||||
|
case sizeof(uint64_t):
|
||||||
|
u64 = *(const uint64_t *)p->data;
|
||||||
|
if (u64 <= UINT32_MAX) {
|
||||||
|
*val = (uint32_t)u64;
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
} else if (p->data_type == OSSL_PARAM_INTEGER) {
|
||||||
|
switch (p->data_size) {
|
||||||
|
case sizeof(int32_t):
|
||||||
|
i32 = *(const int32_t *)p->data;
|
||||||
|
if (i32 >= 0) {
|
||||||
|
*val = i32;
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
case sizeof(int64_t):
|
||||||
|
i64 = *(const int64_t *)p->data;
|
||||||
|
if (i64 >= 0 && i64 <= UINT32_MAX) {
|
||||||
|
*val = (uint32_t)i64;
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
} else if (p->data_type == OSSL_PARAM_REAL) {
|
||||||
|
switch (p->data_size) {
|
||||||
|
case sizeof(double):
|
||||||
|
d = *(const double *)p->data;
|
||||||
|
if (d >= 0 && d <= UINT32_MAX && d == (uint32_t)d) {
|
||||||
|
*val = (uint32_t)d;
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
int OSSL_PARAM_set_uint32(const OSSL_PARAM *p, uint32_t val)
|
int OSSL_PARAM_set_uint32(const OSSL_PARAM *p, uint32_t val)
|
||||||
{
|
{
|
||||||
if (p == NULL) return 0;
|
if (p == NULL)
|
||||||
SET_RETURN_SIZE(p, 0);
|
|
||||||
if (p->data_type != OSSL_PARAM_UNSIGNED_INTEGER)
|
|
||||||
return 0;
|
return 0;
|
||||||
|
SET_RETURN_SIZE(p, 0);
|
||||||
|
|
||||||
SET_RETURN_SIZE(p, sizeof(uint32_t)); /* Minimum expected size */
|
if (p->data_type == OSSL_PARAM_UNSIGNED_INTEGER) {
|
||||||
switch (p->data_size) {
|
SET_RETURN_SIZE(p, sizeof(uint32_t)); /* Minimum expected size */
|
||||||
case sizeof(uint32_t):
|
switch (p->data_size) {
|
||||||
SET_RETURN_SIZE(p, sizeof(uint32_t));
|
case sizeof(uint32_t):
|
||||||
*(uint32_t *)p->data = val;
|
*(uint32_t *)p->data = val;
|
||||||
return 1;
|
return 1;
|
||||||
case sizeof(uint64_t):
|
case sizeof(uint64_t):
|
||||||
SET_RETURN_SIZE(p, sizeof(uint64_t));
|
SET_RETURN_SIZE(p, sizeof(uint64_t));
|
||||||
*(uint64_t *)p->data = (uint64_t)val;
|
*(uint64_t *)p->data = val;
|
||||||
return 1;
|
return 1;
|
||||||
|
}
|
||||||
|
} else if (p->data_type == OSSL_PARAM_INTEGER) {
|
||||||
|
SET_RETURN_SIZE(p, sizeof(int32_t)); /* Minimum expected size */
|
||||||
|
switch (p->data_size) {
|
||||||
|
case sizeof(int32_t):
|
||||||
|
if (val <= INT32_MAX) {
|
||||||
|
*(int32_t *)p->data = (int32_t)val;
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
case sizeof(int64_t):
|
||||||
|
SET_RETURN_SIZE(p, sizeof(int64_t));
|
||||||
|
*(int64_t *)p->data = (int64_t)val;
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
} else if (p->data_type == OSSL_PARAM_REAL) {
|
||||||
|
SET_RETURN_SIZE(p, sizeof(double));
|
||||||
|
switch (p->data_size) {
|
||||||
|
case sizeof(double):
|
||||||
|
*(double *)p->data = (double)val;
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
@@ -239,34 +358,94 @@ OSSL_PARAM OSSL_PARAM_construct_uint32(const char *key, uint32_t *buf,
|
|||||||
|
|
||||||
int OSSL_PARAM_get_int64(const OSSL_PARAM *p, int64_t *val)
|
int OSSL_PARAM_get_int64(const OSSL_PARAM *p, int64_t *val)
|
||||||
{
|
{
|
||||||
if (val == NULL || p == NULL || (p->data_type != OSSL_PARAM_INTEGER))
|
uint64_t u64;
|
||||||
|
double d;
|
||||||
|
|
||||||
|
if (val == NULL || p == NULL )
|
||||||
return 0;
|
return 0;
|
||||||
|
|
||||||
switch (p->data_size) {
|
if (p->data_type == OSSL_PARAM_INTEGER) {
|
||||||
case sizeof(int32_t):
|
switch (p->data_size) {
|
||||||
*val = (int64_t)*(const int32_t *)p->data;
|
case sizeof(int32_t):
|
||||||
return 1;
|
*val = *(const int32_t *)p->data;
|
||||||
case sizeof(int64_t):
|
return 1;
|
||||||
*val = *(const int64_t *)p->data;
|
case sizeof(int64_t):
|
||||||
return 1;
|
*val = *(const int64_t *)p->data;
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
} else if (p->data_type == OSSL_PARAM_UNSIGNED_INTEGER) {
|
||||||
|
switch (p->data_size) {
|
||||||
|
case sizeof(uint32_t):
|
||||||
|
*val = *(const uint32_t *)p->data;
|
||||||
|
return 1;
|
||||||
|
case sizeof(uint64_t):
|
||||||
|
u64 = *(const uint64_t *)p->data;
|
||||||
|
if (u64 <= INT64_MAX) {
|
||||||
|
*val = (int64_t)u64;
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
} else if (p->data_type == OSSL_PARAM_REAL) {
|
||||||
|
switch (p->data_size) {
|
||||||
|
case sizeof(double):
|
||||||
|
d = *(const double *)p->data;
|
||||||
|
if (d >= INT64_MIN && d <= INT64_MAX && d == (int64_t)d) {
|
||||||
|
*val = (int64_t)d;
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
int OSSL_PARAM_set_int64(const OSSL_PARAM *p, int64_t val)
|
int OSSL_PARAM_set_int64(const OSSL_PARAM *p, int64_t val)
|
||||||
{
|
{
|
||||||
|
uint64_t u64;
|
||||||
|
|
||||||
if (p == NULL)
|
if (p == NULL)
|
||||||
return 0;
|
return 0;
|
||||||
SET_RETURN_SIZE(p, 0);
|
SET_RETURN_SIZE(p, 0);
|
||||||
if (p->data_type != OSSL_PARAM_INTEGER)
|
if (p->data_type == OSSL_PARAM_INTEGER) {
|
||||||
return 0;
|
SET_RETURN_SIZE(p, sizeof(int64_t)); /* Expected size */
|
||||||
|
switch (p->data_size) {
|
||||||
SET_RETURN_SIZE(p, sizeof(int64_t)); /* Minimum expected size */
|
case sizeof(int32_t):
|
||||||
switch (p->data_size) {
|
if (val >= INT32_MIN && val <= INT32_MAX) {
|
||||||
case sizeof(int64_t):
|
SET_RETURN_SIZE(p, sizeof(int32_t));
|
||||||
SET_RETURN_SIZE(p, sizeof(int64_t));
|
*(int32_t *)p->data = (int32_t)val;
|
||||||
*(int64_t *)p->data = val;
|
return 1;
|
||||||
return 1;
|
}
|
||||||
|
break;
|
||||||
|
case sizeof(int64_t):
|
||||||
|
*(int64_t *)p->data = val;
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
} else if (p->data_type == OSSL_PARAM_UNSIGNED_INTEGER && val >= 0) {
|
||||||
|
SET_RETURN_SIZE(p, sizeof(uint64_t)); /* Expected size */
|
||||||
|
switch (p->data_size) {
|
||||||
|
case sizeof(uint32_t):
|
||||||
|
if (val <= UINT32_MAX) {
|
||||||
|
SET_RETURN_SIZE(p, sizeof(uint32_t));
|
||||||
|
*(uint32_t *)p->data = (uint32_t)val;
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
case sizeof(uint64_t):
|
||||||
|
*(uint64_t *)p->data = (uint64_t)val;
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
} else if (p->data_type == OSSL_PARAM_REAL) {
|
||||||
|
SET_RETURN_SIZE(p, sizeof(double));
|
||||||
|
switch (p->data_size) {
|
||||||
|
case sizeof(double):
|
||||||
|
u64 = val < 0 ? -val : val;
|
||||||
|
if ((u64 >> 53) == 0) { /* 53 significant bits in the mantissa */
|
||||||
|
*(double *)p->data = (double)val;
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
@@ -280,18 +459,49 @@ OSSL_PARAM OSSL_PARAM_construct_int64(const char *key, int64_t *buf,
|
|||||||
|
|
||||||
int OSSL_PARAM_get_uint64(const OSSL_PARAM *p, uint64_t *val)
|
int OSSL_PARAM_get_uint64(const OSSL_PARAM *p, uint64_t *val)
|
||||||
{
|
{
|
||||||
if (val == NULL
|
int32_t i32;
|
||||||
|| p == NULL
|
int64_t i64;
|
||||||
|| (p->data_type != OSSL_PARAM_UNSIGNED_INTEGER))
|
double d;
|
||||||
|
|
||||||
|
if (val == NULL || p == NULL)
|
||||||
return 0;
|
return 0;
|
||||||
|
|
||||||
switch (p->data_size) {
|
if (p->data_type == OSSL_PARAM_UNSIGNED_INTEGER) {
|
||||||
case sizeof(uint32_t):
|
switch (p->data_size) {
|
||||||
*val = (uint64_t)*(const uint32_t *)p->data;
|
case sizeof(uint32_t):
|
||||||
return 1;
|
*val = *(const uint32_t *)p->data;
|
||||||
case sizeof(uint64_t):
|
return 1;
|
||||||
*val = *(const uint64_t *)p->data;
|
case sizeof(uint64_t):
|
||||||
return 1;
|
*val = *(const uint64_t *)p->data;
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
} else if (p->data_type == OSSL_PARAM_INTEGER) {
|
||||||
|
switch (p->data_size) {
|
||||||
|
case sizeof(int32_t):
|
||||||
|
i32 = *(const int32_t *)p->data;
|
||||||
|
if (i32 >= 0) {
|
||||||
|
*val = (uint64_t)i32;
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
case sizeof(int64_t):
|
||||||
|
i64 = *(const int64_t *)p->data;
|
||||||
|
if (i64 >= 0) {
|
||||||
|
*val = (uint64_t)i64;
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
} else if (p->data_type == OSSL_PARAM_REAL) {
|
||||||
|
switch (p->data_size) {
|
||||||
|
case sizeof(double):
|
||||||
|
d = *(const double *)p->data;
|
||||||
|
if (d >= 0 && d <= INT64_MAX && d == (uint64_t)d) {
|
||||||
|
*val = (uint64_t)d;
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
@@ -301,15 +511,48 @@ int OSSL_PARAM_set_uint64(const OSSL_PARAM *p, uint64_t val)
|
|||||||
if (p == NULL)
|
if (p == NULL)
|
||||||
return 0;
|
return 0;
|
||||||
SET_RETURN_SIZE(p, 0);
|
SET_RETURN_SIZE(p, 0);
|
||||||
if (p->data_type != OSSL_PARAM_UNSIGNED_INTEGER)
|
|
||||||
return 0;
|
|
||||||
|
|
||||||
SET_RETURN_SIZE(p, sizeof(uint64_t)); /* Minimum expected size */
|
if (p->data_type == OSSL_PARAM_UNSIGNED_INTEGER) {
|
||||||
switch (p->data_size) {
|
SET_RETURN_SIZE(p, sizeof(uint64_t)); /* Expected size */
|
||||||
case sizeof(uint64_t):
|
switch (p->data_size) {
|
||||||
SET_RETURN_SIZE(p, sizeof(uint64_t));
|
case sizeof(uint32_t):
|
||||||
*(uint64_t *)p->data = val;
|
if (val <= UINT32_MAX) {
|
||||||
return 1;
|
SET_RETURN_SIZE(p, sizeof(uint32_t));
|
||||||
|
*(uint32_t *)p->data = (uint32_t)val;
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
case sizeof(uint64_t):
|
||||||
|
*(uint64_t *)p->data = val;
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
} else if (p->data_type == OSSL_PARAM_INTEGER) {
|
||||||
|
SET_RETURN_SIZE(p, sizeof(int64_t)); /* Expected size */
|
||||||
|
switch (p->data_size) {
|
||||||
|
case sizeof(int32_t):
|
||||||
|
if (val <= INT32_MAX) {
|
||||||
|
SET_RETURN_SIZE(p, sizeof(int32_t));
|
||||||
|
*(int32_t *)p->data = (int32_t)val;
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
case sizeof(int64_t):
|
||||||
|
if (val <= INT64_MAX) {
|
||||||
|
*(int64_t *)p->data = (int64_t)val;
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
} else if (p->data_type == OSSL_PARAM_REAL) {
|
||||||
|
SET_RETURN_SIZE(p, sizeof(double));
|
||||||
|
switch (p->data_size) {
|
||||||
|
case sizeof(double):
|
||||||
|
if ((val >> 53) == 0) { /* 53 significant bits in the mantissa */
|
||||||
|
*(double *)p->data = (double)val;
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
@@ -402,13 +645,45 @@ OSSL_PARAM OSSL_PARAM_construct_BN(const char *key, unsigned char *buf,
|
|||||||
|
|
||||||
int OSSL_PARAM_get_double(const OSSL_PARAM *p, double *val)
|
int OSSL_PARAM_get_double(const OSSL_PARAM *p, double *val)
|
||||||
{
|
{
|
||||||
if (val == NULL || p == NULL || p->data_type != OSSL_PARAM_REAL)
|
int64_t i64;
|
||||||
|
uint64_t u64;
|
||||||
|
|
||||||
|
if (val == NULL || p == NULL)
|
||||||
return 0;
|
return 0;
|
||||||
|
|
||||||
switch (p->data_size) {
|
if (p->data_type == OSSL_PARAM_REAL) {
|
||||||
case sizeof(double):
|
switch (p->data_size) {
|
||||||
*val = *(const double *)p->data;
|
case sizeof(double):
|
||||||
return 1;
|
*val = *(const double *)p->data;
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
} else if (p->data_type == OSSL_PARAM_UNSIGNED_INTEGER) {
|
||||||
|
switch (p->data_size) {
|
||||||
|
case sizeof(uint32_t):
|
||||||
|
*val = *(const uint32_t *)p->data;
|
||||||
|
return 1;
|
||||||
|
case sizeof(uint64_t):
|
||||||
|
u64 = *(const uint64_t *)p->data;
|
||||||
|
if ((u64 >> 53) == 0) { /* 53 significant bits in the mantissa */
|
||||||
|
*val = (double)u64;
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
} else if (p->data_type == OSSL_PARAM_INTEGER) {
|
||||||
|
switch (p->data_size) {
|
||||||
|
case sizeof(int32_t):
|
||||||
|
*val = *(const int32_t *)p->data;
|
||||||
|
return 1;
|
||||||
|
case sizeof(int64_t):
|
||||||
|
i64 = *(const int64_t *)p->data;
|
||||||
|
u64 = i64 < 0 ? -i64 : i64;
|
||||||
|
if ((u64 >> 53) == 0) { /* 53 significant bits in the mantissa */
|
||||||
|
*val = 0.0 + i64;
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
@@ -418,14 +693,50 @@ int OSSL_PARAM_set_double(const OSSL_PARAM *p, double val)
|
|||||||
if (p == NULL)
|
if (p == NULL)
|
||||||
return 0;
|
return 0;
|
||||||
SET_RETURN_SIZE(p, 0);
|
SET_RETURN_SIZE(p, 0);
|
||||||
if (p->data_type != OSSL_PARAM_REAL)
|
|
||||||
return 0;
|
|
||||||
|
|
||||||
switch (p->data_size) {
|
if (p->data_type == OSSL_PARAM_REAL) {
|
||||||
case sizeof(double):
|
|
||||||
SET_RETURN_SIZE(p, sizeof(double));
|
SET_RETURN_SIZE(p, sizeof(double));
|
||||||
*(double *)p->data = val;
|
switch (p->data_size) {
|
||||||
return 1;
|
case sizeof(double):
|
||||||
|
*(double *)p->data = val;
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
} else if (p->data_type == OSSL_PARAM_UNSIGNED_INTEGER
|
||||||
|
&& val == (uintmax_t)val) {
|
||||||
|
SET_RETURN_SIZE(p, sizeof(double));
|
||||||
|
switch (p->data_size) {
|
||||||
|
case sizeof(uint32_t):
|
||||||
|
if (val >= 0 && val <= UINT32_MAX) {
|
||||||
|
SET_RETURN_SIZE(p, sizeof(uint32_t));
|
||||||
|
*(uint32_t *)p->data = (uint32_t)val;
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
case sizeof(uint64_t):
|
||||||
|
if (val >= 0 && val <= UINT64_MAX) {
|
||||||
|
SET_RETURN_SIZE(p, sizeof(uint64_t));
|
||||||
|
*(uint64_t *)p->data = (uint64_t)val;
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
break; }
|
||||||
|
} else if (p->data_type == OSSL_PARAM_INTEGER && val == (intmax_t)val) {
|
||||||
|
SET_RETURN_SIZE(p, sizeof(double));
|
||||||
|
switch (p->data_size) {
|
||||||
|
case sizeof(int32_t):
|
||||||
|
if (val >= INT32_MIN && val <= INT32_MAX) {
|
||||||
|
SET_RETURN_SIZE(p, sizeof(int32_t));
|
||||||
|
*(int32_t *)p->data = (int32_t)val;
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
case sizeof(int64_t):
|
||||||
|
if (val >= INT64_MIN && val <= INT64_MAX) {
|
||||||
|
SET_RETURN_SIZE(p, sizeof(int64_t));
|
||||||
|
*(int64_t *)p->data = (int64_t)val;
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|||||||
+3
-2
@@ -323,6 +323,7 @@ void OPENSSL_cpuid_setup(void)
|
|||||||
#ifdef OSSL_IMPLEMENT_GETAUXVAL
|
#ifdef OSSL_IMPLEMENT_GETAUXVAL
|
||||||
{
|
{
|
||||||
unsigned long hwcap = getauxval(HWCAP);
|
unsigned long hwcap = getauxval(HWCAP);
|
||||||
|
unsigned long hwcap2 = getauxval(HWCAP2);
|
||||||
|
|
||||||
if (hwcap & HWCAP_FPU) {
|
if (hwcap & HWCAP_FPU) {
|
||||||
OPENSSL_ppccap_P |= PPC_FPU;
|
OPENSSL_ppccap_P |= PPC_FPU;
|
||||||
@@ -341,11 +342,11 @@ void OPENSSL_cpuid_setup(void)
|
|||||||
if (hwcap & HWCAP_ALTIVEC) {
|
if (hwcap & HWCAP_ALTIVEC) {
|
||||||
OPENSSL_ppccap_P |= PPC_ALTIVEC;
|
OPENSSL_ppccap_P |= PPC_ALTIVEC;
|
||||||
|
|
||||||
if ((hwcap & HWCAP_VSX) && (getauxval(HWCAP2) & HWCAP_VEC_CRYPTO))
|
if ((hwcap & HWCAP_VSX) && (hwcap2 & HWCAP_VEC_CRYPTO))
|
||||||
OPENSSL_ppccap_P |= PPC_CRYPTO207;
|
OPENSSL_ppccap_P |= PPC_CRYPTO207;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (hwcap & HWCAP_ARCH_3_00) {
|
if (hwcap2 & HWCAP_ARCH_3_00) {
|
||||||
OPENSSL_ppccap_P |= PPC_MADD300;
|
OPENSSL_ppccap_P |= PPC_MADD300;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -29,8 +29,6 @@ typedef struct {
|
|||||||
|
|
||||||
DEFINE_LHASH_OF(PROPERTY_DEFN_ELEM);
|
DEFINE_LHASH_OF(PROPERTY_DEFN_ELEM);
|
||||||
|
|
||||||
static LHASH_OF(PROPERTY_DEFN_ELEM) *property_defns = NULL;
|
|
||||||
|
|
||||||
static unsigned long property_defn_hash(const PROPERTY_DEFN_ELEM *a)
|
static unsigned long property_defn_hash(const PROPERTY_DEFN_ELEM *a)
|
||||||
{
|
{
|
||||||
return OPENSSL_LH_strhash(a->prop);
|
return OPENSSL_LH_strhash(a->prop);
|
||||||
@@ -48,35 +46,52 @@ static void property_defn_free(PROPERTY_DEFN_ELEM *elem)
|
|||||||
OPENSSL_free(elem);
|
OPENSSL_free(elem);
|
||||||
}
|
}
|
||||||
|
|
||||||
int ossl_prop_defn_init(void)
|
static void property_defns_free(void *vproperty_defns)
|
||||||
{
|
{
|
||||||
property_defns = lh_PROPERTY_DEFN_ELEM_new(&property_defn_hash,
|
LHASH_OF(PROPERTY_DEFN_ELEM) *property_defns = vproperty_defns;
|
||||||
&property_defn_cmp);
|
|
||||||
return property_defns != NULL;
|
|
||||||
}
|
|
||||||
|
|
||||||
void ossl_prop_defn_cleanup(void)
|
|
||||||
{
|
|
||||||
if (property_defns != NULL) {
|
if (property_defns != NULL) {
|
||||||
lh_PROPERTY_DEFN_ELEM_doall(property_defns, &property_defn_free);
|
lh_PROPERTY_DEFN_ELEM_doall(property_defns,
|
||||||
|
&property_defn_free);
|
||||||
lh_PROPERTY_DEFN_ELEM_free(property_defns);
|
lh_PROPERTY_DEFN_ELEM_free(property_defns);
|
||||||
property_defns = NULL;
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
OSSL_PROPERTY_LIST *ossl_prop_defn_get(const char *prop)
|
static void *property_defns_new(OPENSSL_CTX *ctx) {
|
||||||
|
return lh_PROPERTY_DEFN_ELEM_new(&property_defn_hash, &property_defn_cmp);
|
||||||
|
}
|
||||||
|
|
||||||
|
static const OPENSSL_CTX_METHOD property_defns_method = {
|
||||||
|
property_defns_new,
|
||||||
|
property_defns_free,
|
||||||
|
};
|
||||||
|
|
||||||
|
OSSL_PROPERTY_LIST *ossl_prop_defn_get(OPENSSL_CTX *ctx, const char *prop)
|
||||||
{
|
{
|
||||||
PROPERTY_DEFN_ELEM elem, *r;
|
PROPERTY_DEFN_ELEM elem, *r;
|
||||||
|
LHASH_OF(PROPERTY_DEFN_ELEM) *property_defns;
|
||||||
|
|
||||||
|
property_defns = openssl_ctx_get_data(ctx, OPENSSL_CTX_PROPERTY_DEFN_INDEX,
|
||||||
|
&property_defns_method);
|
||||||
|
if (property_defns == NULL)
|
||||||
|
return NULL;
|
||||||
|
|
||||||
elem.prop = prop;
|
elem.prop = prop;
|
||||||
r = lh_PROPERTY_DEFN_ELEM_retrieve(property_defns, &elem);
|
r = lh_PROPERTY_DEFN_ELEM_retrieve(property_defns, &elem);
|
||||||
return r != NULL ? r->defn : NULL;
|
return r != NULL ? r->defn : NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
int ossl_prop_defn_set(const char *prop, OSSL_PROPERTY_LIST *pl)
|
int ossl_prop_defn_set(OPENSSL_CTX *ctx, const char *prop,
|
||||||
|
OSSL_PROPERTY_LIST *pl)
|
||||||
{
|
{
|
||||||
PROPERTY_DEFN_ELEM elem, *old, *p = NULL;
|
PROPERTY_DEFN_ELEM elem, *old, *p = NULL;
|
||||||
size_t len;
|
size_t len;
|
||||||
|
LHASH_OF(PROPERTY_DEFN_ELEM) *property_defns;
|
||||||
|
|
||||||
|
property_defns = openssl_ctx_get_data(ctx, OPENSSL_CTX_PROPERTY_DEFN_INDEX,
|
||||||
|
&property_defns_method);
|
||||||
|
if (property_defns == NULL)
|
||||||
|
return 0;
|
||||||
|
|
||||||
if (prop == NULL)
|
if (prop == NULL)
|
||||||
return 1;
|
return 1;
|
||||||
|
|||||||
@@ -2,16 +2,17 @@
|
|||||||
|
|
||||||
Definition
|
Definition
|
||||||
::= PropertyName ( '=' Value )? ( ',' PropertyName ( '=' Value )? )*
|
::= PropertyName ( '=' Value )? ( ',' PropertyName ( '=' Value )? )*
|
||||||
Query ::= ( '-'? PropertyName | PropertyName ( '=' | '!=' ) Value )
|
Query ::= PropertyQuery ( ',' PropertyQuery )*
|
||||||
( ',' ( '-'? PropertyName | PropertyName ( '=' | '!=' ) Value ) )*
|
PropertyQuery ::= '-'? PropertyName
|
||||||
|
| '?' ( PropertyName (( '=' | '!=' ) Value)?)
|
||||||
Value ::= NumberLiteral
|
Value ::= NumberLiteral
|
||||||
| StringLiteral
|
| StringLiteral
|
||||||
StringLiteral ::= QuotedString | UnquotedString
|
StringLiteral ::= QuotedString | UnquotedString
|
||||||
QuotedString ::= '"' [^"]* '"'
|
QuotedString ::= '"' [^"]* '"'
|
||||||
| "'" [^']* "'"
|
| "'" [^']* "'"
|
||||||
UnquotedString ::= [^{space},]+
|
UnquotedString ::= [^{space},]+
|
||||||
NumberLiteral
|
NumberLiteral
|
||||||
::= '0' ( [0-7]* | 'x' [0-9A-Fa-f]+ )
|
::= '0' ( [0-7]* | 'x' [0-9A-Fa-f]+ )
|
||||||
| '-'? [1-9] [0-9]+
|
| '-'? [1-9] [0-9]+
|
||||||
PropertyName
|
PropertyName
|
||||||
::= [A-Z] [A-Z0-9_]* ( '.' [A-Z] [A-Z0-9_]* )*
|
::= [A-Z] [A-Z0-9_]* ( '.' [A-Z] [A-Z0-9_]* )*
|
||||||
Regular → Executable
+76
-28
@@ -2,7 +2,7 @@
|
|||||||
<html xmlns="http://www.w3.org/1999/xhtml">
|
<html xmlns="http://www.w3.org/1999/xhtml">
|
||||||
<head>
|
<head>
|
||||||
<meta http-equiv="Content-Type" content="application/xhtml+xml; charset=UTF-8" />
|
<meta http-equiv="Content-Type" content="application/xhtml+xml; charset=UTF-8" />
|
||||||
<meta name="generator" content="Railroad Diagram Generator 1.56.1774" />
|
<meta name="generator" content="Railroad Diagram Generator 1.59.1797" />
|
||||||
<style type="text/css">
|
<style type="text/css">
|
||||||
::-moz-selection
|
::-moz-selection
|
||||||
{
|
{
|
||||||
@@ -133,7 +133,7 @@
|
|||||||
display: block;
|
display: block;
|
||||||
padding: 10px;
|
padding: 10px;
|
||||||
background: #FFF6D1;
|
background: #FFF6D1;
|
||||||
width: 1000px;
|
width: 992px;
|
||||||
}
|
}
|
||||||
#divs div.grammar
|
#divs div.grammar
|
||||||
{
|
{
|
||||||
@@ -268,7 +268,7 @@
|
|||||||
<div><a href="#Definition" title="Definition">Definition</a></div>
|
<div><a href="#Definition" title="Definition">Definition</a></div>
|
||||||
<div> ::= <a href="#PropertyName" title="PropertyName">PropertyName</a> ( '=' <a href="#Value" title="Value">Value</a> )? ( ',' <a href="#PropertyName" title="PropertyName">PropertyName</a> ( '=' <a href="#Value" title="Value">Value</a> )? )*</div></xhtml:code></xhtml:div>
|
<div> ::= <a href="#PropertyName" title="PropertyName">PropertyName</a> ( '=' <a href="#Value" title="Value">Value</a> )? ( ',' <a href="#PropertyName" title="PropertyName">PropertyName</a> ( '=' <a href="#Value" title="Value">Value</a> )? )*</div></xhtml:code></xhtml:div>
|
||||||
</xhtml:p>
|
</xhtml:p>
|
||||||
<xhtml:p xmlns:xhtml="http://www.w3.org/1999/xhtml">no references</xhtml:p><xhtml:br xmlns:xhtml="http://www.w3.org/1999/xhtml" /><xhtml:p xmlns:xhtml="http://www.w3.org/1999/xhtml" style="font-size: 14px; font-weight:bold"><xhtml:a name="Query">Query:</xhtml:a></xhtml:p><svg xmlns="http://www.w3.org/2000/svg" width="419" height="201">
|
<xhtml:p xmlns:xhtml="http://www.w3.org/1999/xhtml">no references</xhtml:p><xhtml:br xmlns:xhtml="http://www.w3.org/1999/xhtml" /><xhtml:p xmlns:xhtml="http://www.w3.org/1999/xhtml" style="font-size: 14px; font-weight:bold"><xhtml:a name="Query">Query:</xhtml:a></xhtml:p><svg xmlns="http://www.w3.org/2000/svg" width="211" height="81">
|
||||||
<defs>
|
<defs>
|
||||||
<style type="text/css">
|
<style type="text/css">
|
||||||
@namespace "http://www.w3.org/2000/svg";
|
@namespace "http://www.w3.org/2000/svg";
|
||||||
@@ -299,33 +299,81 @@
|
|||||||
</style>
|
</style>
|
||||||
</defs>
|
</defs>
|
||||||
<polygon points="9 61 1 57 1 65"/>
|
<polygon points="9 61 1 57 1 65"/>
|
||||||
<polygon points="17 61 9 57 9 65"/>
|
<polygon points="17 61 9 57 9 65"/><a xmlns:xlink="http://www.w3.org/1999/xlink" xlink:href="#PropertyQuery" xlink:title="PropertyQuery">
|
||||||
<rect x="91" y="79" width="26" height="32" rx="10"/>
|
<rect x="51" y="47" width="112" height="32"/>
|
||||||
<rect x="89" y="77" width="26" height="32" class="terminal" rx="10"/>
|
<rect x="49" y="45" width="112" height="32" class="nonterminal"/>
|
||||||
<text class="terminal" x="99" y="97">-</text><a xmlns:xlink="http://www.w3.org/1999/xlink" xlink:href="#PropertyName" xlink:title="PropertyName">
|
<text class="nonterminal" x="59" y="65">PropertyQuery</text></a><rect x="51" y="3" width="24" height="32" rx="10"/>
|
||||||
<rect x="157" y="47" width="110" height="32"/>
|
|
||||||
<rect x="155" y="45" width="110" height="32" class="nonterminal"/>
|
|
||||||
<text class="nonterminal" x="165" y="65">PropertyName</text></a><a xmlns:xlink="http://www.w3.org/1999/xlink" xlink:href="#PropertyName" xlink:title="PropertyName">
|
|
||||||
<rect x="71" y="123" width="110" height="32"/>
|
|
||||||
<rect x="69" y="121" width="110" height="32" class="nonterminal"/>
|
|
||||||
<text class="nonterminal" x="79" y="141">PropertyName</text></a><rect x="221" y="123" width="30" height="32" rx="10"/>
|
|
||||||
<rect x="219" y="121" width="30" height="32" class="terminal" rx="10"/>
|
|
||||||
<text class="terminal" x="229" y="141">=</text>
|
|
||||||
<rect x="221" y="167" width="34" height="32" rx="10"/>
|
|
||||||
<rect x="219" y="165" width="34" height="32" class="terminal" rx="10"/>
|
|
||||||
<text class="terminal" x="229" y="185">!=</text><a xmlns:xlink="http://www.w3.org/1999/xlink" xlink:href="#Value" xlink:title="Value">
|
|
||||||
<rect x="295" y="123" width="56" height="32"/>
|
|
||||||
<rect x="293" y="121" width="56" height="32" class="nonterminal"/>
|
|
||||||
<text class="nonterminal" x="303" y="141">Value</text></a><rect x="51" y="3" width="24" height="32" rx="10"/>
|
|
||||||
<rect x="49" y="1" width="24" height="32" class="terminal" rx="10"/>
|
<rect x="49" y="1" width="24" height="32" class="terminal" rx="10"/>
|
||||||
<text class="terminal" x="59" y="21">,</text>
|
<text class="terminal" x="59" y="21">,</text>
|
||||||
<svg:path xmlns:svg="http://www.w3.org/2000/svg" class="line" d="m17 61 h2 m60 0 h10 m0 0 h36 m-66 0 h20 m46 0 h20 m-86 0 q10 0 10 10 m66 0 q0 -10 10 -10 m-76 10 v12 m66 0 v-12 m-66 12 q0 10 10 10 m46 0 q10 0 10 -10 m-56 10 h10 m26 0 h10 m20 -32 h10 m110 0 h10 m0 0 h84 m-320 0 h20 m300 0 h20 m-340 0 q10 0 10 10 m320 0 q0 -10 10 -10 m-330 10 v56 m320 0 v-56 m-320 56 q0 10 10 10 m300 0 q10 0 10 -10 m-310 10 h10 m110 0 h10 m20 0 h10 m30 0 h10 m0 0 h4 m-74 0 h20 m54 0 h20 m-94 0 q10 0 10 10 m74 0 q0 -10 10 -10 m-84 10 v24 m74 0 v-24 m-74 24 q0 10 10 10 m54 0 q10 0 10 -10 m-64 10 h10 m34 0 h10 m20 -44 h10 m56 0 h10 m-340 -76 l20 0 m-1 0 q-9 0 -9 -10 l0 -24 q0 -10 10 -10 m340 44 l20 0 m-20 0 q10 0 10 -10 l0 -24 q0 -10 -10 -10 m-340 0 h10 m24 0 h10 m0 0 h296 m23 44 h-3"/>
|
<svg:path xmlns:svg="http://www.w3.org/2000/svg" class="line" d="m17 61 h2 m20 0 h10 m112 0 h10 m-152 0 l20 0 m-1 0 q-9 0 -9 -10 l0 -24 q0 -10 10 -10 m132 44 l20 0 m-20 0 q10 0 10 -10 l0 -24 q0 -10 -10 -10 m-132 0 h10 m24 0 h10 m0 0 h88 m23 44 h-3"/>
|
||||||
<polygon points="409 61 417 57 417 65"/>
|
<polygon points="201 61 209 57 209 65"/>
|
||||||
<polygon points="409 61 401 57 401 65"/></svg><xhtml:p xmlns:xhtml="http://www.w3.org/1999/xhtml">
|
<polygon points="201 61 193 57 193 65"/></svg><xhtml:p xmlns:xhtml="http://www.w3.org/1999/xhtml">
|
||||||
<xhtml:div class="ebnf"><xhtml:code>
|
<xhtml:div class="ebnf"><xhtml:code>
|
||||||
<div><a href="#Query" title="Query">Query</a> ::= ( '-'? <a href="#PropertyName" title="PropertyName">PropertyName</a> | <a href="#PropertyName" title="PropertyName">PropertyName</a> ( '=' | '!=' ) <a href="#Value" title="Value">Value</a> ) ( ',' ( '-'? <a href="#PropertyName" title="PropertyName">PropertyName</a> | <a href="#PropertyName" title="PropertyName">PropertyName</a> ( '=' | '!=' ) <a href="#Value" title="Value">Value</a> ) )*</div></xhtml:code></xhtml:div>
|
<div><a href="#Query" title="Query">Query</a> ::= <a href="#PropertyQuery" title="PropertyQuery">PropertyQuery</a> ( ',' <a href="#PropertyQuery" title="PropertyQuery">PropertyQuery</a> )*</div></xhtml:code></xhtml:div>
|
||||||
</xhtml:p>
|
</xhtml:p>
|
||||||
<xhtml:p xmlns:xhtml="http://www.w3.org/1999/xhtml">no references</xhtml:p><xhtml:br xmlns:xhtml="http://www.w3.org/1999/xhtml" /><xhtml:p xmlns:xhtml="http://www.w3.org/1999/xhtml" style="font-size: 14px; font-weight:bold"><xhtml:a name="Value">Value:</xhtml:a></xhtml:p><svg xmlns="http://www.w3.org/2000/svg" width="207" height="81">
|
<xhtml:p xmlns:xhtml="http://www.w3.org/1999/xhtml">no references</xhtml:p><xhtml:br xmlns:xhtml="http://www.w3.org/1999/xhtml" /><xhtml:p xmlns:xhtml="http://www.w3.org/1999/xhtml" style="font-size: 14px; font-weight:bold"><xhtml:a name="PropertyQuery">PropertyQuery:</xhtml:a></xhtml:p><svg xmlns="http://www.w3.org/2000/svg" width="465" height="189">
|
||||||
|
<defs>
|
||||||
|
<style type="text/css">
|
||||||
|
@namespace "http://www.w3.org/2000/svg";
|
||||||
|
.line {fill: none; stroke: #332900;}
|
||||||
|
.bold-line {stroke: #141000; shape-rendering: crispEdges; stroke-width: 2; }
|
||||||
|
.thin-line {stroke: #1F1800; shape-rendering: crispEdges}
|
||||||
|
.filled {fill: #332900; stroke: none;}
|
||||||
|
text.terminal {font-family: Verdana, Sans-serif;
|
||||||
|
font-size: 12px;
|
||||||
|
fill: #141000;
|
||||||
|
font-weight: bold;
|
||||||
|
}
|
||||||
|
text.nonterminal {font-family: Verdana, Sans-serif;
|
||||||
|
font-size: 12px;
|
||||||
|
fill: #1A1400;
|
||||||
|
font-weight: normal;
|
||||||
|
}
|
||||||
|
text.regexp {font-family: Verdana, Sans-serif;
|
||||||
|
font-size: 12px;
|
||||||
|
fill: #1F1800;
|
||||||
|
font-weight: normal;
|
||||||
|
}
|
||||||
|
rect, circle, polygon {fill: #332900; stroke: #332900;}
|
||||||
|
rect.terminal {fill: #FFDB4D; stroke: #332900;}
|
||||||
|
rect.nonterminal {fill: #FFEC9E; stroke: #332900;}
|
||||||
|
rect.text {fill: none; stroke: none;}
|
||||||
|
polygon.regexp {fill: #FFF4C7; stroke: #332900;}
|
||||||
|
</style>
|
||||||
|
</defs>
|
||||||
|
<polygon points="9 17 1 13 1 21"/>
|
||||||
|
<polygon points="17 17 9 13 9 21"/>
|
||||||
|
<rect x="71" y="35" width="26" height="32" rx="10"/>
|
||||||
|
<rect x="69" y="33" width="26" height="32" class="terminal" rx="10"/>
|
||||||
|
<text class="terminal" x="79" y="53">-</text><a xmlns:xlink="http://www.w3.org/1999/xlink" xlink:href="#PropertyName" xlink:title="PropertyName">
|
||||||
|
<rect x="137" y="3" width="110" height="32"/>
|
||||||
|
<rect x="135" y="1" width="110" height="32" class="nonterminal"/>
|
||||||
|
<text class="nonterminal" x="145" y="21">PropertyName</text></a><rect x="51" y="79" width="26" height="32" rx="10"/>
|
||||||
|
<rect x="49" y="77" width="26" height="32" class="terminal" rx="10"/>
|
||||||
|
<text class="terminal" x="59" y="97">?</text><a xmlns:xlink="http://www.w3.org/1999/xlink" xlink:href="#PropertyName" xlink:title="PropertyName">
|
||||||
|
<rect x="97" y="79" width="110" height="32"/>
|
||||||
|
<rect x="95" y="77" width="110" height="32" class="nonterminal"/>
|
||||||
|
<text class="nonterminal" x="105" y="97">PropertyName</text></a><rect x="267" y="111" width="30" height="32" rx="10"/>
|
||||||
|
<rect x="265" y="109" width="30" height="32" class="terminal" rx="10"/>
|
||||||
|
<text class="terminal" x="275" y="129">=</text>
|
||||||
|
<rect x="267" y="155" width="34" height="32" rx="10"/>
|
||||||
|
<rect x="265" y="153" width="34" height="32" class="terminal" rx="10"/>
|
||||||
|
<text class="terminal" x="275" y="173">!=</text><a xmlns:xlink="http://www.w3.org/1999/xlink" xlink:href="#Value" xlink:title="Value">
|
||||||
|
<rect x="341" y="111" width="56" height="32"/>
|
||||||
|
<rect x="339" y="109" width="56" height="32" class="nonterminal"/>
|
||||||
|
<text class="nonterminal" x="349" y="129">Value</text></a><svg:path xmlns:svg="http://www.w3.org/2000/svg" class="line" d="m17 17 h2 m40 0 h10 m0 0 h36 m-66 0 h20 m46 0 h20 m-86 0 q10 0 10 10 m66 0 q0 -10 10 -10 m-76 10 v12 m66 0 v-12 m-66 12 q0 10 10 10 m46 0 q10 0 10 -10 m-56 10 h10 m26 0 h10 m20 -32 h10 m110 0 h10 m0 0 h170 m-406 0 h20 m386 0 h20 m-426 0 q10 0 10 10 m406 0 q0 -10 10 -10 m-416 10 v56 m406 0 v-56 m-406 56 q0 10 10 10 m386 0 q10 0 10 -10 m-396 10 h10 m26 0 h10 m0 0 h10 m110 0 h10 m20 0 h10 m0 0 h160 m-190 0 h20 m170 0 h20 m-210 0 q10 0 10 10 m190 0 q0 -10 10 -10 m-200 10 v12 m190 0 v-12 m-190 12 q0 10 10 10 m170 0 q10 0 10 -10 m-160 10 h10 m30 0 h10 m0 0 h4 m-74 0 h20 m54 0 h20 m-94 0 q10 0 10 10 m74 0 q0 -10 10 -10 m-84 10 v24 m74 0 v-24 m-74 24 q0 10 10 10 m54 0 q10 0 10 -10 m-64 10 h10 m34 0 h10 m20 -44 h10 m56 0 h10 m43 -108 h-3"/>
|
||||||
|
<polygon points="455 17 463 13 463 21"/>
|
||||||
|
<polygon points="455 17 447 13 447 21"/></svg><xhtml:p xmlns:xhtml="http://www.w3.org/1999/xhtml">
|
||||||
|
<xhtml:div class="ebnf"><xhtml:code>
|
||||||
|
<div><a href="#PropertyQuery" title="PropertyQuery">PropertyQuery</a></div>
|
||||||
|
<div> ::= '-'? <a href="#PropertyName" title="PropertyName">PropertyName</a></div>
|
||||||
|
<div> | '?' <a href="#PropertyName" title="PropertyName">PropertyName</a> ( ( '=' | '!=' ) <a href="#Value" title="Value">Value</a> )?</div></xhtml:code></xhtml:div>
|
||||||
|
</xhtml:p>
|
||||||
|
<xhtml:p xmlns:xhtml="http://www.w3.org/1999/xhtml">referenced by:
|
||||||
|
<xhtml:ul>
|
||||||
|
<xhtml:li><xhtml:a href="#Query" title="Query">Query</xhtml:a></xhtml:li>
|
||||||
|
</xhtml:ul>
|
||||||
|
</xhtml:p><xhtml:br xmlns:xhtml="http://www.w3.org/1999/xhtml" /><xhtml:p xmlns:xhtml="http://www.w3.org/1999/xhtml" style="font-size: 14px; font-weight:bold"><xhtml:a name="Value">Value:</xhtml:a></xhtml:p><svg xmlns="http://www.w3.org/2000/svg" width="207" height="81">
|
||||||
<defs>
|
<defs>
|
||||||
<style type="text/css">
|
<style type="text/css">
|
||||||
@namespace "http://www.w3.org/2000/svg";
|
@namespace "http://www.w3.org/2000/svg";
|
||||||
@@ -372,7 +420,7 @@
|
|||||||
<xhtml:p xmlns:xhtml="http://www.w3.org/1999/xhtml">referenced by:
|
<xhtml:p xmlns:xhtml="http://www.w3.org/1999/xhtml">referenced by:
|
||||||
<xhtml:ul>
|
<xhtml:ul>
|
||||||
<xhtml:li><xhtml:a href="#Definition" title="Definition">Definition</xhtml:a></xhtml:li>
|
<xhtml:li><xhtml:a href="#Definition" title="Definition">Definition</xhtml:a></xhtml:li>
|
||||||
<xhtml:li><xhtml:a href="#Query" title="Query">Query</xhtml:a></xhtml:li>
|
<xhtml:li><xhtml:a href="#PropertyQuery" title="PropertyQuery">PropertyQuery</xhtml:a></xhtml:li>
|
||||||
</xhtml:ul>
|
</xhtml:ul>
|
||||||
</xhtml:p><xhtml:br xmlns:xhtml="http://www.w3.org/1999/xhtml" /><xhtml:p xmlns:xhtml="http://www.w3.org/1999/xhtml" style="font-size: 14px; font-weight:bold"><xhtml:a name="StringLiteral">StringLiteral:</xhtml:a></xhtml:p><svg xmlns="http://www.w3.org/2000/svg" width="219" height="81">
|
</xhtml:p><xhtml:br xmlns:xhtml="http://www.w3.org/1999/xhtml" /><xhtml:p xmlns:xhtml="http://www.w3.org/1999/xhtml" style="font-size: 14px; font-weight:bold"><xhtml:a name="StringLiteral">StringLiteral:</xhtml:a></xhtml:p><svg xmlns="http://www.w3.org/2000/svg" width="219" height="81">
|
||||||
<defs>
|
<defs>
|
||||||
@@ -659,7 +707,7 @@
|
|||||||
<xhtml:p xmlns:xhtml="http://www.w3.org/1999/xhtml">referenced by:
|
<xhtml:p xmlns:xhtml="http://www.w3.org/1999/xhtml">referenced by:
|
||||||
<xhtml:ul>
|
<xhtml:ul>
|
||||||
<xhtml:li><xhtml:a href="#Definition" title="Definition">Definition</xhtml:a></xhtml:li>
|
<xhtml:li><xhtml:a href="#Definition" title="Definition">Definition</xhtml:a></xhtml:li>
|
||||||
<xhtml:li><xhtml:a href="#Query" title="Query">Query</xhtml:a></xhtml:li>
|
<xhtml:li><xhtml:a href="#PropertyQuery" title="PropertyQuery">PropertyQuery</xhtml:a></xhtml:li>
|
||||||
</xhtml:ul>
|
</xhtml:ul>
|
||||||
</xhtml:p><xhtml:br xmlns:xhtml="http://www.w3.org/1999/xhtml" /><xhtml:hr xmlns:xhtml="http://www.w3.org/1999/xhtml" />
|
</xhtml:p><xhtml:br xmlns:xhtml="http://www.w3.org/1999/xhtml" /><xhtml:hr xmlns:xhtml="http://www.w3.org/1999/xhtml" />
|
||||||
<xhtml:p xmlns:xhtml="http://www.w3.org/1999/xhtml">
|
<xhtml:p xmlns:xhtml="http://www.w3.org/1999/xhtml">
|
||||||
|
|||||||
+27
-34
@@ -47,6 +47,7 @@ typedef struct {
|
|||||||
} ALGORITHM;
|
} ALGORITHM;
|
||||||
|
|
||||||
struct ossl_method_store_st {
|
struct ossl_method_store_st {
|
||||||
|
OPENSSL_CTX *ctx;
|
||||||
size_t nelem;
|
size_t nelem;
|
||||||
SPARSE_ARRAY_OF(ALGORITHM) *algs;
|
SPARSE_ARRAY_OF(ALGORITHM) *algs;
|
||||||
OSSL_PROPERTY_LIST *global_properties;
|
OSSL_PROPERTY_LIST *global_properties;
|
||||||
@@ -82,29 +83,10 @@ int ossl_property_unlock(OSSL_METHOD_STORE *p)
|
|||||||
return p != 0 ? CRYPTO_THREAD_unlock(p->lock) : 0;
|
return p != 0 ? CRYPTO_THREAD_unlock(p->lock) : 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
int ossl_method_store_init(void)
|
static openssl_ctx_run_once_fn do_method_store_init;
|
||||||
|
int do_method_store_init(OPENSSL_CTX *ctx)
|
||||||
{
|
{
|
||||||
if (ossl_property_string_init()
|
return ossl_property_parse_init(ctx);
|
||||||
&& ossl_prop_defn_init()
|
|
||||||
&& ossl_property_parse_init())
|
|
||||||
return 1;
|
|
||||||
|
|
||||||
ossl_method_store_cleanup();
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
void ossl_method_store_cleanup(void)
|
|
||||||
{
|
|
||||||
ossl_property_string_cleanup();
|
|
||||||
ossl_prop_defn_cleanup();
|
|
||||||
}
|
|
||||||
|
|
||||||
static CRYPTO_ONCE method_store_init_flag = CRYPTO_ONCE_STATIC_INIT;
|
|
||||||
DEFINE_RUN_ONCE_STATIC(do_method_store_init)
|
|
||||||
{
|
|
||||||
return OPENSSL_init_crypto(0, NULL)
|
|
||||||
&& ossl_method_store_init()
|
|
||||||
&& OPENSSL_atexit(&ossl_method_store_cleanup);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
static unsigned long query_hash(const QUERY *a)
|
static unsigned long query_hash(const QUERY *a)
|
||||||
@@ -141,15 +123,22 @@ static void alg_cleanup(ossl_uintmax_t idx, ALGORITHM *a)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
OSSL_METHOD_STORE *ossl_method_store_new(void)
|
/*
|
||||||
|
* The OPENSSL_CTX param here allows access to underlying property data needed
|
||||||
|
* for computation
|
||||||
|
*/
|
||||||
|
OSSL_METHOD_STORE *ossl_method_store_new(OPENSSL_CTX *ctx)
|
||||||
{
|
{
|
||||||
OSSL_METHOD_STORE *res;
|
OSSL_METHOD_STORE *res;
|
||||||
|
|
||||||
if (!RUN_ONCE(&method_store_init_flag, do_method_store_init))
|
if (!openssl_ctx_run_once(ctx,
|
||||||
return 0;
|
OPENSSL_CTX_METHOD_STORE_RUN_ONCE_INDEX,
|
||||||
|
do_method_store_init))
|
||||||
|
return NULL;
|
||||||
|
|
||||||
res = OPENSSL_zalloc(sizeof(*res));
|
res = OPENSSL_zalloc(sizeof(*res));
|
||||||
if (res != NULL) {
|
if (res != NULL) {
|
||||||
|
res->ctx = ctx;
|
||||||
if ((res->algs = ossl_sa_ALGORITHM_new()) == NULL) {
|
if ((res->algs = ossl_sa_ALGORITHM_new()) == NULL) {
|
||||||
OPENSSL_free(res);
|
OPENSSL_free(res);
|
||||||
return NULL;
|
return NULL;
|
||||||
@@ -212,10 +201,11 @@ int ossl_method_store_add(OSSL_METHOD_STORE *store,
|
|||||||
*/
|
*/
|
||||||
ossl_property_write_lock(store);
|
ossl_property_write_lock(store);
|
||||||
ossl_method_cache_flush(store, nid);
|
ossl_method_cache_flush(store, nid);
|
||||||
if ((impl->properties = ossl_prop_defn_get(properties)) == NULL) {
|
if ((impl->properties = ossl_prop_defn_get(store->ctx, properties)) == NULL) {
|
||||||
if ((impl->properties = ossl_parse_property(properties)) == NULL)
|
impl->properties = ossl_parse_property(store->ctx, properties);
|
||||||
|
if (impl->properties == NULL)
|
||||||
goto err;
|
goto err;
|
||||||
ossl_prop_defn_set(properties, impl->properties);
|
ossl_prop_defn_set(store->ctx, properties, impl->properties);
|
||||||
}
|
}
|
||||||
|
|
||||||
alg = ossl_method_store_retrieve(store, nid);
|
alg = ossl_method_store_retrieve(store, nid);
|
||||||
@@ -287,7 +277,7 @@ int ossl_method_store_fetch(OSSL_METHOD_STORE *store, int nid,
|
|||||||
IMPLEMENTATION *impl;
|
IMPLEMENTATION *impl;
|
||||||
OSSL_PROPERTY_LIST *pq = NULL, *p2;
|
OSSL_PROPERTY_LIST *pq = NULL, *p2;
|
||||||
int ret = 0;
|
int ret = 0;
|
||||||
int j;
|
int j, best = -1, score, optional;
|
||||||
|
|
||||||
if (nid <= 0 || method == NULL || store == NULL)
|
if (nid <= 0 || method == NULL || store == NULL)
|
||||||
return 0;
|
return 0;
|
||||||
@@ -310,7 +300,7 @@ int ossl_method_store_fetch(OSSL_METHOD_STORE *store, int nid,
|
|||||||
}
|
}
|
||||||
goto fin;
|
goto fin;
|
||||||
}
|
}
|
||||||
pq = ossl_parse_query(prop_query);
|
pq = ossl_parse_query(store->ctx, prop_query);
|
||||||
if (pq == NULL)
|
if (pq == NULL)
|
||||||
goto fin;
|
goto fin;
|
||||||
if (store->global_properties != NULL) {
|
if (store->global_properties != NULL) {
|
||||||
@@ -320,13 +310,16 @@ int ossl_method_store_fetch(OSSL_METHOD_STORE *store, int nid,
|
|||||||
ossl_property_free(pq);
|
ossl_property_free(pq);
|
||||||
pq = p2;
|
pq = p2;
|
||||||
}
|
}
|
||||||
|
optional = ossl_property_has_optional(pq);
|
||||||
for (j = 0; j < sk_IMPLEMENTATION_num(alg->impls); j++) {
|
for (j = 0; j < sk_IMPLEMENTATION_num(alg->impls); j++) {
|
||||||
impl = sk_IMPLEMENTATION_value(alg->impls, j);
|
impl = sk_IMPLEMENTATION_value(alg->impls, j);
|
||||||
|
score = ossl_property_match_count(pq, impl->properties);
|
||||||
if (ossl_property_match(pq, impl->properties)) {
|
if (score > best) {
|
||||||
*method = impl->method;
|
*method = impl->method;
|
||||||
ret = 1;
|
ret = 1;
|
||||||
goto fin;
|
if (!optional)
|
||||||
|
goto fin;
|
||||||
|
best = score;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
fin:
|
fin:
|
||||||
@@ -350,7 +343,7 @@ int ossl_method_store_set_global_properties(OSSL_METHOD_STORE *store,
|
|||||||
ossl_property_unlock(store);
|
ossl_property_unlock(store);
|
||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
store->global_properties = ossl_parse_query(prop_query);
|
store->global_properties = ossl_parse_query(store->ctx, prop_query);
|
||||||
ret = store->global_properties != NULL;
|
ret = store->global_properties != NULL;
|
||||||
ossl_property_unlock(store);
|
ossl_property_unlock(store);
|
||||||
return ret;
|
return ret;
|
||||||
|
|||||||
@@ -14,35 +14,31 @@
|
|||||||
typedef struct ossl_property_list_st OSSL_PROPERTY_LIST;
|
typedef struct ossl_property_list_st OSSL_PROPERTY_LIST;
|
||||||
typedef int OSSL_PROPERTY_IDX;
|
typedef int OSSL_PROPERTY_IDX;
|
||||||
|
|
||||||
/* Initialisation and finalisation for subsystem */
|
|
||||||
int ossl_method_store_init(void);
|
|
||||||
void ossl_method_store_cleanup(void);
|
|
||||||
|
|
||||||
/* Property string functions */
|
/* Property string functions */
|
||||||
OSSL_PROPERTY_IDX ossl_property_name(const char *s, int create);
|
OSSL_PROPERTY_IDX ossl_property_name(OPENSSL_CTX *ctx, const char *s,
|
||||||
OSSL_PROPERTY_IDX ossl_property_value(const char *s, int create);
|
int create);
|
||||||
int ossl_property_string_init(void);
|
OSSL_PROPERTY_IDX ossl_property_value(OPENSSL_CTX *ctx, const char *s,
|
||||||
void ossl_property_string_cleanup(void);
|
int create);
|
||||||
|
|
||||||
/* Property list functions */
|
/* Property list functions */
|
||||||
int ossl_property_parse_init(void);
|
int ossl_property_parse_init(OPENSSL_CTX *ctx);
|
||||||
void ossl_property_free(OSSL_PROPERTY_LIST *p);
|
void ossl_property_free(OSSL_PROPERTY_LIST *p);
|
||||||
int ossl_property_match(const OSSL_PROPERTY_LIST *query,
|
int ossl_property_has_optional(const OSSL_PROPERTY_LIST *query);
|
||||||
const OSSL_PROPERTY_LIST *defn);
|
int ossl_property_match_count(const OSSL_PROPERTY_LIST *query,
|
||||||
|
const OSSL_PROPERTY_LIST *defn);
|
||||||
OSSL_PROPERTY_LIST *ossl_property_merge(const OSSL_PROPERTY_LIST *a,
|
OSSL_PROPERTY_LIST *ossl_property_merge(const OSSL_PROPERTY_LIST *a,
|
||||||
const OSSL_PROPERTY_LIST *b);
|
const OSSL_PROPERTY_LIST *b);
|
||||||
|
|
||||||
/* Property definition functions */
|
/* Property definition functions */
|
||||||
OSSL_PROPERTY_LIST *ossl_parse_property(const char *s);
|
OSSL_PROPERTY_LIST *ossl_parse_property(OPENSSL_CTX *ctx, const char *s);
|
||||||
|
|
||||||
/* Property query functions */
|
/* Property query functions */
|
||||||
OSSL_PROPERTY_LIST *ossl_parse_query(const char *s);
|
OSSL_PROPERTY_LIST *ossl_parse_query(OPENSSL_CTX *ctx, const char *s);
|
||||||
|
|
||||||
/* Property definition cache functions */
|
/* Property definition cache functions */
|
||||||
int ossl_prop_defn_init(void);
|
OSSL_PROPERTY_LIST *ossl_prop_defn_get(OPENSSL_CTX *ctx, const char *prop);
|
||||||
void ossl_prop_defn_cleanup(void);
|
int ossl_prop_defn_set(OPENSSL_CTX *ctx, const char *prop,
|
||||||
OSSL_PROPERTY_LIST *ossl_prop_defn_get(const char *prop);
|
OSSL_PROPERTY_LIST *pl);
|
||||||
int ossl_prop_defn_set(const char *prop, OSSL_PROPERTY_LIST *pl);
|
|
||||||
|
|
||||||
/* Property cache lock / unlock */
|
/* Property cache lock / unlock */
|
||||||
int ossl_property_write_lock(OSSL_METHOD_STORE *);
|
int ossl_property_write_lock(OSSL_METHOD_STORE *);
|
||||||
|
|||||||
@@ -32,6 +32,7 @@ typedef struct {
|
|||||||
OSSL_PROPERTY_IDX name_idx;
|
OSSL_PROPERTY_IDX name_idx;
|
||||||
PROPERTY_TYPE type;
|
PROPERTY_TYPE type;
|
||||||
PROPERTY_OPER oper;
|
PROPERTY_OPER oper;
|
||||||
|
unsigned int optional : 1;
|
||||||
union {
|
union {
|
||||||
int64_t int_val; /* Signed integer */
|
int64_t int_val; /* Signed integer */
|
||||||
OSSL_PROPERTY_IDX str_val; /* String */
|
OSSL_PROPERTY_IDX str_val; /* String */
|
||||||
@@ -40,6 +41,7 @@ typedef struct {
|
|||||||
|
|
||||||
struct ossl_property_list_st {
|
struct ossl_property_list_st {
|
||||||
int n;
|
int n;
|
||||||
|
unsigned int has_optional : 1;
|
||||||
PROPERTY_DEFINITION properties[1];
|
PROPERTY_DEFINITION properties[1];
|
||||||
};
|
};
|
||||||
|
|
||||||
@@ -78,7 +80,8 @@ static int match(const char *t[], const char m[], size_t m_len)
|
|||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
static int parse_name(const char *t[], int create, OSSL_PROPERTY_IDX *idx)
|
static int parse_name(OPENSSL_CTX *ctx, const char *t[], int create,
|
||||||
|
OSSL_PROPERTY_IDX *idx)
|
||||||
{
|
{
|
||||||
char name[100];
|
char name[100];
|
||||||
int err = 0;
|
int err = 0;
|
||||||
@@ -109,7 +112,7 @@ static int parse_name(const char *t[], int create, OSSL_PROPERTY_IDX *idx)
|
|||||||
name[i] = '\0';
|
name[i] = '\0';
|
||||||
*t = skip_space(s);
|
*t = skip_space(s);
|
||||||
if (!err) {
|
if (!err) {
|
||||||
*idx = ossl_property_name(name, user_name && create);
|
*idx = ossl_property_name(ctx, name, user_name && create);
|
||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
PROPerr(PROP_F_PARSE_NAME, PROP_R_NAME_TOO_LONG);
|
PROPerr(PROP_F_PARSE_NAME, PROP_R_NAME_TOO_LONG);
|
||||||
@@ -180,8 +183,8 @@ static int parse_oct(const char *t[], PROPERTY_DEFINITION *res)
|
|||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
static int parse_string(const char *t[], char delim, PROPERTY_DEFINITION *res,
|
static int parse_string(OPENSSL_CTX *ctx, const char *t[], char delim,
|
||||||
const int create)
|
PROPERTY_DEFINITION *res, const int create)
|
||||||
{
|
{
|
||||||
char v[1000];
|
char v[1000];
|
||||||
const char *s = *t;
|
const char *s = *t;
|
||||||
@@ -205,13 +208,13 @@ static int parse_string(const char *t[], char delim, PROPERTY_DEFINITION *res,
|
|||||||
if (err)
|
if (err)
|
||||||
PROPerr(PROP_F_PARSE_STRING, PROP_R_STRING_TOO_LONG);
|
PROPerr(PROP_F_PARSE_STRING, PROP_R_STRING_TOO_LONG);
|
||||||
else
|
else
|
||||||
res->v.str_val = ossl_property_value(v, create);
|
res->v.str_val = ossl_property_value(ctx, v, create);
|
||||||
res->type = PROPERTY_TYPE_STRING;
|
res->type = PROPERTY_TYPE_STRING;
|
||||||
return !err;
|
return !err;
|
||||||
}
|
}
|
||||||
|
|
||||||
static int parse_unquoted(const char *t[], PROPERTY_DEFINITION *res,
|
static int parse_unquoted(OPENSSL_CTX *ctx, const char *t[],
|
||||||
const int create)
|
PROPERTY_DEFINITION *res, const int create)
|
||||||
{
|
{
|
||||||
char v[1000];
|
char v[1000];
|
||||||
const char *s = *t;
|
const char *s = *t;
|
||||||
@@ -236,19 +239,20 @@ static int parse_unquoted(const char *t[], PROPERTY_DEFINITION *res,
|
|||||||
if (err)
|
if (err)
|
||||||
PROPerr(PROP_F_PARSE_UNQUOTED, PROP_R_STRING_TOO_LONG);
|
PROPerr(PROP_F_PARSE_UNQUOTED, PROP_R_STRING_TOO_LONG);
|
||||||
else
|
else
|
||||||
res->v.str_val = ossl_property_value(v, create);
|
res->v.str_val = ossl_property_value(ctx, v, create);
|
||||||
res->type = PROPERTY_TYPE_STRING;
|
res->type = PROPERTY_TYPE_STRING;
|
||||||
return !err;
|
return !err;
|
||||||
}
|
}
|
||||||
|
|
||||||
static int parse_value(const char *t[], PROPERTY_DEFINITION *res, int create)
|
static int parse_value(OPENSSL_CTX *ctx, const char *t[],
|
||||||
|
PROPERTY_DEFINITION *res, int create)
|
||||||
{
|
{
|
||||||
const char *s = *t;
|
const char *s = *t;
|
||||||
int r = 0;
|
int r = 0;
|
||||||
|
|
||||||
if (*s == '"' || *s == '\'') {
|
if (*s == '"' || *s == '\'') {
|
||||||
s++;
|
s++;
|
||||||
r = parse_string(&s, s[-1], res, create);
|
r = parse_string(ctx, &s, s[-1], res, create);
|
||||||
} else if (*s == '+') {
|
} else if (*s == '+') {
|
||||||
s++;
|
s++;
|
||||||
r = parse_number(&s, res);
|
r = parse_number(&s, res);
|
||||||
@@ -265,7 +269,7 @@ static int parse_value(const char *t[], PROPERTY_DEFINITION *res, int create)
|
|||||||
} else if (ossl_isdigit(*s)) {
|
} else if (ossl_isdigit(*s)) {
|
||||||
return parse_number(t, res);
|
return parse_number(t, res);
|
||||||
} else if (ossl_isalpha(*s))
|
} else if (ossl_isalpha(*s))
|
||||||
return parse_unquoted(t, res, create);
|
return parse_unquoted(ctx, t, res, create);
|
||||||
if (r)
|
if (r)
|
||||||
*t = s;
|
*t = s;
|
||||||
return r;
|
return r;
|
||||||
@@ -305,14 +309,17 @@ static OSSL_PROPERTY_LIST *stack_to_property_list(STACK_OF(PROPERTY_DEFINITION)
|
|||||||
if (r != NULL) {
|
if (r != NULL) {
|
||||||
sk_PROPERTY_DEFINITION_sort(sk);
|
sk_PROPERTY_DEFINITION_sort(sk);
|
||||||
|
|
||||||
for (i = 0; i < n; i++)
|
r->has_optional = 0;
|
||||||
|
for (i = 0; i < n; i++) {
|
||||||
r->properties[i] = *sk_PROPERTY_DEFINITION_value(sk, i);
|
r->properties[i] = *sk_PROPERTY_DEFINITION_value(sk, i);
|
||||||
|
r->has_optional |= r->properties[i].optional;
|
||||||
|
}
|
||||||
r->n = n;
|
r->n = n;
|
||||||
}
|
}
|
||||||
return r;
|
return r;
|
||||||
}
|
}
|
||||||
|
|
||||||
OSSL_PROPERTY_LIST *ossl_parse_property(const char *defn)
|
OSSL_PROPERTY_LIST *ossl_parse_property(OPENSSL_CTX *ctx, const char *defn)
|
||||||
{
|
{
|
||||||
PROPERTY_DEFINITION *prop = NULL;
|
PROPERTY_DEFINITION *prop = NULL;
|
||||||
OSSL_PROPERTY_LIST *res = NULL;
|
OSSL_PROPERTY_LIST *res = NULL;
|
||||||
@@ -330,7 +337,8 @@ OSSL_PROPERTY_LIST *ossl_parse_property(const char *defn)
|
|||||||
if (prop == NULL)
|
if (prop == NULL)
|
||||||
goto err;
|
goto err;
|
||||||
memset(&prop->v, 0, sizeof(prop->v));
|
memset(&prop->v, 0, sizeof(prop->v));
|
||||||
if (!parse_name(&s, 1, &prop->name_idx))
|
prop->optional = 0;
|
||||||
|
if (!parse_name(ctx, &s, 1, &prop->name_idx))
|
||||||
goto err;
|
goto err;
|
||||||
prop->oper = PROPERTY_OPER_EQ;
|
prop->oper = PROPERTY_OPER_EQ;
|
||||||
if (prop->name_idx == 0) {
|
if (prop->name_idx == 0) {
|
||||||
@@ -338,7 +346,7 @@ OSSL_PROPERTY_LIST *ossl_parse_property(const char *defn)
|
|||||||
goto err;
|
goto err;
|
||||||
}
|
}
|
||||||
if (match_ch(&s, '=')) {
|
if (match_ch(&s, '=')) {
|
||||||
if (!parse_value(&s, prop, 1)) {
|
if (!parse_value(ctx, &s, prop, 1)) {
|
||||||
PROPerr(PROP_F_OSSL_PARSE_PROPERTY, PROP_R_NO_VALUE);
|
PROPerr(PROP_F_OSSL_PARSE_PROPERTY, PROP_R_NO_VALUE);
|
||||||
goto err;
|
goto err;
|
||||||
}
|
}
|
||||||
@@ -365,7 +373,7 @@ err:
|
|||||||
return res;
|
return res;
|
||||||
}
|
}
|
||||||
|
|
||||||
OSSL_PROPERTY_LIST *ossl_parse_query(const char *s)
|
OSSL_PROPERTY_LIST *ossl_parse_query(OPENSSL_CTX *ctx, const char *s)
|
||||||
{
|
{
|
||||||
STACK_OF(PROPERTY_DEFINITION) *sk;
|
STACK_OF(PROPERTY_DEFINITION) *sk;
|
||||||
OSSL_PROPERTY_LIST *res = NULL;
|
OSSL_PROPERTY_LIST *res = NULL;
|
||||||
@@ -385,11 +393,13 @@ OSSL_PROPERTY_LIST *ossl_parse_query(const char *s)
|
|||||||
|
|
||||||
if (match_ch(&s, '-')) {
|
if (match_ch(&s, '-')) {
|
||||||
prop->oper = PROPERTY_OVERRIDE;
|
prop->oper = PROPERTY_OVERRIDE;
|
||||||
if (!parse_name(&s, 0, &prop->name_idx))
|
prop->optional = 0;
|
||||||
|
if (!parse_name(ctx, &s, 0, &prop->name_idx))
|
||||||
goto err;
|
goto err;
|
||||||
goto skip_value;
|
goto skip_value;
|
||||||
}
|
}
|
||||||
if (!parse_name(&s, 0, &prop->name_idx))
|
prop->optional = match_ch(&s, '?');
|
||||||
|
if (!parse_name(ctx, &s, 0, &prop->name_idx))
|
||||||
goto err;
|
goto err;
|
||||||
|
|
||||||
if (match_ch(&s, '=')) {
|
if (match_ch(&s, '=')) {
|
||||||
@@ -403,7 +413,7 @@ OSSL_PROPERTY_LIST *ossl_parse_query(const char *s)
|
|||||||
prop->v.str_val = ossl_property_true;
|
prop->v.str_val = ossl_property_true;
|
||||||
goto skip_value;
|
goto skip_value;
|
||||||
}
|
}
|
||||||
if (!parse_value(&s, prop, 0))
|
if (!parse_value(ctx, &s, prop, 0))
|
||||||
prop->type = PROPERTY_TYPE_VALUE_UNDEFINED;
|
prop->type = PROPERTY_TYPE_VALUE_UNDEFINED;
|
||||||
|
|
||||||
skip_value:
|
skip_value:
|
||||||
@@ -424,12 +434,22 @@ err:
|
|||||||
return res;
|
return res;
|
||||||
}
|
}
|
||||||
|
|
||||||
int ossl_property_match(const OSSL_PROPERTY_LIST *query,
|
/* Does a property query have any optional clauses */
|
||||||
const OSSL_PROPERTY_LIST *defn)
|
int ossl_property_has_optional(const OSSL_PROPERTY_LIST *query)
|
||||||
|
{
|
||||||
|
return query->has_optional ? 1 : 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Compare a query against a definition.
|
||||||
|
* Return the number of clauses matched or -1 if a mandatory clause is false.
|
||||||
|
*/
|
||||||
|
int ossl_property_match_count(const OSSL_PROPERTY_LIST *query,
|
||||||
|
const OSSL_PROPERTY_LIST *defn)
|
||||||
{
|
{
|
||||||
const PROPERTY_DEFINITION *const q = query->properties;
|
const PROPERTY_DEFINITION *const q = query->properties;
|
||||||
const PROPERTY_DEFINITION *const d = defn->properties;
|
const PROPERTY_DEFINITION *const d = defn->properties;
|
||||||
int i = 0, j = 0;
|
int i = 0, j = 0, matches = 0;
|
||||||
PROPERTY_OPER oper;
|
PROPERTY_OPER oper;
|
||||||
|
|
||||||
while (i < query->n) {
|
while (i < query->n) {
|
||||||
@@ -446,9 +466,11 @@ int ossl_property_match(const OSSL_PROPERTY_LIST *query,
|
|||||||
const int eq = q[i].type == d[j].type
|
const int eq = q[i].type == d[j].type
|
||||||
&& memcmp(&q[i].v, &d[j].v, sizeof(q[i].v)) == 0;
|
&& memcmp(&q[i].v, &d[j].v, sizeof(q[i].v)) == 0;
|
||||||
|
|
||||||
if ((eq && oper != PROPERTY_OPER_EQ)
|
if ((eq && oper == PROPERTY_OPER_EQ)
|
||||||
|| (!eq && oper != PROPERTY_OPER_NE))
|
|| (!eq && oper == PROPERTY_OPER_NE))
|
||||||
return 0;
|
matches++;
|
||||||
|
else if (!q[i].optional)
|
||||||
|
return -1;
|
||||||
i++;
|
i++;
|
||||||
j++;
|
j++;
|
||||||
continue;
|
continue;
|
||||||
@@ -461,18 +483,23 @@ int ossl_property_match(const OSSL_PROPERTY_LIST *query,
|
|||||||
* the latter is treated as a comparison against the Boolean false.
|
* the latter is treated as a comparison against the Boolean false.
|
||||||
*/
|
*/
|
||||||
if (q[i].type == PROPERTY_TYPE_VALUE_UNDEFINED) {
|
if (q[i].type == PROPERTY_TYPE_VALUE_UNDEFINED) {
|
||||||
if (oper != PROPERTY_OPER_NE)
|
if (oper == PROPERTY_OPER_NE)
|
||||||
return 0;
|
matches++;
|
||||||
|
else if (!q[i].optional)
|
||||||
|
return -1;
|
||||||
} else if (q[i].type != PROPERTY_TYPE_STRING
|
} else if (q[i].type != PROPERTY_TYPE_STRING
|
||||||
|| (oper == PROPERTY_OPER_EQ
|
|| (oper == PROPERTY_OPER_EQ
|
||||||
&& q[i].v.str_val != ossl_property_false)
|
&& q[i].v.str_val != ossl_property_false)
|
||||||
|| (oper == PROPERTY_OPER_NE
|
|| (oper == PROPERTY_OPER_NE
|
||||||
&& q[i].v.str_val == ossl_property_false)) {
|
&& q[i].v.str_val == ossl_property_false)) {
|
||||||
return 0;
|
if (!q[i].optional)
|
||||||
|
return -1;
|
||||||
|
} else {
|
||||||
|
matches++;
|
||||||
}
|
}
|
||||||
i++;
|
i++;
|
||||||
}
|
}
|
||||||
return 1;
|
return matches;
|
||||||
}
|
}
|
||||||
|
|
||||||
void ossl_property_free(OSSL_PROPERTY_LIST *p)
|
void ossl_property_free(OSSL_PROPERTY_LIST *p)
|
||||||
@@ -519,7 +546,7 @@ OSSL_PROPERTY_LIST *ossl_property_merge(const OSSL_PROPERTY_LIST *a,
|
|||||||
return r;
|
return r;
|
||||||
}
|
}
|
||||||
|
|
||||||
int ossl_property_parse_init(void)
|
int ossl_property_parse_init(OPENSSL_CTX *ctx)
|
||||||
{
|
{
|
||||||
static const char *const predefined_names[] = {
|
static const char *const predefined_names[] = {
|
||||||
"default", /* Being provided by the default built-in provider */
|
"default", /* Being provided by the default built-in provider */
|
||||||
@@ -532,12 +559,12 @@ int ossl_property_parse_init(void)
|
|||||||
size_t i;
|
size_t i;
|
||||||
|
|
||||||
for (i = 0; i < OSSL_NELEM(predefined_names); i++)
|
for (i = 0; i < OSSL_NELEM(predefined_names); i++)
|
||||||
if (ossl_property_name(predefined_names[i], 1) == 0)
|
if (ossl_property_name(ctx, predefined_names[i], 1) == 0)
|
||||||
goto err;
|
goto err;
|
||||||
|
|
||||||
/* Pre-populate the two Boolean values */
|
/* Pre-populate the two Boolean values */
|
||||||
if ((ossl_property_true = ossl_property_value("yes", 1)) == 0
|
if ((ossl_property_true = ossl_property_value(ctx, "yes", 1)) == 0
|
||||||
|| (ossl_property_false = ossl_property_value("no", 1)) == 0)
|
|| (ossl_property_false = ossl_property_value(ctx, "no", 1)) == 0)
|
||||||
goto err;
|
goto err;
|
||||||
|
|
||||||
return 1;
|
return 1;
|
||||||
|
|||||||
@@ -34,10 +34,12 @@ typedef struct {
|
|||||||
DEFINE_LHASH_OF(PROPERTY_STRING);
|
DEFINE_LHASH_OF(PROPERTY_STRING);
|
||||||
typedef LHASH_OF(PROPERTY_STRING) PROP_TABLE;
|
typedef LHASH_OF(PROPERTY_STRING) PROP_TABLE;
|
||||||
|
|
||||||
static PROP_TABLE *prop_names;
|
typedef struct {
|
||||||
static PROP_TABLE *prop_values;
|
PROP_TABLE *prop_names;
|
||||||
static OSSL_PROPERTY_IDX prop_name_idx = 0;
|
PROP_TABLE *prop_values;
|
||||||
static OSSL_PROPERTY_IDX prop_value_idx = 0;
|
OSSL_PROPERTY_IDX prop_name_idx;
|
||||||
|
OSSL_PROPERTY_IDX prop_value_idx;
|
||||||
|
} PROPERTY_STRING_DATA;
|
||||||
|
|
||||||
static unsigned long property_hash(const PROPERTY_STRING *a)
|
static unsigned long property_hash(const PROPERTY_STRING *a)
|
||||||
{
|
{
|
||||||
@@ -65,6 +67,48 @@ static void property_table_free(PROP_TABLE **pt)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static void property_string_data_free(void *vpropdata)
|
||||||
|
{
|
||||||
|
PROPERTY_STRING_DATA *propdata = vpropdata;
|
||||||
|
|
||||||
|
if (propdata == NULL)
|
||||||
|
return;
|
||||||
|
|
||||||
|
property_table_free(&propdata->prop_names);
|
||||||
|
property_table_free(&propdata->prop_values);
|
||||||
|
propdata->prop_name_idx = propdata->prop_value_idx = 0;
|
||||||
|
|
||||||
|
OPENSSL_free(propdata);
|
||||||
|
}
|
||||||
|
|
||||||
|
static void *property_string_data_new(OPENSSL_CTX *ctx) {
|
||||||
|
PROPERTY_STRING_DATA *propdata = OPENSSL_zalloc(sizeof(*propdata));
|
||||||
|
|
||||||
|
if (propdata == NULL)
|
||||||
|
return NULL;
|
||||||
|
|
||||||
|
propdata->prop_names = lh_PROPERTY_STRING_new(&property_hash,
|
||||||
|
&property_cmp);
|
||||||
|
if (propdata->prop_names == NULL)
|
||||||
|
goto err;
|
||||||
|
|
||||||
|
propdata->prop_values = lh_PROPERTY_STRING_new(&property_hash,
|
||||||
|
&property_cmp);
|
||||||
|
if (propdata->prop_values == NULL)
|
||||||
|
goto err;
|
||||||
|
|
||||||
|
return propdata;
|
||||||
|
|
||||||
|
err:
|
||||||
|
property_string_data_free(propdata);
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
|
|
||||||
|
static const OPENSSL_CTX_METHOD property_string_data_method = {
|
||||||
|
property_string_data_new,
|
||||||
|
property_string_data_free,
|
||||||
|
};
|
||||||
|
|
||||||
static PROPERTY_STRING *new_property_string(const char *s,
|
static PROPERTY_STRING *new_property_string(const char *s,
|
||||||
OSSL_PROPERTY_IDX *pidx)
|
OSSL_PROPERTY_IDX *pidx)
|
||||||
{
|
{
|
||||||
@@ -103,35 +147,30 @@ static OSSL_PROPERTY_IDX ossl_property_string(PROP_TABLE *t,
|
|||||||
return ps != NULL ? ps->idx : 0;
|
return ps != NULL ? ps->idx : 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
OSSL_PROPERTY_IDX ossl_property_name(const char *s, int create)
|
OSSL_PROPERTY_IDX ossl_property_name(OPENSSL_CTX *ctx, const char *s,
|
||||||
|
int create)
|
||||||
{
|
{
|
||||||
return ossl_property_string(prop_names, create ? &prop_name_idx : NULL, s);
|
PROPERTY_STRING_DATA *propdata
|
||||||
}
|
= openssl_ctx_get_data(ctx, OPENSSL_CTX_PROPERTY_STRING_INDEX,
|
||||||
|
&property_string_data_method);
|
||||||
|
|
||||||
OSSL_PROPERTY_IDX ossl_property_value(const char *s, int create)
|
if (propdata == NULL)
|
||||||
{
|
|
||||||
return ossl_property_string(prop_values, create ? &prop_value_idx : NULL, s);
|
|
||||||
}
|
|
||||||
|
|
||||||
int ossl_property_string_init(void)
|
|
||||||
{
|
|
||||||
prop_names = lh_PROPERTY_STRING_new(&property_hash, &property_cmp);
|
|
||||||
if (prop_names == NULL)
|
|
||||||
return 0;
|
return 0;
|
||||||
|
return ossl_property_string(propdata->prop_names,
|
||||||
prop_values = lh_PROPERTY_STRING_new(&property_hash, &property_cmp);
|
create ? &propdata->prop_name_idx : NULL,
|
||||||
if (prop_values == NULL)
|
s);
|
||||||
goto err;
|
|
||||||
return 1;
|
|
||||||
|
|
||||||
err:
|
|
||||||
ossl_property_string_cleanup();
|
|
||||||
return 0;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void ossl_property_string_cleanup(void)
|
OSSL_PROPERTY_IDX ossl_property_value(OPENSSL_CTX *ctx, const char *s,
|
||||||
|
int create)
|
||||||
{
|
{
|
||||||
property_table_free(&prop_names);
|
PROPERTY_STRING_DATA *propdata
|
||||||
property_table_free(&prop_values);
|
= openssl_ctx_get_data(ctx, OPENSSL_CTX_PROPERTY_STRING_INDEX,
|
||||||
prop_name_idx = prop_value_idx = 0;
|
&property_string_data_method);
|
||||||
|
|
||||||
|
if (propdata == NULL)
|
||||||
|
return 0;
|
||||||
|
return ossl_property_string(propdata->prop_values,
|
||||||
|
create ? &propdata->prop_value_idx : NULL,
|
||||||
|
s);
|
||||||
}
|
}
|
||||||
+20
-21
@@ -54,6 +54,9 @@ struct ossl_provider_st {
|
|||||||
OSSL_provider_get_param_types_fn *get_param_types;
|
OSSL_provider_get_param_types_fn *get_param_types;
|
||||||
OSSL_provider_get_params_fn *get_params;
|
OSSL_provider_get_params_fn *get_params;
|
||||||
OSSL_provider_query_operation_fn *query_operation;
|
OSSL_provider_query_operation_fn *query_operation;
|
||||||
|
|
||||||
|
/* Provider side data */
|
||||||
|
void *provctx;
|
||||||
};
|
};
|
||||||
DEFINE_STACK_OF(OSSL_PROVIDER)
|
DEFINE_STACK_OF(OSSL_PROVIDER)
|
||||||
|
|
||||||
@@ -76,7 +79,6 @@ struct provider_store_st {
|
|||||||
CRYPTO_RWLOCK *lock;
|
CRYPTO_RWLOCK *lock;
|
||||||
unsigned int use_fallbacks:1;
|
unsigned int use_fallbacks:1;
|
||||||
};
|
};
|
||||||
static int provider_store_index = -1;
|
|
||||||
|
|
||||||
static void provider_store_free(void *vstore)
|
static void provider_store_free(void *vstore)
|
||||||
{
|
{
|
||||||
@@ -89,7 +91,7 @@ static void provider_store_free(void *vstore)
|
|||||||
OPENSSL_free(store);
|
OPENSSL_free(store);
|
||||||
}
|
}
|
||||||
|
|
||||||
static void *provider_store_new(void)
|
static void *provider_store_new(OPENSSL_CTX *ctx)
|
||||||
{
|
{
|
||||||
struct provider_store_st *store = OPENSSL_zalloc(sizeof(*store));
|
struct provider_store_st *store = OPENSSL_zalloc(sizeof(*store));
|
||||||
const struct predefined_providers_st *p = NULL;
|
const struct predefined_providers_st *p = NULL;
|
||||||
@@ -131,23 +133,12 @@ static const OPENSSL_CTX_METHOD provider_store_method = {
|
|||||||
provider_store_free,
|
provider_store_free,
|
||||||
};
|
};
|
||||||
|
|
||||||
static CRYPTO_ONCE provider_store_init_flag = CRYPTO_ONCE_STATIC_INIT;
|
|
||||||
DEFINE_RUN_ONCE_STATIC(do_provider_store_init)
|
|
||||||
{
|
|
||||||
return OPENSSL_init_crypto(0, NULL)
|
|
||||||
&& (provider_store_index =
|
|
||||||
openssl_ctx_new_index(&provider_store_method)) != -1;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
static struct provider_store_st *get_provider_store(OPENSSL_CTX *libctx)
|
static struct provider_store_st *get_provider_store(OPENSSL_CTX *libctx)
|
||||||
{
|
{
|
||||||
struct provider_store_st *store = NULL;
|
struct provider_store_st *store = NULL;
|
||||||
|
|
||||||
if (!RUN_ONCE(&provider_store_init_flag, do_provider_store_init))
|
store = openssl_ctx_get_data(libctx, OPENSSL_CTX_PROVIDER_STORE_INDEX,
|
||||||
return NULL;
|
&provider_store_method);
|
||||||
|
|
||||||
store = openssl_ctx_get_data(libctx, provider_store_index);
|
|
||||||
if (store == NULL)
|
if (store == NULL)
|
||||||
CRYPTOerr(CRYPTO_F_GET_PROVIDER_STORE, ERR_R_INTERNAL_ERROR);
|
CRYPTOerr(CRYPTO_F_GET_PROVIDER_STORE, ERR_R_INTERNAL_ERROR);
|
||||||
return store;
|
return store;
|
||||||
@@ -275,7 +266,7 @@ void ossl_provider_free(OSSL_PROVIDER *prov)
|
|||||||
*/
|
*/
|
||||||
if (ref < 2 && prov->flag_initialized) {
|
if (ref < 2 && prov->flag_initialized) {
|
||||||
if (prov->teardown != NULL)
|
if (prov->teardown != NULL)
|
||||||
prov->teardown();
|
prov->teardown(prov->provctx);
|
||||||
prov->flag_initialized = 0;
|
prov->flag_initialized = 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -401,7 +392,8 @@ static int provider_activate(OSSL_PROVIDER *prov)
|
|||||||
}
|
}
|
||||||
|
|
||||||
if (prov->init_function == NULL
|
if (prov->init_function == NULL
|
||||||
|| !prov->init_function(prov, core_dispatch, &provider_dispatch)) {
|
|| !prov->init_function(prov, core_dispatch, &provider_dispatch,
|
||||||
|
&prov->provctx)) {
|
||||||
CRYPTOerr(CRYPTO_F_PROVIDER_ACTIVATE, ERR_R_INIT_FAIL);
|
CRYPTOerr(CRYPTO_F_PROVIDER_ACTIVATE, ERR_R_INIT_FAIL);
|
||||||
ERR_add_error_data(2, "name=", prov->name);
|
ERR_add_error_data(2, "name=", prov->name);
|
||||||
DSO_free(prov->module);
|
DSO_free(prov->module);
|
||||||
@@ -448,6 +440,11 @@ int ossl_provider_activate(OSSL_PROVIDER *prov)
|
|||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void *ossl_provider_ctx(const OSSL_PROVIDER *prov)
|
||||||
|
{
|
||||||
|
return prov->provctx;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
static int provider_forall_loaded(struct provider_store_st *store,
|
static int provider_forall_loaded(struct provider_store_st *store,
|
||||||
int *found_activated,
|
int *found_activated,
|
||||||
@@ -573,18 +570,20 @@ const char *ossl_provider_module_path(OSSL_PROVIDER *prov)
|
|||||||
void ossl_provider_teardown(const OSSL_PROVIDER *prov)
|
void ossl_provider_teardown(const OSSL_PROVIDER *prov)
|
||||||
{
|
{
|
||||||
if (prov->teardown != NULL)
|
if (prov->teardown != NULL)
|
||||||
prov->teardown();
|
prov->teardown(prov->provctx);
|
||||||
}
|
}
|
||||||
|
|
||||||
const OSSL_ITEM *ossl_provider_get_param_types(const OSSL_PROVIDER *prov)
|
const OSSL_ITEM *ossl_provider_get_param_types(const OSSL_PROVIDER *prov)
|
||||||
{
|
{
|
||||||
return prov->get_param_types == NULL ? NULL : prov->get_param_types(prov);
|
return prov->get_param_types == NULL
|
||||||
|
? NULL : prov->get_param_types(prov->provctx);
|
||||||
}
|
}
|
||||||
|
|
||||||
int ossl_provider_get_params(const OSSL_PROVIDER *prov,
|
int ossl_provider_get_params(const OSSL_PROVIDER *prov,
|
||||||
const OSSL_PARAM params[])
|
const OSSL_PARAM params[])
|
||||||
{
|
{
|
||||||
return prov->get_params == NULL ? 0 : prov->get_params(prov, params);
|
return prov->get_params == NULL
|
||||||
|
? 0 : prov->get_params(prov->provctx, params);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@@ -592,7 +591,7 @@ const OSSL_ALGORITHM *ossl_provider_query_operation(const OSSL_PROVIDER *prov,
|
|||||||
int operation_id,
|
int operation_id,
|
||||||
int *no_cache)
|
int *no_cache)
|
||||||
{
|
{
|
||||||
return prov->query_operation(prov, operation_id, no_cache);
|
return prov->query_operation(prov->provctx, operation_id, no_cache);
|
||||||
}
|
}
|
||||||
|
|
||||||
/*-
|
/*-
|
||||||
|
|||||||
@@ -1,6 +1,5 @@
|
|||||||
LIBS=../../libcrypto
|
LIBS=../../libcrypto
|
||||||
SOURCE[../../libcrypto]=\
|
SOURCE[../../libcrypto]=\
|
||||||
randfile.c rand_lib.c rand_err.c rand_crng_test.c rand_egd.c \
|
randfile.c rand_lib.c rand_err.c rand_crng_test.c rand_egd.c \
|
||||||
rand_win.c rand_unix.c rand_vms.c drbg_lib.c drbg_ctr.c \
|
rand_win.c rand_unix.c rand_vms.c drbg_lib.c drbg_ctr.c rand_vxworks.c \
|
||||||
drbg_hash.c drbg_hmac.c
|
drbg_hash.c drbg_hmac.c
|
||||||
|
|
||||||
+12
-2
@@ -1101,6 +1101,17 @@ static int drbg_add(const void *buf, int num, double randomness)
|
|||||||
|
|
||||||
buflen = (size_t)num;
|
buflen = (size_t)num;
|
||||||
|
|
||||||
|
#ifdef FIPS_MODE
|
||||||
|
/*
|
||||||
|
* NIST SP-800-90A mandates that entropy *shall not* be provided
|
||||||
|
* by the consuming application. By setting the randomness to zero,
|
||||||
|
* we ensure that the buffer contents will be added to the internal
|
||||||
|
* state of the DRBG only as additional data.
|
||||||
|
*
|
||||||
|
* (NIST SP-800-90Ar1, Sections 9.1 and 9.2)
|
||||||
|
*/
|
||||||
|
randomness = 0.0;
|
||||||
|
#endif
|
||||||
if (buflen < seedlen || randomness < (double) seedlen) {
|
if (buflen < seedlen || randomness < (double) seedlen) {
|
||||||
#if defined(OPENSSL_RAND_SEED_NONE)
|
#if defined(OPENSSL_RAND_SEED_NONE)
|
||||||
/*
|
/*
|
||||||
@@ -1117,7 +1128,7 @@ static int drbg_add(const void *buf, int num, double randomness)
|
|||||||
return ret;
|
return ret;
|
||||||
#else
|
#else
|
||||||
/*
|
/*
|
||||||
* If an os entropy source is avaible then we declare the buffer content
|
* If an os entropy source is available then we declare the buffer content
|
||||||
* as additional data by setting randomness to zero and trigger a regular
|
* as additional data by setting randomness to zero and trigger a regular
|
||||||
* reseeding.
|
* reseeding.
|
||||||
*/
|
*/
|
||||||
@@ -1125,7 +1136,6 @@ static int drbg_add(const void *buf, int num, double randomness)
|
|||||||
#endif
|
#endif
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
if (randomness > (double)seedlen) {
|
if (randomness > (double)seedlen) {
|
||||||
/*
|
/*
|
||||||
* The purpose of this check is to bound |randomness| by a
|
* The purpose of this check is to bound |randomness| by a
|
||||||
|
|||||||
@@ -13,45 +13,52 @@
|
|||||||
*/
|
*/
|
||||||
|
|
||||||
#include <string.h>
|
#include <string.h>
|
||||||
|
#include <openssl/evp.h>
|
||||||
#include "internal/rand_int.h"
|
#include "internal/rand_int.h"
|
||||||
#include "internal/thread_once.h"
|
#include "internal/thread_once.h"
|
||||||
#include "rand_lcl.h"
|
#include "rand_lcl.h"
|
||||||
|
|
||||||
static RAND_POOL *crngt_pool;
|
static RAND_POOL *crngt_pool;
|
||||||
static unsigned char *crngt_prev;
|
static unsigned char crngt_prev[EVP_MAX_MD_SIZE];
|
||||||
|
|
||||||
int (*crngt_get_entropy)(unsigned char *) = &rand_crngt_get_entropy_cb;
|
int (*crngt_get_entropy)(unsigned char *, unsigned char *, unsigned int *)
|
||||||
|
= &rand_crngt_get_entropy_cb;
|
||||||
|
|
||||||
int rand_crngt_get_entropy_cb(unsigned char *buf)
|
int rand_crngt_get_entropy_cb(unsigned char *buf, unsigned char *md,
|
||||||
|
unsigned int *md_size)
|
||||||
{
|
{
|
||||||
|
int r;
|
||||||
size_t n;
|
size_t n;
|
||||||
unsigned char *p;
|
unsigned char *p;
|
||||||
|
|
||||||
while ((n = rand_pool_acquire_entropy(crngt_pool)) != 0)
|
n = rand_pool_acquire_entropy(crngt_pool);
|
||||||
if (n >= CRNGT_BUFSIZ) {
|
if (n >= CRNGT_BUFSIZ) {
|
||||||
p = rand_pool_detach(crngt_pool);
|
p = rand_pool_detach(crngt_pool);
|
||||||
|
r = EVP_Digest(p, CRNGT_BUFSIZ, md, md_size, EVP_sha256(), NULL);
|
||||||
|
if (r != 0)
|
||||||
memcpy(buf, p, CRNGT_BUFSIZ);
|
memcpy(buf, p, CRNGT_BUFSIZ);
|
||||||
rand_pool_reattach(crngt_pool, p);
|
rand_pool_reattach(crngt_pool, p);
|
||||||
return 1;
|
return r;
|
||||||
}
|
}
|
||||||
return 0;
|
return 0;
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void rand_crngt_cleanup(void)
|
void rand_crngt_cleanup(void)
|
||||||
{
|
{
|
||||||
rand_pool_free(crngt_pool);
|
rand_pool_free(crngt_pool);
|
||||||
OPENSSL_secure_free(crngt_prev);
|
|
||||||
crngt_pool = NULL;
|
crngt_pool = NULL;
|
||||||
crngt_prev = NULL;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
int rand_crngt_init(void)
|
int rand_crngt_init(void)
|
||||||
{
|
{
|
||||||
|
unsigned char buf[CRNGT_BUFSIZ];
|
||||||
|
|
||||||
if ((crngt_pool = rand_pool_new(0, CRNGT_BUFSIZ, CRNGT_BUFSIZ)) == NULL)
|
if ((crngt_pool = rand_pool_new(0, CRNGT_BUFSIZ, CRNGT_BUFSIZ)) == NULL)
|
||||||
return 0;
|
return 0;
|
||||||
if ((crngt_prev = OPENSSL_secure_malloc(CRNGT_BUFSIZ)) != NULL
|
if (crngt_get_entropy(buf, crngt_prev, NULL)) {
|
||||||
&& crngt_get_entropy(crngt_prev))
|
OPENSSL_cleanse(buf, sizeof(buf));
|
||||||
return 1;
|
return 1;
|
||||||
|
}
|
||||||
rand_crngt_cleanup();
|
rand_crngt_cleanup();
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
@@ -74,7 +81,8 @@ size_t rand_crngt_get_entropy(RAND_DRBG *drbg,
|
|||||||
int entropy, size_t min_len, size_t max_len,
|
int entropy, size_t min_len, size_t max_len,
|
||||||
int prediction_resistance)
|
int prediction_resistance)
|
||||||
{
|
{
|
||||||
unsigned char buf[CRNGT_BUFSIZ];
|
unsigned char buf[CRNGT_BUFSIZ], md[EVP_MAX_MD_SIZE];
|
||||||
|
unsigned int sz;
|
||||||
RAND_POOL *pool;
|
RAND_POOL *pool;
|
||||||
size_t q, r = 0, s, t = 0;
|
size_t q, r = 0, s, t = 0;
|
||||||
int attempts = 3;
|
int attempts = 3;
|
||||||
@@ -87,17 +95,18 @@ size_t rand_crngt_get_entropy(RAND_DRBG *drbg,
|
|||||||
|
|
||||||
while ((q = rand_pool_bytes_needed(pool, 1)) > 0 && attempts-- > 0) {
|
while ((q = rand_pool_bytes_needed(pool, 1)) > 0 && attempts-- > 0) {
|
||||||
s = q > sizeof(buf) ? sizeof(buf) : q;
|
s = q > sizeof(buf) ? sizeof(buf) : q;
|
||||||
if (!crngt_get_entropy(buf)
|
if (!crngt_get_entropy(buf, md, &sz)
|
||||||
|| memcmp(crngt_prev, buf, CRNGT_BUFSIZ) == 0
|
|| memcmp(crngt_prev, md, sz) == 0
|
||||||
|| !rand_pool_add(pool, buf, s, s * 8))
|
|| !rand_pool_add(pool, buf, s, s * 8))
|
||||||
goto err;
|
goto err;
|
||||||
memcpy(crngt_prev, buf, CRNGT_BUFSIZ);
|
memcpy(crngt_prev, md, sz);
|
||||||
t += s;
|
t += s;
|
||||||
attempts++;
|
attempts++;
|
||||||
}
|
}
|
||||||
r = t;
|
r = t;
|
||||||
*pout = rand_pool_detach(pool);
|
*pout = rand_pool_detach(pool);
|
||||||
err:
|
err:
|
||||||
|
OPENSSL_cleanse(buf, sizeof(buf));
|
||||||
rand_pool_free(pool);
|
rand_pool_free(pool);
|
||||||
return r;
|
return r;
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -334,8 +334,10 @@ int drbg_hmac_init(RAND_DRBG *drbg);
|
|||||||
* Entropy call back for the FIPS 140-2 section 4.9.2 Conditional Tests.
|
* Entropy call back for the FIPS 140-2 section 4.9.2 Conditional Tests.
|
||||||
* These need to be exposed for the unit tests.
|
* These need to be exposed for the unit tests.
|
||||||
*/
|
*/
|
||||||
int rand_crngt_get_entropy_cb(unsigned char *buf);
|
int rand_crngt_get_entropy_cb(unsigned char *buf, unsigned char *md,
|
||||||
extern int (*crngt_get_entropy)(unsigned char *);
|
unsigned int *md_size);
|
||||||
|
extern int (*crngt_get_entropy)(unsigned char *buf, unsigned char *md,
|
||||||
|
unsigned int *md_size);
|
||||||
int rand_crngt_init(void);
|
int rand_crngt_init(void);
|
||||||
void rand_crngt_cleanup(void);
|
void rand_crngt_cleanup(void);
|
||||||
|
|
||||||
|
|||||||
+6
-26
@@ -30,7 +30,8 @@
|
|||||||
# include <sys/param.h>
|
# include <sys/param.h>
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#if defined(OPENSSL_SYS_UNIX) || defined(__DJGPP__)
|
#if (defined(OPENSSL_SYS_UNIX) && !defined(OPENSSL_SYS_VXWORKS)) \
|
||||||
|
|| defined(__DJGPP__)
|
||||||
# include <sys/types.h>
|
# include <sys/types.h>
|
||||||
# include <sys/stat.h>
|
# include <sys/stat.h>
|
||||||
# include <fcntl.h>
|
# include <fcntl.h>
|
||||||
@@ -88,30 +89,8 @@ static uint64_t get_timer_bits(void);
|
|||||||
# undef OPENSSL_RAND_SEED_EGD
|
# undef OPENSSL_RAND_SEED_EGD
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#if (defined(OPENSSL_SYS_VXWORKS) || defined(OPENSSL_SYS_UEFI)) && \
|
#if defined(OPENSSL_SYS_UEFI) && !defined(OPENSSL_RAND_SEED_NONE)
|
||||||
!defined(OPENSSL_RAND_SEED_NONE)
|
# error "UEFI only supports seeding NONE"
|
||||||
# error "UEFI and VXWorks only support seeding NONE"
|
|
||||||
#endif
|
|
||||||
|
|
||||||
#if defined(OPENSSL_SYS_VXWORKS)
|
|
||||||
/* empty implementation */
|
|
||||||
int rand_pool_init(void)
|
|
||||||
{
|
|
||||||
return 1;
|
|
||||||
}
|
|
||||||
|
|
||||||
void rand_pool_cleanup(void)
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
void rand_pool_keep_random_devices_open(int keep)
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
size_t rand_pool_acquire_entropy(RAND_POOL *pool)
|
|
||||||
{
|
|
||||||
return rand_pool_entropy_available(pool);
|
|
||||||
}
|
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#if !(defined(OPENSSL_SYS_WINDOWS) || defined(OPENSSL_SYS_WIN32) \
|
#if !(defined(OPENSSL_SYS_WINDOWS) || defined(OPENSSL_SYS_WIN32) \
|
||||||
@@ -608,7 +587,8 @@ size_t rand_pool_acquire_entropy(RAND_POOL *pool)
|
|||||||
# endif
|
# endif
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#if defined(OPENSSL_SYS_UNIX) || defined(__DJGPP__)
|
#if (defined(OPENSSL_SYS_UNIX) && !defined(OPENSSL_SYS_VXWORKS)) \
|
||||||
|
|| defined(__DJGPP__)
|
||||||
int rand_pool_add_nonce_data(RAND_POOL *pool)
|
int rand_pool_add_nonce_data(RAND_POOL *pool)
|
||||||
{
|
{
|
||||||
struct {
|
struct {
|
||||||
|
|||||||
@@ -0,0 +1,171 @@
|
|||||||
|
/*
|
||||||
|
* Copyright 2019 The OpenSSL Project Authors. All Rights Reserved.
|
||||||
|
*
|
||||||
|
* Licensed under the OpenSSL license (the "License"). You may not use
|
||||||
|
* this file except in compliance with the License. You can obtain a copy
|
||||||
|
* in the file LICENSE in the source distribution or at
|
||||||
|
* https://www.openssl.org/source/license.html
|
||||||
|
*/
|
||||||
|
|
||||||
|
#include <openssl/opensslconf.h>
|
||||||
|
|
||||||
|
#ifndef OPENSSL_SYS_VXWORKS
|
||||||
|
NON_EMPTY_TRANSLATION_UNIT
|
||||||
|
#else
|
||||||
|
# include <openssl/rand.h>
|
||||||
|
# include "rand_lcl.h"
|
||||||
|
# include "internal/rand_int.h"
|
||||||
|
# include "internal/cryptlib.h"
|
||||||
|
# include <version.h>
|
||||||
|
# include <taskLib.h>
|
||||||
|
|
||||||
|
# if defined(OPENSSL_RAND_SEED_NONE)
|
||||||
|
/* none means none */
|
||||||
|
# undef OPENSSL_RAND_SEED_OS
|
||||||
|
# endif
|
||||||
|
|
||||||
|
# if defined(OPENSSL_RAND_SEED_OS)
|
||||||
|
# if _WRS_VXWORKS_MAJOR >= 7
|
||||||
|
# define RAND_SEED_VXRANDLIB
|
||||||
|
# else
|
||||||
|
# error "VxWorks <7 only support RAND_SEED_NONE"
|
||||||
|
# endif
|
||||||
|
# endif
|
||||||
|
|
||||||
|
# if defined(RAND_SEED_VXRANDLIB)
|
||||||
|
# include <randomNumGen.h>
|
||||||
|
# endif
|
||||||
|
|
||||||
|
/* Macro to convert two thirty two bit values into a sixty four bit one */
|
||||||
|
# define TWO32TO64(a, b) ((((uint64_t)(a)) << 32) + (b))
|
||||||
|
|
||||||
|
static uint64_t get_time_stamp(void)
|
||||||
|
{
|
||||||
|
struct timespec ts;
|
||||||
|
|
||||||
|
if (clock_gettime(CLOCK_REALTIME, &ts) == 0)
|
||||||
|
return TWO32TO64(ts.tv_sec, ts.tv_nsec);
|
||||||
|
return time(NULL);
|
||||||
|
}
|
||||||
|
|
||||||
|
static uint64_t get_timer_bits(void)
|
||||||
|
{
|
||||||
|
uint64_t res = OPENSSL_rdtsc();
|
||||||
|
struct timespec ts;
|
||||||
|
|
||||||
|
if (res != 0)
|
||||||
|
return res;
|
||||||
|
|
||||||
|
if (clock_gettime(CLOCK_MONOTONIC, &ts) == 0)
|
||||||
|
return TWO32TO64(ts.tv_sec, ts.tv_nsec);
|
||||||
|
return time(NULL);
|
||||||
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
* empty implementation
|
||||||
|
* vxworks does not need to init/cleanup or keep open the random lib
|
||||||
|
*/
|
||||||
|
int rand_pool_init(void)
|
||||||
|
{
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
void rand_pool_cleanup(void)
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
void rand_pool_keep_random_devices_open(int keep)
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
int rand_pool_add_additional_data(RAND_POOL *pool)
|
||||||
|
{
|
||||||
|
struct {
|
||||||
|
CRYPTO_THREAD_ID tid;
|
||||||
|
uint64_t time;
|
||||||
|
} data;
|
||||||
|
|
||||||
|
memset(&data, 0, sizeof(data));
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Add some noise from the thread id and a high resolution timer.
|
||||||
|
* The thread id adds a little randomness if the drbg is accessed
|
||||||
|
* concurrently (which is the case for the <master> drbg).
|
||||||
|
*/
|
||||||
|
data.tid = CRYPTO_THREAD_get_current_id();
|
||||||
|
data.time = get_timer_bits();
|
||||||
|
|
||||||
|
return rand_pool_add(pool, (unsigned char *)&data, sizeof(data), 0);
|
||||||
|
}
|
||||||
|
|
||||||
|
int rand_pool_add_nonce_data(RAND_POOL *pool)
|
||||||
|
{
|
||||||
|
struct {
|
||||||
|
pid_t pid;
|
||||||
|
CRYPTO_THREAD_ID tid;
|
||||||
|
uint64_t time;
|
||||||
|
} data;
|
||||||
|
|
||||||
|
memset(&data, 0, sizeof(data));
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Add process id, thread id, and a high resolution timestamp to
|
||||||
|
* ensure that the nonce is unique with high probability for
|
||||||
|
* different process instances.
|
||||||
|
*/
|
||||||
|
data.pid = getpid();
|
||||||
|
data.tid = CRYPTO_THREAD_get_current_id();
|
||||||
|
data.time = get_time_stamp();
|
||||||
|
|
||||||
|
return rand_pool_add(pool, (unsigned char *)&data, sizeof(data), 0);
|
||||||
|
}
|
||||||
|
|
||||||
|
size_t rand_pool_acquire_entropy(RAND_POOL *pool)
|
||||||
|
{
|
||||||
|
# if defined(RAND_SEED_VXRANDLIB)
|
||||||
|
/* vxRandLib based entropy method */
|
||||||
|
size_t bytes_needed;
|
||||||
|
|
||||||
|
bytes_needed = rand_pool_bytes_needed(pool, 1 /*entropy_factor*/);
|
||||||
|
if (bytes_needed > 0)
|
||||||
|
{
|
||||||
|
int retryCount = 0;
|
||||||
|
STATUS result = ERROR;
|
||||||
|
unsigned char *buffer;
|
||||||
|
|
||||||
|
buffer = rand_pool_add_begin(pool, bytes_needed);
|
||||||
|
while ((result != OK) && (retryCount < 10)) {
|
||||||
|
RANDOM_NUM_GEN_STATUS status = randStatus();
|
||||||
|
|
||||||
|
if ((status == RANDOM_NUM_GEN_ENOUGH_ENTROPY)
|
||||||
|
|| (status == RANDOM_NUM_GEN_MAX_ENTROPY) ) {
|
||||||
|
result = randBytes(buffer, bytes_needed);
|
||||||
|
if (result == OK)
|
||||||
|
rand_pool_add_end(pool, bytes_needed, 8 * bytes_needed);
|
||||||
|
/*
|
||||||
|
* no else here: randStatus said ok, if randBytes failed
|
||||||
|
* it will result in another loop or no entropy
|
||||||
|
*/
|
||||||
|
} else {
|
||||||
|
/*
|
||||||
|
* give a minimum delay here to allow OS to collect more
|
||||||
|
* entropy. taskDelay duration will depend on the system tick,
|
||||||
|
* this is by design as the sw-random lib uses interrupts
|
||||||
|
* which will at least happen during ticks
|
||||||
|
*/
|
||||||
|
taskDelay(5);
|
||||||
|
}
|
||||||
|
retryCount++;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return rand_pool_entropy_available(pool);
|
||||||
|
# else
|
||||||
|
/*
|
||||||
|
* SEED_NONE means none, without randlib we dont have entropy and
|
||||||
|
* rely on it being added externally
|
||||||
|
*/
|
||||||
|
return rand_pool_entropy_available(pool);
|
||||||
|
# endif /* defined(RAND_SEED_VXRANDLIB) */
|
||||||
|
}
|
||||||
|
|
||||||
|
#endif /* OPENSSL_SYS_VXWORKS */
|
||||||
@@ -25,11 +25,9 @@ int RSA_check_key(const RSA *key)
|
|||||||
int RSA_check_key_ex(const RSA *key, BN_GENCB *cb)
|
int RSA_check_key_ex(const RSA *key, BN_GENCB *cb)
|
||||||
{
|
{
|
||||||
#ifdef FIPS_MODE
|
#ifdef FIPS_MODE
|
||||||
if (!(rsa_sp800_56b_check_public(key)
|
return rsa_sp800_56b_check_public(key)
|
||||||
&& rsa_sp800_56b_check_private(key)
|
&& rsa_sp800_56b_check_private(key)
|
||||||
&& rsa_sp800_56b_check_keypair(key, NULL, -1, RSA_bits(key))
|
&& rsa_sp800_56b_check_keypair(key, NULL, -1, RSA_bits(key));
|
||||||
return 0;
|
|
||||||
|
|
||||||
#else
|
#else
|
||||||
BIGNUM *i, *j, *k, *l, *m;
|
BIGNUM *i, *j, *k, *l, *m;
|
||||||
BN_CTX *ctx;
|
BN_CTX *ctx;
|
||||||
|
|||||||
@@ -56,7 +56,7 @@ static int pkey_rsa_init(EVP_PKEY_CTX *ctx)
|
|||||||
|
|
||||||
if (rctx == NULL)
|
if (rctx == NULL)
|
||||||
return 0;
|
return 0;
|
||||||
rctx->nbits = 1024;
|
rctx->nbits = 2048;
|
||||||
rctx->primes = RSA_DEFAULT_PRIME_NUM;
|
rctx->primes = RSA_DEFAULT_PRIME_NUM;
|
||||||
if (pkey_ctx_is_pss(ctx))
|
if (pkey_ctx_is_pss(ctx))
|
||||||
rctx->pad_mode = RSA_PKCS1_PSS_PADDING;
|
rctx->pad_mode = RSA_PKCS1_PSS_PADDING;
|
||||||
@@ -89,6 +89,7 @@ static int pkey_rsa_copy(EVP_PKEY_CTX *dst, const EVP_PKEY_CTX *src)
|
|||||||
dctx->pad_mode = sctx->pad_mode;
|
dctx->pad_mode = sctx->pad_mode;
|
||||||
dctx->md = sctx->md;
|
dctx->md = sctx->md;
|
||||||
dctx->mgf1md = sctx->mgf1md;
|
dctx->mgf1md = sctx->mgf1md;
|
||||||
|
dctx->saltlen = sctx->saltlen;
|
||||||
if (sctx->oaep_label) {
|
if (sctx->oaep_label) {
|
||||||
OPENSSL_free(dctx->oaep_label);
|
OPENSSL_free(dctx->oaep_label);
|
||||||
dctx->oaep_label = OPENSSL_memdup(sctx->oaep_label, sctx->oaep_labellen);
|
dctx->oaep_label = OPENSSL_memdup(sctx->oaep_label, sctx->oaep_labellen);
|
||||||
|
|||||||
@@ -11,7 +11,6 @@
|
|||||||
#include "internal/cryptlib.h"
|
#include "internal/cryptlib.h"
|
||||||
#include "internal/numbers.h"
|
#include "internal/numbers.h"
|
||||||
#include <openssl/stack.h>
|
#include <openssl/stack.h>
|
||||||
#include <openssl/objects.h>
|
|
||||||
#include <errno.h>
|
#include <errno.h>
|
||||||
#include <openssl/e_os2.h> /* For ossl_inline */
|
#include <openssl/e_os2.h> /* For ossl_inline */
|
||||||
|
|
||||||
@@ -307,20 +306,20 @@ static int internal_find(OPENSSL_STACK *st, const void *data,
|
|||||||
}
|
}
|
||||||
if (data == NULL)
|
if (data == NULL)
|
||||||
return -1;
|
return -1;
|
||||||
r = OBJ_bsearch_ex_(&data, st->data, st->num, sizeof(void *), st->comp,
|
r = ossl_bsearch(&data, st->data, st->num, sizeof(void *), st->comp,
|
||||||
ret_val_options);
|
ret_val_options);
|
||||||
|
|
||||||
return r == NULL ? -1 : (int)((const void **)r - st->data);
|
return r == NULL ? -1 : (int)((const void **)r - st->data);
|
||||||
}
|
}
|
||||||
|
|
||||||
int OPENSSL_sk_find(OPENSSL_STACK *st, const void *data)
|
int OPENSSL_sk_find(OPENSSL_STACK *st, const void *data)
|
||||||
{
|
{
|
||||||
return internal_find(st, data, OBJ_BSEARCH_FIRST_VALUE_ON_MATCH);
|
return internal_find(st, data, OSSL_BSEARCH_FIRST_VALUE_ON_MATCH);
|
||||||
}
|
}
|
||||||
|
|
||||||
int OPENSSL_sk_find_ex(OPENSSL_STACK *st, const void *data)
|
int OPENSSL_sk_find_ex(OPENSSL_STACK *st, const void *data)
|
||||||
{
|
{
|
||||||
return internal_find(st, data, OBJ_BSEARCH_VALUE_ON_NOMATCH);
|
return internal_find(st, data, OSSL_BSEARCH_VALUE_ON_NOMATCH);
|
||||||
}
|
}
|
||||||
|
|
||||||
int OPENSSL_sk_push(OPENSSL_STACK *st, const void *data)
|
int OPENSSL_sk_push(OPENSSL_STACK *st, const void *data)
|
||||||
|
|||||||
@@ -15,10 +15,10 @@ ossl_method_store_cache_get, ossl_method_store_cache_set
|
|||||||
|
|
||||||
typedef struct ossl_method_store_st OSSL_METHOD_STORE;
|
typedef struct ossl_method_store_st OSSL_METHOD_STORE;
|
||||||
|
|
||||||
OSSL_METHOD_STORE *ossl_method_store_new(void);
|
OSSL_METHOD_STORE *ossl_method_store_new(OPENSSL_CTX *ctx);
|
||||||
void ossl_method_store_free(OSSL_METHOD_STORE *store);
|
void ossl_method_store_free(OSSL_METHOD_STORE *store);
|
||||||
int ossl_method_store_init(void);
|
int ossl_method_store_init(OPENSSL_CTX *ctx);
|
||||||
void ossl_method_store_cleanup(void);
|
void ossl_method_store_cleanup(OPENSSL_CTX *ctx);
|
||||||
int ossl_method_store_add(OSSL_METHOD_STORE *store,
|
int ossl_method_store_add(OSSL_METHOD_STORE *store,
|
||||||
int nid, const char *properties,
|
int nid, const char *properties,
|
||||||
void *method, void (*method_destruct)(void *));
|
void *method, void (*method_destruct)(void *));
|
||||||
@@ -51,12 +51,14 @@ separately (see L</Cache Functions> below).
|
|||||||
|
|
||||||
=head2 Store Functions
|
=head2 Store Functions
|
||||||
|
|
||||||
ossl_method_store_init() initialises the method store subsystem.
|
ossl_method_store_init() initialises the method store subsystem in the scope of
|
||||||
|
the library context B<ctx>.
|
||||||
|
|
||||||
ossl_method_store_cleanup() cleans up and shuts down the implementation method
|
ossl_method_store_cleanup() cleans up and shuts down the implementation method
|
||||||
store subsystem.
|
store subsystem in the scope of the library context B<ctx>.
|
||||||
|
|
||||||
ossl_method_store_new() create a new empty method store.
|
ossl_method_store_new() create a new empty method store using the supplied
|
||||||
|
B<ctx> to allow access to the required underlying property data.
|
||||||
|
|
||||||
ossl_method_store_free() frees resources allocated to B<store>.
|
ossl_method_store_free() frees resources allocated to B<store>.
|
||||||
|
|
||||||
|
|||||||
@@ -10,17 +10,16 @@ evp_generic_fetch - generic algorithm fetcher and method creator for EVP
|
|||||||
#include "evp_locl.h"
|
#include "evp_locl.h"
|
||||||
|
|
||||||
void *evp_generic_fetch(OPENSSL_CTX *libctx, int operation_id,
|
void *evp_generic_fetch(OPENSSL_CTX *libctx, int operation_id,
|
||||||
const char *algorithm, const char *properties,
|
const char *name, const char *properties,
|
||||||
void *(*new_method)(int nid, const OSSL_DISPATCH *fns,
|
void *(*new_method)(const OSSL_DISPATCH *fns,
|
||||||
OSSL_PROVIDER *prov),
|
OSSL_PROVIDER *prov),
|
||||||
int (*upref_method)(void *),
|
int (*upref_method)(void *),
|
||||||
void (*free_method)(void *),
|
void (*free_method)(void *));
|
||||||
int (*nid_method)(void *));
|
|
||||||
|
|
||||||
=head1 DESCRIPTION
|
=head1 DESCRIPTION
|
||||||
|
|
||||||
evp_generic_fetch() calls ossl_method_construct() with the given
|
evp_generic_fetch() calls ossl_method_construct() with the given
|
||||||
C<libctx>, C<operation_id>, C<algorithm>, and C<properties> and uses
|
C<libctx>, C<operation_id>, C<name>, and C<properties> and uses
|
||||||
it to create an EVP method with the help of the functions
|
it to create an EVP method with the help of the functions
|
||||||
C<new_method>, C<upref_method>, and C<free_method>.
|
C<new_method>, C<upref_method>, and C<free_method>.
|
||||||
|
|
||||||
@@ -42,10 +41,6 @@ one.
|
|||||||
|
|
||||||
frees the given method.
|
frees the given method.
|
||||||
|
|
||||||
=item nid_method()
|
|
||||||
|
|
||||||
returns the nid associated with the given method.
|
|
||||||
|
|
||||||
=back
|
=back
|
||||||
|
|
||||||
=head1 RETURN VALUES
|
=head1 RETURN VALUES
|
||||||
@@ -80,7 +75,6 @@ And here's the implementation of the FOO method fetcher:
|
|||||||
/* typedef struct evp_foo_st EVP_FOO */
|
/* typedef struct evp_foo_st EVP_FOO */
|
||||||
struct evp_foo_st {
|
struct evp_foo_st {
|
||||||
OSSL_PROVIDER *prov;
|
OSSL_PROVIDER *prov;
|
||||||
int nid;
|
|
||||||
CRYPTO_REF_COUNT refcnt;
|
CRYPTO_REF_COUNT refcnt;
|
||||||
OSSL_OP_foo_newctx_fn *newctx;
|
OSSL_OP_foo_newctx_fn *newctx;
|
||||||
OSSL_OP_foo_init_fn *init;
|
OSSL_OP_foo_init_fn *init;
|
||||||
@@ -93,7 +87,7 @@ And here's the implementation of the FOO method fetcher:
|
|||||||
* In this example, we have a public method creator and destructor.
|
* In this example, we have a public method creator and destructor.
|
||||||
* It's not absolutely necessary, but is in the spirit of OpenSSL.
|
* It's not absolutely necessary, but is in the spirit of OpenSSL.
|
||||||
*/
|
*/
|
||||||
EVP_FOO *EVP_FOO_meth_from_dispatch(int foo_type, const OSSL_DISPATCH *fns,
|
EVP_FOO *EVP_FOO_meth_from_dispatch(const OSSL_DISPATCH *fns,
|
||||||
OSSL_PROVIDER *prov)
|
OSSL_PROVIDER *prov)
|
||||||
{
|
{
|
||||||
EVP_FOO *foo = NULL;
|
EVP_FOO *foo = NULL;
|
||||||
@@ -120,7 +114,6 @@ And here's the implementation of the FOO method fetcher:
|
|||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
foo->nid = foo_type;
|
|
||||||
foo->prov = prov;
|
foo->prov = prov;
|
||||||
if (prov)
|
if (prov)
|
||||||
ossl_provider_upref(prov);
|
ossl_provider_upref(prov);
|
||||||
@@ -138,10 +131,10 @@ And here's the implementation of the FOO method fetcher:
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
static void *foo_from_dispatch(int nid, const OSSL_DISPATCH *fns,
|
static void *foo_from_dispatch(const OSSL_DISPATCH *fns,
|
||||||
OSSL_PROVIDER *prov)
|
OSSL_PROVIDER *prov)
|
||||||
{
|
{
|
||||||
return EVP_FOO_meth_from_dispatch(nid, fns, prov);
|
return EVP_FOO_meth_from_dispatch(fns, prov);
|
||||||
}
|
}
|
||||||
|
|
||||||
static int foo_upref(void *vfoo)
|
static int foo_upref(void *vfoo)
|
||||||
@@ -159,11 +152,21 @@ And here's the implementation of the FOO method fetcher:
|
|||||||
}
|
}
|
||||||
|
|
||||||
EVP_FOO *EVP_FOO_fetch(OPENSSL_CTX *ctx,
|
EVP_FOO *EVP_FOO_fetch(OPENSSL_CTX *ctx,
|
||||||
const char *algorithm,
|
const char *name,
|
||||||
const char *properties)
|
const char *properties)
|
||||||
{
|
{
|
||||||
return evp_generic_fetch(ctx, OSSL_OP_FOO, algorithm, properties,
|
EVP_FOO *foo =
|
||||||
foo_from_dispatch, foo_upref, foo_free);
|
evp_generic_fetch(ctx, OSSL_OP_FOO, name, properties,
|
||||||
|
foo_from_dispatch, foo_upref, foo_free);
|
||||||
|
|
||||||
|
/*
|
||||||
|
* If this method exists in legacy form, with a constant NID for the
|
||||||
|
* given |name|, this is the spot to find that NID and set it in
|
||||||
|
* the newly constructed EVP_FOO instance.
|
||||||
|
*/
|
||||||
|
|
||||||
|
return foo;
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
And finally, the library functions:
|
And finally, the library functions:
|
||||||
|
|||||||
@@ -2,7 +2,8 @@
|
|||||||
|
|
||||||
=head1 NAME
|
=head1 NAME
|
||||||
|
|
||||||
openssl_ctx_new_index, openssl_ctx_get_data - internal OPENSSL_CTX routines
|
openssl_ctx_get_data, openssl_ctx_run_once, openssl_ctx_onfree
|
||||||
|
- internal OPENSSL_CTX routines
|
||||||
|
|
||||||
=head1 SYNOPSIS
|
=head1 SYNOPSIS
|
||||||
|
|
||||||
@@ -10,12 +11,16 @@ openssl_ctx_new_index, openssl_ctx_get_data - internal OPENSSL_CTX routines
|
|||||||
#include "internal/cryptlib.h"
|
#include "internal/cryptlib.h"
|
||||||
|
|
||||||
typedef struct openssl_ctx_method {
|
typedef struct openssl_ctx_method {
|
||||||
void *(*new_func)(void);
|
void *(*new_func)(OPENSSL_CTX *ctx);
|
||||||
void (*free_func)(void *);
|
void (*free_func)(void *);
|
||||||
} OPENSSL_CTX_METHOD;
|
} OPENSSL_CTX_METHOD;
|
||||||
|
|
||||||
int openssl_ctx_new_index(const OPENSSL_CTX_METHOD *meth);
|
void *openssl_ctx_get_data(OPENSSL_CTX *ctx, int index,
|
||||||
void *openssl_ctx_get_data(OPENSSL_CTX *ctx, int index);
|
const OPENSSL_CTX_METHOD *meth);
|
||||||
|
|
||||||
|
int openssl_ctx_run_once(OPENSSL_CTX *ctx, unsigned int idx,
|
||||||
|
openssl_ctx_run_once_fn run_once_fn);
|
||||||
|
int openssl_ctx_onfree(OPENSSL_CTX *ctx, openssl_ctx_onfree_fn onfreefn);
|
||||||
|
|
||||||
=head1 DESCRIPTION
|
=head1 DESCRIPTION
|
||||||
|
|
||||||
@@ -23,27 +28,33 @@ Internally, the OpenSSL library context C<OPENSSL_CTX> is implemented
|
|||||||
as a C<CRYPTO_EX_DATA>, which allows data from diverse parts of the
|
as a C<CRYPTO_EX_DATA>, which allows data from diverse parts of the
|
||||||
library to be added and removed dynamically.
|
library to be added and removed dynamically.
|
||||||
Each such data item must have a corresponding CRYPTO_EX_DATA index
|
Each such data item must have a corresponding CRYPTO_EX_DATA index
|
||||||
associated with it.
|
associated with it. Unlike normal CRYPTO_EX_DATA objects we use static indexes
|
||||||
|
to identify data items. These are mapped transparetnly to CRYPTO_EX_DATA dynamic
|
||||||
|
indexes internally to the implementation.
|
||||||
See the example further down to see how that's done.
|
See the example further down to see how that's done.
|
||||||
|
|
||||||
openssl_ctx_new_index() allocates a new library context index, and
|
openssl_ctx_get_data() is used to retrieve a pointer to the data in
|
||||||
associates it with the functions given through C<meth>.
|
the library context C<ctx> associated with the given C<index>. An
|
||||||
The functions given through that method are used to create or free
|
OPENSSL_CTX_METHOD must be defined and given in the C<meth> parameter. The index
|
||||||
items that are stored at that index whenever a library context is
|
for it should be defined in cryptlib.h. The functions through the method are
|
||||||
created or freed, meaning that the code that use a data item of that
|
used to create or free items that are stored at that index whenever a library
|
||||||
|
context is created or freed, meaning that the code that use a data item of that
|
||||||
index doesn't have to worry about that, just use the data available.
|
index doesn't have to worry about that, just use the data available.
|
||||||
|
|
||||||
Deallocation of an index happens automatically when the library
|
Deallocation of an index happens automatically when the library
|
||||||
context is freed.
|
context is freed.
|
||||||
|
|
||||||
openssl_ctx_get_data() is used to retrieve a pointer to the data in
|
openssl_ctx_run_once is used to run some initialisation routine C<run_once_fn>
|
||||||
the library context C<ctx> associated with the given C<index>.
|
exactly once per library context C<ctx> object. Each initialisation routine
|
||||||
|
should be allocate a unique run once index in cryptlib.h.
|
||||||
|
|
||||||
|
Any resources allocated via a run once initialisation routine can be cleaned up
|
||||||
|
using openssl_ctx_onfree. This associates an "on free" routine C<onfreefn> with
|
||||||
|
the library context C<ctx>. When C<ctx> is freed all associated "on free"
|
||||||
|
routines are called.
|
||||||
|
|
||||||
=head1 RETURN VALUES
|
=head1 RETURN VALUES
|
||||||
|
|
||||||
openssl_ctx_new_index() returns -1 on error, otherwise the allocated
|
|
||||||
index number.
|
|
||||||
|
|
||||||
openssl_ctx_get_data() returns a pointer on success, or C<NULL> on
|
openssl_ctx_get_data() returns a pointer on success, or C<NULL> on
|
||||||
failure.
|
failure.
|
||||||
|
|
||||||
@@ -53,17 +64,14 @@ failure.
|
|||||||
|
|
||||||
For a type C<FOO> that should end up in the OpenSSL library context, a
|
For a type C<FOO> that should end up in the OpenSSL library context, a
|
||||||
small bit of initialization is needed, i.e. to associate a constructor
|
small bit of initialization is needed, i.e. to associate a constructor
|
||||||
and a destructor to a new index.
|
and a destructor to an index.
|
||||||
|
|
||||||
/* The index will always be entirely global, and dynamically allocated */
|
|
||||||
static int foo_index = -1;
|
|
||||||
|
|
||||||
typedef struct foo_st {
|
typedef struct foo_st {
|
||||||
int i;
|
int i;
|
||||||
void *data;
|
void *data;
|
||||||
} FOO;
|
} FOO;
|
||||||
|
|
||||||
static void *foo_new(void)
|
static void *foo_new(OPENSSL_CTX *ctx)
|
||||||
{
|
{
|
||||||
FOO *ptr = OPENSSL_zalloc(sizeof(*foo));
|
FOO *ptr = OPENSSL_zalloc(sizeof(*foo));
|
||||||
if (ptr != NULL)
|
if (ptr != NULL)
|
||||||
@@ -74,27 +82,49 @@ and a destructor to a new index.
|
|||||||
{
|
{
|
||||||
OPENSSL_free(ptr);
|
OPENSSL_free(ptr);
|
||||||
}
|
}
|
||||||
static const OPENSSL_CTX_METHOD foo_method = {
|
|
||||||
|
/*
|
||||||
|
* Include a reference to this in the methods table in context.c
|
||||||
|
* OPENSSL_CTX_FOO_INDEX should be added to internal/cryptlib.h
|
||||||
|
*/
|
||||||
|
const OPENSSL_CTX_METHOD foo_method = {
|
||||||
foo_new,
|
foo_new,
|
||||||
foo_free
|
foo_free
|
||||||
};
|
};
|
||||||
|
|
||||||
static int foo_init(void)
|
|
||||||
{
|
|
||||||
foo_index = openssl_ctx_new_index(foo_method);
|
|
||||||
|
|
||||||
return foo_index != -1;
|
|
||||||
}
|
|
||||||
|
|
||||||
=head2 Usage
|
=head2 Usage
|
||||||
|
|
||||||
To get and use the data stored in the library context, simply do this:
|
To get and use the data stored in the library context, simply do this:
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* ctx is received from a caller,
|
* ctx is received from a caller,
|
||||||
* foo_index comes from the example above
|
|
||||||
*/
|
*/
|
||||||
FOO *data = openssl_ctx_get_data(ctx, foo_index);
|
FOO *data = openssl_ctx_get_data(ctx, OPENSSL_CTX_FOO_INDEX, &foo_method);
|
||||||
|
|
||||||
|
=head2 Run Once
|
||||||
|
|
||||||
|
void foo_cleanup(OPENSSL_CTX *ctx)
|
||||||
|
{
|
||||||
|
/* Free foo resources associated with ctx */
|
||||||
|
}
|
||||||
|
|
||||||
|
static openssl_ctx_run_once_fn do_foo_init;
|
||||||
|
static int do_foo_init(OPENSSL_CTX *ctx)
|
||||||
|
{
|
||||||
|
/* Allocate and initialise some foo resources and associated with ctx */
|
||||||
|
return openssl_ctx_onfree(ctx, &foo_cleanup)
|
||||||
|
}
|
||||||
|
|
||||||
|
int foo_some_function(OPENSSL_CTX *ctx)
|
||||||
|
{
|
||||||
|
if (!openssl_ctx_run_once(ctx,
|
||||||
|
OPENSSL_CTX_FOO_RUN_ONCE_INDEX,
|
||||||
|
do_foo_init))
|
||||||
|
return 0;
|
||||||
|
|
||||||
|
/* Do some work using foo resources in ctx */
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
=head1 SEE ALSO
|
=head1 SEE ALSO
|
||||||
|
|
||||||
|
|||||||
@@ -11,17 +11,17 @@ OSSL_METHOD_CONSTRUCT_METHOD, ossl_method_construct
|
|||||||
|
|
||||||
struct ossl_method_construct_method_st {
|
struct ossl_method_construct_method_st {
|
||||||
/* Create store */
|
/* Create store */
|
||||||
void *(*alloc_tmp_store)(void);
|
void *(*alloc_tmp_store)(OPENSSL_CTX *ctx);
|
||||||
/* Remove a store */
|
/* Remove a store */
|
||||||
void (*dealloc_tmp_store)(void *store);
|
void (*dealloc_tmp_store)(void *store);
|
||||||
/* Get an already existing method from a store */
|
/* Get an already existing method from a store */
|
||||||
void *(*get)(OPENSSL_CTX *libctx, void *store, const char *propquery,
|
void *(*get)(OPENSSL_CTX *libctx, void *store, const char *name,
|
||||||
void *data);
|
const char *propquery, void *data);
|
||||||
/* Store a method in a store */
|
/* Store a method in a store */
|
||||||
int (*put)(OPENSSL_CTX *libctx, void *store, const char *propdef,
|
int (*put)(OPENSSL_CTX *libctx, void *store, void *method,
|
||||||
void *method, void *data);
|
const char *name, const char *propdef, void *data);
|
||||||
/* Construct a new method */
|
/* Construct a new method */
|
||||||
void *(*construct)(const char *algorithm_name, const OSSL_DISPATCH *fns,
|
void *(*construct)(const char *name, const OSSL_DISPATCH *fns,
|
||||||
OSSL_PROVIDER *prov, void *data);
|
OSSL_PROVIDER *prov, void *data);
|
||||||
/* Destruct a method */
|
/* Destruct a method */
|
||||||
void (*destruct)(void *method);
|
void (*destruct)(void *method);
|
||||||
@@ -33,6 +33,7 @@ OSSL_METHOD_CONSTRUCT_METHOD, ossl_method_construct
|
|||||||
int force_cache,
|
int force_cache,
|
||||||
OSSL_METHOD_CONSTRUCT_METHOD *mcm, void *mcm_data);
|
OSSL_METHOD_CONSTRUCT_METHOD *mcm, void *mcm_data);
|
||||||
|
|
||||||
|
|
||||||
=head1 DESCRIPTION
|
=head1 DESCRIPTION
|
||||||
|
|
||||||
All libcrypto sub-systems that want to create their own methods based
|
All libcrypto sub-systems that want to create their own methods based
|
||||||
@@ -65,7 +66,7 @@ function pointers:
|
|||||||
|
|
||||||
=item alloc_tmp_store()
|
=item alloc_tmp_store()
|
||||||
|
|
||||||
Create a temporary method store.
|
Create a temporary method store in the scope of the library context C<ctx>.
|
||||||
This store is used to temporarily store methods for easier lookup, for
|
This store is used to temporarily store methods for easier lookup, for
|
||||||
when the provider doesn't want its dispatch table stored in a longer
|
when the provider doesn't want its dispatch table stored in a longer
|
||||||
term cache.
|
term cache.
|
||||||
@@ -76,14 +77,15 @@ Remove a temporary store.
|
|||||||
|
|
||||||
=item get()
|
=item get()
|
||||||
|
|
||||||
Look up an already existing method from a store.
|
Look up an already existing method from a store by name.
|
||||||
|
|
||||||
The store may be given with C<store>.
|
The store may be given with C<store>.
|
||||||
B<NULL> is a valid value and means that a sub-system default store
|
B<NULL> is a valid value and means that a sub-system default store
|
||||||
must be used.
|
must be used.
|
||||||
This default store should be stored in the library context C<libctx>.
|
This default store should be stored in the library context C<libctx>.
|
||||||
|
|
||||||
The method to be looked up should be identified with data from C<data>
|
The method to be looked up should be identified with the given C<name> and
|
||||||
|
data from C<data>
|
||||||
(which is the C<mcm_data> that was passed to ossl_construct_method())
|
(which is the C<mcm_data> that was passed to ossl_construct_method())
|
||||||
and the provided property query C<propquery>.
|
and the provided property query C<propquery>.
|
||||||
|
|
||||||
@@ -99,15 +101,15 @@ B<NULL> is a valid value and means that a sub-system default store
|
|||||||
must be used.
|
must be used.
|
||||||
This default store should be stored in the library context C<libctx>.
|
This default store should be stored in the library context C<libctx>.
|
||||||
|
|
||||||
The method should be associated with the given property definition
|
The method should be associated with the given C<name> and property definition
|
||||||
C<propdef> and any identification data given through C<data> (which is
|
C<propdef> as well as any identification data given through C<data> (which is
|
||||||
the C<mcm_data> that was passed to ossl_construct_method()).
|
the C<mcm_data> that was passed to ossl_construct_method()).
|
||||||
|
|
||||||
This function is expected to increment the C<method>'s reference count.
|
This function is expected to increment the C<method>'s reference count.
|
||||||
|
|
||||||
=item construct()
|
=item construct()
|
||||||
|
|
||||||
Constructs a sub-system method for the given C<algorithm_name> and the given
|
Constructs a sub-system method for the given C<name> and the given
|
||||||
dispatch table C<fns>.
|
dispatch table C<fns>.
|
||||||
|
|
||||||
The associated I<provider object> C<prov> is passed as well, to make
|
The associated I<provider object> C<prov> is passed as well, to make
|
||||||
@@ -132,7 +134,7 @@ B<NULL> on error.
|
|||||||
|
|
||||||
=head1 HISTORY
|
=head1 HISTORY
|
||||||
|
|
||||||
This functionality was added to OpenSSL 3.0.0.
|
This functionality was added to OpenSSL 3.0.
|
||||||
|
|
||||||
=head1 COPYRIGHT
|
=head1 COPYRIGHT
|
||||||
|
|
||||||
|
|||||||
@@ -0,0 +1,74 @@
|
|||||||
|
=pod
|
||||||
|
|
||||||
|
=head1 NAME
|
||||||
|
|
||||||
|
ossl_namemap_new, ossl_namemap_free, ossl_namemap_stored,
|
||||||
|
ossl_namemap_add, ossl_namemap_name, ossl_namemap_number
|
||||||
|
- internal number E<lt>-E<gt> name map
|
||||||
|
|
||||||
|
=head1 SYNOPSIS
|
||||||
|
|
||||||
|
#include "internal/cryptlib.h"
|
||||||
|
|
||||||
|
OSSL_NAMEMAP *ossl_namemap_stored(OPENSSL_CTX *libctx);
|
||||||
|
|
||||||
|
OSSL_NAMEMAP *ossl_namemap_new(void);
|
||||||
|
void ossl_namemap_free(OSSL_NAMEMAP *namemap);
|
||||||
|
|
||||||
|
int ossl_namemap_add(OSSL_NAMEMAP *namemap, const char *name);
|
||||||
|
const char *ossl_namemap_name(const OSSL_NAMEMAP *namemap, int number);
|
||||||
|
int ossl_namemap_number(const OSSL_NAMEMAP *namemap, const char *name);
|
||||||
|
|
||||||
|
=head1 DESCRIPTION
|
||||||
|
|
||||||
|
A B<OSSL_NAMEMAP> is a simple number E<lt>-E<gt> name map, which can
|
||||||
|
be used to give any arbitrary name (any string) a unique dynamic
|
||||||
|
identity that is valid throughout the lifetime of the associated
|
||||||
|
library context.
|
||||||
|
|
||||||
|
ossl_namemap_new() and ossl_namemap_free() construct and destruct a
|
||||||
|
new B<OSSL_NAMEMAP>.
|
||||||
|
This is suitable to use when the B<OSSL_NAMEMAP> is embedded in other
|
||||||
|
structures, or should be independent for any reason.
|
||||||
|
|
||||||
|
ossl_namemap_stored() finds or auto-creates the default namemap in the
|
||||||
|
given library context.
|
||||||
|
The returned B<OSSL_NAMEMAP> can't be destructed using
|
||||||
|
ossl_namemap_free().
|
||||||
|
|
||||||
|
ossl_namemap_add() adds a new name to the namemap if it's not already
|
||||||
|
present.
|
||||||
|
|
||||||
|
ossl_namemap_name() finds the name corresponding to the given number.
|
||||||
|
|
||||||
|
ossl_namemap_number() finds the number corresponding to the given
|
||||||
|
name.
|
||||||
|
|
||||||
|
=head1 RETURN VALUES
|
||||||
|
|
||||||
|
ossl_namemap_new() and ossl_namemap_stored() return the pointer to a
|
||||||
|
B<OSSL_NAMEMAP>, or NULL on error.
|
||||||
|
|
||||||
|
ossl_namemap_add() returns the number associated with the added
|
||||||
|
string, or zero on error.
|
||||||
|
|
||||||
|
ossl_namemap_name() returns a pointer to the name corresponding to the
|
||||||
|
given number, or NULL if it's undefined in the given B<OSSL_NAMEMAP>.
|
||||||
|
|
||||||
|
ossl_namemap_number() returns the number corresponding to the given
|
||||||
|
name, or 0 if it's undefined in the given B<OSSL_NAMEMAP>.
|
||||||
|
|
||||||
|
=head1 HISTORY
|
||||||
|
|
||||||
|
The functions described here were all added in OpenSSL 3.0.
|
||||||
|
|
||||||
|
=head1 COPYRIGHT
|
||||||
|
|
||||||
|
Copyright 2019 The OpenSSL Project Authors. All Rights Reserved.
|
||||||
|
|
||||||
|
Licensed under the Apache License 2.0 (the "License"). You may not use
|
||||||
|
this file except in compliance with the License. You can obtain a copy
|
||||||
|
in the file LICENSE in the source distribution or at
|
||||||
|
L<https://www.openssl.org/source/license.html>.
|
||||||
|
|
||||||
|
=cut
|
||||||
@@ -5,7 +5,7 @@
|
|||||||
ossl_provider_find, ossl_provider_new, ossl_provider_upref,
|
ossl_provider_find, ossl_provider_new, ossl_provider_upref,
|
||||||
ossl_provider_free, ossl_provider_add_module_location,
|
ossl_provider_free, ossl_provider_add_module_location,
|
||||||
ossl_provider_set_fallback, ossl_provider_activate,
|
ossl_provider_set_fallback, ossl_provider_activate,
|
||||||
ossl_provider_forall_loaded,
|
ossl_provider_ctx, ossl_provider_forall_loaded,
|
||||||
ossl_provider_name, ossl_provider_dso,
|
ossl_provider_name, ossl_provider_dso,
|
||||||
ossl_provider_module_name, ossl_provider_module_path,
|
ossl_provider_module_name, ossl_provider_module_path,
|
||||||
ossl_provider_teardown, ossl_provider_get_param_types,
|
ossl_provider_teardown, ossl_provider_get_param_types,
|
||||||
@@ -29,6 +29,9 @@ ossl_provider_get_params, ossl_provider_query_operation
|
|||||||
/* Load and initialize the Provider */
|
/* Load and initialize the Provider */
|
||||||
int ossl_provider_activate(OSSL_PROVIDER *prov);
|
int ossl_provider_activate(OSSL_PROVIDER *prov);
|
||||||
|
|
||||||
|
/* Return pointer to the provider's context */
|
||||||
|
void *ossl_provider_ctx(const OSSL_PROVIDER *prov);
|
||||||
|
|
||||||
/* Iterate over all loaded providers */
|
/* Iterate over all loaded providers */
|
||||||
int ossl_provider_forall_loaded(OPENSSL_CTX *,
|
int ossl_provider_forall_loaded(OPENSSL_CTX *,
|
||||||
int (*cb)(OSSL_PROVIDER *provider,
|
int (*cb)(OSSL_PROVIDER *provider,
|
||||||
@@ -121,6 +124,10 @@ be located in that module, and called.
|
|||||||
|
|
||||||
=back
|
=back
|
||||||
|
|
||||||
|
ossl_provider_ctx() returns a context created by the provider.
|
||||||
|
Outside of the provider, it's completely opaque, but it needs to be
|
||||||
|
passed back to some of the provider functions.
|
||||||
|
|
||||||
ossl_provider_forall_loaded() iterates over all the currently
|
ossl_provider_forall_loaded() iterates over all the currently
|
||||||
"activated" providers, and calls C<cb> for each of them.
|
"activated" providers, and calls C<cb> for each of them.
|
||||||
If no providers have been "activated" yet, it tries to activate all
|
If no providers have been "activated" yet, it tries to activate all
|
||||||
|
|||||||
+11
-6
@@ -20,6 +20,7 @@ B<openssl dsaparam>
|
|||||||
[B<-writerand file>]
|
[B<-writerand file>]
|
||||||
[B<-genkey>]
|
[B<-genkey>]
|
||||||
[B<-engine id>]
|
[B<-engine id>]
|
||||||
|
[B<-verbose>]
|
||||||
[B<numbits>]
|
[B<numbits>]
|
||||||
|
|
||||||
=head1 DESCRIPTION
|
=head1 DESCRIPTION
|
||||||
@@ -89,12 +90,6 @@ all others.
|
|||||||
Writes random data to the specified I<file> upon exit.
|
Writes random data to the specified I<file> upon exit.
|
||||||
This can be used with a subsequent B<-rand> flag.
|
This can be used with a subsequent B<-rand> flag.
|
||||||
|
|
||||||
=item B<numbits>
|
|
||||||
|
|
||||||
This option specifies that a parameter set should be generated of size
|
|
||||||
B<numbits>. It must be the last option. If this option is included then
|
|
||||||
the input file (if any) is ignored.
|
|
||||||
|
|
||||||
=item B<-engine id>
|
=item B<-engine id>
|
||||||
|
|
||||||
Specifying an engine (by its unique B<id> string) will cause B<dsaparam>
|
Specifying an engine (by its unique B<id> string) will cause B<dsaparam>
|
||||||
@@ -102,6 +97,16 @@ to attempt to obtain a functional reference to the specified engine,
|
|||||||
thus initialising it if needed. The engine will then be set as the default
|
thus initialising it if needed. The engine will then be set as the default
|
||||||
for all available algorithms.
|
for all available algorithms.
|
||||||
|
|
||||||
|
=item B<-verbose>
|
||||||
|
|
||||||
|
Print extra details about the operations being performed.
|
||||||
|
|
||||||
|
=item B<numbits>
|
||||||
|
|
||||||
|
This option specifies that a parameter set should be generated of size
|
||||||
|
B<numbits>. It must be the last option. If this option is included then
|
||||||
|
the input file (if any) is ignored.
|
||||||
|
|
||||||
=back
|
=back
|
||||||
|
|
||||||
=head1 NOTES
|
=head1 NOTES
|
||||||
|
|||||||
@@ -25,6 +25,7 @@ B<openssl> B<gendsa>
|
|||||||
[B<-rand file...>]
|
[B<-rand file...>]
|
||||||
[B<-writerand file>]
|
[B<-writerand file>]
|
||||||
[B<-engine id>]
|
[B<-engine id>]
|
||||||
|
[B<-verbose>]
|
||||||
[B<paramfile>]
|
[B<paramfile>]
|
||||||
|
|
||||||
=head1 DESCRIPTION
|
=head1 DESCRIPTION
|
||||||
@@ -71,6 +72,10 @@ to attempt to obtain a functional reference to the specified engine,
|
|||||||
thus initialising it if needed. The engine will then be set as the default
|
thus initialising it if needed. The engine will then be set as the default
|
||||||
for all available algorithms.
|
for all available algorithms.
|
||||||
|
|
||||||
|
=item B<-verbose>
|
||||||
|
|
||||||
|
Print extra details about the operations being performed.
|
||||||
|
|
||||||
=item B<paramfile>
|
=item B<paramfile>
|
||||||
|
|
||||||
This option specifies the DSA parameter file to use. The parameters in this
|
This option specifies the DSA parameter file to use. The parameters in this
|
||||||
|
|||||||
@@ -118,7 +118,7 @@ or ED448 algorithms.
|
|||||||
|
|
||||||
=item B<rsa_keygen_bits:numbits>
|
=item B<rsa_keygen_bits:numbits>
|
||||||
|
|
||||||
The number of bits in the generated key. If not specified 1024 is used.
|
The number of bits in the generated key. If not specified 2048 is used.
|
||||||
|
|
||||||
=item B<rsa_keygen_primes:numprimes>
|
=item B<rsa_keygen_primes:numprimes>
|
||||||
|
|
||||||
@@ -185,12 +185,12 @@ below.
|
|||||||
|
|
||||||
=item B<dsa_paramgen_bits:numbits>
|
=item B<dsa_paramgen_bits:numbits>
|
||||||
|
|
||||||
The number of bits in the generated prime. If not specified 1024 is used.
|
The number of bits in the generated prime. If not specified 2048 is used.
|
||||||
|
|
||||||
=item B<dsa_paramgen_q_bits:numbits>
|
=item B<dsa_paramgen_q_bits:numbits>
|
||||||
|
|
||||||
The number of bits in the q parameter. Must be one of 160, 224 or 256. If not
|
The number of bits in the q parameter. Must be one of 160, 224 or 256. If not
|
||||||
specified 160 is used.
|
specified 224 is used.
|
||||||
|
|
||||||
=item B<dsa_paramgen_md:digest>
|
=item B<dsa_paramgen_md:digest>
|
||||||
|
|
||||||
@@ -209,7 +209,7 @@ or B<sha256> if it is 256.
|
|||||||
|
|
||||||
=item B<dh_paramgen_prime_len:numbits>
|
=item B<dh_paramgen_prime_len:numbits>
|
||||||
|
|
||||||
The number of bits in the prime parameter B<p>. The default is 1024.
|
The number of bits in the prime parameter B<p>. The default is 2048.
|
||||||
|
|
||||||
=item B<dh_paramgen_subprime_len:numbits>
|
=item B<dh_paramgen_subprime_len:numbits>
|
||||||
|
|
||||||
|
|||||||
@@ -29,6 +29,7 @@ B<openssl> B<genrsa>
|
|||||||
[B<-writerand file>]
|
[B<-writerand file>]
|
||||||
[B<-engine id>]
|
[B<-engine id>]
|
||||||
[B<-primes num>]
|
[B<-primes num>]
|
||||||
|
[B<-verbose>]
|
||||||
[B<numbits>]
|
[B<numbits>]
|
||||||
|
|
||||||
=head1 DESCRIPTION
|
=head1 DESCRIPTION
|
||||||
@@ -91,6 +92,10 @@ parameter must be a positive integer that is greater than 1 and less than 16.
|
|||||||
If B<num> is greater than 2, then the generated key is called a 'multi-prime'
|
If B<num> is greater than 2, then the generated key is called a 'multi-prime'
|
||||||
RSA key, which is defined in RFC 8017.
|
RSA key, which is defined in RFC 8017.
|
||||||
|
|
||||||
|
=item B<-verbose>
|
||||||
|
|
||||||
|
Print extra details about the operations being performed.
|
||||||
|
|
||||||
=item B<numbits>
|
=item B<numbits>
|
||||||
|
|
||||||
The size of the private key to generate in bits. This must be the last option
|
The size of the private key to generate in bits. This must be the last option
|
||||||
|
|||||||
@@ -184,6 +184,7 @@ B<openssl> B<s_server>
|
|||||||
[B<-early_data>]
|
[B<-early_data>]
|
||||||
[B<-anti_replay>]
|
[B<-anti_replay>]
|
||||||
[B<-no_anti_replay>]
|
[B<-no_anti_replay>]
|
||||||
|
[B<-http_server_binmode>]
|
||||||
|
|
||||||
=head1 DESCRIPTION
|
=head1 DESCRIPTION
|
||||||
|
|
||||||
@@ -743,6 +744,11 @@ has been negotiated, and early data is enabled on the server. A full handshake
|
|||||||
is forced if a session ticket is used a second or subsequent time. Any early
|
is forced if a session ticket is used a second or subsequent time. Any early
|
||||||
data that was sent will be rejected.
|
data that was sent will be rejected.
|
||||||
|
|
||||||
|
=item B<-http_server_binmode>
|
||||||
|
|
||||||
|
When acting as web-server (using option B<-WWW> or B<-HTTP>) open files requested
|
||||||
|
by the client in binary mode.
|
||||||
|
|
||||||
=back
|
=back
|
||||||
|
|
||||||
=head1 CONNECTED COMMANDS
|
=head1 CONNECTED COMMANDS
|
||||||
|
|||||||
@@ -412,7 +412,9 @@ The following I<ctrl>s are supported in CCM mode.
|
|||||||
This call is made to set the expected B<CCM> tag value when decrypting or
|
This call is made to set the expected B<CCM> tag value when decrypting or
|
||||||
the length of the tag (with the C<tag> parameter set to NULL) when encrypting.
|
the length of the tag (with the C<tag> parameter set to NULL) when encrypting.
|
||||||
The tag length is often referred to as B<M>. If not set a default value is
|
The tag length is often referred to as B<M>. If not set a default value is
|
||||||
used (12 for AES).
|
used (12 for AES). When decrypting, the tag needs to be set before passing
|
||||||
|
in data to be decrypted, but as in GCM and OCB mode, it can be set after
|
||||||
|
passing additional authenticated data (see L<AEAD Interface>).
|
||||||
|
|
||||||
=item EVP_CIPHER_CTX_ctrl(ctx, EVP_CTRL_CCM_SET_L, ivlen, NULL)
|
=item EVP_CIPHER_CTX_ctrl(ctx, EVP_CTRL_CCM_SET_L, ivlen, NULL)
|
||||||
|
|
||||||
|
|||||||
+61
-16
@@ -2,17 +2,21 @@
|
|||||||
|
|
||||||
=head1 NAME
|
=head1 NAME
|
||||||
|
|
||||||
EVP_KDF_CTX, EVP_KDF_CTX_new_id, EVP_KDF_CTX_free, EVP_KDF_reset,
|
EVP_KDF, EVP_KDF_CTX, EVP_KDF_CTX_new, EVP_KDF_CTX_new_id, EVP_KDF_CTX_free,
|
||||||
EVP_KDF_ctrl, EVP_KDF_vctrl, EVP_KDF_ctrl_str, EVP_KDF_size,
|
EVP_KDF_CTX_kdf, EVP_KDF_reset, EVP_KDF_ctrl, EVP_KDF_vctrl, EVP_KDF_ctrl_str,
|
||||||
EVP_KDF_derive - EVP KDF routines
|
EVP_KDF_size, EVP_KDF_derive, EVP_KDF_nid, EVP_KDF_name,
|
||||||
|
EVP_get_kdfbyname, EVP_get_kdfbynid, EVP_get_kdfbyobj - EVP KDF routines
|
||||||
|
|
||||||
=head1 SYNOPSIS
|
=head1 SYNOPSIS
|
||||||
|
|
||||||
#include <openssl/kdf.h>
|
#include <openssl/kdf.h>
|
||||||
|
|
||||||
|
typedef struct evp_kdf_st EVP_KDF;
|
||||||
typedef struct evp_kdf_ctx_st EVP_KDF_CTX;
|
typedef struct evp_kdf_ctx_st EVP_KDF_CTX;
|
||||||
|
|
||||||
EVP_KDF_CTX *EVP_KDF_CTX_new_id(int id);
|
EVP_KDF_CTX *EVP_KDF_CTX_new(const EVP_KDF *kdf);
|
||||||
|
EVP_KDF_CTX *EVP_KDF_CTX_new_id(int nid);
|
||||||
|
const EVP_KDF *EVP_KDF_CTX_kdf(EVP_KDF_CTX *ctx);
|
||||||
void EVP_KDF_CTX_free(EVP_KDF_CTX *ctx);
|
void EVP_KDF_CTX_free(EVP_KDF_CTX *ctx);
|
||||||
void EVP_KDF_reset(EVP_KDF_CTX *ctx);
|
void EVP_KDF_reset(EVP_KDF_CTX *ctx);
|
||||||
int EVP_KDF_ctrl(EVP_KDF_CTX *ctx, int cmd, ...);
|
int EVP_KDF_ctrl(EVP_KDF_CTX *ctx, int cmd, ...);
|
||||||
@@ -20,29 +24,40 @@ EVP_KDF_derive - EVP KDF routines
|
|||||||
int EVP_KDF_ctrl_str(EVP_KDF_CTX *ctx, const char *type, const char *value);
|
int EVP_KDF_ctrl_str(EVP_KDF_CTX *ctx, const char *type, const char *value);
|
||||||
size_t EVP_KDF_size(EVP_KDF_CTX *ctx);
|
size_t EVP_KDF_size(EVP_KDF_CTX *ctx);
|
||||||
int EVP_KDF_derive(EVP_KDF_CTX *ctx, unsigned char *key, size_t keylen);
|
int EVP_KDF_derive(EVP_KDF_CTX *ctx, unsigned char *key, size_t keylen);
|
||||||
|
int EVP_KDF_nid(const EVP_KDF *kdf);
|
||||||
|
const char *EVP_KDF_name(const EVP_KDF *kdf);
|
||||||
|
const EVP_KDF *EVP_get_kdfbyname(const char *name);
|
||||||
|
const EVP_KDF *EVP_get_kdfbynid(int nid);
|
||||||
|
const EVP_KDF *EVP_get_kdfbyobj(const ASN1_OBJECT *o);
|
||||||
|
|
||||||
=head1 DESCRIPTION
|
=head1 DESCRIPTION
|
||||||
|
|
||||||
The EVP KDF routines are a high level interface to Key Derivation Function
|
The EVP KDF routines are a high level interface to Key Derivation Function
|
||||||
algorithms and should be used instead of algorithm-specific functions.
|
algorithms and should be used instead of algorithm-specific functions.
|
||||||
|
|
||||||
After creating a C<EVP_KDF_CTX> for the required algorithm using
|
After creating a C<EVP_KDF_CTX> for the required algorithm using either
|
||||||
EVP_KDF_CTX_new_id(), inputs to the algorithm are supplied using calls to
|
EVP_KDF_CTX_new() or EVP_KDF_CTX_new_id(), inputs to the algorithm are supplied
|
||||||
EVP_KDF_ctrl(), EVP_KDF_vctrl() or EVP_KDF_ctrl_str() before calling
|
using calls to EVP_KDF_ctrl(), EVP_KDF_vctrl() or EVP_KDF_ctrl_str() before
|
||||||
EVP_KDF_derive() to derive the key.
|
calling EVP_KDF_derive() to derive the key.
|
||||||
|
|
||||||
=head2 Types
|
=head2 Types
|
||||||
|
|
||||||
|
B<EVP_KDF> is a type that holds the implementation of a KDF.
|
||||||
|
|
||||||
B<EVP_KDF_CTX> is a context type that holds the algorithm inputs.
|
B<EVP_KDF_CTX> is a context type that holds the algorithm inputs.
|
||||||
|
|
||||||
=head2 Context manipulation functions
|
=head2 Context manipulation functions
|
||||||
|
|
||||||
EVP_KDF_CTX_new_id() creates a KDF context for the algorithm identified by the
|
EVP_KDF_CTX_new() creates a new context for the KDF type C<kdf>.
|
||||||
specified NID.
|
|
||||||
|
EVP_KDF_CTX_new_id() creates a new context for the numerical KDF identity C<nid>.
|
||||||
|
|
||||||
EVP_KDF_CTX_free() frees up the context C<ctx>. If C<ctx> is C<NULL>, nothing
|
EVP_KDF_CTX_free() frees up the context C<ctx>. If C<ctx> is C<NULL>, nothing
|
||||||
is done.
|
is done.
|
||||||
|
|
||||||
|
EVP_KDF_CTX_kdf() returns the B<EVP_KDF> associated with the context
|
||||||
|
C<ctx>.
|
||||||
|
|
||||||
=head2 Computing functions
|
=head2 Computing functions
|
||||||
|
|
||||||
EVP_KDF_reset() resets the context to the default state as if the context
|
EVP_KDF_reset() resets the context to the default state as if the context
|
||||||
@@ -61,15 +76,32 @@ EVP_KDF_ctrl_str() allows an application to send an algorithm specific control
|
|||||||
operation to a context C<ctx> in string form. This is intended to be used for
|
operation to a context C<ctx> in string form. This is intended to be used for
|
||||||
options specified on the command line or in text files.
|
options specified on the command line or in text files.
|
||||||
|
|
||||||
|
EVP_KDF_derive() derives C<keylen> bytes of key material and places it in the
|
||||||
|
C<key> buffer. If the algorithm produces a fixed amount of output then an
|
||||||
|
error will occur unless the C<keylen> parameter is equal to that output size,
|
||||||
|
as returned by EVP_KDF_size().
|
||||||
|
|
||||||
|
=head2 Information functions
|
||||||
|
|
||||||
EVP_KDF_size() returns the output size if the algorithm produces a fixed amount
|
EVP_KDF_size() returns the output size if the algorithm produces a fixed amount
|
||||||
of output and C<SIZE_MAX> otherwise. If an error occurs then 0 is returned.
|
of output and C<SIZE_MAX> otherwise. If an error occurs then 0 is returned.
|
||||||
For some algorithms an error may result if input parameters necessary to
|
For some algorithms an error may result if input parameters necessary to
|
||||||
calculate a fixed output size have not yet been supplied.
|
calculate a fixed output size have not yet been supplied.
|
||||||
|
|
||||||
EVP_KDF_derive() derives C<keylen> bytes of key material and places it in the
|
EVP_KDF_nid() returns the numeric identity of the given KDF implementation.
|
||||||
C<key> buffer. If the algorithm produces a fixed amount of output then an
|
|
||||||
error will occur unless the C<keylen> parameter is equal to that output size,
|
EVP_KDF_name() returns the name of the given KDF implementation.
|
||||||
as returned by EVP_KDF_size().
|
|
||||||
|
=head2 Object database functions
|
||||||
|
|
||||||
|
EVP_get_kdfbyname() fetches a KDF implementation from the object
|
||||||
|
database by name.
|
||||||
|
|
||||||
|
EVP_get_kdfbynid() fetches a KDF implementation from the object
|
||||||
|
database by numeric identity.
|
||||||
|
|
||||||
|
EVP_get_kdfbyobj() fetches a KDF implementation from the object
|
||||||
|
database by ASN.1 OBJECT (i.e. an encoded OID).
|
||||||
|
|
||||||
=head1 CONTROLS
|
=head1 CONTROLS
|
||||||
|
|
||||||
@@ -213,14 +245,26 @@ The value string is expected to be a decimal number.
|
|||||||
|
|
||||||
=head1 RETURN VALUES
|
=head1 RETURN VALUES
|
||||||
|
|
||||||
EVP_KDF_CTX_new_id() returns either the newly allocated C<EVP_KDF_CTX>
|
EVP_KDF_CTX_new() and EVP_KDF_CTX_new_id() return either the newly allocated
|
||||||
structure or C<NULL> if an error occurred.
|
C<EVP_KDF_CTX> structure or C<NULL> if an error occurred.
|
||||||
|
|
||||||
EVP_KDF_CTX_free() and EVP_KDF_reset() do not return a value.
|
EVP_KDF_CTX_free() and EVP_KDF_reset() do not return a value.
|
||||||
|
|
||||||
EVP_KDF_size() returns the output size. C<SIZE_MAX> is returned to indicate
|
EVP_KDF_size() returns the output size. C<SIZE_MAX> is returned to indicate
|
||||||
that the algorithm produces a variable amount of output; 0 to indicate failure.
|
that the algorithm produces a variable amount of output; 0 to indicate failure.
|
||||||
|
|
||||||
|
EVP_KDF_nid() returns the numeric identity for the given C<kdf>.
|
||||||
|
|
||||||
|
EVP_KDF_name() returns the name for the given C<kdf>, if it has been
|
||||||
|
added to the object database.
|
||||||
|
|
||||||
|
EVP_add_kdf() returns 1 if the given C<kdf> was successfully added to
|
||||||
|
the object database, otherwise 0.
|
||||||
|
|
||||||
|
EVP_get_kdfbyname(), EVP_get_kdfbynid() and EVP_get_kdfbyobj() return
|
||||||
|
the requested KDF implementation, if it exists in the object database,
|
||||||
|
otherwise B<NULL>.
|
||||||
|
|
||||||
The remaining functions return 1 for success and 0 or a negative value for
|
The remaining functions return 1 for success and 0 or a negative value for
|
||||||
failure. In particular, a return value of -2 indicates the operation is not
|
failure. In particular, a return value of -2 indicates the operation is not
|
||||||
supported by the KDF algorithm.
|
supported by the KDF algorithm.
|
||||||
@@ -233,6 +277,7 @@ L<EVP_KDF_PBKDF2(7)>
|
|||||||
L<EVP_KDF_HKDF(7)>
|
L<EVP_KDF_HKDF(7)>
|
||||||
L<EVP_KDF_SS(7)>
|
L<EVP_KDF_SS(7)>
|
||||||
L<EVP_KDF_SSHKDF(7)>
|
L<EVP_KDF_SSHKDF(7)>
|
||||||
|
L<EVP_KDF_X963(7)>
|
||||||
|
|
||||||
=head1 HISTORY
|
=head1 HISTORY
|
||||||
|
|
||||||
|
|||||||
@@ -286,7 +286,7 @@ L<EVP_PKEY_verify_recover_init(3)> and L<EVP_PKEY_verify_recover(3)>.
|
|||||||
|
|
||||||
The signctx_init() and signctx() methods are used to sign a digest present by
|
The signctx_init() and signctx() methods are used to sign a digest present by
|
||||||
a B<EVP_MD_CTX> object. They are called by the EVP_DigestSign functions. See
|
a B<EVP_MD_CTX> object. They are called by the EVP_DigestSign functions. See
|
||||||
L<EVP_DigestSignInit(3)> for detail.
|
L<EVP_DigestSignInit(3)> for details.
|
||||||
|
|
||||||
int (*verifyctx_init) (EVP_PKEY_CTX *ctx, EVP_MD_CTX *mctx);
|
int (*verifyctx_init) (EVP_PKEY_CTX *ctx, EVP_MD_CTX *mctx);
|
||||||
int (*verifyctx) (EVP_PKEY_CTX *ctx, const unsigned char *sig, int siglen,
|
int (*verifyctx) (EVP_PKEY_CTX *ctx, const unsigned char *sig, int siglen,
|
||||||
@@ -294,7 +294,7 @@ L<EVP_DigestSignInit(3)> for detail.
|
|||||||
|
|
||||||
The verifyctx_init() and verifyctx() methods are used to verify a signature
|
The verifyctx_init() and verifyctx() methods are used to verify a signature
|
||||||
against the data in a B<EVP_MD_CTX> object. They are called by the various
|
against the data in a B<EVP_MD_CTX> object. They are called by the various
|
||||||
EVP_DigestVerify functions. See L<EVP_DigestVerifyInit(3)> for detail.
|
EVP_DigestVerify functions. See L<EVP_DigestVerifyInit(3)> for details.
|
||||||
|
|
||||||
int (*encrypt_init) (EVP_PKEY_CTX *ctx);
|
int (*encrypt_init) (EVP_PKEY_CTX *ctx);
|
||||||
int (*encrypt) (EVP_PKEY_CTX *ctx, unsigned char *out, size_t *outlen,
|
int (*encrypt) (EVP_PKEY_CTX *ctx, unsigned char *out, size_t *outlen,
|
||||||
@@ -321,7 +321,7 @@ L<EVP_PKEY_derive_init(3)> and L<EVP_PKEY_derive(3)>.
|
|||||||
int (*ctrl_str) (EVP_PKEY_CTX *ctx, const char *type, const char *value);
|
int (*ctrl_str) (EVP_PKEY_CTX *ctx, const char *type, const char *value);
|
||||||
|
|
||||||
The ctrl() and ctrl_str() methods are used to adjust algorithm-specific
|
The ctrl() and ctrl_str() methods are used to adjust algorithm-specific
|
||||||
settings. See L<EVP_PKEY_CTX_ctrl(3)> and related functions for detail.
|
settings. See L<EVP_PKEY_CTX_ctrl(3)> and related functions for details.
|
||||||
|
|
||||||
int (*digestsign) (EVP_MD_CTX *ctx, unsigned char *sig, size_t *siglen,
|
int (*digestsign) (EVP_MD_CTX *ctx, unsigned char *sig, size_t *siglen,
|
||||||
const unsigned char *tbs, size_t tbslen);
|
const unsigned char *tbs, size_t tbslen);
|
||||||
@@ -330,7 +330,7 @@ settings. See L<EVP_PKEY_CTX_ctrl(3)> and related functions for detail.
|
|||||||
size_t tbslen);
|
size_t tbslen);
|
||||||
|
|
||||||
The digestsign() and digestverify() methods are used to generate or verify
|
The digestsign() and digestverify() methods are used to generate or verify
|
||||||
a signature in a one-shot mode. They could be called by L<EVP_DigetSign(3)>
|
a signature in a one-shot mode. They could be called by L<EVP_DigestSign(3)>
|
||||||
and L<EVP_DigestVerify(3)>.
|
and L<EVP_DigestVerify(3)>.
|
||||||
|
|
||||||
int (*check) (EVP_PKEY *pkey);
|
int (*check) (EVP_PKEY *pkey);
|
||||||
|
|||||||
@@ -250,7 +250,8 @@ All other functions return B<1> on success and B<0> on failure.
|
|||||||
|
|
||||||
=head1 NOTES
|
=head1 NOTES
|
||||||
|
|
||||||
Integral types will be widened and sign extended as required.
|
Native types will be converted as required only if the value is exactly
|
||||||
|
representable by the target type or parameter.
|
||||||
Apart from that, the functions must be used appropriately for the
|
Apart from that, the functions must be used appropriately for the
|
||||||
expected type of the parameter.
|
expected type of the parameter.
|
||||||
|
|
||||||
|
|||||||
@@ -55,6 +55,11 @@ The content of B<buf> cannot be recovered from subsequent random generator outpu
|
|||||||
Applications that intend to save and restore random state in an external file
|
Applications that intend to save and restore random state in an external file
|
||||||
should consider using L<RAND_load_file(3)> instead.
|
should consider using L<RAND_load_file(3)> instead.
|
||||||
|
|
||||||
|
NOTE: In FIPS mode, random data provided by the application is not considered to
|
||||||
|
be a trusted entropy source. It is mixed into the internal state of the RNG as
|
||||||
|
additional data only and this does not count as a full reseed.
|
||||||
|
For more details, see L<RAND_DRBG(7)>.
|
||||||
|
|
||||||
RAND_seed() is equivalent to RAND_add() with B<randomness> set to B<num>.
|
RAND_seed() is equivalent to RAND_add() with B<randomness> set to B<num>.
|
||||||
|
|
||||||
RAND_keep_random_devices_open() is used to control file descriptor
|
RAND_keep_random_devices_open() is used to control file descriptor
|
||||||
@@ -86,6 +91,7 @@ L<RAND_bytes(3)>,
|
|||||||
L<RAND_egd(3)>,
|
L<RAND_egd(3)>,
|
||||||
L<RAND_load_file(3)>,
|
L<RAND_load_file(3)>,
|
||||||
L<RAND(7)>
|
L<RAND(7)>
|
||||||
|
L<RAND_DRBG(7)>
|
||||||
|
|
||||||
=head1 HISTORY
|
=head1 HISTORY
|
||||||
|
|
||||||
|
|||||||
@@ -8,7 +8,7 @@ SSL_session_reused - query whether a reused session was negotiated during handsh
|
|||||||
|
|
||||||
#include <openssl/ssl.h>
|
#include <openssl/ssl.h>
|
||||||
|
|
||||||
int SSL_session_reused(SSL *ssl);
|
int SSL_session_reused(const SSL *ssl);
|
||||||
|
|
||||||
=head1 DESCRIPTION
|
=head1 DESCRIPTION
|
||||||
|
|
||||||
|
|||||||
+29
-2
@@ -2,12 +2,13 @@
|
|||||||
|
|
||||||
=head1 NAME
|
=head1 NAME
|
||||||
|
|
||||||
SSL_write_ex, SSL_write - write bytes to a TLS/SSL connection
|
SSL_write_ex, SSL_write, SSL_sendfile - write bytes to a TLS/SSL connection
|
||||||
|
|
||||||
=head1 SYNOPSIS
|
=head1 SYNOPSIS
|
||||||
|
|
||||||
#include <openssl/ssl.h>
|
#include <openssl/ssl.h>
|
||||||
|
|
||||||
|
ossl_ssize_t SSL_sendfile(SSL *s, int fd, off_t offset, size_t size, int flags);
|
||||||
int SSL_write_ex(SSL *s, const void *buf, size_t num, size_t *written);
|
int SSL_write_ex(SSL *s, const void *buf, size_t num, size_t *written);
|
||||||
int SSL_write(SSL *ssl, const void *buf, int num);
|
int SSL_write(SSL *ssl, const void *buf, int num);
|
||||||
|
|
||||||
@@ -17,6 +18,14 @@ SSL_write_ex() and SSL_write() write B<num> bytes from the buffer B<buf> into
|
|||||||
the specified B<ssl> connection. On success SSL_write_ex() will store the number
|
the specified B<ssl> connection. On success SSL_write_ex() will store the number
|
||||||
of bytes written in B<*written>.
|
of bytes written in B<*written>.
|
||||||
|
|
||||||
|
SSL_sendfile() writes B<size> bytes from offset B<offset> in the file
|
||||||
|
descriptor B<fd> to the specified SSL connection B<s>. This function provides
|
||||||
|
efficient zero-copy semantics. SSL_sendfile() is available only when
|
||||||
|
Kernel TLS is enabled, which can be checked by calling BIO_get_ktls_send().
|
||||||
|
It is provided here to allow users to maintain the same interface.
|
||||||
|
The meaning of B<flags> is platform dependent.
|
||||||
|
Currently, under Linux it is ignored.
|
||||||
|
|
||||||
=head1 NOTES
|
=head1 NOTES
|
||||||
|
|
||||||
In the paragraphs below a "write function" is defined as one of either
|
In the paragraphs below a "write function" is defined as one of either
|
||||||
@@ -104,17 +113,35 @@ You should instead call SSL_get_error() to find out if it's retryable.
|
|||||||
|
|
||||||
=back
|
=back
|
||||||
|
|
||||||
|
For SSL_sendfile(), the following return values can occur:
|
||||||
|
|
||||||
|
=over 4
|
||||||
|
|
||||||
|
=item Z<>>= 0
|
||||||
|
|
||||||
|
The write operation was successful, the return value is the number
|
||||||
|
of bytes of the file written to the TLS/SSL connection.
|
||||||
|
|
||||||
|
=item E<lt> 0
|
||||||
|
|
||||||
|
The write operation was not successful, because either the connection was
|
||||||
|
closed, an error occured or action must be taken by the calling process.
|
||||||
|
Call SSL_get_error() with the return value to find out the reason.
|
||||||
|
|
||||||
|
=back
|
||||||
|
|
||||||
=head1 SEE ALSO
|
=head1 SEE ALSO
|
||||||
|
|
||||||
L<SSL_get_error(3)>, L<SSL_read_ex(3)>, L<SSL_read(3)>
|
L<SSL_get_error(3)>, L<SSL_read_ex(3)>, L<SSL_read(3)>
|
||||||
L<SSL_CTX_set_mode(3)>, L<SSL_CTX_new(3)>,
|
L<SSL_CTX_set_mode(3)>, L<SSL_CTX_new(3)>,
|
||||||
L<SSL_connect(3)>, L<SSL_accept(3)>
|
L<SSL_connect(3)>, L<SSL_accept(3)>
|
||||||
L<SSL_set_connect_state(3)>,
|
L<SSL_set_connect_state(3)>, L<BIO_ctrl(3)>,
|
||||||
L<ssl(7)>, L<bio(7)>
|
L<ssl(7)>, L<bio(7)>
|
||||||
|
|
||||||
=head1 HISTORY
|
=head1 HISTORY
|
||||||
|
|
||||||
The SSL_write_ex() function was added in OpenSSL 1.1.1.
|
The SSL_write_ex() function was added in OpenSSL 1.1.1.
|
||||||
|
The SSL_sendfile() function was added in OpenSSL 3.0.0.
|
||||||
|
|
||||||
=head1 COPYRIGHT
|
=head1 COPYRIGHT
|
||||||
|
|
||||||
|
|||||||
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user