Skip to content

Commit d891f43

Browse files
committed
Reed-Solomon compiles, but doesn't test right.
Frankly, could do with being split up, but ¯\_(ツ)_/¯
1 parent 809a402 commit d891f43

File tree

8 files changed

+407
-53
lines changed

8 files changed

+407
-53
lines changed

.vscode/settings.json

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,7 @@
33
"./qr-generator/Cargo.toml",
44
"./Cargo.toml",
55
"./polynomial-arithmetic/Cargo.toml",
6-
"./galois-field/Cargo.toml"
6+
"./galois-field/Cargo.toml",
7+
"./reed-solomon/Cargo.toml"
78
]
89
}

galois-field/src/lib.rs

Lines changed: 20 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -1,22 +1,23 @@
11
use std::ops::{Add, Sub, Mul, Div, Rem};
22

3+
use polynomial_arithmetic::Polynomial;
4+
35
#[derive(Debug, PartialEq)]
4-
pub struct PolyModPoly<Polynomial>
5-
where Polynomial: PartialEq
6+
pub struct PolyModPoly<Polynomial: PartialEq>
67
{
78
pub poly: Polynomial,
8-
primitive: Polynomial
9+
prime: Polynomial
910
}
1011

1112
impl<Polynomial> Add for &PolyModPoly<Polynomial>
12-
where Polynomial: Clone + PartialEq,
13+
where Polynomial: Add + Clone + PartialEq,
1314
for<'a> &'a Polynomial: Add<Output = Polynomial> {
1415
type Output = PolyModPoly<Polynomial>;
1516

1617
fn add(self, other: &PolyModPoly<Polynomial>) -> PolyModPoly<Polynomial> {
1718
PolyModPoly::<Polynomial> {
1819
poly: &self.poly + &other.poly,
19-
primitive: self.primitive.clone()
20+
prime: self.prime.clone()
2021
}
2122
}
2223
}
@@ -28,25 +29,26 @@ where Polynomial: Clone + PartialEq,
2829

2930
fn mul(self, other: &PolyModPoly<Polynomial>) -> PolyModPoly<Polynomial> {
3031
PolyModPoly::<Polynomial> {
31-
poly: &(&self.poly * &other.poly) % &self.primitive,
32-
primitive: self.primitive.clone()
32+
poly: &(&self.poly * &other.poly) % &self.prime,
33+
prime: self.prime.clone()
3334
}
3435
}
3536
}
3637

