Skip to content

Commit

Permalink
Implement vm for python
Browse files Browse the repository at this point in the history
  • Loading branch information
quackzar committed Sep 6, 2024
1 parent c39dcd6 commit 994ad69
Show file tree
Hide file tree
Showing 13 changed files with 440 additions and 74 deletions.
32 changes: 17 additions & 15 deletions pycare/Cargo.lock

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

2 changes: 1 addition & 1 deletion pycare/Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -9,5 +9,5 @@ name = "caring"
crate-type = ["cdylib"]

[dependencies]
pyo3 = { version = "0.21", features = ["abi3-py37", "generate-import-lib", "extension-module"]}
pyo3 = { version = "0.22", features = ["abi3-py37", "generate-import-lib", "extension-module"]}
wecare = { path = "../wecare" }
56 changes: 55 additions & 1 deletion pycare/caring.pyi
Original file line number Diff line number Diff line change
@@ -1,4 +1,58 @@
# TODO: Add documentation

class Id:
...

class Opened:
...

class Computed:
def as_float(self) -> list[float]: ...
def as_integer(self) -> list[int]: ...


class Expr:
@staticmethod
def share(num: float | int | list[float] | list[int]) -> Expr: ...

@staticmethod
def recv(id: Id) -> Expr: ...

@staticmethod
def symmetric_share(num: float | int | list[float] | list[int], id: Id, size: int) -> list[Expr]: ...

def open(self) -> Opened: ...

def __add__(self, other: Expr) -> Expr: ...
def __sub__(self, other: Expr) -> Expr: ...
def __mul__(self, other: Expr) -> Expr: ...
def __iadd__(self, other: Expr) -> None: ...
def __isub__(self, other: Expr) -> None: ...
def __imul__(self, other: Expr) -> None: ...

class Engine:
def __init__(
self,
scheme: str,
address: str,
peers: list[str],
multithreaded: bool = False,
threshold: int | None = None,
preprocessed: str | None = None,
) -> None: ...

def execute(self, script: Opened) -> Computed: ...

def id(self) -> Id: ...

def peers(self) -> list[Id]: ...


#
# Old stuff
#

class OldEngine:
"""
Performs a summation with the connected parties.
Returns the sum of all the numbers.
Expand All @@ -18,7 +72,7 @@ class Engine:
"""
Takedown the MPC Engine, releasing the resources and dropping connections.
"""
def takedown(self): ...
def takedown(self) -> None: ...


"""
Expand Down
13 changes: 13 additions & 0 deletions pycare/examples/vm1.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
from caring import Expr, Engine

engine = Engine(scheme="shamir-25519", address="localhost:1234", peers=["localhost:1235"], threshold=1)

[a, b] = Expr.symmetric_share(23, id=engine.id(), size=2)

c = a + b;

script = c.open()

res = engine.execute(script).as_float()

print(res)
13 changes: 13 additions & 0 deletions pycare/examples/vm2.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
from caring import Expr, Engine

engine = Engine(scheme="shamir-25519", address="localhost:1235", peers=["localhost:1234"], threshold=1)

[a, b] = Expr.symmetric_share(7, id=engine.id(), size=2)

c = a + b;

script = c.open()

res = engine.execute(script).as_float()

print(res)
106 changes: 106 additions & 0 deletions pycare/src/expr.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,106 @@
use pyo3::{exceptions::PyTypeError, prelude::*};
use wecare::vm;

#[pyclass]
pub struct Expr(vm::Expr);

#[pyclass(frozen)]
pub struct Opened(pub(crate) vm::Opened);

#[pyclass(frozen)]
#[derive(Debug, Clone, Copy)]
pub struct Id(pub(crate) vm::Id);

#[pymethods]
impl Expr {
/// Construct a new share expression
#[staticmethod]
fn share(num: &Bound<'_, PyAny>) -> PyResult<Self> {
let res = if let Ok(num) = num.extract::<f64>() {
let num = vm::Number::Float(num);
vm::Expr::share(num)
} else if let Ok(num) = num.extract::<u64>() {
// TODO: Consider signedness
let num = vm::Number::Integer(num);
vm::Expr::share(num)
} else if let Ok(num) = num.extract::<Vec<f64>>() {
let num: Vec<_> = num.into_iter().map(vm::Number::Float).collect();
vm::Expr::share_vec(num)
} else if let Ok(num) = num.extract::<Vec<u64>>() {
// TODO: Consider signedness
let num: Vec<_> = num.into_iter().map(vm::Number::Integer).collect();
vm::Expr::share_vec(num)
} else {
return Err(PyTypeError::new_err("num is not a number"));
};
Ok(Self(res))
}

#[staticmethod]
fn symmetric_share(num: &Bound<'_, PyAny>, id: Id, size: usize) -> PyResult<Vec<Expr>> {
let res = if let Ok(num) = num.extract::<f64>() {
let num = vm::Number::Float(num);
vm::Expr::symmetric_share(num)
} else if let Ok(num) = num.extract::<u64>() {
// TODO: Consider signedness
let num = vm::Number::Integer(num);
vm::Expr::symmetric_share(num)
} else if let Ok(num) = num.extract::<Vec<f64>>() {
let num: Vec<_> = num.into_iter().map(vm::Number::Float).collect();
vm::Expr::symmetric_share_vec(num)
} else if let Ok(num) = num.extract::<Vec<u64>>() {
// TODO: Consider signedness
let num: Vec<_> = num.into_iter().map(vm::Number::Integer).collect();
vm::Expr::symmetric_share_vec(num)
} else {
return Err(PyTypeError::new_err("num is not a number"));
};

let res = res.concrete(id.0 .0, size);
let res = res.into_iter().map(Expr).collect();
Ok(res)
}

/// recv from a given party
#[staticmethod]
fn recv(id: &Id) -> Self {
Self(vm::Expr::receive_input(id.0))
}

fn open(&self) -> Opened {
Opened(self.0.clone().open())
}

fn __iadd__(&mut self, other: &Self) {
let rhs: vm::Expr = other.0.clone();
self.0 += rhs;
}

fn __add__(&self, other: &Self) -> Self {
let lhs: vm::Expr = self.0.clone();
let rhs: vm::Expr = other.0.clone();
Self(lhs + rhs)
}

fn __sub__(&self, other: &Self) -> Self {
let lhs: vm::Expr = self.0.clone();
let rhs: vm::Expr = other.0.clone();
Self(lhs - rhs)
}

fn __isub__(&mut self, other: &Self) {
let rhs: vm::Expr = other.0.clone();
self.0 -= rhs;
}

fn __mul__(&self, other: &Self) -> Self {
let lhs: vm::Expr = self.0.clone();
let rhs: vm::Expr = other.0.clone();
Self(lhs * rhs)
}

fn __imul__(&mut self, other: &Self) {
let rhs: vm::Expr = other.0.clone();
self.0 *= rhs;
}
}
Loading

0 comments on commit 994ad69

Please sign in to comment.