Add arm-xlate.pl and initial iOS asm support.
This is as partial import of upstream's 9b05cbc33e7895ed033b1119e300782d9e0cf23c. It includes the perlasm changes, but not the CPU feature detection bits as we do those differently. This is largely so we don't diverge from upstream, but it'll help with iOS assembly in the future. sha512-armv8.pl is modified slightly from upstream to switch from conditioning on the output file to conditioning on an extra argument. This makes our previous change from upstream (removing the 'open STDOUT' line) more explicit. BUG=338886 Change-Id: Ic8ca1388ae20e94566f475bad3464ccc73f445df Reviewed-on: https://boringssl-review.googlesource.com/4405 Reviewed-by: Adam Langley <agl@google.com>
This commit is contained in:
parent
c574f4114d
commit
f06802f1e4
@ -41,6 +41,7 @@ function(perlasm dest src)
|
||||
COMMAND ${PERL_EXECUTABLE} ${CMAKE_CURRENT_SOURCE_DIR}/${src} ${PERLASM_STYLE} ${PERLASM_FLAGS} ${ARGN} > ${dest}
|
||||
DEPENDS
|
||||
${src}
|
||||
${PROJECT_SOURCE_DIR}/crypto/perlasm/arm-xlate.pl
|
||||
${PROJECT_SOURCE_DIR}/crypto/perlasm/x86_64-xlate.pl
|
||||
${PROJECT_SOURCE_DIR}/crypto/perlasm/x86asm.pl
|
||||
${PROJECT_SOURCE_DIR}/crypto/perlasm/x86gas.pl
|
||||
|
@ -28,7 +28,15 @@
|
||||
# Cortex-A57 3.64 1.34 1.32
|
||||
|
||||
$flavour = shift;
|
||||
open STDOUT,">".shift;
|
||||
$output = shift;
|
||||
|
||||
$0 =~ m/(.*[\/\\])[^\/\\]+$/; $dir=$1;
|
||||
( $xlate="${dir}arm-xlate.pl" and -f $xlate ) or
|
||||
( $xlate="${dir}../../perlasm/arm-xlate.pl" and -f $xlate) or
|
||||
die "can't locate arm-xlate.pl";
|
||||
|
||||
open OUT,"| \"$^X\" $xlate $flavour $output";
|
||||
*STDOUT=*OUT;
|
||||
|
||||
$prefix="aes_v8";
|
||||
|
||||
@ -56,7 +64,7 @@ my ($zero,$rcon,$mask,$in0,$in1,$tmp,$key)=
|
||||
|
||||
$code.=<<___;
|
||||
.align 5
|
||||
rcon:
|
||||
.Lrcon:
|
||||
.long 0x01,0x01,0x01,0x01
|
||||
.long 0x0c0f0e0d,0x0c0f0e0d,0x0c0f0e0d,0x0c0f0e0d // rotate-n-splat
|
||||
.long 0x1b,0x1b,0x1b,0x1b
|
||||
@ -85,7 +93,7 @@ $code.=<<___;
|
||||
tst $bits,#0x3f
|
||||
b.ne .Lenc_key_abort
|
||||
|
||||
adr $ptr,rcon
|
||||
adr $ptr,.Lrcon
|
||||
cmp $bits,#192
|
||||
|
||||
veor $zero,$zero,$zero
|
||||
|
@ -26,7 +26,15 @@
|
||||
# (*) presented for reference/comparison purposes;
|
||||
|
||||
$flavour = shift;
|
||||
open STDOUT,">".shift;
|
||||
$output = shift;
|
||||
|
||||
$0 =~ m/(.*[\/\\])[^\/\\]+$/; $dir=$1;
|
||||
( $xlate="${dir}arm-xlate.pl" and -f $xlate ) or
|
||||
( $xlate="${dir}../../perlasm/arm-xlate.pl" and -f $xlate) or
|
||||
die "can't locate arm-xlate.pl";
|
||||
|
||||
open OUT,"| \"$^X\" $xlate $flavour $output";
|
||||
*STDOUT=*OUT;
|
||||
|
||||
$Xi="x0"; # argument block
|
||||
$Htbl="x1";
|
||||
|
140
crypto/perlasm/arm-xlate.pl
Executable file
140
crypto/perlasm/arm-xlate.pl
Executable file
@ -0,0 +1,140 @@
|
||||
#!/usr/bin/env perl
|
||||
|
||||
# ARM assembler distiller by <appro>.
|
||||
|
||||
my $flavour = shift;
|
||||
my $output = shift;
|
||||
open STDOUT,">$output" || die "can't open $output: $!";
|
||||
|
||||
$flavour = "linux32" if (!$flavour or $flavour eq "void");
|
||||
|
||||
my %GLOBALS;
|
||||
my $dotinlocallabels=($flavour=~/linux/)?1:0;
|
||||
|
||||
################################################################
|
||||
# directives which need special treatment on different platforms
|
||||
################################################################
|
||||
my $arch = sub {
|
||||
if ($flavour =~ /linux/) { ".arch\t".join(',',@_); }
|
||||
else { ""; }
|
||||
};
|
||||
my $globl = sub {
|
||||
my $name = shift;
|
||||
my $global = \$GLOBALS{$name};
|
||||
my $ret;
|
||||
|
||||
SWITCH: for ($flavour) {
|
||||
/ios/ && do { $name = "_$name";
|
||||
last;
|
||||
};
|
||||
}
|
||||
|
||||
$ret = ".globl $name" if (!$ret);
|
||||
$$global = $name;
|
||||
$ret;
|
||||
};
|
||||
my $global = $globl;
|
||||
my $extern = sub {
|
||||
&$globl(@_);
|
||||
return; # return nothing
|
||||
};
|
||||
my $type = sub {
|
||||
if ($flavour =~ /linux/) { ".type\t".join(',',@_); }
|
||||
else { ""; }
|
||||
};
|
||||
my $size = sub {
|
||||
if ($flavour =~ /linux/) { ".size\t".join(',',@_); }
|
||||
else { ""; }
|
||||
};
|
||||
my $inst = sub {
|
||||
if ($flavour =~ /linux/) { ".inst\t".join(',',@_); }
|
||||
else { ".long\t".join(',',@_); }
|
||||
};
|
||||
my $asciz = sub {
|
||||
my $line = join(",",@_);
|
||||
if ($line =~ /^"(.*)"$/)
|
||||
{ ".byte " . join(",",unpack("C*",$1),0) . "\n.align 2"; }
|
||||
else
|
||||
{ ""; }
|
||||
};
|
||||
|
||||
sub range {
|
||||
my ($r,$sfx,$start,$end) = @_;
|
||||
|
||||
join(",",map("$r$_$sfx",($start..$end)));
|
||||
}
|
||||
|
||||
sub parse_args {
|
||||
my $line = shift;
|
||||
my @ret = ();
|
||||
|
||||
pos($line)=0;
|
||||
|
||||
while (1) {
|
||||
if ($line =~ m/\G\[/gc) {
|
||||
$line =~ m/\G([^\]]+\][^,]*)\s*/g;
|
||||
push @ret,"[$1";
|
||||
}
|
||||
elsif ($line =~ m/\G\{/gc) {
|
||||
$line =~ m/\G([^\}]+\}[^,]*)\s*/g;
|
||||
my $arg = $1;
|
||||
$arg =~ s/([rdqv])([0-9]+)([^\-]*)\-\1([0-9]+)\3/range($1,$3,$2,$4)/ge;
|
||||
push @ret,"{$arg";
|
||||
}
|
||||
elsif ($line =~ m/\G([^,]+)\s*/g) {
|
||||
push @ret,$1;
|
||||
}
|
||||
|
||||
last if ($line =~ m/\G$/gc);
|
||||
|
||||
$line =~ m/\G,\s*/g;
|
||||
}
|
||||
|
||||
map {my $s=$_;$s=~s/\b(\w+)/$GLOBALS{$1} or $1/ge;$s} @ret;
|
||||
}
|
||||
|
||||
while($line=<>) {
|
||||
|
||||
$line =~ s|/\*.*\*/||; # get rid of C-style comments...
|
||||
$line =~ s|^\s+||; # ... and skip white spaces in beginning...
|
||||
$line =~ s|\s+$||; # ... and at the end
|
||||
|
||||
{
|
||||
$line =~ s|[\b\.]L(\w+)|L$1|g; # common denominator for Locallabel
|
||||
$line =~ s|\bL(\w+)|\.L$1|g if ($dotinlocallabels);
|
||||
}
|
||||
|
||||
{
|
||||
$line =~ s|(^[\.\w]+)\:\s*||;
|
||||
my $label = $1;
|
||||
if ($label) {
|
||||
printf "%s:",($GLOBALS{$label} or $label);
|
||||
}
|
||||
}
|
||||
|
||||
if ($line !~ m/^#/o) {
|
||||
$line =~ s|^\s*(\.?)(\S+)\s*||o;
|
||||
my $c = $1; $c = "\t" if ($c eq "");
|
||||
my $mnemonic = $2;
|
||||
my $opcode;
|
||||
if ($mnemonic =~ m/([^\.]+)\.([^\.]+)/o) {
|
||||
$opcode = eval("\$$1_$2");
|
||||
} else {
|
||||
$opcode = eval("\$$mnemonic");
|
||||
}
|
||||
|
||||
my @args=parse_args($line);
|
||||
|
||||
if (ref($opcode) eq 'CODE') {
|
||||
$line = &$opcode(@args);
|
||||
} elsif ($mnemonic) {
|
||||
$line = $c.$mnemonic;
|
||||
$line.= "\t".join(',',@args) if ($#args>=0);
|
||||
}
|
||||
}
|
||||
|
||||
print $line if ($line);
|
||||
print "\n";
|
||||
}
|
||||
|
||||
close STDOUT;
|
@ -20,7 +20,15 @@
|
||||
# (*) Software results are presented mostly for reference purposes.
|
||||
|
||||
$flavour = shift;
|
||||
open STDOUT,">".shift;
|
||||
$output = shift;
|
||||
|
||||
$0 =~ m/(.*[\/\\])[^\/\\]+$/; $dir=$1;
|
||||
( $xlate="${dir}arm-xlate.pl" and -f $xlate ) or
|
||||
( $xlate="${dir}../../perlasm/arm-xlate.pl" and -f $xlate) or
|
||||
die "can't locate arm-xlate.pl";
|
||||
|
||||
open OUT,"| \"$^X\" $xlate $flavour $output";
|
||||
*STDOUT=*OUT;
|
||||
|
||||
($ctx,$inp,$num)=("x0","x1","x2");
|
||||
@Xw=map("w$_",(3..17,19));
|
||||
@ -154,6 +162,7 @@ $code.=<<___;
|
||||
|
||||
.text
|
||||
|
||||
.extern OPENSSL_armcap_P
|
||||
.globl sha1_block_data_order
|
||||
.type sha1_block_data_order,%function
|
||||
.align 6
|
||||
|
@ -28,9 +28,21 @@
|
||||
# and lags behind assembly only by 50-90%.
|
||||
|
||||
$flavour=shift;
|
||||
# Unlike most perlasm files, sha512-armv8.pl takes an additional argument to
|
||||
# determine which hash function to emit. This differs from upstream OpenSSL so
|
||||
# that the script may continue to output to stdout.
|
||||
$variant=shift;
|
||||
$output=shift;
|
||||
|
||||
if ($output =~ /512/) {
|
||||
$0 =~ m/(.*[\/\\])[^\/\\]+$/; $dir=$1;
|
||||
( $xlate="${dir}arm-xlate.pl" and -f $xlate ) or
|
||||
( $xlate="${dir}../../perlasm/arm-xlate.pl" and -f $xlate) or
|
||||
die "can't locate arm-xlate.pl";
|
||||
|
||||
open OUT,"| \"$^X\" $xlate $flavour $output";
|
||||
*STDOUT=*OUT;
|
||||
|
||||
if ($variant eq "sha512") {
|
||||
$BITS=512;
|
||||
$SZ=8;
|
||||
@Sigma0=(28,34,39);
|
||||
@ -39,7 +51,7 @@ if ($output =~ /512/) {
|
||||
@sigma1=(19,61, 6);
|
||||
$rounds=80;
|
||||
$reg_t="x";
|
||||
} else {
|
||||
} elsif ($variant eq "sha256") {
|
||||
$BITS=256;
|
||||
$SZ=4;
|
||||
@Sigma0=( 2,13,22);
|
||||
@ -48,6 +60,8 @@ if ($output =~ /512/) {
|
||||
@sigma1=(17,19,10);
|
||||
$rounds=64;
|
||||
$reg_t="w";
|
||||
} else {
|
||||
die "Unknown variant: $variant";
|
||||
}
|
||||
|
||||
$func="sha${BITS}_block_data_order";
|
||||
@ -152,6 +166,7 @@ $code.=<<___;
|
||||
|
||||
.text
|
||||
|
||||
.extern OPENSSL_armcap_P
|
||||
.globl $func
|
||||
.type $func,%function
|
||||
.align 6
|
||||
@ -181,7 +196,7 @@ $code.=<<___;
|
||||
ldp $E,$F,[$ctx,#4*$SZ]
|
||||
add $num,$inp,$num,lsl#`log(16*$SZ)/log(2)` // end of input
|
||||
ldp $G,$H,[$ctx,#6*$SZ]
|
||||
adr $Ktbl,K$BITS
|
||||
adr $Ktbl,.LK$BITS
|
||||
stp $ctx,$num,[x29,#96]
|
||||
|
||||
.Loop:
|
||||
@ -231,8 +246,8 @@ $code.=<<___;
|
||||
.size $func,.-$func
|
||||
|
||||
.align 6
|
||||
.type K$BITS,%object
|
||||
K$BITS:
|
||||
.type .LK$BITS,%object
|
||||
.LK$BITS:
|
||||
___
|
||||
$code.=<<___ if ($SZ==8);
|
||||
.quad 0x428a2f98d728ae22,0x7137449123ef65cd
|
||||
@ -297,7 +312,7 @@ $code.=<<___ if ($SZ==4);
|
||||
.long 0 //terminator
|
||||
___
|
||||
$code.=<<___;
|
||||
.size K$BITS,.-K$BITS
|
||||
.size .LK$BITS,.-.LK$BITS
|
||||
.align 3
|
||||
.LOPENSSL_armcap_P:
|
||||
.quad OPENSSL_armcap_P-.
|
||||
@ -322,7 +337,7 @@ sha256_block_armv8:
|
||||
add x29,sp,#0
|
||||
|
||||
ld1.32 {$ABCD,$EFGH},[$ctx]
|
||||
adr $Ktbl,K256
|
||||
adr $Ktbl,.LK256
|
||||
|
||||
.Loop_hw:
|
||||
ld1 {@MSG[0]-@MSG[3]},[$inp],#64
|
||||
|
Loading…
x
Reference in New Issue
Block a user