1.section	".text",#alloc,#execinstr
2
3.global	bn_mul_mont_int
4.align	32
5bn_mul_mont_int:
6	cmp	%o5,4			! 128 bits minimum
7	bge,pt	%icc,.Lenter
8	sethi	%hi(0xffffffff),%g1
9	retl
10	clr	%o0
11.align	32
12.Lenter:
13	save	%sp,-192,%sp
14	sll	%i5,2,%i5		! num*=4
15	or	%g1,%lo(0xffffffff),%g1
16	ld	[%i4],%i4
17	cmp	%i1,%i2
18	and	%i5,%g1,%i5
19	ld	[%i2],%l2		! bp[0]
20	nop
21
22	add	%sp,2047,%o7		! real top of stack
23	ld	[%i1],%o0		! ap[0] ! redundant in squaring context
24	sub	%o7,%i5,%o7
25	ld	[%i1+4],%l5		! ap[1]
26	and	%o7,-1024,%o7
27	ld	[%i3],%o1		! np[0]
28	sub	%o7,2047,%sp		! alloca
29	ld	[%i3+4],%l6		! np[1]
30	be,pt	%xcc,.Lbn_sqr_mont
31	mov	12,%l1
32
33	mulx	%o0,%l2,%o0	! ap[0]*bp[0]
34	mulx	%l5,%l2,%g4	!prologue! ap[1]*bp[0]
35	and	%o0,%g1,%o3
36	add	%sp,2047+192,%l4
37	ld	[%i1+8],%l5		!prologue!
38
39	mulx	%i4,%o3,%l3		! "t[0]"*n0
40	and	%l3,%g1,%l3
41
42	mulx	%o1,%l3,%o1	! np[0]*"t[0]"*n0
43	mulx	%l6,%l3,%o4	!prologue! np[1]*"t[0]"*n0
44	srlx	%o0,32,%o0
45	add	%o3,%o1,%o1
46	ld	[%i3+8],%l6		!prologue!
47	srlx	%o1,32,%o1
48	mov	%g4,%o3		!prologue!
49
50.L1st:
51	mulx	%l5,%l2,%g4
52	mulx	%l6,%l3,%g5
53	add	%o3,%o0,%o0
54	ld	[%i1+%l1],%l5		! ap[j]
55	and	%o0,%g1,%o3
56	add	%o4,%o1,%o1
57	ld	[%i3+%l1],%l6		! np[j]
58	srlx	%o0,32,%o0
59	add	%o3,%o1,%o1
60	add	%l1,4,%l1			! j++
61	mov	%g4,%o3
62	st	%o1,[%l4]
63	cmp	%l1,%i5
64	mov	%g5,%o4
65	srlx	%o1,32,%o1
66	bl	%icc,.L1st
67	add	%l4,4,%l4		! tp++
68!.L1st
69
70	mulx	%l5,%l2,%g4	!epilogue!
71	mulx	%l6,%l3,%g5
72	add	%o3,%o0,%o0
73	and	%o0,%g1,%o3
74	add	%o4,%o1,%o1
75	srlx	%o0,32,%o0
76	add	%o3,%o1,%o1
77	st	%o1,[%l4]
78	srlx	%o1,32,%o1
79
80	add	%g4,%o0,%o0
81	and	%o0,%g1,%o3
82	add	%g5,%o1,%o1
83	srlx	%o0,32,%o0
84	add	%o3,%o1,%o1
85	st	%o1,[%l4+4]
86	srlx	%o1,32,%o1
87
88	add	%o0,%o1,%o1
89	st	%o1,[%l4+8]
90	srlx	%o1,32,%o2
91
92	mov	4,%l0			! i++
93	ld	[%i2+4],%l2		! bp[1]
94.Louter:
95	add	%sp,2047+192,%l4
96	ld	[%i1],%o0		! ap[0]
97	ld	[%i1+4],%l5		! ap[1]
98	ld	[%i3],%o1		! np[0]
99	ld	[%i3+4],%l6		! np[1]
100	ld	[%l4],%g5		! tp[0]
101	ld	[%l4+4],%l7		! tp[1]
102	mov	12,%l1
103
104	mulx	%o0,%l2,%o0
105	mulx	%l5,%l2,%g4	!prologue!
106	add	%g5,%o0,%o0
107	ld	[%i1+8],%l5		!prologue!
108	and	%o0,%g1,%o3
109
110	mulx	%i4,%o3,%l3
111	and	%l3,%g1,%l3
112
113	mulx	%o1,%l3,%o1
114	mulx	%l6,%l3,%o4	!prologue!
115	srlx	%o0,32,%o0
116	add	%o3,%o1,%o1
117	ld	[%i3+8],%l6		!prologue!
118	srlx	%o1,32,%o1
119	mov	%g4,%o3		!prologue!
120
121.Linner:
122	mulx	%l5,%l2,%g4
123	mulx	%l6,%l3,%g5
124	add	%l7,%o0,%o0
125	ld	[%i1+%l1],%l5		! ap[j]
126	add	%o3,%o0,%o0
127	add	%o4,%o1,%o1
128	ld	[%i3+%l1],%l6		! np[j]
129	and	%o0,%g1,%o3
130	ld	[%l4+8],%l7		! tp[j]
131	srlx	%o0,32,%o0
132	add	%o3,%o1,%o1
133	add	%l1,4,%l1			! j++
134	mov	%g4,%o3
135	st	%o1,[%l4]		! tp[j-1]
136	srlx	%o1,32,%o1
137	mov	%g5,%o4
138	cmp	%l1,%i5
139	bl	%icc,.Linner
140	add	%l4,4,%l4		! tp++
141!.Linner
142
143	mulx	%l5,%l2,%g4	!epilogue!
144	mulx	%l6,%l3,%g5
145	add	%l7,%o0,%o0
146	add	%o3,%o0,%o0
147	ld	[%l4+8],%l7		! tp[j]
148	and	%o0,%g1,%o3
149	add	%o4,%o1,%o1
150	srlx	%o0,32,%o0
151	add	%o3,%o1,%o1
152	st	%o1,[%l4]		! tp[j-1]
153	srlx	%o1,32,%o1
154
155	add	%l7,%o0,%o0
156	add	%g4,%o0,%o0
157	and	%o0,%g1,%o3
158	add	%g5,%o1,%o1
159	add	%o3,%o1,%o1
160	st	%o1,[%l4+4]		! tp[j-1]
161	srlx	%o0,32,%o0
162	add	%l0,4,%l0			! i++
163	srlx	%o1,32,%o1
164
165	add	%o0,%o1,%o1
166	cmp	%l0,%i5
167	add	%o2,%o1,%o1
168	st	%o1,[%l4+8]
169
170	srlx	%o1,32,%o2
171	bl,a	%icc,.Louter
172	ld	[%i2+%l0],%l2		! bp[i]
173!.Louter
174
175	add	%l4,12,%l4
176
177.Ltail:
178	add	%i3,%i5,%i3
179	add	%i0,%i5,%i0
180	mov	%l4,%i1
181	sub	%g0,%i5,%o7		! k=-num
182	ba	.Lsub
183	subcc	%g0,%g0,%g0		! clear %icc.c
184.align	16
185.Lsub:
186	ld	[%l4+%o7],%o0
187	ld	[%i3+%o7],%o1
188	subccc	%o0,%o1,%o1		! tp[j]-np[j]
189	add	%i0,%o7,%l0
190	add	%o7,4,%o7
191	brnz	%o7,.Lsub
192	st	%o1,[%l0]
193	subc	%o2,0,%o2		! handle upmost overflow bit
194	and	%l4,%o2,%i1
195	andn	%i0,%o2,%i3
196	or	%i1,%i3,%i1
197	sub	%g0,%i5,%o7
198
199.Lcopy:
200	ld	[%i1+%o7],%o0		! copy or in-place refresh
201	st	%g0,[%l4+%o7]		! zap tp
202	st	%o0,[%i0+%o7]
203	add	%o7,4,%o7
204	brnz	%o7,.Lcopy
205	nop
206	mov	1,%i0
207	ret
208	restore
209.align	32
210.Lbn_sqr_mont:
211	mulx	%l2,%l2,%o0		! ap[0]*ap[0]
212	mulx	%l5,%l2,%g4		!prologue!
213	and	%o0,%g1,%o3
214	add	%sp,2047+192,%l4
215	ld	[%i1+8],%l5			!prologue!
216
217	mulx	%i4,%o3,%l3			! "t[0]"*n0
218	srlx	%o0,32,%o0
219	and	%l3,%g1,%l3
220
221	mulx	%o1,%l3,%o1		! np[0]*"t[0]"*n0
222	mulx	%l6,%l3,%o4		!prologue!
223	and	%o0,1,%i2
224	ld	[%i3+8],%l6			!prologue!
225	srlx	%o0,1,%o0
226	add	%o3,%o1,%o1
227	srlx	%o1,32,%o1
228	mov	%g4,%o3			!prologue!
229
230.Lsqr_1st:
231	mulx	%l5,%l2,%g4
232	mulx	%l6,%l3,%g5
233	add	%o3,%o0,%o0		! ap[j]*a0+c0
234	add	%o4,%o1,%o1
235	ld	[%i1+%l1],%l5			! ap[j]
236	and	%o0,%g1,%o3
237	ld	[%i3+%l1],%l6			! np[j]
238	srlx	%o0,32,%o0
239	add	%o3,%o3,%o3
240	or	%i2,%o3,%o3
241	mov	%g5,%o4
242	srlx	%o3,32,%i2
243	add	%l1,4,%l1				! j++
244	and	%o3,%g1,%o3
245	cmp	%l1,%i5
246	add	%o3,%o1,%o1
247	st	%o1,[%l4]
248	mov	%g4,%o3
249	srlx	%o1,32,%o1
250	bl	%icc,.Lsqr_1st
251	add	%l4,4,%l4			! tp++
252!.Lsqr_1st
253
254	mulx	%l5,%l2,%g4		! epilogue
255	mulx	%l6,%l3,%g5
256	add	%o3,%o0,%o0		! ap[j]*a0+c0
257	add	%o4,%o1,%o1
258	and	%o0,%g1,%o3
259	srlx	%o0,32,%o0
260	add	%o3,%o3,%o3
261	or	%i2,%o3,%o3
262	srlx	%o3,32,%i2
263	and	%o3,%g1,%o3
264	add	%o3,%o1,%o1
265	st	%o1,[%l4]
266	srlx	%o1,32,%o1
267
268	add	%g4,%o0,%o0		! ap[j]*a0+c0
269	add	%g5,%o1,%o1
270	and	%o0,%g1,%o3
271	srlx	%o0,32,%o0
272	add	%o3,%o3,%o3
273	or	%i2,%o3,%o3
274	srlx	%o3,32,%i2
275	and	%o3,%g1,%o3
276	add	%o3,%o1,%o1
277	st	%o1,[%l4+4]
278	srlx	%o1,32,%o1
279
280	add	%o0,%o0,%o0
281	or	%i2,%o0,%o0
282	add	%o0,%o1,%o1
283	st	%o1,[%l4+8]
284	srlx	%o1,32,%o2
285
286	ld	[%sp+2047+192],%g4	! tp[0]
287	ld	[%sp+2047+192+4],%g5	! tp[1]
288	ld	[%sp+2047+192+8],%l7	! tp[2]
289	ld	[%i1+4],%l2			! ap[1]
290	ld	[%i1+8],%l5			! ap[2]
291	ld	[%i3],%o1			! np[0]
292	ld	[%i3+4],%l6			! np[1]
293	mulx	%i4,%g4,%l3
294
295	mulx	%l2,%l2,%o0
296	and	%l3,%g1,%l3
297
298	mulx	%o1,%l3,%o1
299	mulx	%l6,%l3,%o4
300	add	%g4,%o1,%o1
301	and	%o0,%g1,%o3
302	ld	[%i3+8],%l6			! np[2]
303	srlx	%o1,32,%o1
304	add	%g5,%o1,%o1
305	srlx	%o0,32,%o0
306	add	%o3,%o1,%o1
307	and	%o0,1,%i2
308	add	%o4,%o1,%o1
309	srlx	%o0,1,%o0
310	mov	12,%l1
311	st	%o1,[%sp+2047+192]	! tp[0]=
312	srlx	%o1,32,%o1
313	add	%sp,2047+192+4,%l4
314
315.Lsqr_2nd:
316	mulx	%l5,%l2,%o3
317	mulx	%l6,%l3,%o4
318	add	%o3,%o0,%o0
319	add	%l7,%o1,%o1
320	ld	[%i1+%l1],%l5			! ap[j]
321	and	%o0,%g1,%o3
322	ld	[%i3+%l1],%l6			! np[j]
323	srlx	%o0,32,%o0
324	add	%o4,%o1,%o1
325	ld	[%l4+8],%l7			! tp[j]
326	add	%o3,%o3,%o3
327	add	%l1,4,%l1				! j++
328	or	%i2,%o3,%o3
329	srlx	%o3,32,%i2
330	and	%o3,%g1,%o3
331	cmp	%l1,%i5
332	add	%o3,%o1,%o1
333	st	%o1,[%l4]			! tp[j-1]
334	srlx	%o1,32,%o1
335	bl	%icc,.Lsqr_2nd
336	add	%l4,4,%l4			! tp++
337!.Lsqr_2nd
338
339	mulx	%l5,%l2,%o3
340	mulx	%l6,%l3,%o4
341	add	%o3,%o0,%o0
342	add	%l7,%o1,%o1
343	and	%o0,%g1,%o3
344	srlx	%o0,32,%o0
345	add	%o4,%o1,%o1
346	add	%o3,%o3,%o3
347	or	%i2,%o3,%o3
348	srlx	%o3,32,%i2
349	and	%o3,%g1,%o3
350	add	%o3,%o1,%o1
351	st	%o1,[%l4]			! tp[j-1]
352	srlx	%o1,32,%o1
353
354	add	%o0,%o0,%o0
355	or	%i2,%o0,%o0
356	add	%o0,%o1,%o1
357	add	%o2,%o1,%o1
358	st	%o1,[%l4+4]
359	srlx	%o1,32,%o2
360
361	ld	[%sp+2047+192],%g5	! tp[0]
362	ld	[%sp+2047+192+4],%l7	! tp[1]
363	ld	[%i1+8],%l2			! ap[2]
364	ld	[%i3],%o1			! np[0]
365	ld	[%i3+4],%l6			! np[1]
366	mulx	%i4,%g5,%l3
367	and	%l3,%g1,%l3
368	mov	8,%l0
369
370	mulx	%l2,%l2,%o0
371	mulx	%o1,%l3,%o1
372	and	%o0,%g1,%o3
373	add	%g5,%o1,%o1
374	srlx	%o0,32,%o0
375	add	%sp,2047+192,%l4
376	srlx	%o1,32,%o1
377	and	%o0,1,%i2
378	srlx	%o0,1,%o0
379	mov	4,%l1
380
381.Lsqr_outer:
382.Lsqr_inner1:
383	mulx	%l6,%l3,%o4
384	add	%l7,%o1,%o1
385	add	%l1,4,%l1
386	ld	[%l4+8],%l7
387	cmp	%l1,%l0
388	add	%o4,%o1,%o1
389	ld	[%i3+%l1],%l6
390	st	%o1,[%l4]
391	srlx	%o1,32,%o1
392	bl	%icc,.Lsqr_inner1
393	add	%l4,4,%l4
394!.Lsqr_inner1
395
396	add	%l1,4,%l1
397	ld	[%i1+%l1],%l5			! ap[j]
398	mulx	%l6,%l3,%o4
399	add	%l7,%o1,%o1
400	ld	[%i3+%l1],%l6			! np[j]
401	add	%o3,%o1,%o1
402	ld	[%l4+8],%l7			! tp[j]
403	add	%o4,%o1,%o1
404	st	%o1,[%l4]
405	srlx	%o1,32,%o1
406
407	add	%l1,4,%l1
408	cmp	%l1,%i5
409	be,pn	%icc,.Lsqr_no_inner2
410	add	%l4,4,%l4
411
412.Lsqr_inner2:
413	mulx	%l5,%l2,%o3
414	mulx	%l6,%l3,%o4
415	add	%l7,%o1,%o1
416	add	%o3,%o0,%o0
417	ld	[%i1+%l1],%l5			! ap[j]
418	and	%o0,%g1,%o3
419	ld	[%i3+%l1],%l6			! np[j]
420	srlx	%o0,32,%o0
421	add	%o3,%o3,%o3
422	ld	[%l4+8],%l7			! tp[j]
423	or	%i2,%o3,%o3
424	add	%l1,4,%l1				! j++
425	srlx	%o3,32,%i2
426	and	%o3,%g1,%o3
427	cmp	%l1,%i5
428	add	%o3,%o1,%o1
429	add	%o4,%o1,%o1
430	st	%o1,[%l4]			! tp[j-1]
431	srlx	%o1,32,%o1
432	bl	%icc,.Lsqr_inner2
433	add	%l4,4,%l4			! tp++
434
435.Lsqr_no_inner2:
436	mulx	%l5,%l2,%o3
437	mulx	%l6,%l3,%o4
438	add	%l7,%o1,%o1
439	add	%o3,%o0,%o0
440	and	%o0,%g1,%o3
441	srlx	%o0,32,%o0
442	add	%o3,%o3,%o3
443	or	%i2,%o3,%o3
444	srlx	%o3,32,%i2
445	and	%o3,%g1,%o3
446	add	%o3,%o1,%o1
447	add	%o4,%o1,%o1
448	st	%o1,[%l4]			! tp[j-1]
449	srlx	%o1,32,%o1
450
451	add	%o0,%o0,%o0
452	or	%i2,%o0,%o0
453	add	%o0,%o1,%o1
454	add	%o2,%o1,%o1
455	st	%o1,[%l4+4]
456	srlx	%o1,32,%o2
457
458	add	%l0,4,%l0				! i++
459	ld	[%sp+2047+192],%g5	! tp[0]
460	ld	[%sp+2047+192+4],%l7	! tp[1]
461	ld	[%i1+%l0],%l2			! ap[j]
462	ld	[%i3],%o1			! np[0]
463	ld	[%i3+4],%l6			! np[1]
464	mulx	%i4,%g5,%l3
465	and	%l3,%g1,%l3
466	add	%l0,4,%g4
467
468	mulx	%l2,%l2,%o0
469	mulx	%o1,%l3,%o1
470	and	%o0,%g1,%o3
471	add	%g5,%o1,%o1
472	srlx	%o0,32,%o0
473	add	%sp,2047+192,%l4
474	srlx	%o1,32,%o1
475	and	%o0,1,%i2
476	srlx	%o0,1,%o0
477
478	cmp	%g4,%i5			! i<num-1
479	bl	%icc,.Lsqr_outer
480	mov	4,%l1
481
482.Lsqr_last:
483	mulx	%l6,%l3,%o4
484	add	%l7,%o1,%o1
485	add	%l1,4,%l1
486	ld	[%l4+8],%l7
487	cmp	%l1,%l0
488	add	%o4,%o1,%o1
489	ld	[%i3+%l1],%l6
490	st	%o1,[%l4]
491	srlx	%o1,32,%o1
492	bl	%icc,.Lsqr_last
493	add	%l4,4,%l4
494!.Lsqr_last
495
496	mulx	%l6,%l3,%o4
497	add	%l7,%o1,%o1
498	add	%o3,%o1,%o1
499	add	%o4,%o1,%o1
500	st	%o1,[%l4]
501	srlx	%o1,32,%o1
502
503	add	%o0,%o0,%o0		! recover %o0
504	or	%i2,%o0,%o0
505	add	%o0,%o1,%o1
506	add	%o2,%o1,%o1
507	st	%o1,[%l4+4]
508	srlx	%o1,32,%o2
509
510	ba	.Ltail
511	add	%l4,8,%l4
512.type	bn_mul_mont_int,#function
513.size	bn_mul_mont_int,(.-bn_mul_mont_int)
514.asciz	"Montgomery Multipltication for SPARCv9, CRYPTOGAMS by <appro@openssl.org>"
515.align	32
516