openvm_pairing_guest/pairing/
sextic_ext_field.rs
1use core::{
2 fmt::{Debug, Formatter, Result},
3 ops::{Add, AddAssign, Sub, SubAssign},
4};
5
6use openvm_algebra_guest::field::Field;
7
8#[derive(Clone, PartialEq, Eq, serde::Serialize, serde::Deserialize)]
13#[repr(C)]
14pub struct SexticExtField<F> {
15 pub c: [F; 6],
16}
17
18impl<F> SexticExtField<F> {
19 pub const fn new(c: [F; 6]) -> Self {
20 Self { c }
21 }
22}
23
24impl<'a, F: Field> AddAssign<&'a SexticExtField<F>> for SexticExtField<F> {
25 #[inline(always)]
26 fn add_assign(&mut self, other: &'a SexticExtField<F>) {
27 for i in 0..6 {
28 self.c[i] += &other.c[i];
29 }
30 }
31}
32
33impl<'a, F: Field> Add<&'a SexticExtField<F>> for &SexticExtField<F> {
34 type Output = SexticExtField<F>;
35 #[inline(always)]
36 fn add(self, other: &'a SexticExtField<F>) -> Self::Output {
37 let mut res = self.clone();
38 res += other;
39 res
40 }
41}
42
43impl<'a, F: Field> SubAssign<&'a SexticExtField<F>> for SexticExtField<F> {
44 #[inline(always)]
45 fn sub_assign(&mut self, other: &'a SexticExtField<F>) {
46 for i in 0..6 {
47 self.c[i] -= &other.c[i];
48 }
49 }
50}
51
52impl<'a, F: Field> Sub<&'a SexticExtField<F>> for &SexticExtField<F> {
53 type Output = SexticExtField<F>;
54 #[inline(always)]
55 fn sub(self, other: &'a SexticExtField<F>) -> Self::Output {
56 let mut res = self.clone();
57 res -= other;
58 res
59 }
60}
61
62pub(crate) fn sextic_tower_mul<F: Field>(
63 lhs: &SexticExtField<F>,
64 rhs: &SexticExtField<F>,
65 xi: &F,
66) -> SexticExtField<F>
67where
68 for<'a> &'a F: core::ops::Mul<&'a F, Output = F>,
69{
70 let (s0, s1, s2, s3, s4, s5) = (
82 &lhs.c[0], &lhs.c[2], &lhs.c[4], &lhs.c[1], &lhs.c[3], &lhs.c[5],
83 );
84 let (o0, o1, o2, o3, o4, o5) = (
85 &rhs.c[0], &rhs.c[2], &rhs.c[4], &rhs.c[1], &rhs.c[3], &rhs.c[5],
86 );
87
88 let c0 = s0 * o0 + xi * &(s1 * o2 + s2 * o1 + s3 * o5 + s4 * o4 + s5 * o3);
89 let c1 = s0 * o1 + s1 * o0 + s3 * o3 + xi * &(s2 * o2 + s4 * o5 + s5 * o4);
90 let c2 = s0 * o2 + s1 * o1 + s2 * o0 + s3 * o4 + s4 * o3 + xi * &(s5 * o5);
91 let c3 = s0 * o3 + s3 * o0 + xi * &(s1 * o5 + s2 * o4 + s4 * o2 + s5 * o1);
92 let c4 = s0 * o4 + s1 * o3 + s3 * o1 + s4 * o0 + xi * &(s2 * o5 + s5 * o2);
93 let c5 = s0 * o5 + s1 * o4 + s2 * o3 + s3 * o2 + s4 * o1 + s5 * o0;
94
95 SexticExtField::new([c0, c3, c1, c4, c2, c5])
96}
97
98impl<F: Field> AddAssign for SexticExtField<F> {
101 #[inline(always)]
102 fn add_assign(&mut self, other: Self) {
103 self.add_assign(&other);
104 }
105}
106
107impl<F: Field> Add for SexticExtField<F> {
108 type Output = Self;
109 #[inline(always)]
110 fn add(mut self, other: Self) -> Self::Output {
111 self += other;
112 self
113 }
114}
115
116impl<'a, F: Field> Add<&'a SexticExtField<F>> for SexticExtField<F> {
117 type Output = Self;
118 #[inline(always)]
119 fn add(mut self, other: &'a SexticExtField<F>) -> Self::Output {
120 self += other;
121 self
122 }
123}
124
125impl<F: Field> SubAssign for SexticExtField<F> {
126 #[inline(always)]
127 fn sub_assign(&mut self, other: Self) {
128 self.sub_assign(&other);
129 }
130}
131
132impl<F: Field> Sub for SexticExtField<F> {
133 type Output = Self;
134 #[inline(always)]
135 fn sub(mut self, other: Self) -> Self::Output {
136 self -= other;
137 self
138 }
139}
140
141impl<'a, F: Field> Sub<&'a SexticExtField<F>> for SexticExtField<F> {
142 type Output = Self;
143 #[inline(always)]
144 fn sub(mut self, other: &'a SexticExtField<F>) -> Self::Output {
145 self -= other;
146 self
147 }
148}
149
150impl<F: Field> Debug for SexticExtField<F> {
151 fn fmt(&self, f: &mut Formatter<'_>) -> Result {
152 write!(
153 f,
154 "{:?}, {:?}, {:?}, {:?}, {:?}, {:?}",
155 self.c[0], self.c[1], self.c[2], self.c[3], self.c[4], self.c[5]
156 )
157 }
158}