CryptoPkg/OpensslLib: Add native instruction support for X64

BZ: https://bugzilla.tianocore.org/show_bug.cgi?id=2507

Adding OpensslLibX64.inf and modifying process_files.pl to process this
file and generate the necessary assembly files.
Adding OpensslLibX64Gcc.inf to allow building with GCC toolchain.
ApiHooks.c contains a stub function for a Windows API call.
uefi-asm.conf contains the limited assembly configurations for OpenSSL.

Cc: Jiewen Yao <jiewen.yao@intel.com>
Cc: Jian J Wang <jian.j.wang@intel.com>
Cc: Xiaoyu Lu <xiaoyux.lu@intel.com>
Cc: Mike Kinney <michael.d.kinney@intel.com>
Cc: Ard Biesheuvel <ardb@kernel.org>
Signed-off-by: Christopher Zurcher <christopher.zurcher@microsoft.com>
Reviewed-by: Jiewen Yao <Jiewen.yao@intel.com>
This commit is contained in:
Christopher Zurcher
2021-07-21 06:06:45 +08:00
committed by mergify[bot]
parent 4d28a1c2fd
commit 878a92a887
11 changed files with 1618 additions and 53 deletions

View File

@@ -9,9 +9,65 @@
# do not need to do this, since the results are stored in the EDK2
# git repository for them.
#
# Due to the script wrapping required to process the OpenSSL
# configuration data, each native architecture must be processed
# individually by the maintainer (in addition to the standard version):
# ./process_files.pl
# ./process_files.pl X64
# ./process_files.pl [Arch]
use strict;
use Cwd;
use File::Copy;
use File::Basename;
use File::Path qw(make_path remove_tree);
use Text::Tabs;
my $comment_character;
#
# OpenSSL perlasm generator script does not transfer the copyright header
#
sub copy_license_header
{
my @args = split / /, shift; #Separate args by spaces
my $source = $args[1]; #Source file is second (after "perl")
my $target = pop @args; #Target file is always last
chop ($target); #Remove newline char
my $temp_file_name = "license.tmp";
open (my $source_file, "<" . $source) || die $source;
open (my $target_file, "<" . $target) || die $target;
open (my $temp_file, ">" . $temp_file_name) || die $temp_file_name;
#Add "generated file" warning
$source =~ s/^..//; #Remove leading "./"
print ($temp_file "$comment_character WARNING: do not edit!\r\n");
print ($temp_file "$comment_character Generated from $source\r\n");
print ($temp_file "$comment_character\r\n");
#Copy source file header to temp file
while (my $line = <$source_file>) {
next if ($line =~ /#!/); #Ignore shebang line
$line =~ s/#/$comment_character/; #Fix comment character for assembly
$line =~ s/\s+$/\r\n/; #Trim trailing whitepsace, fixup line endings
print ($temp_file $line);
last if ($line =~ /http/); #Last line of copyright header contains a web link
}
print ($temp_file "\r\n");
#Retrieve generated assembly contents
while (my $line = <$target_file>) {
$line =~ s/\s+$/\r\n/; #Trim trailing whitepsace, fixup line endings
print ($temp_file expand ($line)); #expand() replaces tabs with spaces
}
close ($source_file);
close ($target_file);
close ($temp_file);
move ($temp_file_name, $target) ||
die "Cannot replace \"" . $target . "\"!";
}
#
# Find the openssl directory name for use lib. We have to do this
@@ -21,10 +77,57 @@ use File::Copy;
#
my $inf_file;
my $OPENSSL_PATH;
my $uefi_config;
my $extension;
my $arch;
my @inf;
BEGIN {
$inf_file = "OpensslLib.inf";
$uefi_config = "UEFI";
$arch = shift;
if (defined $arch) {
if (uc ($arch) eq "X64") {
$arch = "X64";
$inf_file = "OpensslLibX64.inf";
$uefi_config = "UEFI-x86_64";
$extension = "nasm";
$comment_character = ";";
} elsif (uc ($arch) eq "X64GCC") {
$arch = "X64Gcc";
$inf_file = "OpensslLibX64Gcc.inf";
$uefi_config = "UEFI-x86_64-GCC";
$extension = "S";
$comment_character = "#";
} else {
die "Unsupported architecture \"" . $arch . "\"!";
}
if ($extension eq "nasm") {
if (`nasm -v 2>&1`) {
#Presence of nasm executable will trigger inclusion of AVX instructions
die "\nCannot run assembly generators with NASM in path!\n\n";
}
}
# Prepare assembly folder
if (-d $arch) {
opendir my $dir, $arch ||
die "Cannot open assembly folder \"" . $arch . "\"!";
while (defined (my $file = readdir $dir)) {
if (-d "$arch/$file") {
next if $file eq ".";
next if $file eq "..";
remove_tree ("$arch/$file", {safe => 1}) ||
die "Cannot clean assembly folder \"" . "$arch/$file" . "\"!";
}
}
} else {
mkdir $arch ||
die "Cannot create assembly folder \"" . $arch . "\"!";
}
}
# Read the contents of the inf file
open( FD, "<" . $inf_file ) ||
@@ -47,9 +150,9 @@ BEGIN {
# Configure UEFI
system(
"./Configure",
"UEFI",
"--config=../UefiAsm.conf",
"$uefi_config",
"no-afalgeng",
"no-asm",
"no-async",
"no-autoerrinit",
"no-autoload-config",
@@ -129,23 +232,53 @@ BEGIN {
# Retrieve file lists from OpenSSL configdata
#
use configdata qw/%unified_info/;
use configdata qw/%config/;
use configdata qw/%target/;
#
# Collect build flags from configdata
#
my $flags = "";
foreach my $f (@{$config{lib_defines}}) {
$flags .= " -D$f";
}
my @cryptofilelist = ();
my @sslfilelist = ();
my @asmfilelist = ();
my @asmbuild = ();
foreach my $product ((@{$unified_info{libraries}},
@{$unified_info{engines}})) {
foreach my $o (@{$unified_info{sources}->{$product}}) {
foreach my $s (@{$unified_info{sources}->{$o}}) {
next if ($unified_info{generate}->{$s});
next if $s =~ "crypto/bio/b_print.c";
# No need to add unused files in UEFI.
# So it can reduce porting time, compile time, library size.
next if $s =~ "crypto/bio/b_print.c";
next if $s =~ "crypto/rand/randfile.c";
next if $s =~ "crypto/store/";
next if $s =~ "crypto/err/err_all.c";
next if $s =~ "crypto/aes/aes_ecb.c";
if ($unified_info{generate}->{$s}) {
if (defined $arch) {
my $buildstring = "perl";
foreach my $arg (@{$unified_info{generate}->{$s}}) {
if ($arg =~ ".pl") {
$buildstring .= " ./openssl/$arg";
} elsif ($arg =~ "PERLASM_SCHEME") {
$buildstring .= " $target{perlasm_scheme}";
} elsif ($arg =~ "LIB_CFLAGS") {
$buildstring .= "$flags";
}
}
($s, my $path, undef) = fileparse($s, qr/\.[^.]*/);
$buildstring .= " ./$arch/$path$s.$extension";
make_path ("./$arch/$path");
push @asmbuild, "$buildstring\n";
push @asmfilelist, " $arch/$path$s.$extension\r\n";
}
next;
}
if ($product =~ "libssl") {
push @sslfilelist, ' $(OPENSSL_PATH)/' . $s . "\r\n";
next;
@@ -183,15 +316,31 @@ foreach (@headers){
}
#
# Generate assembly files
#
if (@asmbuild) {
print "\n--> Generating assembly files ... ";
foreach my $buildstring (@asmbuild) {
system ("$buildstring");
copy_license_header ($buildstring);
}
print "Done!";
}
#
# Update OpensslLib.inf with autogenerated file list
#
my @new_inf = ();
my $subbing = 0;
print "\n--> Updating OpensslLib.inf ... ";
print "\n--> Updating $inf_file ... ";
foreach (@inf) {
if ($_ =~ "DEFINE OPENSSL_FLAGS_CONFIG") {
push @new_inf, " DEFINE OPENSSL_FLAGS_CONFIG =" . $flags . "\r\n";
next;
}
if ( $_ =~ "# Autogenerated files list starts here" ) {
push @new_inf, $_, @cryptofilelist, @sslfilelist;
push @new_inf, $_, @asmfilelist, @cryptofilelist, @sslfilelist;
$subbing = 1;
next;
}
@@ -216,49 +365,51 @@ rename( $new_inf_file, $inf_file ) ||
die "rename $inf_file";
print "Done!";
#
# Update OpensslLibCrypto.inf with auto-generated file list (no libssl)
#
$inf_file = "OpensslLibCrypto.inf";
if (!defined $arch) {
#
# Update OpensslLibCrypto.inf with auto-generated file list (no libssl)
#
$inf_file = "OpensslLibCrypto.inf";
# Read the contents of the inf file
@inf = ();
@new_inf = ();
open( FD, "<" . $inf_file ) ||
die "Cannot open \"" . $inf_file . "\"!";
@inf = (<FD>);
close(FD) ||
die "Cannot close \"" . $inf_file . "\"!";
# Read the contents of the inf file
@inf = ();
@new_inf = ();
open( FD, "<" . $inf_file ) ||
die "Cannot open \"" . $inf_file . "\"!";
@inf = (<FD>);
close(FD) ||
die "Cannot close \"" . $inf_file . "\"!";
$subbing = 0;
print "\n--> Updating OpensslLibCrypto.inf ... ";
foreach (@inf) {
if ( $_ =~ "# Autogenerated files list starts here" ) {
push @new_inf, $_, @cryptofilelist;
$subbing = 1;
next;
}
if ( $_ =~ "# Autogenerated files list ends here" ) {
push @new_inf, $_;
$subbing = 0;
next;
$subbing = 0;
print "\n--> Updating OpensslLibCrypto.inf ... ";
foreach (@inf) {
if ( $_ =~ "# Autogenerated files list starts here" ) {
push @new_inf, $_, @cryptofilelist;
$subbing = 1;
next;
}
if ( $_ =~ "# Autogenerated files list ends here" ) {
push @new_inf, $_;
$subbing = 0;
next;
}
push @new_inf, $_
unless ($subbing);
}
push @new_inf, $_
unless ($subbing);
$new_inf_file = $inf_file . ".new";
open( FD, ">" . $new_inf_file ) ||
die $new_inf_file;
print( FD @new_inf ) ||
die $new_inf_file;
close(FD) ||
die $new_inf_file;
rename( $new_inf_file, $inf_file ) ||
die "rename $inf_file";
print "Done!";
}
$new_inf_file = $inf_file . ".new";
open( FD, ">" . $new_inf_file ) ||
die $new_inf_file;
print( FD @new_inf ) ||
die $new_inf_file;
close(FD) ||
die $new_inf_file;
rename( $new_inf_file, $inf_file ) ||
die "rename $inf_file";
print "Done!";
#
# Copy opensslconf.h and dso_conf.h generated from OpenSSL Configuration
#