3738
pub struct GaloisField<Polynomial>
3839
where Polynomial: PartialEq + Clone
3940
{
40-
primitive: Polynomial
41+
pub primitive: Polynomial,
42+
pub prime: Polynomial
4143
}
4244
impl<Polynomial> GaloisField<Polynomial>
4345
where Polynomial: Clone + PartialEq,
4446
for<'a> &'a Polynomial: Rem<Output = Polynomial>
4547
{
4648
pub fn make_polynomial(&self, poly: Polynomial) -> PolyModPoly<Polynomial> {
4749
PolyModPoly {
48-
poly: &poly % &self.primitive,
49-
primitive: self.primitive.clone()
50+
poly: &poly % &self.prime,
51+
prime: self.prime.clone()
5052
}
5153
}
5254
}
@@ -60,18 +62,18 @@ mod tests {
6062
fn test_addition_in_GF9() {
6163
// Test that (x + 2) + (x + 1) = 2x
6264
type Element = Polynomial<IntMod<3>>;
63-
let primitive = Element::from([2, 2, 1].iter().map(|&c| IntMod::<3>::from(c)).collect::<Vec<IntMod<3>>>());
65+
let prime = Element::from([2, 2, 1].iter().map(|&c| IntMod::<3>::from(c)).collect::<Vec<IntMod<3>>>());
6466
let lhs = PolyModPoly::<Element> {
6567
poly: Element::from([2, 1].iter().map(|&c| IntMod::<3>::from(c)).collect::<Vec<IntMod<3>>>()),
66-
primitive: primitive.clone()
68+
prime: prime.clone()
6769
};
6870
let rhs = PolyModPoly::<Element> {
6971
poly: Element::from([1, 1].iter().map(|&c| IntMod::<3>::from(c)).collect::<Vec<IntMod<3>>>()),
70-
primitive: primitive.clone()
72+
prime: prime.clone()
7173
};
7274
let result = PolyModPoly::<Element> {
7375
poly: Element::from([0, 2].iter().map(|&c| IntMod::<3>::from(c)).collect::<Vec<IntMod<3>>>()),
74-
primitive: primitive.clone()
76+
prime: prime.clone()
7577
};
7678
assert_eq!(&lhs + &rhs, result);
7779
}
@@ -80,8 +82,10 @@ mod tests {
8082
fn test_multiplication_in_GF9() {
8183
// Test that (x + 2)(x + 1) = x
8284
type Element = Polynomial<IntMod<3>>;
83-
let primitive = Element::from([2, 2, 1].iter().map(|&c| IntMod::<3>::from(c)).collect::<Vec<IntMod<3>>>());
84-
let gf9 = GaloisField::<Polynomial<IntMod<3>>> {
85+
let prime = Element::from([2, 2, 1].iter().map(|&c| IntMod::<3>::from(c)).collect::<Vec<IntMod<3>>>());
86+
let primitive = Element::from(vec![IntMod::<3>::from(0), IntMod::<3>::from(1)]);
87+
let gf9 = GaloisField::<Element> {
88+
prime,
8589
primitive
8690
};
8791
let lhs = gf9.make_polynomial(Element::from([2, 1].iter().map(|&c| IntMod::<3>::from(c)).collect::<Vec<IntMod<3>>>()));

polynomial-arithmetic/Cargo.toml

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -6,3 +6,4 @@ edition = "2021"
66
# See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html
77

88
[dependencies]
9+
num = "0.4.1"

polynomial-arithmetic/src/int_mod.rs

Lines changed: 59 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,8 +1,16 @@
1-
#[derive(Clone, Copy, PartialEq, Eq, Debug)]
1+
pub use num::traits::{Zero, One};
2+
3+
#[derive(Clone, Copy, PartialEq, Eq)]
24
pub struct IntMod<const MODULUS: u32> {
35
pub value: u32,
46
}
57

8+
impl<const MODULUS: u32> Debug for IntMod<MODULUS> {
9+
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
10+
write!(f, "{}", self.value)
11+
}
12+
}
13+
614
impl<const MODULUS: u32> From<u32> for IntMod<MODULUS> {
715
fn from(value: u32) -> Self {
816
Self {
@@ -11,6 +19,30 @@ impl<const MODULUS: u32> From<u32> for IntMod<MODULUS> {
1119
}
1220
}
1321

22+
impl<const MODULUS: u32> Zero for IntMod<MODULUS> {
23+
fn zero() -> Self {
24+
Self { value: 0 }
25+
}
26+
fn is_zero(&self) -> bool {
27+
self.value == 0
28+
}
29+
fn set_zero(&mut self) {
30+
self.value = 0;
31+
}
32+
}
33+
impl<const MODULUS: u32> One for IntMod<MODULUS> {
34+
fn one() -> Self {
35+
Self { value: 1 }
36+
}
37+
fn is_one(&self) -> bool {
38+
self.value == 1
39+
}
40+
fn set_one(&mut self) {
41+
self.value = 1;
42+
}
43+
}
44+
45+
use std::fmt::Debug;
1446
use std::ops::Add;
1547
impl<const MODULUS: u32> Add for IntMod<MODULUS> {
1648
type Output = Self;
@@ -121,6 +153,32 @@ impl<const MODULUS: u32> Div<&IntMod<MODULUS>> for IntMod<MODULUS> {
121153
}
122154
}
123155

156+
use std::ops::Rem;
157+
impl<const MODULUS: u32> Rem for IntMod<MODULUS> {
158+
type Output = IntMod<MODULUS>;
159+
fn rem(self, _other: IntMod<MODULUS>) -> Self::Output {
160+
Self { value: 0 }
161+
}
162+
}
163+
impl<const MODULUS: u32> Rem<IntMod<MODULUS>> for &IntMod<MODULUS> {
164+
type Output = IntMod<MODULUS>;
165+
fn rem(self, other: IntMod<MODULUS>) -> Self::Output {
166+
*self % other
167+
}
168+
}
169+
impl<const MODULUS: u32> Rem<&IntMod<MODULUS>> for &IntMod<MODULUS> {
170+
type Output = IntMod<MODULUS>;
171+
fn rem(self, other: &IntMod<MODULUS>) -> Self::Output {
172+
*self % *other
173+
}
174+
}
175+
impl<const MODULUS: u32> Rem<&IntMod<MODULUS>> for IntMod<MODULUS> {
176+
type Output = IntMod<MODULUS>;
177+
fn rem(self, other: &IntMod<MODULUS>) -> Self::Output {
178+
self % *other
179+
}
180+
}
181+
124182
impl<const MODULUS: u32> From<IntMod<MODULUS>> for u32 {
125183
fn from(int_mod: IntMod<MODULUS>) -> u32 {
126184
int_mod.value

0 commit comments

Comments
 (0)