OpenCore  1.0.4
OpenCore Bootloader
Loading...
Searching...
No Matches
BigNumPrimitives.c
Go to the documentation of this file.
1
34#include "BigNumLibInternal.h"
35
36#define OC_BN_MAX_VAL ((OC_BN_WORD)0U - 1U)
37
39 OC_BN_WORD_SIZE == sizeof (UINT32) || OC_BN_WORD_SIZE == sizeof (UINT64),
40 "OC_BN_WORD_SIZE and OC_BN_WORD_NUM_BITS usages must be adapted."
41 );
42
45 IN OC_BN_WORD Word
46 )
47{
48 if (OC_BN_WORD_SIZE == sizeof (UINT32)) {
49 return (OC_BN_WORD)SwapBytes32 ((UINT32)Word);
50 }
51
52 if (OC_BN_WORD_SIZE == sizeof (UINT64)) {
53 return (OC_BN_WORD)SwapBytes64 ((UINT64)Word);
54 }
55
56 ASSERT (FALSE);
57}
58
69STATIC
70VOID
72 IN OUT OC_BN_WORD *Result,
73 IN OC_BN_NUM_WORDS NumWordsResult,
74 IN CONST OC_BN_WORD *A,
75 IN OC_BN_NUM_WORDS NumWordsA,
76 IN UINTN Exponent
77 )
78{
79 ASSERT (Result != NULL);
80 ASSERT (NumWordsResult > 0);
81 ASSERT (A != NULL);
82 ASSERT (NumWordsA > 0);
83 ASSERT (Exponent < NumWordsResult);
84 ASSERT (NumWordsResult - Exponent >= NumWordsA);
85
86 CopyMem (&Result[Exponent], A, OC_BN_SIZE (NumWordsResult - Exponent));
87 ZeroMem (Result, OC_BN_SIZE (Exponent));
88 if (NumWordsResult - Exponent > NumWordsA) {
89 ZeroMem (
90 &Result[NumWordsA + Exponent],
91 OC_BN_SIZE (NumWordsResult - Exponent - NumWordsA)
92 );
93 }
94}
95
108STATIC
109VOID
111 IN OUT OC_BN_WORD *Result,
112 IN OC_BN_NUM_WORDS NumWordsResult,
113 IN CONST OC_BN_WORD *A,
114 IN OC_BN_NUM_WORDS NumWordsA,
115 IN UINTN NumWords,
116 IN UINT8 NumBits
117 )
118{
119 OC_BN_NUM_WORDS Index;
120
121 ASSERT (Result != NULL);
122 ASSERT (NumWordsResult > 0);
123 ASSERT (A != NULL);
124 ASSERT (NumWordsA > 0);
125 ASSERT (NumWordsResult == NumWordsA + NumWords + 1);
126 //
127 // NumBits must not be 0 because a shift of a Word by its Bit width or
128 // larger is Undefined Behaviour.
129 //
130 ASSERT (NumBits > 0);
131 ASSERT (NumBits < OC_BN_WORD_NUM_BITS);
132 //
133 // This is not an algorithmic requirement, but BigNumLeftShiftWords shall be
134 // called if TRUE.
135 //
136 ASSERT (NumWords > 0);
137
138 for (Index = (NumWordsA - 1); Index > 0; --Index) {
139 Result[Index + NumWords] = (A[Index] << NumBits) | (A[Index - 1] >> (OC_BN_WORD_NUM_BITS - NumBits));
140 }
141
142 //
143 // Handle the edge-cases at the beginning and the end of the value.
144 //
145 Result[NumWords] = A[0] << NumBits;
146 Result[NumWordsA + NumWords] = A[NumWordsA - 1] >> (OC_BN_WORD_NUM_BITS - NumBits);
147 //
148 // Zero everything outside of the previously set ranges.
149 //
150 ZeroMem (Result, OC_BN_SIZE (NumWords));
151}
152
163STATIC
164VOID
166 IN OUT OC_BN_WORD *Result,
167 IN OC_BN_NUM_WORDS NumWordsResult,
168 IN CONST OC_BN_WORD *A,
169 IN OC_BN_NUM_WORDS NumWordsA,
170 IN UINTN Exponent
171 )
172{
173 UINTN NumWords;
174 UINT8 NumBits;
175
176 ASSERT (Result != NULL);
177 ASSERT (NumWordsResult > 0);
178 ASSERT (A != NULL);
179 ASSERT (NumWordsA > 0);
180
181 NumWords = Exponent / OC_BN_WORD_NUM_BITS;
182 NumBits = Exponent % OC_BN_WORD_NUM_BITS;
183
184 if (NumBits != 0) {
186 Result,
187 NumWordsResult,
188 A,
189 NumWordsA,
190 NumWords,
191 NumBits
192 );
193 } else {
194 BigNumLeftShiftWords (Result, NumWordsResult, A, NumWordsA, NumWords);
195 }
196}
197
208STATIC
209VOID
211 IN OUT OC_BN_WORD *Result,
212 IN OC_BN_NUM_WORDS NumWordsResult,
213 IN CONST OC_BN_WORD *A,
214 IN OC_BN_NUM_WORDS NumWordsA,
215 IN UINTN Exponent
216 )
217{
218 ASSERT (Result != NULL);
219 ASSERT (NumWordsResult > 0);
220 ASSERT (A != NULL);
221 ASSERT (NumWordsA > 0);
222 ASSERT (Exponent < NumWordsResult);
223 ASSERT (NumWordsResult - Exponent >= NumWordsA);
224
225 CopyMem (Result, &A[Exponent], OC_BN_SIZE (NumWordsResult - Exponent));
226 ZeroMem (&Result[NumWordsResult - Exponent], OC_BN_SIZE (Exponent));
227}
228
237STATIC
238VOID
240 IN OUT OC_BN_WORD *A,
241 IN OC_BN_NUM_WORDS NumWords,
242 IN UINT8 Exponent
243 )
244{
245 UINTN Index;
246
247 ASSERT (A != NULL);
248 ASSERT (NumWords > 0);
249 //
250 // Exponent must not be 0 because a shift of a Word by its Bit width or
251 // larger is Undefined Behaviour.
252 //
253 ASSERT (Exponent > 0);
254 ASSERT (Exponent < OC_BN_WORD_NUM_BITS);
255
256 for (Index = 0; Index < (NumWords - 1U); ++Index) {
257 A[Index] = (A[Index] >> Exponent) | (A[Index + 1] << (OC_BN_WORD_NUM_BITS - Exponent));
258 }
259
260 A[Index] >>= Exponent;
261}
262
274STATIC
275VOID
277 IN OUT OC_BN_WORD *Result,
278 IN OC_BN_NUM_WORDS NumWordsResult,
279 IN CONST OC_BN_WORD *A,
280 IN OC_BN_NUM_WORDS NumWordsA,
281 IN UINTN NumWords,
282 IN UINT8 NumBits
283 )
284{
285 UINTN Index;
286
287 ASSERT (Result != NULL);
288 ASSERT (NumWordsResult > 0);
289 ASSERT (A != NULL);
290 ASSERT (NumWordsA > 0);
291 ASSERT (NumWordsA >= NumWords);
292 //
293 // NumBits must not be 0 because a shift of a Word by its Bit width or
294 // larger is Undefined Behaviour.
295 //
296 ASSERT (NumBits > 0);
297 ASSERT (NumBits < OC_BN_WORD_NUM_BITS);
298 //
299 // This, assuming below, is required to avoid overflows, which purely
300 // internal calls should never produce.
301 //
302 ASSERT (NumWordsA - NumWords >= NumWordsResult);
303 //
304 // This is not an algorithmic requirement, but BigNumRightShiftWords shall be
305 // called if FALSE.
306 //
307 // ASSERT (NumWords > 0);
308
309 for (Index = NumWords; Index < (UINTN)(NumWordsA - 1); ++Index) {
310 Result[Index - NumWords] = (A[Index] >> NumBits) | (A[Index + 1] << (OC_BN_WORD_NUM_BITS - NumBits));
311 }
312
313 //
314 // Handle the edge-cases at the beginning and the end of the value.
315 //
316 Result[Index - NumWords] = (A[NumWordsA - 1] >> NumBits);
317 //
318 // Zero everything outside of the previously set ranges.
319 //
320 ZeroMem (&Result[Index - NumWords + 1], OC_BN_SIZE (NumWordsResult - (Index - NumWords + 1)));
321}
322
333STATIC
334VOID
336 IN OUT OC_BN_WORD *Result,
337 IN OC_BN_NUM_WORDS NumWordsResult,
338 IN CONST OC_BN_WORD *A,
339 IN OC_BN_NUM_WORDS NumWordsA,
340 IN UINTN Exponent
341 )
342{
343 UINTN NumWords;
344 UINT8 NumBits;
345
346 ASSERT (Result != NULL);
347 ASSERT (NumWordsResult > 0);
348 ASSERT (A != NULL);
349 ASSERT (NumWordsA > 0);
350
351 NumWords = Exponent / OC_BN_WORD_NUM_BITS;
352 NumBits = Exponent % OC_BN_WORD_NUM_BITS;
353
354 if (NumBits != 0) {
356 Result,
357 NumWordsResult,
358 A,
359 NumWordsA,
360 NumWords,
361 NumBits
362 );
363 } else {
364 BigNumRightShiftWords (Result, NumWordsResult, A, NumWordsA, NumWords);
365 }
366}
367
380 OUT OC_BN_WORD *Hi,
381 IN OC_BN_WORD A,
382 IN OC_BN_WORD B
383 )
384{
385 UINT64 Result64;
386
387 ASSERT (Hi != NULL);
388
389 if (OC_BN_WORD_SIZE == sizeof (UINT32)) {
390 Result64 = (UINT64)A * B;
391 //
392 // FIXME: The subtraction in the shift is a dirty hack to shut up MSVC.
393 //
394 *Hi = (OC_BN_WORD)(RShiftU64 (Result64, OC_BN_WORD_NUM_BITS));
395 return (OC_BN_WORD)Result64;
396 }
397
398 if (OC_BN_WORD_SIZE == sizeof (UINT64)) {
399 return BigNumWordMul64 (Hi, A, B);
400 }
401}
402
403VOID
405 IN OUT OC_BN_WORD *Result,
406 IN OC_BN_NUM_WORDS NumWords,
407 IN CONST OC_BN_WORD *A,
408 IN CONST OC_BN_WORD *B
409 )
410{
411 OC_BN_WORD TmpResult;
412 OC_BN_WORD Tmp1;
413 OC_BN_WORD Tmp2;
414 UINTN Index;
415 UINT8 Borrow;
416
417 ASSERT (Result != NULL);
418 ASSERT (NumWords > 0);
419 ASSERT (A != NULL);
420 ASSERT (B != NULL);
421 //
422 // As only the same indices are ever accessed at a step, it is safe to call
423 // this function with Result = A or Result = B.
424 //
425 Borrow = 0;
426 for (Index = 0; Index < NumWords; ++Index) {
427 Tmp1 = A[Index];
428 Tmp2 = B[Index] + Borrow;
429 TmpResult = (Tmp1 - Tmp2);
430 //
431 // When a subtraction wraps around, the result must be bigger than either
432 // operand.
433 //
434 Borrow = (Tmp2 < Borrow) | (Tmp1 < TmpResult);
435 Result[Index] = TmpResult;
436 }
437}
438
447STATIC
448UINT8
450 IN OC_BN_WORD Word
451 )
452{
453 UINT8 NumBits;
454 OC_BN_WORD Mask;
455
456 //
457 // The values we are receiving are very likely large, thus this approach
458 // should be reasonably fast.
459 //
460 NumBits = OC_BN_WORD_NUM_BITS;
461 Mask = (OC_BN_WORD)1U << (OC_BN_WORD_NUM_BITS - 1);
462 while (Mask != 0 && (Word & Mask) == 0) {
463 --NumBits;
464 Mask >>= 1U;
465 }
466
467 return NumBits;
468}
469
479STATIC
482 IN CONST OC_BN_WORD *A,
483 IN OC_BN_NUM_WORDS NumWords
484 )
485{
486 OC_BN_NUM_WORDS Index;
487
488 ASSERT (A != NULL);
489 ASSERT (NumWords > 0);
490
491 Index = NumWords;
492 do {
493 --Index;
494 if (A[Index] != 0) {
495 return Index;
496 }
497 } while (Index != 0);
498
499 return 0;
500}
501
504 IN CONST OC_BN_WORD *A,
505 IN OC_BN_NUM_WORDS NumWords
506 )
507{
508 OC_BN_NUM_BITS Index;
509
510 ASSERT (A != NULL);
511 ASSERT (NumWords > 0);
512
513 Index = BigNumMostSignificantWord (A, NumWords);
514 return ((Index * OC_BN_WORD_NUM_BITS) + BigNumSignificantBitsWord (A[Index]));
515}
516
517VOID
519 IN OUT OC_BN_WORD *A,
520 IN OC_BN_NUM_WORDS NumWords,
521 IN OC_BN_WORD Value,
522 IN UINTN Exponent
523 )
524{
525 UINTN WordIndex;
526 UINT8 NumBits;
527
528 ASSERT (A != NULL);
529 ASSERT (NumWords > 0);
530 ASSERT (Exponent / OC_BN_WORD_NUM_BITS < NumWords);
531
532 WordIndex = Exponent / OC_BN_WORD_NUM_BITS;
533 if (WordIndex < NumWords) {
534 NumBits = Exponent % OC_BN_WORD_NUM_BITS;
535 A[WordIndex] |= (Value << NumBits);
536 }
537}
538
539INTN
541 IN CONST OC_BN_WORD *A,
542 IN OC_BN_NUM_WORDS NumWords,
543 IN CONST OC_BN_WORD *B
544 )
545{
546 UINTN Index;
547
548 ASSERT (A != NULL);
549 ASSERT (NumWords > 0);
550 ASSERT (B != NULL);
551
552 Index = NumWords;
553 do {
554 --Index;
555 if (A[Index] > B[Index]) {
556 return 1;
557 } else if (A[Index] < B[Index]) {
558 return -1;
559 }
560 } while (Index != 0);
561
562 return 0;
563}
564
565VOID
567 IN OUT OC_BN_WORD *Result,
568 IN OC_BN_NUM_WORDS NumWordsRest,
569 IN CONST OC_BN_WORD *A,
570 IN OC_BN_NUM_WORDS NumWordsA,
571 IN CONST OC_BN_WORD *B,
572 IN OC_BN_WORD *Scratch
573 )
574{
575 INTN CmpResult;
576
577 OC_BN_NUM_BITS SigBitsModTmp;
578 OC_BN_NUM_WORDS SigWordsModTmp;
579 OC_BN_WORD *ModTmp;
580 OC_BN_NUM_BITS BigDivExp;
581 OC_BN_WORD *BigDiv;
582 OC_BN_NUM_BITS SigBitsBigDiv;
583 OC_BN_NUM_WORDS SigWordsBigDiv;
584
585 OC_BN_NUM_BITS DeltaBits;
586
587 ASSERT (Result != NULL);
588 ASSERT (NumWordsRest > 0);
589 ASSERT (A != NULL);
590 ASSERT (NumWordsA > 0);
591 ASSERT (B != NULL);
592 ASSERT (NumWordsA >= NumWordsRest);
593 //
594 // SigBitsModTmp is calculated manually to avoid calculating SigWordsModTmp
595 // by modulo.
596 //
597 SigWordsModTmp = BigNumMostSignificantWord (A, NumWordsA);
598 SigBitsModTmp = SigWordsModTmp * OC_BN_WORD_NUM_BITS + BigNumSignificantBitsWord (A[SigWordsModTmp]);
599 ++SigWordsModTmp;
600 ASSERT (SigBitsModTmp == BigNumSignificantBits (A, SigWordsModTmp));
601
602 ModTmp = &Scratch[0];
603 BigDiv = &Scratch[SigWordsModTmp];
604 SigWordsBigDiv = SigWordsModTmp;
605 //
606 // Invariant: BigDiv > ModTmp / 2
607 // The invariant implies ModTmp / BigDiv <= 1 (latter in the strictest case).
608 //
609 // This loop iteratively subtracts multiples BigDiv of B from ModTmp := A [1],
610 // otherwise ModTmp is not modified. BigDiv is iteratively reduced such that
611 // ModTmp >= BigDiv [2]. The loop terminates once BigDiv < B yields true [3].
612 //
613 CopyMem (ModTmp, A, OC_BN_SIZE (SigWordsModTmp));
614 //
615 // Initialisation:
616 // A bit-shift by x is equal to multiplying the operand with 2^x.
617 // BigDiv := B << x so that its MSB is equal to the MSB of A implies:
618 // 2*BigDiv > A <=> BigDiv > ModTmp / 2 with ModTmp = A.
619 //
620 SigBitsBigDiv = BigNumSignificantBits (B, NumWordsRest);
621 ASSERT (SigBitsModTmp >= SigBitsBigDiv);
622 BigDivExp = SigBitsModTmp - SigBitsBigDiv;
623
624 BigNumLeftShift (BigDiv, SigWordsBigDiv, B, NumWordsRest, BigDivExp);
625 SigBitsBigDiv = SigBitsModTmp;
626 ASSERT (SigBitsBigDiv == BigNumSignificantBits (BigDiv, SigWordsBigDiv));
627
628 while (TRUE) {
629 //
630 // Because the invariant is maintained optimally, the MSB of BigDiv is
631 // either the MSB of ModTmp or one below. SigWords* are maintained
632 // precisely during the loop's execution, so when SigWordsModTmp is larger
633 // than SigWordsBigDiv, ModTmp is larger than BigDiv.
634 //
635 ASSERT (SigWordsModTmp == SigWordsBigDiv || SigWordsModTmp == SigWordsBigDiv + 1);
636 if (SigWordsModTmp > SigWordsBigDiv) {
637 ASSERT (ModTmp[SigWordsModTmp - 1] != 0);
638 CmpResult = 1;
639 } else {
640 CmpResult = BigNumCmp (ModTmp, SigWordsBigDiv, BigDiv);
641 }
642
643 if (CmpResult >= 0) {
644 //
645 // Iteration 1: [1] ModTmp >= BigDiv means ModTmp is reduced.
646 //
647 // Subtract SigWordsModTmp words because the current divisor value may be
648 // shorter than the current modulus value. As both reside in buffers of
649 // equal length and no high word is stripped without being set to 0, this
650 // is safe.
651 //
652 BigNumSub (ModTmp, SigWordsModTmp, ModTmp, BigDiv);
653
654 if (BigDivExp == 0) {
655 //
656 // Iteration 1: [3] BigDiv = B implies BigDiv < B would yield true
657 // after executing the reduction below.
658 //
659 ASSERT (BigNumCmp (BigDiv, SigWordsBigDiv, B) == 0);
660 break;
661 }
662
663 //
664 // SigBitsModTmp is calculated manually to avoid calculating
665 // SigWordsModTmp by modulo.
666 //
667 SigWordsModTmp = BigNumMostSignificantWord (ModTmp, SigWordsModTmp);
668 SigBitsModTmp = SigWordsModTmp * OC_BN_WORD_NUM_BITS + BigNumSignificantBitsWord (ModTmp[SigWordsModTmp]);
669 ++SigWordsModTmp;
670 ASSERT (SigBitsModTmp == BigNumSignificantBits (ModTmp, SigWordsModTmp));
671
672 ASSERT (SigBitsBigDiv >= SigBitsModTmp);
673 DeltaBits = SigBitsBigDiv - SigBitsModTmp;
674 if (DeltaBits > BigDivExp) {
675 //
676 // Iteration 1: [3] This implies BigDiv < B would yield true after
677 // executing the reduction below.
678 //
679 break;
680 }
681
682 //
683 // Iteration 1: [2] Please refer to Initialisation.
684 //
685 BigNumRightShift (BigDiv, SigWordsBigDiv, BigDiv, SigWordsBigDiv, DeltaBits);
686
687 SigWordsBigDiv = (OC_BN_NUM_WORDS)((SigBitsModTmp + (OC_BN_WORD_NUM_BITS - 1U)) / OC_BN_WORD_NUM_BITS);
688 SigBitsBigDiv = SigBitsModTmp;
689
690 BigDivExp -= DeltaBits;
691 } else {
692 //
693 // Iteration 2: [1] BigDiv > ModTmp means ModTmp will be reduced next
694 // iteration.
695 //
696 if (BigDivExp == 0) {
697 //
698 // Iteration 2: [3] BigDiv = B implies BigDiv < B would yield true
699 // after executing the reduction below.
700 //
701 ASSERT (BigNumCmp (BigDiv, SigWordsBigDiv, B) == 0);
702 break;
703 }
704
705 //
706 // Iteration 2: [2] BigDiv > ModTmp means BigDiv is reduced to more
707 // strictly maintain the invariant BigDiv / 2 > ModTmp.
708 //
709 BigNumRightShiftBitsSmall (BigDiv, SigWordsBigDiv, 1);
710
711 --SigBitsBigDiv;
712 --BigDivExp;
713
714 if (SigBitsBigDiv % OC_BN_WORD_NUM_BITS == 0) {
715 //
716 // Every time the subtraction by 1 yields a multiplie of the word
717 // length, the most significant Byte has become zero and is stripped.
718 //
719 ASSERT (BigDiv[SigWordsBigDiv - 1] == 0);
720 --SigWordsBigDiv;
721 }
722 }
723
724 //
725 // ASSERT both branches maintain SigBitsBigDiv correctly.
726 //
727 ASSERT (SigBitsBigDiv == BigNumSignificantBits (BigDiv, SigWordsBigDiv));
728 }
729
730 //
731 // Termination:
732 // Because BigDiv = B and, by invariant, BigDiv > ModTmp / 2 are true in the
733 // last iteration, B > ModTmp / 2 <=> 2 * B > ModTmp is true and thus
734 // conditionally subtracting B from ModTmp once more yields B > ModTmp, at
735 // which point ModTmp must carry the modulus of A / B. The final reduction
736 // of BigDiv yields BigDiv < B and thus the loop is terminated without
737 // further effects.
738 //
739
740 //
741 // Assuming correctness, the modulus cannot be larger than the divisor.
742 //
743 ASSERT (BigNumMostSignificantWord (ModTmp, SigWordsModTmp) + 1 <= NumWordsRest);
744 CopyMem (Result, ModTmp, OC_BN_SIZE (NumWordsRest));
745}
746
747VOID
749 IN OUT OC_BN_WORD *Result,
750 IN OC_BN_NUM_WORDS NumWords,
751 IN CONST UINT8 *Buffer,
752 IN UINTN BufferSize
753 )
754{
755 UINTN Index;
756 OC_BN_WORD Tmp;
757
758 ASSERT (Result != NULL);
759 ASSERT (OC_BN_SIZE (NumWords) == BufferSize);
760 ASSERT (Buffer != NULL);
761 ASSERT (BufferSize > 0);
762
763 for (Index = OC_BN_WORD_SIZE; Index <= BufferSize; Index += OC_BN_WORD_SIZE) {
764 if (OC_BN_WORD_SIZE == sizeof (UINT32)) {
765 Tmp = (OC_BN_WORD)(
766 ((UINT32)Buffer[(BufferSize - Index) + 0] << 24U) |
767 ((UINT32)Buffer[(BufferSize - Index) + 1] << 16U) |
768 ((UINT32)Buffer[(BufferSize - Index) + 2] << 8U) |
769 ((UINT32)Buffer[(BufferSize - Index) + 3] << 0U));
770 } else if (OC_BN_WORD_SIZE == sizeof (UINT64)) {
771 Tmp = (OC_BN_WORD)(
772 ((UINT64)Buffer[(BufferSize - Index) + 0] << 56U) |
773 ((UINT64)Buffer[(BufferSize - Index) + 1] << 48U) |
774 ((UINT64)Buffer[(BufferSize - Index) + 2] << 40U) |
775 ((UINT64)Buffer[(BufferSize - Index) + 3] << 32U) |
776 ((UINT64)Buffer[(BufferSize - Index) + 4] << 24U) |
777 ((UINT64)Buffer[(BufferSize - Index) + 5] << 16U) |
778 ((UINT64)Buffer[(BufferSize - Index) + 6] << 8U) |
779 ((UINT64)Buffer[(BufferSize - Index) + 7] << 0U));
780 }
781
782 Result[(Index / OC_BN_WORD_SIZE) - 1] = Tmp;
783 }
784}
UINTN OC_BN_WORD
Definition BigNumLib.h:26
#define OC_BN_WORD_SIZE
Definition BigNumLib.h:30
UINT32 OC_BN_NUM_BITS
Definition BigNumLib.h:37
#define OC_BN_WORD_NUM_BITS
Definition BigNumLib.h:31
UINT32 OC_BN_SIZE
Definition BigNumLib.h:36
UINT16 OC_BN_NUM_WORDS
Definition BigNumLib.h:35
OC_BN_WORD BigNumWordMul64(OUT OC_BN_WORD *Hi, IN OC_BN_WORD A, IN OC_BN_WORD B)
STATIC VOID BigNumRightShift(IN OUT OC_BN_WORD *Result, IN OC_BN_NUM_WORDS NumWordsResult, IN CONST OC_BN_WORD *A, IN OC_BN_NUM_WORDS NumWordsA, IN UINTN Exponent)
STATIC UINT8 BigNumSignificantBitsWord(IN OC_BN_WORD Word)
STATIC VOID BigNumRightShiftBitsSmall(IN OUT OC_BN_WORD *A, IN OC_BN_NUM_WORDS NumWords, IN UINT8 Exponent)
STATIC OC_BN_NUM_WORDS BigNumMostSignificantWord(IN CONST OC_BN_WORD *A, IN OC_BN_NUM_WORDS NumWords)
STATIC VOID BigNumRightShiftWords(IN OUT OC_BN_WORD *Result, IN OC_BN_NUM_WORDS NumWordsResult, IN CONST OC_BN_WORD *A, IN OC_BN_NUM_WORDS NumWordsA, IN UINTN Exponent)
VOID BigNumSub(IN OUT OC_BN_WORD *Result, IN OC_BN_NUM_WORDS NumWords, IN CONST OC_BN_WORD *A, IN CONST OC_BN_WORD *B)
OC_BN_WORD BigNumSwapWord(IN OC_BN_WORD Word)
VOID BigNumMod(IN OUT OC_BN_WORD *Result, IN OC_BN_NUM_WORDS NumWordsRest, IN CONST OC_BN_WORD *A, IN OC_BN_NUM_WORDS NumWordsA, IN CONST OC_BN_WORD *B, IN OC_BN_WORD *Scratch)
STATIC_ASSERT(OC_BN_WORD_SIZE==sizeof(UINT32)||OC_BN_WORD_SIZE==sizeof(UINT64), "OC_BN_WORD_SIZE and OC_BN_WORD_NUM_BITS usages must be adapted.")
OC_BN_WORD BigNumWordMul(OUT OC_BN_WORD *Hi, IN OC_BN_WORD A, IN OC_BN_WORD B)
VOID BigNumOrWord(IN OUT OC_BN_WORD *A, IN OC_BN_NUM_WORDS NumWords, IN OC_BN_WORD Value, IN UINTN Exponent)
STATIC VOID BigNumLeftShiftWords(IN OUT OC_BN_WORD *Result, IN OC_BN_NUM_WORDS NumWordsResult, IN CONST OC_BN_WORD *A, IN OC_BN_NUM_WORDS NumWordsA, IN UINTN Exponent)
OC_BN_NUM_BITS BigNumSignificantBits(IN CONST OC_BN_WORD *A, IN OC_BN_NUM_WORDS NumWords)
VOID BigNumParseBuffer(IN OUT OC_BN_WORD *Result, IN OC_BN_NUM_WORDS NumWords, IN CONST UINT8 *Buffer, IN UINTN BufferSize)
INTN BigNumCmp(IN CONST OC_BN_WORD *A, IN OC_BN_NUM_WORDS NumWords, IN CONST OC_BN_WORD *B)
STATIC VOID BigNumRightShiftWordsAndBits(IN OUT OC_BN_WORD *Result, IN OC_BN_NUM_WORDS NumWordsResult, IN CONST OC_BN_WORD *A, IN OC_BN_NUM_WORDS NumWordsA, IN UINTN NumWords, IN UINT8 NumBits)
STATIC VOID BigNumLeftShift(IN OUT OC_BN_WORD *Result, IN OC_BN_NUM_WORDS NumWordsResult, IN CONST OC_BN_WORD *A, IN OC_BN_NUM_WORDS NumWordsA, IN UINTN Exponent)
STATIC VOID BigNumLeftShiftWordsAndBits(IN OUT OC_BN_WORD *Result, IN OC_BN_NUM_WORDS NumWordsResult, IN CONST OC_BN_WORD *A, IN OC_BN_NUM_WORDS NumWordsA, IN UINTN NumWords, IN UINT8 NumBits)
OC_TYPING_BUFFER_ENTRY Buffer[OC_TYPING_BUFFER_SIZE]
Definition OcTypingLib.h:42
VOID *EFIAPI CopyMem(OUT VOID *DestinationBuffer, IN CONST VOID *SourceBuffer, IN UINTN Length)
VOID *EFIAPI ZeroMem(OUT VOID *Buffer, IN UINTN Length)
UINT64 EFIAPI RShiftU64(IN UINT64 Operand, IN UINTN Count)
Definition UserMath.c:86
UINT64 SwapBytes64(UINT64 Operand)
Definition UserMath.c:125
#define ASSERT(x)
Definition coder.h:55