Created
March 24, 2024 01:55
-
-
Save namnc/1351994aacb25054ee4696c52ad0802e to your computer and use it in GitHub Desktop.
Fun proj during EthTaipei 2024 for linking circom-2-arithc and MP-SPDZ
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
import json | |
f = open('circ.json') | |
# f = open('nn_circuit_small.json') | |
data = json.load(f) | |
class AGate: | |
def __init__(self, id, type, lhs, rhs, out): | |
self.id = id | |
self.type = type | |
self.lhs = lhs | |
self.rhs = rhs | |
self.out = out | |
class ANode: | |
def __init__(self, id, signals, names, is_const, const_value): | |
self.id = id | |
self.signals = signals | |
self.names = names | |
self.is_const = is_const | |
self.const_value = const_value | |
anodes = {} | |
anode_consts = {} | |
anode_inputs = {} | |
anode_outputs = {} | |
for node in data['nodes']: | |
node_id = node['id'] | |
node_signals = node['signals'] | |
node_names = node['names'] | |
node_is_const = node['is_const'] | |
node_const_value = node['const_value'] | |
anode = ANode(node_id, node_signals, node_names, node_is_const, node_const_value) | |
anodes[node_id] = anode | |
for node_name in node_names: | |
if "0." in node_name: | |
anode_inputs[node_id] = node_name[2:] | |
anode_outputs[node_id] = node_name[2:] | |
if node_is_const: | |
anode_consts[node_id] = node_const_value | |
agates = {} | |
for gate in data['gates']: | |
gate_id = gate['id'] | |
gate_type = gate['gate_type'] | |
glh_input = gate['lh_input'] | |
grh_input = gate['rh_input'] | |
goutput = gate['output'] | |
agate = AGate(gate_id, gate_type, glh_input, grh_input, goutput) | |
agates[gate_id] = agate | |
for gid in agates: | |
gate = agates[gid] | |
lhs = gate.lhs | |
rhs = gate.rhs | |
out = gate.out | |
anode_outputs.pop(lhs, None) | |
anode_outputs.pop(rhs, None) | |
anode_inputs.pop(out, None) | |
if anode_consts.get(lhs) is not None: | |
lhs = "("+str(anode_consts[lhs])+")" | |
if anode_consts.get(rhs) is not None: | |
rhs = "("+str(anode_consts[rhs])+")" | |
# if gate.type == 'AAdd': | |
# print(""+str(out)+" = "+str(lhs)+" + "+str(rhs)) | |
# elif gate.type == 'ASub': | |
# print(""+str(out)+" = "+str(lhs)+" - "+str(rhs)) | |
# elif gate.type == 'AMul': | |
# print(""+str(out)+" = "+str(lhs)+" * "+str(rhs)) | |
# elif gate.type == 'ALt': | |
# print(""+str(out)+" = "+str(lhs)+" < "+str(rhs)) | |
# print(anode_inputs) | |
# print(anode_outputs) | |
f.close() | |
class TNode: | |
def __init__(self, rid, type, lnode, rnode): | |
self.iid = 0 | |
self.rid = rid | |
self.lnode = lnode | |
self.rnode = rnode | |
self.type = type | |
self.is_root = True | |
self.is_leaf = True | |
self.is_visited = False | |
def visit_dfs(self, id): | |
if self.is_visited: | |
return id | |
self.is_visited = True | |
if self.lnode is not None: | |
id = self.lnode.visit_dfs(id) | |
if self.rnode is not None: | |
id = self.rnode.visit_dfs(id) | |
self.iid = id | |
return id+1 | |
def visit_root(self): | |
if self.is_visited: | |
return | |
self.is_visited = True | |
id = 0 | |
print(id) | |
id = self.lnode.visit_dfs(id) | |
id = self.rnode.visit_dfs(id) | |
self.iid = id | |
print(id) | |
def fill_iid_dfs2(self, id): | |
if self.is_visited: | |
return id | |
self.is_visited = True | |
if (self.lnode is None) and (self.rnode is None): | |
return id | |
if self.lnode is not None: | |
id = self.lnode.fill_iid_dfs2(id) | |
if self.rnode is not None: | |
id = self.rnode.fill_iid_dfs2(id) | |
self.iid = id | |
return id + 1 | |
def visit_dfs2(self, id): | |
if self.is_visited: | |
return id | |
self.is_visited = True | |
if self.lnode is not None: | |
id = self.lnode.visit_dfs2(id) | |
if self.rnode is not None: | |
id = self.rnode.visit_dfs2(id) | |
if (self.lnode is None) and (self.rnode is None): | |
self.iid = id | |
return id + 1 | |
return id | |
def visit_root2(self, tt): | |
if self.is_visited: | |
return id | |
self.is_visited = True | |
id = 0 | |
print(id) | |
id = self.lnode.visit_dfs2(id) | |
id = self.rnode.visit_dfs2(id) | |
tt.reset_visit() | |
id = self.fill_iid_dfs2(id) | |
print(id) | |
return id | |
def print_dfs(self, f): | |
if self.is_visited: | |
return | |
self.is_visited = True | |
if self.lnode is not None: | |
id = self.lnode.print_dfs(f) | |
if self.rnode is not None: | |
id = self.rnode.print_dfs(f) | |
if (self.lnode is None) & (self.rnode is None): | |
return | |
f.write("2 1 " + str(self.lnode.iid) + " " + str(self.rnode.iid) + " " + str(self.iid) + " " + str(self.type) + "\n") | |
def print_root(self, f): | |
if self.is_visited: | |
return | |
self.is_visited = True | |
self.lnode.print_dfs(f) | |
self.rnode.print_dfs(f) | |
f.write("2 1 " + str(self.lnode.iid) + " " + str(self.rnode.iid) + " " + str(self.iid) + " " + str(self.type) + "\n") | |
class TTree: | |
def __init__(self): | |
self.roots = None | |
self.tnodes = {} | |
self.leaves = {} | |
self.gcount = 0 | |
self.wcount = 0 | |
def insert_node(self, gate): | |
gid = gate.id | |
gtype = gate.type | |
gout = gate.out | |
glhs = gate.lhs | |
grhs = gate.rhs | |
tnode = TNode(gout, gtype, None, None) | |
self.tnodes[gout] = tnode | |
if (self.tnodes.get(glhs) is None): | |
lnode = TNode(glhs, None, None, None) | |
self.tnodes[glhs] = lnode | |
if (self.tnodes.get(grhs) is None): | |
rnode = TNode(grhs, None, None, None) | |
self.tnodes[grhs] = rnode | |
def reset_visit(self): | |
for nid in self.tnodes: | |
tnode = self.tnodes[nid] | |
tnode.is_visited = False | |
def build_tree(self, gates): | |
for gid in gates: | |
gate = gates[gid] | |
self.insert_node(gate) | |
for gid in gates: | |
gate = gates[gid] | |
gout = gate.out | |
tnode = self.tnodes[gout] | |
glhs = gate.lhs | |
grhs = gate.rhs | |
lnode = self.tnodes[glhs] | |
rnode = self.tnodes[grhs] | |
lnode.is_root = False | |
rnode.is_root = False | |
tnode.is_leaf = False | |
tnode.lnode = lnode | |
tnode.rnode = rnode | |
self.gcount += 1 | |
for tnid in self.tnodes: | |
tnode = self.tnodes[tnid] | |
if tnode.is_root: | |
self.roots = tnode | |
elif tnode.is_leaf: | |
self.leaves[tnode.rid] = tnode | |
self.wcount = self.roots.visit_root2(self) | |
def print_tree(self, f): | |
self.roots.print_root(f) | |
def leaves_ordered(self): | |
ls = {} | |
for lid in self.leaves: | |
leaf = self.leaves[lid] | |
ls[leaf.iid] = leaf | |
return ls | |
tt = TTree() | |
tt.build_tree(agates) | |
f = open("circ.txt", "w") | |
f.write(str(tt.gcount)) | |
f.write(" ") | |
f.write(str((tt.wcount))) | |
f.write("\n") | |
f.write(str(len(tt.leaves))) | |
f.write(" ") | |
for i in range(0, len(tt.leaves)): | |
f.write("1 ") | |
f.write("\n") | |
f.write("1") | |
f.write(" ") | |
for i in range(0, 1): | |
f.write("1 ") | |
f.write("\n") | |
f.write("\n") | |
tt.reset_visit() | |
tt.print_tree(f) | |
# ls = tt.leaves_ordered() | |
f.close() | |
# f = open("circ.conf", "w") | |
# for lid in ls: | |
# leaf = ls[lid] | |
# f.write(str(lid) + " " + anode_inputs[leaf.rid] + "\n") | |
# f.close() | |
# from ast import literal_eval | |
# fi = open('inputs.json') | |
# datai = json.load(fi) | |
# mapi = {} | |
# for aid in anode_inputs: | |
# aname = anode_inputs.get(aid) | |
# sep = aname.find("[") | |
# access = "datai['"+aname[:sep]+"']"+aname[sep:] | |
# mapi[aname] = eval(access) | |
# for aid in anode_outputs: | |
# aname = anode_outputs.get(aid) | |
# sep = aname.find("[") | |
# access = "datai['"+aname[:sep]+"']"+aname[sep:] | |
# mapi[aname] = eval(access) | |
# print(mapi) | |
# # Closing file | |
# fi.close() |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
{ | |
"vars": { | |
"2274727901": null, | |
"256027254": null, | |
"707860729": null, | |
"2573828220": null, | |
"0": 0, | |
"10": 10, | |
"3418096790": null, | |
"1716273923": null, | |
"950363519": null, | |
"3408241754": null, | |
"11305347": null, | |
"2871116428": null, | |
"4076123877": null, | |
"3251828585": null, | |
"2151764623": null, | |
"3686905244": null, | |
"1127324556": null, | |
"140409081": null, | |
"782492029": null, | |
"1206250264": null, | |
"2539431855": null, | |
"482585862": null | |
}, | |
"nodes": [ | |
{ | |
"id": 3398201401, | |
"signals": [ | |
10 | |
], | |
"names": [ | |
"CALL_DeScale.isf" | |
], | |
"is_const": true, | |
"const_value": 10 | |
}, | |
{ | |
"id": 570082499, | |
"signals": [ | |
1716273923, | |
2573828220 | |
], | |
"names": [ | |
"0.in", | |
"CALL_DeScale.in" | |
], | |
"is_const": false, | |
"const_value": 0 | |
}, | |
{ | |
"id": 318995186, | |
"signals": [ | |
707860729 | |
], | |
"names": [ | |
"CALL_Switcher.random_4281045258" | |
], | |
"is_const": false, | |
"const_value": 0 | |
}, | |
{ | |
"id": 4060015081, | |
"signals": [ | |
11305347, | |
3418096790 | |
], | |
"names": [ | |
"CALL_Switcher.random_2102410497", | |
"CALL_Switcher.aux" | |
], | |
"is_const": false, | |
"const_value": 0 | |
}, | |
{ | |
"id": 1867749162, | |
"signals": [ | |
2871116428, | |
482585862 | |
], | |
"names": [ | |
"CALL_Switcher.random_3986217929", | |
"CALL_Switcher.outL" | |
], | |
"is_const": false, | |
"const_value": 0 | |
}, | |
{ | |
"id": 2902071736, | |
"signals": [ | |
4076123877, | |
3251828585 | |
], | |
"names": [ | |
"CALL_Switcher.random_2117015335", | |
"CALL_Switcher.outR" | |
], | |
"is_const": false, | |
"const_value": 0 | |
}, | |
{ | |
"id": 995677393, | |
"signals": [ | |
1206250264, | |
2539431855, | |
3686905244 | |
], | |
"names": [ | |
"CALL_Sign.random_238866503", | |
"CALL_Sign.sign", | |
"CALL_Switcher.sel" | |
], | |
"is_const": false, | |
"const_value": 0 | |
}, | |
{ | |
"id": 2732172177, | |
"signals": [ | |
2274727901, | |
950363519, | |
782492029, | |
1127324556 | |
], | |
"names": [ | |
"CALL_DeScale.random_4088491867", | |
"CALL_DeScale.out", | |
"CALL_Sign.in", | |
"CALL_Switcher.L" | |
], | |
"is_const": false, | |
"const_value": 0 | |
}, | |
{ | |
"id": 116951668, | |
"signals": [ | |
0, | |
3408241754 | |
], | |
"names": [ | |
"CALL_Sign.random_126383539", | |
"CALL_Switcher.R" | |
], | |
"is_const": true, | |
"const_value": 0 | |
}, | |
{ | |
"id": 946705336, | |
"signals": [ | |
140409081 | |
], | |
"names": [ | |
"0.random_4263890812" | |
], | |
"is_const": false, | |
"const_value": 0 | |
}, | |
{ | |
"id": 2111524539, | |
"signals": [ | |
256027254, | |
2151764623 | |
], | |
"names": [ | |
"0.random_4024064508", | |
"0.out" | |
], | |
"is_const": false, | |
"const_value": 0 | |
} | |
], | |
"gates": [ | |
{ | |
"id": 0, | |
"gate_type": "AMul", | |
"lh_input": 570082499, | |
"rh_input": 3398201401, | |
"output": 2732172177 | |
}, | |
{ | |
"id": 1, | |
"gate_type": "ALt", | |
"lh_input": 2732172177, | |
"rh_input": 116951668, | |
"output": 995677393 | |
}, | |
{ | |
"id": 2, | |
"gate_type": "ASub", | |
"lh_input": 116951668, | |
"rh_input": 2732172177, | |
"output": 318995186 | |
}, | |
{ | |
"id": 3, | |
"gate_type": "AMul", | |
"lh_input": 318995186, | |
"rh_input": 995677393, | |
"output": 4060015081 | |
}, | |
{ | |
"id": 4, | |
"gate_type": "AAdd", | |
"lh_input": 4060015081, | |
"rh_input": 2732172177, | |
"output": 1867749162 | |
}, | |
{ | |
"id": 5, | |
"gate_type": "ASub", | |
"lh_input": 116951668, | |
"rh_input": 4060015081, | |
"output": 2902071736 | |
}, | |
{ | |
"id": 6, | |
"gate_type": "AAdd", | |
"lh_input": 2902071736, | |
"rh_input": 116951668, | |
"output": 946705336 | |
}, | |
{ | |
"id": 7, | |
"gate_type": "AAdd", | |
"lh_input": 1867749162, | |
"rh_input": 946705336, | |
"output": 2111524539 | |
} | |
] | |
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
8 11 | |
3 1 1 1 | |
1 1 | |
2 1 1 2 3 AMul | |
2 1 0 3 4 ASub | |
2 1 3 0 5 ALt | |
2 1 4 5 6 AMul | |
2 1 6 3 7 AAdd | |
2 1 0 6 8 ASub | |
2 1 8 0 9 AAdd | |
2 1 7 9 10 AAdd |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment