1e1051a39Sopenharmony_ci#! /usr/bin/env perl
2e1051a39Sopenharmony_ci# Copyright 2009-2020 The OpenSSL Project Authors. All Rights Reserved.
3e1051a39Sopenharmony_ci#
4e1051a39Sopenharmony_ci# Licensed under the Apache License 2.0 (the "License").  You may not use
5e1051a39Sopenharmony_ci# this file except in compliance with the License.  You can obtain a copy
6e1051a39Sopenharmony_ci# in the file LICENSE in the source distribution or at
7e1051a39Sopenharmony_ci# https://www.openssl.org/source/license.html
8e1051a39Sopenharmony_ci
9e1051a39Sopenharmony_ci
10e1051a39Sopenharmony_ci# ====================================================================
11e1051a39Sopenharmony_ci# Written by Andy Polyakov <appro@openssl.org> for the OpenSSL
12e1051a39Sopenharmony_ci# project. The module is, however, dual licensed under OpenSSL and
13e1051a39Sopenharmony_ci# CRYPTOGAMS licenses depending on where you obtain it. For further
14e1051a39Sopenharmony_ci# details see http://www.openssl.org/~appro/cryptogams/.
15e1051a39Sopenharmony_ci# ====================================================================
16e1051a39Sopenharmony_ci
17e1051a39Sopenharmony_ci# SHA1 block procedure for PA-RISC.
18e1051a39Sopenharmony_ci
19e1051a39Sopenharmony_ci# June 2009.
20e1051a39Sopenharmony_ci#
21e1051a39Sopenharmony_ci# On PA-7100LC performance is >30% better than gcc 3.2 generated code
22e1051a39Sopenharmony_ci# for aligned input and >50% better for unaligned. Compared to vendor
23e1051a39Sopenharmony_ci# compiler on PA-8600 it's almost 60% faster in 64-bit build and just
24e1051a39Sopenharmony_ci# few percent faster in 32-bit one (this for aligned input, data for
25e1051a39Sopenharmony_ci# unaligned input is not available).
26e1051a39Sopenharmony_ci#
27e1051a39Sopenharmony_ci# Special thanks to polarhome.com for providing HP-UX account.
28e1051a39Sopenharmony_ci
29e1051a39Sopenharmony_ci# $output is the last argument if it looks like a file (it has an extension)
30e1051a39Sopenharmony_ci# $flavour is the first argument if it doesn't look like a file
31e1051a39Sopenharmony_ci$output = $#ARGV >= 0 && $ARGV[$#ARGV] =~ m|\.\w+$| ? pop : undef;
32e1051a39Sopenharmony_ci$flavour = $#ARGV >= 0 && $ARGV[0] !~ m|\.| ? shift : undef;
33e1051a39Sopenharmony_ci
34e1051a39Sopenharmony_ci$output and open STDOUT,">$output";
35e1051a39Sopenharmony_ci
36e1051a39Sopenharmony_ciif ($flavour =~ /64/) {
37e1051a39Sopenharmony_ci	$LEVEL		="2.0W";
38e1051a39Sopenharmony_ci	$SIZE_T		=8;
39e1051a39Sopenharmony_ci	$FRAME_MARKER	=80;
40e1051a39Sopenharmony_ci	$SAVED_RP	=16;
41e1051a39Sopenharmony_ci	$PUSH		="std";
42e1051a39Sopenharmony_ci	$PUSHMA		="std,ma";
43e1051a39Sopenharmony_ci	$POP		="ldd";
44e1051a39Sopenharmony_ci	$POPMB		="ldd,mb";
45e1051a39Sopenharmony_ci} else {
46e1051a39Sopenharmony_ci	$LEVEL		="1.0";
47e1051a39Sopenharmony_ci	$SIZE_T		=4;
48e1051a39Sopenharmony_ci	$FRAME_MARKER	=48;
49e1051a39Sopenharmony_ci	$SAVED_RP	=20;
50e1051a39Sopenharmony_ci	$PUSH		="stw";
51e1051a39Sopenharmony_ci	$PUSHMA		="stwm";
52e1051a39Sopenharmony_ci	$POP		="ldw";
53e1051a39Sopenharmony_ci	$POPMB		="ldwm";
54e1051a39Sopenharmony_ci}
55e1051a39Sopenharmony_ci
56e1051a39Sopenharmony_ci$FRAME=14*$SIZE_T+$FRAME_MARKER;# 14 saved regs + frame marker
57e1051a39Sopenharmony_ci				#                 [+ argument transfer]
58e1051a39Sopenharmony_ci$ctx="%r26";		# arg0
59e1051a39Sopenharmony_ci$inp="%r25";		# arg1
60e1051a39Sopenharmony_ci$num="%r24";		# arg2
61e1051a39Sopenharmony_ci
62e1051a39Sopenharmony_ci$t0="%r28";
63e1051a39Sopenharmony_ci$t1="%r29";
64e1051a39Sopenharmony_ci$K="%r31";
65e1051a39Sopenharmony_ci
66e1051a39Sopenharmony_ci@X=("%r1", "%r2", "%r3", "%r4", "%r5", "%r6", "%r7", "%r8",
67e1051a39Sopenharmony_ci    "%r9", "%r10","%r11","%r12","%r13","%r14","%r15","%r16",$t0);
68e1051a39Sopenharmony_ci
69e1051a39Sopenharmony_ci@V=($A,$B,$C,$D,$E)=("%r19","%r20","%r21","%r22","%r23");
70e1051a39Sopenharmony_ci
71e1051a39Sopenharmony_cisub BODY_00_19 {
72e1051a39Sopenharmony_cimy ($i,$a,$b,$c,$d,$e)=@_;
73e1051a39Sopenharmony_cimy $j=$i+1;
74e1051a39Sopenharmony_ci$code.=<<___ if ($i<15);
75e1051a39Sopenharmony_ci	addl	$K,$e,$e	; $i
76e1051a39Sopenharmony_ci	shd	$a,$a,27,$t1
77e1051a39Sopenharmony_ci	addl	@X[$i],$e,$e
78e1051a39Sopenharmony_ci	and	$c,$b,$t0
79e1051a39Sopenharmony_ci	addl	$t1,$e,$e
80e1051a39Sopenharmony_ci	andcm	$d,$b,$t1
81e1051a39Sopenharmony_ci	shd	$b,$b,2,$b
82e1051a39Sopenharmony_ci	or	$t1,$t0,$t0
83e1051a39Sopenharmony_ci	addl	$t0,$e,$e
84e1051a39Sopenharmony_ci___
85e1051a39Sopenharmony_ci$code.=<<___ if ($i>=15);	# with forward Xupdate
86e1051a39Sopenharmony_ci	addl	$K,$e,$e	; $i
87e1051a39Sopenharmony_ci	shd	$a,$a,27,$t1
88e1051a39Sopenharmony_ci	xor	@X[($j+2)%16],@X[$j%16],@X[$j%16]
89e1051a39Sopenharmony_ci	addl	@X[$i%16],$e,$e
90e1051a39Sopenharmony_ci	and	$c,$b,$t0
91e1051a39Sopenharmony_ci	xor	@X[($j+8)%16],@X[$j%16],@X[$j%16]
92e1051a39Sopenharmony_ci	addl	$t1,$e,$e
93e1051a39Sopenharmony_ci	andcm	$d,$b,$t1
94e1051a39Sopenharmony_ci	shd	$b,$b,2,$b
95e1051a39Sopenharmony_ci	or	$t1,$t0,$t0
96e1051a39Sopenharmony_ci	xor	@X[($j+13)%16],@X[$j%16],@X[$j%16]
97e1051a39Sopenharmony_ci	add	$t0,$e,$e
98e1051a39Sopenharmony_ci	shd	@X[$j%16],@X[$j%16],31,@X[$j%16]
99e1051a39Sopenharmony_ci___
100e1051a39Sopenharmony_ci}
101e1051a39Sopenharmony_ci
102e1051a39Sopenharmony_cisub BODY_20_39 {
103e1051a39Sopenharmony_cimy ($i,$a,$b,$c,$d,$e)=@_;
104e1051a39Sopenharmony_cimy $j=$i+1;
105e1051a39Sopenharmony_ci$code.=<<___ if ($i<79);
106e1051a39Sopenharmony_ci	xor	@X[($j+2)%16],@X[$j%16],@X[$j%16]	; $i
107e1051a39Sopenharmony_ci	addl	$K,$e,$e
108e1051a39Sopenharmony_ci	shd	$a,$a,27,$t1
109e1051a39Sopenharmony_ci	xor	@X[($j+8)%16],@X[$j%16],@X[$j%16]
110e1051a39Sopenharmony_ci	addl	@X[$i%16],$e,$e
111e1051a39Sopenharmony_ci	xor	$b,$c,$t0
112e1051a39Sopenharmony_ci	xor	@X[($j+13)%16],@X[$j%16],@X[$j%16]
113e1051a39Sopenharmony_ci	addl	$t1,$e,$e
114e1051a39Sopenharmony_ci	shd	$b,$b,2,$b
115e1051a39Sopenharmony_ci	xor	$d,$t0,$t0
116e1051a39Sopenharmony_ci	shd	@X[$j%16],@X[$j%16],31,@X[$j%16]
117e1051a39Sopenharmony_ci	addl	$t0,$e,$e
118e1051a39Sopenharmony_ci___
119e1051a39Sopenharmony_ci$code.=<<___ if ($i==79);	# with context load
120e1051a39Sopenharmony_ci	ldw	0($ctx),@X[0]	; $i
121e1051a39Sopenharmony_ci	addl	$K,$e,$e
122e1051a39Sopenharmony_ci	shd	$a,$a,27,$t1
123e1051a39Sopenharmony_ci	ldw	4($ctx),@X[1]
124e1051a39Sopenharmony_ci	addl	@X[$i%16],$e,$e
125e1051a39Sopenharmony_ci	xor	$b,$c,$t0
126e1051a39Sopenharmony_ci	ldw	8($ctx),@X[2]
127e1051a39Sopenharmony_ci	addl	$t1,$e,$e
128e1051a39Sopenharmony_ci	shd	$b,$b,2,$b
129e1051a39Sopenharmony_ci	xor	$d,$t0,$t0
130e1051a39Sopenharmony_ci	ldw	12($ctx),@X[3]
131e1051a39Sopenharmony_ci	addl	$t0,$e,$e
132e1051a39Sopenharmony_ci	ldw	16($ctx),@X[4]
133e1051a39Sopenharmony_ci___
134e1051a39Sopenharmony_ci}
135e1051a39Sopenharmony_ci
136e1051a39Sopenharmony_cisub BODY_40_59 {
137e1051a39Sopenharmony_cimy ($i,$a,$b,$c,$d,$e)=@_;
138e1051a39Sopenharmony_cimy $j=$i+1;
139e1051a39Sopenharmony_ci$code.=<<___;
140e1051a39Sopenharmony_ci	shd	$a,$a,27,$t1	; $i
141e1051a39Sopenharmony_ci	addl	$K,$e,$e
142e1051a39Sopenharmony_ci	xor	@X[($j+2)%16],@X[$j%16],@X[$j%16]
143e1051a39Sopenharmony_ci	xor	$d,$c,$t0
144e1051a39Sopenharmony_ci	addl	@X[$i%16],$e,$e
145e1051a39Sopenharmony_ci	xor	@X[($j+8)%16],@X[$j%16],@X[$j%16]
146e1051a39Sopenharmony_ci	and	$b,$t0,$t0
147e1051a39Sopenharmony_ci	addl	$t1,$e,$e
148e1051a39Sopenharmony_ci	shd	$b,$b,2,$b
149e1051a39Sopenharmony_ci	xor	@X[($j+13)%16],@X[$j%16],@X[$j%16]
150e1051a39Sopenharmony_ci	addl	$t0,$e,$e
151e1051a39Sopenharmony_ci	and	$d,$c,$t1
152e1051a39Sopenharmony_ci	shd	@X[$j%16],@X[$j%16],31,@X[$j%16]
153e1051a39Sopenharmony_ci	addl	$t1,$e,$e
154e1051a39Sopenharmony_ci___
155e1051a39Sopenharmony_ci}
156e1051a39Sopenharmony_ci
157e1051a39Sopenharmony_ci$code=<<___;
158e1051a39Sopenharmony_ci	.LEVEL	$LEVEL
159e1051a39Sopenharmony_ci	.SPACE	\$TEXT\$
160e1051a39Sopenharmony_ci	.SUBSPA	\$CODE\$,QUAD=0,ALIGN=8,ACCESS=0x2C,CODE_ONLY
161e1051a39Sopenharmony_ci
162e1051a39Sopenharmony_ci	.EXPORT	sha1_block_data_order,ENTRY,ARGW0=GR,ARGW1=GR,ARGW2=GR
163e1051a39Sopenharmony_cisha1_block_data_order
164e1051a39Sopenharmony_ci	.PROC
165e1051a39Sopenharmony_ci	.CALLINFO	FRAME=`$FRAME-14*$SIZE_T`,NO_CALLS,SAVE_RP,ENTRY_GR=16
166e1051a39Sopenharmony_ci	.ENTRY
167e1051a39Sopenharmony_ci	$PUSH	%r2,-$SAVED_RP(%sp)	; standard prologue
168e1051a39Sopenharmony_ci	$PUSHMA	%r3,$FRAME(%sp)
169e1051a39Sopenharmony_ci	$PUSH	%r4,`-$FRAME+1*$SIZE_T`(%sp)
170e1051a39Sopenharmony_ci	$PUSH	%r5,`-$FRAME+2*$SIZE_T`(%sp)
171e1051a39Sopenharmony_ci	$PUSH	%r6,`-$FRAME+3*$SIZE_T`(%sp)
172e1051a39Sopenharmony_ci	$PUSH	%r7,`-$FRAME+4*$SIZE_T`(%sp)
173e1051a39Sopenharmony_ci	$PUSH	%r8,`-$FRAME+5*$SIZE_T`(%sp)
174e1051a39Sopenharmony_ci	$PUSH	%r9,`-$FRAME+6*$SIZE_T`(%sp)
175e1051a39Sopenharmony_ci	$PUSH	%r10,`-$FRAME+7*$SIZE_T`(%sp)
176e1051a39Sopenharmony_ci	$PUSH	%r11,`-$FRAME+8*$SIZE_T`(%sp)
177e1051a39Sopenharmony_ci	$PUSH	%r12,`-$FRAME+9*$SIZE_T`(%sp)
178e1051a39Sopenharmony_ci	$PUSH	%r13,`-$FRAME+10*$SIZE_T`(%sp)
179e1051a39Sopenharmony_ci	$PUSH	%r14,`-$FRAME+11*$SIZE_T`(%sp)
180e1051a39Sopenharmony_ci	$PUSH	%r15,`-$FRAME+12*$SIZE_T`(%sp)
181e1051a39Sopenharmony_ci	$PUSH	%r16,`-$FRAME+13*$SIZE_T`(%sp)
182e1051a39Sopenharmony_ci
183e1051a39Sopenharmony_ci	ldw	0($ctx),$A
184e1051a39Sopenharmony_ci	ldw	4($ctx),$B
185e1051a39Sopenharmony_ci	ldw	8($ctx),$C
186e1051a39Sopenharmony_ci	ldw	12($ctx),$D
187e1051a39Sopenharmony_ci	ldw	16($ctx),$E
188e1051a39Sopenharmony_ci
189e1051a39Sopenharmony_ci	extru	$inp,31,2,$t0		; t0=inp&3;
190e1051a39Sopenharmony_ci	sh3addl	$t0,%r0,$t0		; t0*=8;
191e1051a39Sopenharmony_ci	subi	32,$t0,$t0		; t0=32-t0;
192e1051a39Sopenharmony_ci	mtctl	$t0,%cr11		; %sar=t0;
193e1051a39Sopenharmony_ci
194e1051a39Sopenharmony_ciL\$oop
195e1051a39Sopenharmony_ci	ldi	3,$t0
196e1051a39Sopenharmony_ci	andcm	$inp,$t0,$t0		; 64-bit neutral
197e1051a39Sopenharmony_ci___
198e1051a39Sopenharmony_ci	for ($i=0;$i<15;$i++) {		# load input block
199e1051a39Sopenharmony_ci	$code.="\tldw	`4*$i`($t0),@X[$i]\n";		}
200e1051a39Sopenharmony_ci$code.=<<___;
201e1051a39Sopenharmony_ci	cmpb,*=	$inp,$t0,L\$aligned
202e1051a39Sopenharmony_ci	ldw	60($t0),@X[15]
203e1051a39Sopenharmony_ci	ldw	64($t0),@X[16]
204e1051a39Sopenharmony_ci___
205e1051a39Sopenharmony_ci	for ($i=0;$i<16;$i++) {		# align input
206e1051a39Sopenharmony_ci	$code.="\tvshd	@X[$i],@X[$i+1],@X[$i]\n";	}
207e1051a39Sopenharmony_ci$code.=<<___;
208e1051a39Sopenharmony_ciL\$aligned
209e1051a39Sopenharmony_ci	ldil	L'0x5a827000,$K		; K_00_19
210e1051a39Sopenharmony_ci	ldo	0x999($K),$K
211e1051a39Sopenharmony_ci___
212e1051a39Sopenharmony_cifor ($i=0;$i<20;$i++)   { &BODY_00_19($i,@V); unshift(@V,pop(@V)); }
213e1051a39Sopenharmony_ci$code.=<<___;
214e1051a39Sopenharmony_ci	ldil	L'0x6ed9e000,$K		; K_20_39
215e1051a39Sopenharmony_ci	ldo	0xba1($K),$K
216e1051a39Sopenharmony_ci___
217e1051a39Sopenharmony_ci
218e1051a39Sopenharmony_cifor (;$i<40;$i++)       { &BODY_20_39($i,@V); unshift(@V,pop(@V)); }
219e1051a39Sopenharmony_ci$code.=<<___;
220e1051a39Sopenharmony_ci	ldil	L'0x8f1bb000,$K		; K_40_59
221e1051a39Sopenharmony_ci	ldo	0xcdc($K),$K
222e1051a39Sopenharmony_ci___
223e1051a39Sopenharmony_ci
224e1051a39Sopenharmony_cifor (;$i<60;$i++)       { &BODY_40_59($i,@V); unshift(@V,pop(@V)); }
225e1051a39Sopenharmony_ci$code.=<<___;
226e1051a39Sopenharmony_ci	ldil	L'0xca62c000,$K		; K_60_79
227e1051a39Sopenharmony_ci	ldo	0x1d6($K),$K
228e1051a39Sopenharmony_ci___
229e1051a39Sopenharmony_cifor (;$i<80;$i++)       { &BODY_20_39($i,@V); unshift(@V,pop(@V)); }
230e1051a39Sopenharmony_ci
231e1051a39Sopenharmony_ci$code.=<<___;
232e1051a39Sopenharmony_ci	addl	@X[0],$A,$A
233e1051a39Sopenharmony_ci	addl	@X[1],$B,$B
234e1051a39Sopenharmony_ci	addl	@X[2],$C,$C
235e1051a39Sopenharmony_ci	addl	@X[3],$D,$D
236e1051a39Sopenharmony_ci	addl	@X[4],$E,$E
237e1051a39Sopenharmony_ci	stw	$A,0($ctx)
238e1051a39Sopenharmony_ci	stw	$B,4($ctx)
239e1051a39Sopenharmony_ci	stw	$C,8($ctx)
240e1051a39Sopenharmony_ci	stw	$D,12($ctx)
241e1051a39Sopenharmony_ci	stw	$E,16($ctx)
242e1051a39Sopenharmony_ci	addib,*<> -1,$num,L\$oop
243e1051a39Sopenharmony_ci	ldo	64($inp),$inp
244e1051a39Sopenharmony_ci
245e1051a39Sopenharmony_ci	$POP	`-$FRAME-$SAVED_RP`(%sp),%r2	; standard epilogue
246e1051a39Sopenharmony_ci	$POP	`-$FRAME+1*$SIZE_T`(%sp),%r4
247e1051a39Sopenharmony_ci	$POP	`-$FRAME+2*$SIZE_T`(%sp),%r5
248e1051a39Sopenharmony_ci	$POP	`-$FRAME+3*$SIZE_T`(%sp),%r6
249e1051a39Sopenharmony_ci	$POP	`-$FRAME+4*$SIZE_T`(%sp),%r7
250e1051a39Sopenharmony_ci	$POP	`-$FRAME+5*$SIZE_T`(%sp),%r8
251e1051a39Sopenharmony_ci	$POP	`-$FRAME+6*$SIZE_T`(%sp),%r9
252e1051a39Sopenharmony_ci	$POP	`-$FRAME+7*$SIZE_T`(%sp),%r10
253e1051a39Sopenharmony_ci	$POP	`-$FRAME+8*$SIZE_T`(%sp),%r11
254e1051a39Sopenharmony_ci	$POP	`-$FRAME+9*$SIZE_T`(%sp),%r12
255e1051a39Sopenharmony_ci	$POP	`-$FRAME+10*$SIZE_T`(%sp),%r13
256e1051a39Sopenharmony_ci	$POP	`-$FRAME+11*$SIZE_T`(%sp),%r14
257e1051a39Sopenharmony_ci	$POP	`-$FRAME+12*$SIZE_T`(%sp),%r15
258e1051a39Sopenharmony_ci	$POP	`-$FRAME+13*$SIZE_T`(%sp),%r16
259e1051a39Sopenharmony_ci	bv	(%r2)
260e1051a39Sopenharmony_ci	.EXIT
261e1051a39Sopenharmony_ci	$POPMB	-$FRAME(%sp),%r3
262e1051a39Sopenharmony_ci	.PROCEND
263e1051a39Sopenharmony_ci	.STRINGZ "SHA1 block transform for PA-RISC, CRYPTOGAMS by <appro\@openssl.org>"
264e1051a39Sopenharmony_ci___
265e1051a39Sopenharmony_ci
266e1051a39Sopenharmony_ciif (`$ENV{CC} -Wa,-v -c -o /dev/null -x assembler /dev/null 2>&1`
267e1051a39Sopenharmony_ci	=~ /GNU assembler/) {
268e1051a39Sopenharmony_ci    $gnuas = 1;
269e1051a39Sopenharmony_ci}
270e1051a39Sopenharmony_ci
271e1051a39Sopenharmony_ciforeach(split("\n",$code)) {
272e1051a39Sopenharmony_ci	s/\`([^\`]*)\`/eval $1/ge;
273e1051a39Sopenharmony_ci
274e1051a39Sopenharmony_ci	s/(\.LEVEL\s+2\.0)W/$1w/	if ($gnuas && $SIZE_T==8);
275e1051a39Sopenharmony_ci	s/\.SPACE\s+\$TEXT\$/.text/	if ($gnuas && $SIZE_T==8);
276e1051a39Sopenharmony_ci	s/\.SUBSPA.*//			if ($gnuas && $SIZE_T==8);
277e1051a39Sopenharmony_ci	s/,\*/,/			if ($SIZE_T==4);
278e1051a39Sopenharmony_ci	s/\bbv\b/bve/			if ($SIZE_T==8);
279e1051a39Sopenharmony_ci
280e1051a39Sopenharmony_ci	print $_,"\n";
281e1051a39Sopenharmony_ci}
282e1051a39Sopenharmony_ciclose STDOUT or die "error closing STDOUT: $!";
283