6 changed files with 97 additions and 52 deletions
@ -1 +1 @@ |
|||||||
Subproject commit c90bc89522bd0ba39ac0786dd43f19a8502c4224 |
Subproject commit 53309f9e597c91bf630886f7e125995bf48c6f53 |
||||||
@ -1,47 +0,0 @@ |
|||||||
import time |
|
||||||
from collections.abc import Collection |
|
||||||
|
|
||||||
import numpy as np |
|
||||||
|
|
||||||
from kyupy import log, batchrange |
|
||||||
from kyupy.circuit import Circuit |
|
||||||
from kyupy.logic_sim import LogicSim2V |
|
||||||
|
|
||||||
class SAFSimSimple: |
|
||||||
|
|
||||||
def __init__(self, circuit_resolved: Circuit, batch_size: int): |
|
||||||
self.sim = LogicSim2V(circuit_resolved, sims=batch_size) |
|
||||||
self.sim_time = 0 |
|
||||||
pass |
|
||||||
|
|
||||||
def classify_faults(self, faults: Collection[int], patterns: np.ndarray): |
|
||||||
|
|
||||||
golden = np.zeros_like(patterns) |
|
||||||
self.sim.simulate(patterns, golden) |
|
||||||
log.info(f'golden sim finished.') |
|
||||||
|
|
||||||
syndrome = np.zeros_like(patterns) |
|
||||||
|
|
||||||
fclass_NO = set() |
|
||||||
fclass_DS = set() |
|
||||||
|
|
||||||
start_time = time.perf_counter() |
|
||||||
|
|
||||||
with log.progress() as p: |
|
||||||
for fidx, fault in enumerate(faults): |
|
||||||
fault_site = fault//2 |
|
||||||
fault_polarity = fault&1 |
|
||||||
p.update((fidx+1) / len(faults), f'DS:{len(fclass_DS)} NO:{len(fclass_NO)}') |
|
||||||
for bo, bs in batchrange(patterns.shape[1], self.sim.sims): |
|
||||||
self.sim.s_assign[:, :bs] = patterns[:, bo:bo+bs] |
|
||||||
self.sim.s_to_c() |
|
||||||
self.sim.c_prop(fault_line=fault_site, fault_model=fault_polarity) |
|
||||||
self.sim.c_to_s() |
|
||||||
syndrome[:, bo:bo+bs] = self.sim.s_result[:,:bs] |
|
||||||
if np.allclose(golden, syndrome): |
|
||||||
fclass_NO.add(fault) |
|
||||||
else: |
|
||||||
fclass_DS.add(fault) |
|
||||||
|
|
||||||
self.sim_time += time.perf_counter() - start_time |
|
||||||
return {'DS': fclass_DS, 'NO': fclass_NO} |
|
||||||
@ -0,0 +1,47 @@ |
|||||||
|
import time |
||||||
|
from collections.abc import Collection |
||||||
|
|
||||||
|
import numpy as np |
||||||
|
|
||||||
|
from kyupy import log, batchrange, cdiv, Timers |
||||||
|
from kyupy.circuit import Circuit |
||||||
|
from kyupy.logic_sim import LogicSim2V |
||||||
|
|
||||||
|
class SAFSimIncremental: |
||||||
|
|
||||||
|
def __init__(self, circuit_resolved: Circuit, batch_size: int): |
||||||
|
self.sim = LogicSim2V(circuit_resolved, sims=batch_size) |
||||||
|
self.timers = Timers() |
||||||
|
|
||||||
|
def classify_faults(self, faults: Collection[int], patterns: np.ndarray): |
||||||
|
|
||||||
|
with self.timers['startup']: |
||||||
|
self.sim.c_prop() # trigger jit |
||||||
|
c_golden = np.zeros_like(self.sim.c) |
||||||
|
fclass_DS = set() |
||||||
|
nbatches = cdiv(patterns.shape[1], self.sim.sims) |
||||||
|
nfaults = len(faults) |
||||||
|
|
||||||
|
with self.timers['sim'], log.progress() as p: |
||||||
|
for bidx, (bo, bs) in enumerate(batchrange(patterns.shape[1], self.sim.sims)): |
||||||
|
self.sim.s_assign[:, :bs] = patterns[:, bo:bo+bs] |
||||||
|
self.sim.s_to_c() |
||||||
|
self.sim.c_dirty[...] = 1 |
||||||
|
with self.timers['sim_full_prop']: |
||||||
|
self.sim.c_prop() |
||||||
|
c_golden[...] = self.sim.c |
||||||
|
c_golden_poppo = c_golden[self.sim.poppo_c_locs] |
||||||
|
for fidx, fault in enumerate(faults): |
||||||
|
fault_site = fault//2 |
||||||
|
fault_polarity = fault&1 |
||||||
|
self.sim.c_dirty[...] = 0 |
||||||
|
with self.timers['sim_incr_prop']: |
||||||
|
self.sim.c_prop(fault_line=fault_site, fault_model=fault_polarity) |
||||||
|
with self.timers['sim_incr_eval']: |
||||||
|
if not np.all(c_golden_poppo == self.sim.c[self.sim.poppo_c_locs]): |
||||||
|
fclass_DS.add(fault) |
||||||
|
with self.timers['sim_incr_reset']: |
||||||
|
self.sim.c[...] = c_golden # clear fault |
||||||
|
p.update(((fidx+1) / nfaults) * ((bidx+1) / nbatches)) |
||||||
|
|
||||||
|
return {'DS': fclass_DS, 'NO': set(faults) - fclass_DS} |
||||||
@ -0,0 +1,44 @@ |
|||||||
|
import time |
||||||
|
from collections.abc import Collection |
||||||
|
|
||||||
|
import numpy as np |
||||||
|
|
||||||
|
from kyupy import log, batchrange, Timers |
||||||
|
from kyupy.circuit import Circuit |
||||||
|
from kyupy.logic_sim import LogicSim2V |
||||||
|
|
||||||
|
class SAFSimSimple: |
||||||
|
|
||||||
|
def __init__(self, circuit_resolved: Circuit, batch_size: int): |
||||||
|
self.sim = LogicSim2V(circuit_resolved, sims=batch_size) |
||||||
|
self.timers = Timers() |
||||||
|
|
||||||
|
def classify_faults(self, faults: Collection[int], patterns: np.ndarray): |
||||||
|
|
||||||
|
with self.timers['startup']: |
||||||
|
golden = np.zeros_like(patterns) |
||||||
|
self.sim.simulate(patterns, golden) |
||||||
|
syndrome = np.zeros_like(patterns) |
||||||
|
fclass_NO = set() |
||||||
|
fclass_DS = set() |
||||||
|
|
||||||
|
with self.timers['sim'], log.progress() as p: |
||||||
|
for fidx, fault in enumerate(faults): |
||||||
|
fault_site = fault//2 |
||||||
|
fault_polarity = fault&1 |
||||||
|
p.update((fidx+1) / len(faults), f'DS:{len(fclass_DS)} NO:{len(fclass_NO)}') |
||||||
|
for bo, bs in batchrange(patterns.shape[1], self.sim.sims): |
||||||
|
self.sim.s_assign[:, :bs] = patterns[:, bo:bo+bs] |
||||||
|
self.sim.s_to_c() |
||||||
|
with self.timers['sim_prop']: |
||||||
|
self.sim.c_prop(fault_line=fault_site, fault_model=fault_polarity) |
||||||
|
with self.timers['sim_eval']: |
||||||
|
self.sim.c_to_s() |
||||||
|
syndrome[:, bo:bo+bs] = self.sim.s_result[:,:bs] |
||||||
|
with self.timers['sim_eval2']: |
||||||
|
if np.allclose(golden, syndrome): |
||||||
|
fclass_NO.add(fault) |
||||||
|
else: |
||||||
|
fclass_DS.add(fault) |
||||||
|
|
||||||
|
return {'DS': fclass_DS, 'NO': fclass_NO} |
||||||
Loading…
Reference in new issue