1#! /usr/bin/env perl 2# Copyright 2020-2021 The OpenSSL Project Authors. All Rights Reserved. 3# 4# Licensed under the Apache License 2.0 (the "License"). You may not use 5# this file except in compliance with the License. You can obtain a copy 6# in the file LICENSE in the source distribution or at 7# https://www.openssl.org/source/license.html 8 9use strict; 10use warnings; 11 12use File::Spec; 13use File::Spec::Functions qw/curdir abs2rel/; 14use File::Copy; 15use OpenSSL::Glob; 16use OpenSSL::Test qw/:DEFAULT srctop_dir bldtop_dir bldtop_file srctop_file data_file/; 17use OpenSSL::Test::Utils; 18 19BEGIN { 20 setup("test_cli_fips"); 21} 22use lib srctop_dir('Configurations'); 23use lib bldtop_dir('.'); 24use platform; 25 26my $no_check = disabled("fips") || disabled('fips-securitychecks'); 27plan skip_all => "Test only supported in a fips build with security checks" 28 if $no_check; 29plan tests => 11; 30 31my $fipsmodule = bldtop_file('providers', platform->dso('fips')); 32my $fipsconf = srctop_file("test", "fips-and-base.cnf"); 33my $defaultconf = srctop_file("test", "default.cnf"); 34my $tbs_data = $fipsmodule; 35my $bogus_data = $fipsconf; 36 37$ENV{OPENSSL_CONF} = $fipsconf; 38 39ok(run(app(['openssl', 'list', '-public-key-methods', '-verbose'])), 40 "provider listing of public key methods"); 41ok(run(app(['openssl', 'list', '-public-key-algorithms', '-verbose'])), 42 "provider listing of public key algorithms"); 43ok(run(app(['openssl', 'list', '-key-managers', '-verbose'])), 44 "provider listing of keymanagers"); 45ok(run(app(['openssl', 'list', '-key-exchange-algorithms', '-verbose'])), 46 "provider listing of key exchange algorithms"); 47ok(run(app(['openssl', 'list', '-kem-algorithms', '-verbose'])), 48 "provider listing of key encapsulation algorithms"); 49ok(run(app(['openssl', 'list', '-signature-algorithms', '-verbose'])), 50 "provider listing of signature algorithms"); 51ok(run(app(['openssl', 'list', '-asymcipher-algorithms', '-verbose'])), 52 "provider listing of encryption algorithms"); 53ok(run(app(['openssl', 'list', '-key-managers', '-verbose', '-select', 'DSA' ])), 54 "provider listing of one item in the keymanager"); 55 56sub pubfrompriv { 57 my $prefix = shift; 58 my $key = shift; 59 my $pub_key = shift; 60 my $type = shift; 61 62 ok(run(app(['openssl', 'pkey', 63 '-in', $key, 64 '-pubout', 65 '-out', $pub_key])), 66 $prefix.': '."Create the public key with $type parameters"); 67 68} 69 70my $tsignverify_count = 8; 71sub tsignverify { 72 my $prefix = shift; 73 my $fips_key = shift; 74 my $fips_pub_key = shift; 75 my $nonfips_key = shift; 76 my $nonfips_pub_key = shift; 77 my $fips_sigfile = $prefix.'.fips.sig'; 78 my $nonfips_sigfile = $prefix.'.nonfips.sig'; 79 my $sigfile = ''; 80 my $testtext = ''; 81 82 $ENV{OPENSSL_CONF} = $fipsconf; 83 84 $sigfile = $fips_sigfile; 85 $testtext = $prefix.': '. 86 'Sign something with a FIPS key'; 87 ok(run(app(['openssl', 'dgst', '-sha256', 88 '-sign', $fips_key, 89 '-out', $sigfile, 90 $tbs_data])), 91 $testtext); 92 93 $testtext = $prefix.': '. 94 'Verify something with a FIPS key'; 95 ok(run(app(['openssl', 'dgst', '-sha256', 96 '-verify', $fips_pub_key, 97 '-signature', $sigfile, 98 $tbs_data])), 99 $testtext); 100 101 $testtext = $prefix.': '. 102 'Verify a valid signature against the wrong data with a FIPS key'. 103 ' (should fail)'; 104 ok(!run(app(['openssl', 'dgst', '-sha256', 105 '-verify', $fips_pub_key, 106 '-signature', $sigfile, 107 $bogus_data])), 108 $testtext); 109 110 $ENV{OPENSSL_CONF} = $defaultconf; 111 112 $sigfile = $nonfips_sigfile; 113 $testtext = $prefix.': '. 114 'Sign something with a non-FIPS key'. 115 ' with the default provider'; 116 ok(run(app(['openssl', 'dgst', '-sha256', 117 '-sign', $nonfips_key, 118 '-out', $sigfile, 119 $tbs_data])), 120 $testtext); 121 122 $testtext = $prefix.': '. 123 'Verify something with a non-FIPS key'. 124 ' with the default provider'; 125 ok(run(app(['openssl', 'dgst', '-sha256', 126 '-verify', $nonfips_pub_key, 127 '-signature', $sigfile, 128 $tbs_data])), 129 $testtext); 130 131 $ENV{OPENSSL_CONF} = $fipsconf; 132 133 $testtext = $prefix.': '. 134 'Sign something with a non-FIPS key'. 135 ' (should fail)'; 136 ok(!run(app(['openssl', 'dgst', '-sha256', 137 '-sign', $nonfips_key, 138 '-out', $prefix.'.nonfips.fail.sig', 139 $tbs_data])), 140 $testtext); 141 142 $testtext = $prefix.': '. 143 'Verify something with a non-FIPS key'. 144 ' (should fail)'; 145 ok(!run(app(['openssl', 'dgst', '-sha256', 146 '-verify', $nonfips_pub_key, 147 '-signature', $sigfile, 148 $tbs_data])), 149 $testtext); 150 151 $testtext = $prefix.': '. 152 'Verify a valid signature against the wrong data with a non-FIPS key'. 153 ' (should fail)'; 154 ok(!run(app(['openssl', 'dgst', '-sha256', 155 '-verify', $nonfips_pub_key, 156 '-signature', $sigfile, 157 $bogus_data])), 158 $testtext); 159} 160 161SKIP : { 162 skip "FIPS EC tests because of no ec in this build", 1 163 if disabled("ec"); 164 165 subtest EC => sub { 166 my $testtext_prefix = 'EC'; 167 my $a_fips_curve = 'prime256v1'; 168 my $fips_key = $testtext_prefix.'.fips.priv.pem'; 169 my $fips_pub_key = $testtext_prefix.'.fips.pub.pem'; 170 my $a_nonfips_curve = 'brainpoolP256r1'; 171 my $nonfips_key = $testtext_prefix.'.nonfips.priv.pem'; 172 my $nonfips_pub_key = $testtext_prefix.'.nonfips.pub.pem'; 173 my $testtext = ''; 174 my $curvename = ''; 175 176 plan tests => 5 + $tsignverify_count; 177 178 $ENV{OPENSSL_CONF} = $defaultconf; 179 $curvename = $a_nonfips_curve; 180 $testtext = $testtext_prefix.': '. 181 'Generate a key with a non-FIPS algorithm with the default provider'; 182 ok(run(app(['openssl', 'genpkey', '-algorithm', 'EC', 183 '-pkeyopt', 'ec_paramgen_curve:'.$curvename, 184 '-out', $nonfips_key])), 185 $testtext); 186 187 pubfrompriv($testtext_prefix, $nonfips_key, $nonfips_pub_key, "non-FIPS"); 188 189 $ENV{OPENSSL_CONF} = $fipsconf; 190 191 $curvename = $a_fips_curve; 192 $testtext = $testtext_prefix.': '. 193 'Generate a key with a FIPS algorithm'; 194 ok(run(app(['openssl', 'genpkey', '-algorithm', 'EC', 195 '-pkeyopt', 'ec_paramgen_curve:'.$curvename, 196 '-out', $fips_key])), 197 $testtext); 198 199 pubfrompriv($testtext_prefix, $fips_key, $fips_pub_key, "FIPS"); 200 201 $curvename = $a_nonfips_curve; 202 $testtext = $testtext_prefix.': '. 203 'Generate a key with a non-FIPS algorithm'. 204 ' (should fail)'; 205 ok(!run(app(['openssl', 'genpkey', '-algorithm', 'EC', 206 '-pkeyopt', 'ec_paramgen_curve:'.$curvename, 207 '-out', $testtext_prefix.'.'.$curvename.'.priv.pem'])), 208 $testtext); 209 210 tsignverify($testtext_prefix, $fips_key, $fips_pub_key, $nonfips_key, 211 $nonfips_pub_key); 212 }; 213} 214 215SKIP: { 216 skip "FIPS RSA tests because of no rsa in this build", 1 217 if disabled("rsa"); 218 219 subtest RSA => sub { 220 my $testtext_prefix = 'RSA'; 221 my $fips_key = $testtext_prefix.'.fips.priv.pem'; 222 my $fips_pub_key = $testtext_prefix.'.fips.pub.pem'; 223 my $nonfips_key = $testtext_prefix.'.nonfips.priv.pem'; 224 my $nonfips_pub_key = $testtext_prefix.'.nonfips.pub.pem'; 225 my $testtext = ''; 226 227 plan tests => 5 + $tsignverify_count; 228 229 $ENV{OPENSSL_CONF} = $defaultconf; 230 $testtext = $testtext_prefix.': '. 231 'Generate a key with a non-FIPS algorithm with the default provider'; 232 ok(run(app(['openssl', 'genpkey', '-algorithm', 'RSA', 233 '-pkeyopt', 'rsa_keygen_bits:512', 234 '-out', $nonfips_key])), 235 $testtext); 236 237 pubfrompriv($testtext_prefix, $nonfips_key, $nonfips_pub_key, "non-FIPS"); 238 239 $ENV{OPENSSL_CONF} = $fipsconf; 240 241 $testtext = $testtext_prefix.': '. 242 'Generate a key with a FIPS algorithm'; 243 ok(run(app(['openssl', 'genpkey', '-algorithm', 'RSA', 244 '-pkeyopt', 'rsa_keygen_bits:2048', 245 '-out', $fips_key])), 246 $testtext); 247 248 pubfrompriv($testtext_prefix, $fips_key, $fips_pub_key, "FIPS"); 249 250 $testtext = $testtext_prefix.': '. 251 'Generate a key with a non-FIPS algorithm'. 252 ' (should fail)'; 253 ok(!run(app(['openssl', 'genpkey', '-algorithm', 'RSA', 254 '-pkeyopt', 'rsa_keygen_bits:512', 255 '-out', $testtext_prefix.'.fail.priv.pem'])), 256 $testtext); 257 258 tsignverify($testtext_prefix, $fips_key, $fips_pub_key, $nonfips_key, 259 $nonfips_pub_key); 260 }; 261} 262 263SKIP : { 264 skip "FIPS DSA tests because of no dsa in this build", 1 265 if disabled("dsa"); 266 267 subtest DSA => sub { 268 my $testtext_prefix = 'DSA'; 269 my $fips_key = $testtext_prefix.'.fips.priv.pem'; 270 my $fips_pub_key = $testtext_prefix.'.fips.pub.pem'; 271 my $nonfips_key = $testtext_prefix.'.nonfips.priv.pem'; 272 my $nonfips_pub_key = $testtext_prefix.'.nonfips.pub.pem'; 273 my $testtext = ''; 274 my $fips_param = $testtext_prefix.'.fips.param.pem'; 275 my $nonfips_param = $testtext_prefix.'.nonfips.param.pem'; 276 277 plan tests => 8 + $tsignverify_count; 278 279 $ENV{OPENSSL_CONF} = $defaultconf; 280 281 $testtext = $testtext_prefix.': '. 282 'Generate non-FIPS params with the default provider'; 283 ok(run(app(['openssl', 'genpkey', '-genparam', 284 '-algorithm', 'DSA', 285 '-pkeyopt', 'type:fips186_2', 286 '-pkeyopt', 'dsa_paramgen_bits:512', 287 '-out', $nonfips_param])), 288 $testtext); 289 290 $ENV{OPENSSL_CONF} = $fipsconf; 291 292 $testtext = $testtext_prefix.': '. 293 'Generate FIPS params'; 294 ok(run(app(['openssl', 'genpkey', '-genparam', 295 '-algorithm', 'DSA', 296 '-pkeyopt', 'dsa_paramgen_bits:2048', 297 '-out', $fips_param])), 298 $testtext); 299 300 $testtext = $testtext_prefix.': '. 301 'Generate non-FIPS params'. 302 ' (should fail)'; 303 ok(!run(app(['openssl', 'genpkey', '-genparam', 304 '-algorithm', 'DSA', 305 '-pkeyopt', 'dsa_paramgen_bits:512', 306 '-out', $testtext_prefix.'.fail.param.pem'])), 307 $testtext); 308 309 $ENV{OPENSSL_CONF} = $defaultconf; 310 311 $testtext = $testtext_prefix.': '. 312 'Generate a key with non-FIPS params with the default provider'; 313 ok(run(app(['openssl', 'genpkey', 314 '-paramfile', $nonfips_param, 315 '-pkeyopt', 'type:fips186_2', 316 '-out', $nonfips_key])), 317 $testtext); 318 319 pubfrompriv($testtext_prefix, $nonfips_key, $nonfips_pub_key, "non-FIPS"); 320 321 $ENV{OPENSSL_CONF} = $fipsconf; 322 323 $testtext = $testtext_prefix.': '. 324 'Generate a key with FIPS parameters'; 325 ok(run(app(['openssl', 'genpkey', 326 '-paramfile', $fips_param, 327 '-pkeyopt', 'type:fips186_4', 328 '-out', $fips_key])), 329 $testtext); 330 331 pubfrompriv($testtext_prefix, $fips_key, $fips_pub_key, "FIPS"); 332 333 $testtext = $testtext_prefix.': '. 334 'Generate a key with non-FIPS parameters'. 335 ' (should fail)'; 336 ok(!run(app(['openssl', 'genpkey', 337 '-paramfile', $nonfips_param, 338 '-pkeyopt', 'type:fips186_2', 339 '-out', $testtext_prefix.'.fail.priv.pem'])), 340 $testtext); 341 342 tsignverify($testtext_prefix, $fips_key, $fips_pub_key, $nonfips_key, 343 $nonfips_pub_key); 344 }; 345} 346