Text file src/crypto/internal/fips140/nistec/p256_asm_arm64.s

     1  // Copyright 2018 The Go Authors. All rights reserved.
     2  // Use of this source code is governed by a BSD-style
     3  // license that can be found in the LICENSE file.
     4  
     5  //go:build !purego
     6  
     7  // This file contains constant-time, 64-bit assembly implementation of
     8  // P256. The optimizations performed here are described in detail in:
     9  // S.Gueron and V.Krasnov, "Fast prime field elliptic-curve cryptography with
    10  //                          256-bit primes"
    11  // http://link.springer.com/article/10.1007%2Fs13389-014-0090-x
    12  // https://eprint.iacr.org/2013/816.pdf
    13  
    14  #include "textflag.h"
    15  
    16  #define res_ptr R0
    17  #define a_ptr R1
    18  #define b_ptr R2
    19  
    20  #define acc0 R3
    21  #define acc1 R4
    22  #define acc2 R5
    23  #define acc3 R6
    24  
    25  #define acc4 R7
    26  #define acc5 R8
    27  #define acc6 R9
    28  #define acc7 R10
    29  #define t0 R11
    30  #define t1 R12
    31  #define t2 R13
    32  #define t3 R14
    33  #define const0 R15
    34  #define const1 R16
    35  
    36  #define hlp0 R17
    37  #define hlp1 res_ptr
    38  
    39  #define x0 R19
    40  #define x1 R20
    41  #define x2 R21
    42  #define x3 R22
    43  #define y0 R23
    44  #define y1 R24
    45  #define y2 R25
    46  #define y3 R26
    47  
    48  DATA p256const0<>+0x00(SB)/8, $0x00000000ffffffff
    49  DATA p256const1<>+0x00(SB)/8, $0xffffffff00000001
    50  DATA p256one<>+0x00(SB)/8, $0x0000000000000001
    51  DATA p256one<>+0x08(SB)/8, $0xffffffff00000000
    52  DATA p256one<>+0x10(SB)/8, $0xffffffffffffffff
    53  DATA p256one<>+0x18(SB)/8, $0x00000000fffffffe
    54  GLOBL p256const0<>(SB), 8, $8
    55  GLOBL p256const1<>(SB), 8, $8
    56  GLOBL p256one<>(SB), 8, $32
    57  
    58  /* ---------------------------------------*/
    59  // func p256MovCond(res, a, b *P256Point, cond int)
    60  // If cond == 0 res=b, else res=a
    61  TEXT ·p256MovCond(SB),NOSPLIT,$0
    62  	MOVD	res+0(FP), res_ptr
    63  	MOVD	a+8(FP), a_ptr
    64  	MOVD	b+16(FP), b_ptr
    65  	MOVD	cond+24(FP), R3
    66  
    67  	CMP	$0, R3
    68  	// Two remarks:
    69  	// 1) Will want to revisit NEON, when support is better
    70  	// 2) CSEL might not be constant time on all ARM processors
    71  	LDP	0*16(a_ptr), (R4, R5)
    72  	LDP	1*16(a_ptr), (R6, R7)
    73  	LDP	2*16(a_ptr), (R8, R9)
    74  	LDP	0*16(b_ptr), (R16, R17)
    75  	LDP	1*16(b_ptr), (R19, R20)
    76  	LDP	2*16(b_ptr), (R21, R22)
    77  	CSEL	EQ, R16, R4, R4
    78  	CSEL	EQ, R17, R5, R5
    79  	CSEL	EQ, R19, R6, R6
    80  	CSEL	EQ, R20, R7, R7
    81  	CSEL	EQ, R21, R8, R8
    82  	CSEL	EQ, R22, R9, R9
    83  	STP	(R4, R5), 0*16(res_ptr)
    84  	STP	(R6, R7), 1*16(res_ptr)
    85  	STP	(R8, R9), 2*16(res_ptr)
    86  
    87  	LDP	3*16(a_ptr), (R4, R5)
    88  	LDP	4*16(a_ptr), (R6, R7)
    89  	LDP	5*16(a_ptr), (R8, R9)
    90  	LDP	3*16(b_ptr), (R16, R17)
    91  	LDP	4*16(b_ptr), (R19, R20)
    92  	LDP	5*16(b_ptr), (R21, R22)
    93  	CSEL	EQ, R16, R4, R4
    94  	CSEL	EQ, R17, R5, R5
    95  	CSEL	EQ, R19, R6, R6
    96  	CSEL	EQ, R20, R7, R7
    97  	CSEL	EQ, R21, R8, R8
    98  	CSEL	EQ, R22, R9, R9
    99  	STP	(R4, R5), 3*16(res_ptr)
   100  	STP	(R6, R7), 4*16(res_ptr)
   101  	STP	(R8, R9), 5*16(res_ptr)
   102  
   103  	RET
   104  /* ---------------------------------------*/
   105  // func p256NegCond(val *p256Element, cond int)
   106  TEXT ·p256NegCond(SB),NOSPLIT,$0
   107  	MOVD	val+0(FP), a_ptr
   108  	MOVD	cond+8(FP), hlp0
   109  	MOVD	a_ptr, res_ptr
   110  	// acc = poly
   111  	MOVD	$-1, acc0
   112  	MOVD	p256const0<>(SB), acc1
   113  	MOVD	$0, acc2
   114  	MOVD	p256const1<>(SB), acc3
   115  	// Load the original value
   116  	LDP	0*16(a_ptr), (t0, t1)
   117  	LDP	1*16(a_ptr), (t2, t3)
   118  	// Speculatively subtract
   119  	SUBS	t0, acc0
   120  	SBCS	t1, acc1
   121  	SBCS	t2, acc2
   122  	SBC	t3, acc3
   123  	// If condition is 0, keep original value
   124  	CMP	$0, hlp0
   125  	CSEL	EQ, t0, acc0, acc0
   126  	CSEL	EQ, t1, acc1, acc1
   127  	CSEL	EQ, t2, acc2, acc2
   128  	CSEL	EQ, t3, acc3, acc3
   129  	// Store result
   130  	STP	(acc0, acc1), 0*16(res_ptr)
   131  	STP	(acc2, acc3), 1*16(res_ptr)
   132  
   133  	RET
   134  /* ---------------------------------------*/
   135  // func p256Sqr(res, in *p256Element, n int)
   136  TEXT ·p256Sqr(SB),NOSPLIT,$0
   137  	MOVD	res+0(FP), res_ptr
   138  	MOVD	in+8(FP), a_ptr
   139  	MOVD	n+16(FP), b_ptr
   140  
   141  	MOVD	p256const0<>(SB), const0
   142  	MOVD	p256const1<>(SB), const1
   143  
   144  	LDP	0*16(a_ptr), (x0, x1)
   145  	LDP	1*16(a_ptr), (x2, x3)
   146  
   147  sqrLoop:
   148  	SUB	$1, b_ptr
   149  	CALL	p256SqrInternal<>(SB)
   150  	MOVD	y0, x0
   151  	MOVD	y1, x1
   152  	MOVD	y2, x2
   153  	MOVD	y3, x3
   154  	CBNZ	b_ptr, sqrLoop
   155  
   156  	STP	(y0, y1), 0*16(res_ptr)
   157  	STP	(y2, y3), 1*16(res_ptr)
   158  	RET
   159  /* ---------------------------------------*/
   160  // func p256Mul(res, in1, in2 *p256Element)
   161  TEXT ·p256Mul(SB),NOSPLIT,$0
   162  	MOVD	res+0(FP), res_ptr
   163  	MOVD	in1+8(FP), a_ptr
   164  	MOVD	in2+16(FP), b_ptr
   165  
   166  	MOVD	p256const0<>(SB), const0
   167  	MOVD	p256const1<>(SB), const1
   168  
   169  	LDP	0*16(a_ptr), (x0, x1)
   170  	LDP	1*16(a_ptr), (x2, x3)
   171  
   172  	LDP	0*16(b_ptr), (y0, y1)
   173  	LDP	1*16(b_ptr), (y2, y3)
   174  
   175  	CALL	p256MulInternal<>(SB)
   176  
   177  	STP	(y0, y1), 0*16(res_ptr)
   178  	STP	(y2, y3), 1*16(res_ptr)
   179  	RET
   180  /* ---------------------------------------*/
   181  // func p256FromMont(res, in *p256Element)
   182  TEXT ·p256FromMont(SB),NOSPLIT,$0
   183  	MOVD	res+0(FP), res_ptr
   184  	MOVD	in+8(FP), a_ptr
   185  
   186  	MOVD	p256const0<>(SB), const0
   187  	MOVD	p256const1<>(SB), const1
   188  
   189  	LDP	0*16(a_ptr), (acc0, acc1)
   190  	LDP	1*16(a_ptr), (acc2, acc3)
   191  	// Only reduce, no multiplications are needed
   192  	// First reduction step
   193  	ADDS	acc0<<32, acc1, acc1
   194  	LSR	$32, acc0, t0
   195  	MUL	acc0, const1, t1
   196  	UMULH	acc0, const1, acc0
   197  	ADCS	t0, acc2
   198  	ADCS	t1, acc3
   199  	ADC	$0, acc0
   200  	// Second reduction step
   201  	ADDS	acc1<<32, acc2, acc2
   202  	LSR	$32, acc1, t0
   203  	MUL	acc1, const1, t1
   204  	UMULH	acc1, const1, acc1
   205  	ADCS	t0, acc3
   206  	ADCS	t1, acc0
   207  	ADC	$0, acc1
   208  	// Third reduction step
   209  	ADDS	acc2<<32, acc3, acc3
   210  	LSR	$32, acc2, t0
   211  	MUL	acc2, const1, t1
   212  	UMULH	acc2, const1, acc2
   213  	ADCS	t0, acc0
   214  	ADCS	t1, acc1
   215  	ADC	$0, acc2
   216  	// Last reduction step
   217  	ADDS	acc3<<32, acc0, acc0
   218  	LSR	$32, acc3, t0
   219  	MUL	acc3, const1, t1
   220  	UMULH	acc3, const1, acc3
   221  	ADCS	t0, acc1
   222  	ADCS	t1, acc2
   223  	ADC	$0, acc3
   224  
   225  	SUBS	$-1, acc0, t0
   226  	SBCS	const0, acc1, t1
   227  	SBCS	$0, acc2, t2
   228  	SBCS	const1, acc3, t3
   229  
   230  	CSEL	CS, t0, acc0, acc0
   231  	CSEL	CS, t1, acc1, acc1
   232  	CSEL	CS, t2, acc2, acc2
   233  	CSEL	CS, t3, acc3, acc3
   234  
   235  	STP	(acc0, acc1), 0*16(res_ptr)
   236  	STP	(acc2, acc3), 1*16(res_ptr)
   237  
   238  	RET
   239  /* ---------------------------------------*/
   240  // func p256Select(res *P256Point, table *p256Table, idx int)
   241  TEXT ·p256Select(SB),NOSPLIT,$0
   242  	MOVD	idx+16(FP), const0
   243  	MOVD	table+8(FP), b_ptr
   244  	MOVD	res+0(FP), res_ptr
   245  
   246  	EOR	x0, x0, x0
   247  	EOR	x1, x1, x1
   248  	EOR	x2, x2, x2
   249  	EOR	x3, x3, x3
   250  	EOR	y0, y0, y0
   251  	EOR	y1, y1, y1
   252  	EOR	y2, y2, y2
   253  	EOR	y3, y3, y3
   254  	EOR	t0, t0, t0
   255  	EOR	t1, t1, t1
   256  	EOR	t2, t2, t2
   257  	EOR	t3, t3, t3
   258  
   259  	MOVD	$0, const1
   260  
   261  loop_select:
   262  		ADD	$1, const1
   263  		CMP	const0, const1
   264  		LDP.P	16(b_ptr), (acc0, acc1)
   265  		CSEL	EQ, acc0, x0, x0
   266  		CSEL	EQ, acc1, x1, x1
   267  		LDP.P	16(b_ptr), (acc2, acc3)
   268  		CSEL	EQ, acc2, x2, x2
   269  		CSEL	EQ, acc3, x3, x3
   270  		LDP.P	16(b_ptr), (acc4, acc5)
   271  		CSEL	EQ, acc4, y0, y0
   272  		CSEL	EQ, acc5, y1, y1
   273  		LDP.P	16(b_ptr), (acc6, acc7)
   274  		CSEL	EQ, acc6, y2, y2
   275  		CSEL	EQ, acc7, y3, y3
   276  		LDP.P	16(b_ptr), (acc0, acc1)
   277  		CSEL	EQ, acc0, t0, t0
   278  		CSEL	EQ, acc1, t1, t1
   279  		LDP.P	16(b_ptr), (acc2, acc3)
   280  		CSEL	EQ, acc2, t2, t2
   281  		CSEL	EQ, acc3, t3, t3
   282  
   283  		CMP	$16, const1
   284  		BNE	loop_select
   285  
   286  	STP	(x0, x1), 0*16(res_ptr)
   287  	STP	(x2, x3), 1*16(res_ptr)
   288  	STP	(y0, y1), 2*16(res_ptr)
   289  	STP	(y2, y3), 3*16(res_ptr)
   290  	STP	(t0, t1), 4*16(res_ptr)
   291  	STP	(t2, t3), 5*16(res_ptr)
   292  	RET
   293  /* ---------------------------------------*/
   294  // func p256SelectAffine(res *p256AffinePoint, table *p256AffineTable, idx int)
   295  TEXT ·p256SelectAffine(SB),NOSPLIT,$0
   296  	MOVD	idx+16(FP), t0
   297  	MOVD	table+8(FP), t1
   298  	MOVD	res+0(FP), res_ptr
   299  
   300  	EOR	x0, x0, x0
   301  	EOR	x1, x1, x1
   302  	EOR	x2, x2, x2
   303  	EOR	x3, x3, x3
   304  	EOR	y0, y0, y0
   305  	EOR	y1, y1, y1
   306  	EOR	y2, y2, y2
   307  	EOR	y3, y3, y3
   308  
   309  	MOVD	$0, t2
   310  
   311  loop_select:
   312  		ADD	$1, t2
   313  		CMP	t0, t2
   314  		LDP.P	16(t1), (acc0, acc1)
   315  		CSEL	EQ, acc0, x0, x0
   316  		CSEL	EQ, acc1, x1, x1
   317  		LDP.P	16(t1), (acc2, acc3)
   318  		CSEL	EQ, acc2, x2, x2
   319  		CSEL	EQ, acc3, x3, x3
   320  		LDP.P	16(t1), (acc4, acc5)
   321  		CSEL	EQ, acc4, y0, y0
   322  		CSEL	EQ, acc5, y1, y1
   323  		LDP.P	16(t1), (acc6, acc7)
   324  		CSEL	EQ, acc6, y2, y2
   325  		CSEL	EQ, acc7, y3, y3
   326  
   327  		CMP	$32, t2
   328  		BNE	loop_select
   329  
   330  	STP	(x0, x1), 0*16(res_ptr)
   331  	STP	(x2, x3), 1*16(res_ptr)
   332  	STP	(y0, y1), 2*16(res_ptr)
   333  	STP	(y2, y3), 3*16(res_ptr)
   334  	RET
   335  /* ---------------------------------------*/
   336  // input: x0-x3, y0-y3
   337  // output: x0-x3
   338  // uses: const0, const1
   339  // clobbers: y0-y3, hlp0
   340  TEXT p256SubInternal<>(SB),NOSPLIT,$0
   341  	SUBS	x0, y0, acc0
   342  	SBCS	x1, y1, acc1
   343  	SBCS	x2, y2, acc2
   344  	SBCS	x3, y3, acc3
   345  	SBC	$0, ZR, t0
   346  
   347  	ADDS	$-1, acc0, acc4
   348  	ADCS	const0, acc1, acc5
   349  	ADCS	$0, acc2, acc6
   350  	ADC	const1, acc3, acc7
   351  
   352  	ANDS	$1, t0
   353  	CSEL	EQ, acc0, acc4, x0
   354  	CSEL	EQ, acc1, acc5, x1
   355  	CSEL	EQ, acc2, acc6, x2
   356  	CSEL	EQ, acc3, acc7, x3
   357  
   358  	RET
   359  /* ---------------------------------------*/
   360  TEXT p256SqrInternal<>(SB),NOSPLIT,$0
   361  	// x[1:] * x[0]
   362  	MUL	x0, x1, acc1
   363  	UMULH	x0, x1, acc2
   364  
   365  	MUL	x0, x2, t0
   366  	ADDS	t0, acc2, acc2
   367  	UMULH	x0, x2, acc3
   368  
   369  	MUL	x0, x3, t0
   370  	ADCS	t0, acc3, acc3
   371  	UMULH	x0, x3, acc4
   372  	ADC	$0, acc4, acc4
   373  	// x[2:] * x[1]
   374  	MUL	x1, x2, t0
   375  	ADDS	t0, acc3
   376  	UMULH	x1, x2, t1
   377  	ADCS	t1, acc4
   378  	ADC	$0, ZR, acc5
   379  
   380  	MUL	x1, x3, t0
   381  	ADDS	t0, acc4
   382  	UMULH	x1, x3, t1
   383  	ADC	t1, acc5
   384  	// x[3] * x[2]
   385  	MUL	x2, x3, t0
   386  	ADDS	t0, acc5
   387  	UMULH	x2, x3, acc6
   388  	ADC	$0, acc6
   389  
   390  	MOVD	$0, acc7
   391  	// *2
   392  	ADDS	acc1, acc1
   393  	ADCS	acc2, acc2
   394  	ADCS	acc3, acc3
   395  	ADCS	acc4, acc4
   396  	ADCS	acc5, acc5
   397  	ADCS	acc6, acc6
   398  	ADC	$0, acc7
   399  	// Missing products
   400  	MUL	x0, x0, acc0
   401  	UMULH	x0, x0, t0
   402  	ADDS	t0, acc1, acc1
   403  
   404  	MUL	x1, x1, t0
   405  	ADCS	t0, acc2, acc2
   406  	UMULH	x1, x1, t1
   407  	ADCS	t1, acc3, acc3
   408  
   409  	MUL	x2, x2, t0
   410  	ADCS	t0, acc4, acc4
   411  	UMULH	x2, x2, t1
   412  	ADCS	t1, acc5, acc5
   413  
   414  	MUL	x3, x3, t0
   415  	ADCS	t0, acc6, acc6
   416  	UMULH	x3, x3, t1
   417  	ADCS	t1, acc7, acc7
   418  	// First reduction step
   419  	ADDS	acc0<<32, acc1, acc1
   420  	LSR	$32, acc0, t0
   421  	MUL	acc0, const1, t1
   422  	UMULH	acc0, const1, acc0
   423  	ADCS	t0, acc2, acc2
   424  	ADCS	t1, acc3, acc3
   425  	ADC	$0, acc0, acc0
   426  	// Second reduction step
   427  	ADDS	acc1<<32, acc2, acc2
   428  	LSR	$32, acc1, t0
   429  	MUL	acc1, const1, t1
   430  	UMULH	acc1, const1, acc1
   431  	ADCS	t0, acc3, acc3
   432  	ADCS	t1, acc0, acc0
   433  	ADC	$0, acc1, acc1
   434  	// Third reduction step
   435  	ADDS	acc2<<32, acc3, acc3
   436  	LSR	$32, acc2, t0
   437  	MUL	acc2, const1, t1
   438  	UMULH	acc2, const1, acc2
   439  	ADCS	t0, acc0, acc0
   440  	ADCS	t1, acc1, acc1
   441  	ADC	$0, acc2, acc2
   442  	// Last reduction step
   443  	ADDS	acc3<<32, acc0, acc0
   444  	LSR	$32, acc3, t0
   445  	MUL	acc3, const1, t1
   446  	UMULH	acc3, const1, acc3
   447  	ADCS	t0, acc1, acc1
   448  	ADCS	t1, acc2, acc2
   449  	ADC	$0, acc3, acc3
   450  	// Add bits [511:256] of the sqr result
   451  	ADDS	acc4, acc0, acc0
   452  	ADCS	acc5, acc1, acc1
   453  	ADCS	acc6, acc2, acc2
   454  	ADCS	acc7, acc3, acc3
   455  	ADC	$0, ZR, acc4
   456  
   457  	SUBS	$-1, acc0, t0
   458  	SBCS	const0, acc1, t1
   459  	SBCS	$0, acc2, t2
   460  	SBCS	const1, acc3, t3
   461  	SBCS	$0, acc4, acc4
   462  
   463  	CSEL	CS, t0, acc0, y0
   464  	CSEL	CS, t1, acc1, y1
   465  	CSEL	CS, t2, acc2, y2
   466  	CSEL	CS, t3, acc3, y3
   467  	RET
   468  /* ---------------------------------------*/
   469  TEXT p256MulInternal<>(SB),NOSPLIT,$0
   470  	// y[0] * x
   471  	MUL	y0, x0, acc0
   472  	UMULH	y0, x0, acc1
   473  
   474  	MUL	y0, x1, t0
   475  	ADDS	t0, acc1
   476  	UMULH	y0, x1, acc2
   477  
   478  	MUL	y0, x2, t0
   479  	ADCS	t0, acc2
   480  	UMULH	y0, x2, acc3
   481  
   482  	MUL	y0, x3, t0
   483  	ADCS	t0, acc3
   484  	UMULH	y0, x3, acc4
   485  	ADC	$0, acc4
   486  	// First reduction step
   487  	ADDS	acc0<<32, acc1, acc1
   488  	LSR	$32, acc0, t0
   489  	MUL	acc0, const1, t1
   490  	UMULH	acc0, const1, acc0
   491  	ADCS	t0, acc2
   492  	ADCS	t1, acc3
   493  	ADC	$0, acc0
   494  	// y[1] * x
   495  	MUL	y1, x0, t0
   496  	ADDS	t0, acc1
   497  	UMULH	y1, x0, t1
   498  
   499  	MUL	y1, x1, t0
   500  	ADCS	t0, acc2
   501  	UMULH	y1, x1, t2
   502  
   503  	MUL	y1, x2, t0
   504  	ADCS	t0, acc3
   505  	UMULH	y1, x2, t3
   506  
   507  	MUL	y1, x3, t0
   508  	ADCS	t0, acc4
   509  	UMULH	y1, x3, hlp0
   510  	ADC	$0, ZR, acc5
   511  
   512  	ADDS	t1, acc2
   513  	ADCS	t2, acc3
   514  	ADCS	t3, acc4
   515  	ADC	hlp0, acc5
   516  	// Second reduction step
   517  	ADDS	acc1<<32, acc2, acc2
   518  	LSR	$32, acc1, t0
   519  	MUL	acc1, const1, t1
   520  	UMULH	acc1, const1, acc1
   521  	ADCS	t0, acc3
   522  	ADCS	t1, acc0
   523  	ADC	$0, acc1
   524  	// y[2] * x
   525  	MUL	y2, x0, t0
   526  	ADDS	t0, acc2
   527  	UMULH	y2, x0, t1
   528  
   529  	MUL	y2, x1, t0
   530  	ADCS	t0, acc3
   531  	UMULH	y2, x1, t2
   532  
   533  	MUL	y2, x2, t0
   534  	ADCS	t0, acc4
   535  	UMULH	y2, x2, t3
   536  
   537  	MUL	y2, x3, t0
   538  	ADCS	t0, acc5
   539  	UMULH	y2, x3, hlp0
   540  	ADC	$0, ZR, acc6
   541  
   542  	ADDS	t1, acc3
   543  	ADCS	t2, acc4
   544  	ADCS	t3, acc5
   545  	ADC	hlp0, acc6
   546  	// Third reduction step
   547  	ADDS	acc2<<32, acc3, acc3
   548  	LSR	$32, acc2, t0
   549  	MUL	acc2, const1, t1
   550  	UMULH	acc2, const1, acc2
   551  	ADCS	t0, acc0
   552  	ADCS	t1, acc1
   553  	ADC	$0, acc2
   554  	// y[3] * x
   555  	MUL	y3, x0, t0
   556  	ADDS	t0, acc3
   557  	UMULH	y3, x0, t1
   558  
   559  	MUL	y3, x1, t0
   560  	ADCS	t0, acc4
   561  	UMULH	y3, x1, t2
   562  
   563  	MUL	y3, x2, t0
   564  	ADCS	t0, acc5
   565  	UMULH	y3, x2, t3
   566  
   567  	MUL	y3, x3, t0
   568  	ADCS	t0, acc6
   569  	UMULH	y3, x3, hlp0
   570  	ADC	$0, ZR, acc7
   571  
   572  	ADDS	t1, acc4
   573  	ADCS	t2, acc5
   574  	ADCS	t3, acc6
   575  	ADC	hlp0, acc7
   576  	// Last reduction step
   577  	ADDS	acc3<<32, acc0, acc0
   578  	LSR	$32, acc3, t0
   579  	MUL	acc3, const1, t1
   580  	UMULH	acc3, const1, acc3
   581  	ADCS	t0, acc1
   582  	ADCS	t1, acc2
   583  	ADC	$0, acc3
   584  	// Add bits [511:256] of the mul result
   585  	ADDS	acc4, acc0, acc0
   586  	ADCS	acc5, acc1, acc1
   587  	ADCS	acc6, acc2, acc2
   588  	ADCS	acc7, acc3, acc3
   589  	ADC	$0, ZR, acc4
   590  
   591  	SUBS	$-1, acc0, t0
   592  	SBCS	const0, acc1, t1
   593  	SBCS	$0, acc2, t2
   594  	SBCS	const1, acc3, t3
   595  	SBCS	$0, acc4, acc4
   596  
   597  	CSEL	CS, t0, acc0, y0
   598  	CSEL	CS, t1, acc1, y1
   599  	CSEL	CS, t2, acc2, y2
   600  	CSEL	CS, t3, acc3, y3
   601  	RET
   602  /* ---------------------------------------*/
   603  #define p256MulBy2Inline       \
   604  	ADDS	y0, y0, x0;    \
   605  	ADCS	y1, y1, x1;    \
   606  	ADCS	y2, y2, x2;    \
   607  	ADCS	y3, y3, x3;    \
   608  	ADC	$0, ZR, hlp0;  \
   609  	SUBS	$-1, x0, t0;   \
   610  	SBCS	const0, x1, t1;\
   611  	SBCS	$0, x2, t2;    \
   612  	SBCS	const1, x3, t3;\
   613  	SBCS	$0, hlp0, hlp0;\
   614  	CSEL	CC, x0, t0, x0;\
   615  	CSEL	CC, x1, t1, x1;\
   616  	CSEL	CC, x2, t2, x2;\
   617  	CSEL	CC, x3, t3, x3;
   618  /* ---------------------------------------*/
   619  #define x1in(off) (off)(a_ptr)
   620  #define y1in(off) (off + 32)(a_ptr)
   621  #define z1in(off) (off + 64)(a_ptr)
   622  #define x2in(off) (off)(b_ptr)
   623  #define z2in(off) (off + 64)(b_ptr)
   624  #define x3out(off) (off)(res_ptr)
   625  #define y3out(off) (off + 32)(res_ptr)
   626  #define z3out(off) (off + 64)(res_ptr)
   627  #define LDx(src) LDP src(0), (x0, x1); LDP src(16), (x2, x3)
   628  #define LDy(src) LDP src(0), (y0, y1); LDP src(16), (y2, y3)
   629  #define STx(src) STP (x0, x1), src(0); STP (x2, x3), src(16)
   630  #define STy(src) STP (y0, y1), src(0); STP (y2, y3), src(16)
   631  /* ---------------------------------------*/
   632  #define y2in(off)  (32*0 + 8 + off)(RSP)
   633  #define s2(off)    (32*1 + 8 + off)(RSP)
   634  #define z1sqr(off) (32*2 + 8 + off)(RSP)
   635  #define h(off)	   (32*3 + 8 + off)(RSP)
   636  #define r(off)	   (32*4 + 8 + off)(RSP)
   637  #define hsqr(off)  (32*5 + 8 + off)(RSP)
   638  #define rsqr(off)  (32*6 + 8 + off)(RSP)
   639  #define hcub(off)  (32*7 + 8 + off)(RSP)
   640  
   641  #define z2sqr(off) (32*8 + 8 + off)(RSP)
   642  #define s1(off) (32*9 + 8 + off)(RSP)
   643  #define u1(off) (32*10 + 8 + off)(RSP)
   644  #define u2(off) (32*11 + 8 + off)(RSP)
   645  
   646  // func p256PointAddAffineAsm(res, in1 *P256Point, in2 *p256AffinePoint, sign, sel, zero int)
   647  TEXT ·p256PointAddAffineAsm(SB),0,$264-48
   648  	MOVD	in1+8(FP), a_ptr
   649  	MOVD	in2+16(FP), b_ptr
   650  	MOVD	sign+24(FP), hlp0
   651  	MOVD	sel+32(FP), hlp1
   652  	MOVD	zero+40(FP), t2
   653  
   654  	MOVD	$1, t0
   655  	CMP	$0, t2
   656  	CSEL	EQ, ZR, t0, t2
   657  	CMP	$0, hlp1
   658  	CSEL	EQ, ZR, t0, hlp1
   659  
   660  	MOVD	p256const0<>(SB), const0
   661  	MOVD	p256const1<>(SB), const1
   662  	EOR	t2<<1, hlp1
   663  
   664  	// Negate y2in based on sign
   665  	LDP	2*16(b_ptr), (y0, y1)
   666  	LDP	3*16(b_ptr), (y2, y3)
   667  	MOVD	$-1, acc0
   668  
   669  	SUBS	y0, acc0, acc0
   670  	SBCS	y1, const0, acc1
   671  	SBCS	y2, ZR, acc2
   672  	SBCS	y3, const1, acc3
   673  	SBC	$0, ZR, t0
   674  
   675  	ADDS	$-1, acc0, acc4
   676  	ADCS	const0, acc1, acc5
   677  	ADCS	$0, acc2, acc6
   678  	ADCS	const1, acc3, acc7
   679  	ADC	$0, t0, t0
   680  
   681  	CMP	$0, t0
   682  	CSEL	EQ, acc4, acc0, acc0
   683  	CSEL	EQ, acc5, acc1, acc1
   684  	CSEL	EQ, acc6, acc2, acc2
   685  	CSEL	EQ, acc7, acc3, acc3
   686  	// If condition is 0, keep original value
   687  	CMP	$0, hlp0
   688  	CSEL	EQ, y0, acc0, y0
   689  	CSEL	EQ, y1, acc1, y1
   690  	CSEL	EQ, y2, acc2, y2
   691  	CSEL	EQ, y3, acc3, y3
   692  	// Store result
   693  	STy(y2in)
   694  	// Begin point add
   695  	LDx(z1in)
   696  	CALL	p256SqrInternal<>(SB)    // z1ˆ2
   697  	STy(z1sqr)
   698  
   699  	LDx(x2in)
   700  	CALL	p256MulInternal<>(SB)    // x2 * z1ˆ2
   701  
   702  	LDx(x1in)
   703  	CALL	p256SubInternal<>(SB)    // h = u2 - u1
   704  	STx(h)
   705  
   706  	LDy(z1in)
   707  	CALL	p256MulInternal<>(SB)    // z3 = h * z1
   708  
   709  	LDP	4*16(a_ptr), (acc0, acc1)// iff select[0] == 0, z3 = z1
   710  	LDP	5*16(a_ptr), (acc2, acc3)
   711  	ANDS	$1, hlp1, ZR
   712  	CSEL	EQ, acc0, y0, y0
   713  	CSEL	EQ, acc1, y1, y1
   714  	CSEL	EQ, acc2, y2, y2
   715  	CSEL	EQ, acc3, y3, y3
   716  	LDP	p256one<>+0x00(SB), (acc0, acc1)
   717  	LDP	p256one<>+0x10(SB), (acc2, acc3)
   718  	ANDS	$2, hlp1, ZR            // iff select[1] == 0, z3 = 1
   719  	CSEL	EQ, acc0, y0, y0
   720  	CSEL	EQ, acc1, y1, y1
   721  	CSEL	EQ, acc2, y2, y2
   722  	CSEL	EQ, acc3, y3, y3
   723  	LDx(z1in)
   724  	MOVD	res+0(FP), t0
   725  	STP	(y0, y1), 4*16(t0)
   726  	STP	(y2, y3), 5*16(t0)
   727  
   728  	LDy(z1sqr)
   729  	CALL	p256MulInternal<>(SB)    // z1 ^ 3
   730  
   731  	LDx(y2in)
   732  	CALL	p256MulInternal<>(SB)    // s2 = y2 * z1ˆ3
   733  	STy(s2)
   734  
   735  	LDx(y1in)
   736  	CALL	p256SubInternal<>(SB)    // r = s2 - s1
   737  	STx(r)
   738  
   739  	CALL	p256SqrInternal<>(SB)    // rsqr = rˆ2
   740  	STy	(rsqr)
   741  
   742  	LDx(h)
   743  	CALL	p256SqrInternal<>(SB)    // hsqr = hˆ2
   744  	STy(hsqr)
   745  
   746  	CALL	p256MulInternal<>(SB)    // hcub = hˆ3
   747  	STy(hcub)
   748  
   749  	LDx(y1in)
   750  	CALL	p256MulInternal<>(SB)    // y1 * hˆ3
   751  	STy(s2)
   752  
   753  	LDP	hsqr(0*8), (x0, x1)
   754  	LDP	hsqr(2*8), (x2, x3)
   755  	LDP	0*16(a_ptr), (y0, y1)
   756  	LDP	1*16(a_ptr), (y2, y3)
   757  	CALL	p256MulInternal<>(SB)    // u1 * hˆ2
   758  	STP	(y0, y1), h(0*8)
   759  	STP	(y2, y3), h(2*8)
   760  
   761  	p256MulBy2Inline               // u1 * hˆ2 * 2, inline
   762  
   763  	LDy(rsqr)
   764  	CALL	p256SubInternal<>(SB)    // rˆ2 - u1 * hˆ2 * 2
   765  
   766  	MOVD	x0, y0
   767  	MOVD	x1, y1
   768  	MOVD	x2, y2
   769  	MOVD	x3, y3
   770  	LDx(hcub)
   771  	CALL	p256SubInternal<>(SB)
   772  
   773  	LDP	0*16(a_ptr), (acc0, acc1)
   774  	LDP	1*16(a_ptr), (acc2, acc3)
   775  	ANDS	$1, hlp1, ZR           // iff select[0] == 0, x3 = x1
   776  	CSEL	EQ, acc0, x0, x0
   777  	CSEL	EQ, acc1, x1, x1
   778  	CSEL	EQ, acc2, x2, x2
   779  	CSEL	EQ, acc3, x3, x3
   780  	LDP	0*16(b_ptr), (acc0, acc1)
   781  	LDP	1*16(b_ptr), (acc2, acc3)
   782  	ANDS	$2, hlp1, ZR           // iff select[1] == 0, x3 = x2
   783  	CSEL	EQ, acc0, x0, x0
   784  	CSEL	EQ, acc1, x1, x1
   785  	CSEL	EQ, acc2, x2, x2
   786  	CSEL	EQ, acc3, x3, x3
   787  	MOVD	res+0(FP), t0
   788  	STP	(x0, x1), 0*16(t0)
   789  	STP	(x2, x3), 1*16(t0)
   790  
   791  	LDP	h(0*8), (y0, y1)
   792  	LDP	h(2*8), (y2, y3)
   793  	CALL	p256SubInternal<>(SB)
   794  
   795  	LDP	r(0*8), (y0, y1)
   796  	LDP	r(2*8), (y2, y3)
   797  	CALL	p256MulInternal<>(SB)
   798  
   799  	LDP	s2(0*8), (x0, x1)
   800  	LDP	s2(2*8), (x2, x3)
   801  	CALL	p256SubInternal<>(SB)
   802  	LDP	2*16(a_ptr), (acc0, acc1)
   803  	LDP	3*16(a_ptr), (acc2, acc3)
   804  	ANDS	$1, hlp1, ZR           // iff select[0] == 0, y3 = y1
   805  	CSEL	EQ, acc0, x0, x0
   806  	CSEL	EQ, acc1, x1, x1
   807  	CSEL	EQ, acc2, x2, x2
   808  	CSEL	EQ, acc3, x3, x3
   809  	LDP	y2in(0*8), (acc0, acc1)
   810  	LDP	y2in(2*8), (acc2, acc3)
   811  	ANDS	$2, hlp1, ZR            // iff select[1] == 0, y3 = y2
   812  	CSEL	EQ, acc0, x0, x0
   813  	CSEL	EQ, acc1, x1, x1
   814  	CSEL	EQ, acc2, x2, x2
   815  	CSEL	EQ, acc3, x3, x3
   816  	MOVD	res+0(FP), t0
   817  	STP	(x0, x1), 2*16(t0)
   818  	STP	(x2, x3), 3*16(t0)
   819  
   820  	RET
   821  
   822  #define p256AddInline          \
   823  	ADDS	y0, x0, x0;    \
   824  	ADCS	y1, x1, x1;    \
   825  	ADCS	y2, x2, x2;    \
   826  	ADCS	y3, x3, x3;    \
   827  	ADC	$0, ZR, hlp0;  \
   828  	SUBS	$-1, x0, t0;   \
   829  	SBCS	const0, x1, t1;\
   830  	SBCS	$0, x2, t2;    \
   831  	SBCS	const1, x3, t3;\
   832  	SBCS	$0, hlp0, hlp0;\
   833  	CSEL	CC, x0, t0, x0;\
   834  	CSEL	CC, x1, t1, x1;\
   835  	CSEL	CC, x2, t2, x2;\
   836  	CSEL	CC, x3, t3, x3;
   837  
   838  #define s(off)	(32*0 + 8 + off)(RSP)
   839  #define m(off)	(32*1 + 8 + off)(RSP)
   840  #define zsqr(off) (32*2 + 8 + off)(RSP)
   841  #define tmp(off)  (32*3 + 8 + off)(RSP)
   842  
   843  //func p256PointDoubleAsm(res, in *P256Point)
   844  TEXT ·p256PointDoubleAsm(SB),NOSPLIT,$136-16
   845  	MOVD	res+0(FP), res_ptr
   846  	MOVD	in+8(FP), a_ptr
   847  
   848  	MOVD	p256const0<>(SB), const0
   849  	MOVD	p256const1<>(SB), const1
   850  
   851  	// Begin point double
   852  	LDP	4*16(a_ptr), (x0, x1)
   853  	LDP	5*16(a_ptr), (x2, x3)
   854  	CALL	p256SqrInternal<>(SB)
   855  	STP	(y0, y1), zsqr(0*8)
   856  	STP	(y2, y3), zsqr(2*8)
   857  
   858  	LDP	0*16(a_ptr), (x0, x1)
   859  	LDP	1*16(a_ptr), (x2, x3)
   860  	p256AddInline
   861  	STx(m)
   862  
   863  	LDx(z1in)
   864  	LDy(y1in)
   865  	CALL	p256MulInternal<>(SB)
   866  	p256MulBy2Inline
   867  	STx(z3out)
   868  
   869  	LDy(x1in)
   870  	LDx(zsqr)
   871  	CALL	p256SubInternal<>(SB)
   872  	LDy(m)
   873  	CALL	p256MulInternal<>(SB)
   874  
   875  	// Multiply by 3
   876  	p256MulBy2Inline
   877  	p256AddInline
   878  	STx(m)
   879  
   880  	LDy(y1in)
   881  	p256MulBy2Inline
   882  	CALL	p256SqrInternal<>(SB)
   883  	STy(s)
   884  	MOVD	y0, x0
   885  	MOVD	y1, x1
   886  	MOVD	y2, x2
   887  	MOVD	y3, x3
   888  	CALL	p256SqrInternal<>(SB)
   889  
   890  	// Divide by 2
   891  	ADDS	$-1, y0, t0
   892  	ADCS	const0, y1, t1
   893  	ADCS	$0, y2, t2
   894  	ADCS	const1, y3, t3
   895  	ADC	$0, ZR, hlp0
   896  
   897  	ANDS	$1, y0, ZR
   898  	CSEL	EQ, y0, t0, t0
   899  	CSEL	EQ, y1, t1, t1
   900  	CSEL	EQ, y2, t2, t2
   901  	CSEL	EQ, y3, t3, t3
   902  	AND	y0, hlp0, hlp0
   903  
   904  	EXTR	$1, t0, t1, y0
   905  	EXTR	$1, t1, t2, y1
   906  	EXTR	$1, t2, t3, y2
   907  	EXTR	$1, t3, hlp0, y3
   908  	STy(y3out)
   909  
   910  	LDx(x1in)
   911  	LDy(s)
   912  	CALL	p256MulInternal<>(SB)
   913  	STy(s)
   914  	p256MulBy2Inline
   915  	STx(tmp)
   916  
   917  	LDx(m)
   918  	CALL	p256SqrInternal<>(SB)
   919  	LDx(tmp)
   920  	CALL	p256SubInternal<>(SB)
   921  
   922  	STx(x3out)
   923  
   924  	LDy(s)
   925  	CALL	p256SubInternal<>(SB)
   926  
   927  	LDy(m)
   928  	CALL	p256MulInternal<>(SB)
   929  
   930  	LDx(y3out)
   931  	CALL	p256SubInternal<>(SB)
   932  	STx(y3out)
   933  	RET
   934  /* ---------------------------------------*/
   935  #undef y2in
   936  #undef x3out
   937  #undef y3out
   938  #undef z3out
   939  #define y2in(off) (off + 32)(b_ptr)
   940  #define x3out(off) (off)(b_ptr)
   941  #define y3out(off) (off + 32)(b_ptr)
   942  #define z3out(off) (off + 64)(b_ptr)
   943  // func p256PointAddAsm(res, in1, in2 *P256Point) int
   944  TEXT ·p256PointAddAsm(SB),0,$392-32
   945  	// See https://hyperelliptic.org/EFD/g1p/auto-shortw-jacobian-3.html#addition-add-2007-bl
   946  	// Move input to stack in order to free registers
   947  	MOVD	in1+8(FP), a_ptr
   948  	MOVD	in2+16(FP), b_ptr
   949  
   950  	MOVD	p256const0<>(SB), const0
   951  	MOVD	p256const1<>(SB), const1
   952  
   953  	// Begin point add
   954  	LDx(z2in)
   955  	CALL	p256SqrInternal<>(SB)    // z2^2
   956  	STy(z2sqr)
   957  
   958  	CALL	p256MulInternal<>(SB)    // z2^3
   959  
   960  	LDx(y1in)
   961  	CALL	p256MulInternal<>(SB)    // s1 = z2ˆ3*y1
   962  	STy(s1)
   963  
   964  	LDx(z1in)
   965  	CALL	p256SqrInternal<>(SB)    // z1^2
   966  	STy(z1sqr)
   967  
   968  	CALL	p256MulInternal<>(SB)    // z1^3
   969  
   970  	LDx(y2in)
   971  	CALL	p256MulInternal<>(SB)    // s2 = z1ˆ3*y2
   972  
   973  	LDx(s1)
   974  	CALL	p256SubInternal<>(SB)    // r = s2 - s1
   975  	STx(r)
   976  
   977  	MOVD	$1, t2
   978  	ORR	x0, x1, t0             // Check if zero mod p256
   979  	ORR	x2, x3, t1
   980  	ORR	t1, t0, t0
   981  	CMP	$0, t0
   982  	CSEL	EQ, t2, ZR, hlp1
   983  
   984  	EOR	$-1, x0, t0
   985  	EOR	const0, x1, t1
   986  	EOR	const1, x3, t3
   987  
   988  	ORR	t0, t1, t0
   989  	ORR	x2, t3, t1
   990  	ORR	t1, t0, t0
   991  	CMP	$0, t0
   992  	CSEL	EQ, t2, hlp1, hlp1
   993  
   994  	LDx(z2sqr)
   995  	LDy(x1in)
   996  	CALL	p256MulInternal<>(SB)    // u1 = x1 * z2ˆ2
   997  	STy(u1)
   998  
   999  	LDx(z1sqr)
  1000  	LDy(x2in)
  1001  	CALL	p256MulInternal<>(SB)    // u2 = x2 * z1ˆ2
  1002  	STy(u2)
  1003  
  1004  	LDx(u1)
  1005  	CALL	p256SubInternal<>(SB)    // h = u2 - u1
  1006  	STx(h)
  1007  
  1008  	MOVD	$1, t2
  1009  	ORR	x0, x1, t0             // Check if zero mod p256
  1010  	ORR	x2, x3, t1
  1011  	ORR	t1, t0, t0
  1012  	CMP	$0, t0
  1013  	CSEL	EQ, t2, ZR, hlp0
  1014  
  1015  	EOR	$-1, x0, t0
  1016  	EOR	const0, x1, t1
  1017  	EOR	const1, x3, t3
  1018  
  1019  	ORR	t0, t1, t0
  1020  	ORR	x2, t3, t1
  1021  	ORR	t1, t0, t0
  1022  	CMP	$0, t0
  1023  	CSEL	EQ, t2, hlp0, hlp0
  1024  
  1025  	AND	hlp0, hlp1, hlp1
  1026  
  1027  	LDx(r)
  1028  	CALL	p256SqrInternal<>(SB)    // rsqr = rˆ2
  1029  	STy(rsqr)
  1030  
  1031  	LDx(h)
  1032  	CALL	p256SqrInternal<>(SB)    // hsqr = hˆ2
  1033  	STy(hsqr)
  1034  
  1035  	LDx(h)
  1036  	CALL	p256MulInternal<>(SB)    // hcub = hˆ3
  1037  	STy(hcub)
  1038  
  1039  	LDx(s1)
  1040  	CALL	p256MulInternal<>(SB)
  1041  	STy(s2)
  1042  
  1043  	LDx(z1in)
  1044  	LDy(z2in)
  1045  	CALL	p256MulInternal<>(SB)    // z1 * z2
  1046  	LDx(h)
  1047  	CALL	p256MulInternal<>(SB)    // z1 * z2 * h
  1048  	MOVD	res+0(FP), b_ptr
  1049  	STy(z3out)
  1050  
  1051  	LDx(hsqr)
  1052  	LDy(u1)
  1053  	CALL	p256MulInternal<>(SB)    // hˆ2 * u1
  1054  	STy(u2)
  1055  
  1056  	p256MulBy2Inline               // u1 * hˆ2 * 2, inline
  1057  	LDy(rsqr)
  1058  	CALL	p256SubInternal<>(SB)    // rˆ2 - u1 * hˆ2 * 2
  1059  
  1060  	MOVD	x0, y0
  1061  	MOVD	x1, y1
  1062  	MOVD	x2, y2
  1063  	MOVD	x3, y3
  1064  	LDx(hcub)
  1065  	CALL	p256SubInternal<>(SB)
  1066  	STx(x3out)
  1067  
  1068  	LDy(u2)
  1069  	CALL	p256SubInternal<>(SB)
  1070  
  1071  	LDy(r)
  1072  	CALL	p256MulInternal<>(SB)
  1073  
  1074  	LDx(s2)
  1075  	CALL	p256SubInternal<>(SB)
  1076  	STx(y3out)
  1077  
  1078  	MOVD	hlp1, R0
  1079  	MOVD	R0, ret+24(FP)
  1080  
  1081  	RET
  1082  

View as plain text