use of com.dat3m.dartagnan.wmm.utils.Tuple in project Dat3M by hernanponcedeleon.
the class RelCo method encodeApprox.
@Override
protected BooleanFormula encodeApprox(SolverContext ctx) {
AliasAnalysis alias = analysisContext.get(AliasAnalysis.class);
WmmAnalysis wmmAnalysis = analysisContext.get(WmmAnalysis.class);
FormulaManager fmgr = ctx.getFormulaManager();
BooleanFormulaManager bmgr = fmgr.getBooleanFormulaManager();
IntegerFormulaManager imgr = fmgr.getIntegerFormulaManager();
BooleanFormula enc = bmgr.makeTrue();
List<Event> eventsInit = task.getProgram().getCache().getEvents(FilterBasic.get(INIT));
List<Event> eventsStore = task.getProgram().getCache().getEvents(FilterMinus.get(FilterBasic.get(WRITE), FilterBasic.get(INIT)));
for (Event e : eventsInit) {
enc = bmgr.and(enc, imgr.equal(getIntVar(e, ctx), imgr.makeNumber(BigInteger.ZERO)));
}
List<IntegerFormula> intVars = new ArrayList<>();
for (Event w : eventsStore) {
IntegerFormula coVar = getIntVar(w, ctx);
enc = bmgr.and(enc, imgr.greaterThan(coVar, imgr.makeNumber(BigInteger.ZERO)));
intVars.add(coVar);
}
BooleanFormula distinct = intVars.size() > 1 ? imgr.distinct(intVars) : bmgr.makeTrue();
enc = bmgr.and(enc, distinct);
for (Event w : task.getProgram().getCache().getEvents(FilterBasic.get(WRITE))) {
MemEvent w1 = (MemEvent) w;
BooleanFormula lastCo = w1.exec();
for (Tuple t : maxTupleSet.getByFirst(w1)) {
MemEvent w2 = (MemEvent) t.getSecond();
BooleanFormula relation = getSMTVar(t, ctx);
BooleanFormula execPair = getExecPair(t, ctx);
lastCo = bmgr.and(lastCo, bmgr.not(relation));
Formula a1 = w1.getMemAddressExpr();
Formula a2 = w2.getMemAddressExpr();
BooleanFormula sameAddress = generalEqual(a1, a2, ctx);
enc = bmgr.and(enc, bmgr.equivalence(relation, bmgr.and(execPair, sameAddress, imgr.lessThan(getIntVar(w1, ctx), getIntVar(w2, ctx)))));
// ============ Local consistency optimizations ============
if (getMinTupleSet().contains(t)) {
enc = bmgr.and(enc, bmgr.equivalence(relation, execPair));
} else if (wmmAnalysis.isLocallyConsistent()) {
if (w2.is(INIT) || t.isBackward()) {
enc = bmgr.and(enc, bmgr.equivalence(relation, bmgr.makeFalse()));
}
if (w1.is(INIT) || t.isForward()) {
enc = bmgr.and(enc, bmgr.implication(bmgr.and(execPair, sameAddress), relation));
}
}
}
if (task.getProgram().getFormat().equals(LITMUS) || task.getProperty().contains(LIVENESS)) {
BooleanFormula lastCoExpr = getLastCoVar(w1, ctx);
enc = bmgr.and(enc, bmgr.equivalence(lastCoExpr, lastCo));
for (Event i : eventsInit) {
Init init = (Init) i;
if (!alias.mayAlias(w1, init)) {
continue;
}
IExpr address = init.getAddress();
Formula a1 = w1.getMemAddressExpr();
Formula a2 = address.toIntFormula(init, ctx);
BooleanFormula sameAddress = generalEqual(a1, a2, ctx);
Formula v1 = w1.getMemValueExpr();
Formula v2 = init.getBase().getLastMemValueExpr(ctx, init.getOffset());
BooleanFormula sameValue = generalEqual(v1, v2, ctx);
enc = bmgr.and(enc, bmgr.implication(bmgr.and(lastCoExpr, sameAddress), sameValue));
}
}
}
return enc;
}
use of com.dat3m.dartagnan.wmm.utils.Tuple in project Dat3M by hernanponcedeleon.
the class RelLoc method encodeApprox.
@Override
protected BooleanFormula encodeApprox(SolverContext ctx) {
FormulaManager fmgr = ctx.getFormulaManager();
BooleanFormulaManager bmgr = fmgr.getBooleanFormulaManager();
BooleanFormula enc = bmgr.makeTrue();
for (Tuple tuple : encodeTupleSet) {
BooleanFormula rel = this.getSMTVar(tuple, ctx);
enc = bmgr.and(enc, bmgr.equivalence(rel, bmgr.and(getExecPair(tuple, ctx), Utils.generalEqual(((MemEvent) tuple.getFirst()).getMemAddressExpr(), ((MemEvent) tuple.getSecond()).getMemAddressExpr(), ctx))));
}
return enc;
}
use of com.dat3m.dartagnan.wmm.utils.Tuple in project Dat3M by hernanponcedeleon.
the class RelLoc method getMaxTupleSet.
@Override
public TupleSet getMaxTupleSet() {
if (maxTupleSet == null) {
AliasAnalysis alias = analysisContext.get(AliasAnalysis.class);
maxTupleSet = new TupleSet();
Collection<Event> events = task.getProgram().getCache().getEvents(FilterBasic.get(MEMORY));
for (Event e1 : events) {
for (Event e2 : events) {
if (alias.mayAlias((MemEvent) e1, (MemEvent) e2)) {
maxTupleSet.add(new Tuple(e1, e2));
}
}
}
removeMutuallyExclusiveTuples(maxTupleSet);
}
return maxTupleSet;
}
use of com.dat3m.dartagnan.wmm.utils.Tuple in project Dat3M by hernanponcedeleon.
the class RelRf method applyLocalConsistency.
private void applyLocalConsistency() {
// Remove future reads
maxTupleSet.removeIf(Tuple::isBackward);
// Remove past reads
ExecutionAnalysis exec = analysisContext.get(ExecutionAnalysis.class);
AliasAnalysis alias = analysisContext.get(AliasAnalysis.class);
Set<Tuple> deletedTuples = new HashSet<>();
for (Event r : task.getProgram().getCache().getEvents(FilterBasic.get(READ))) {
MemEvent read = (MemEvent) r;
// The set of same-thread writes as well as init writes that could be read from (all before the read)
// sorted by order (init events first)
List<MemEvent> possibleWrites = maxTupleSet.getBySecond(read).stream().map(Tuple::getFirst).filter(e -> (e.getThread() == read.getThread() || e.is(INIT))).map(x -> (MemEvent) x).sorted((o1, o2) -> o1.is(INIT) == o2.is(INIT) ? (o1.getCId() - o2.getCId()) : o1.is(INIT) ? -1 : 1).collect(Collectors.toList());
// The set of writes that won't be readable due getting overwritten.
Set<MemEvent> deletedWrites = new HashSet<>();
// - w2 must alias with either w1 or r.
for (int i = 0; i < possibleWrites.size(); i++) {
MemEvent w1 = possibleWrites.get(i);
for (MemEvent w2 : possibleWrites.subList(i + 1, possibleWrites.size())) {
// executed
if ((exec.isImplied(w1, w2) || exec.isImplied(read, w2)) && (alias.mustAlias(w1, w2) || alias.mustAlias(w2, read))) {
deletedWrites.add(w1);
break;
}
}
}
for (Event w : deletedWrites) {
deletedTuples.add(new Tuple(w, read));
}
}
maxTupleSet.removeAll(deletedTuples);
}
use of com.dat3m.dartagnan.wmm.utils.Tuple in project Dat3M by hernanponcedeleon.
the class RelExt method getMaxTupleSet.
@Override
public TupleSet getMaxTupleSet() {
if (maxTupleSet == null) {
maxTupleSet = new TupleSet();
List<Thread> threads = task.getProgram().getThreads();
for (int i = 0; i < threads.size(); i++) {
Thread t1 = threads.get(i);
for (int j = i + 1; j < threads.size(); j++) {
Thread t2 = threads.get(j);
for (Event e1 : t1.getCache().getEvents(FilterBasic.get(Tag.VISIBLE))) {
for (Event e2 : t2.getCache().getEvents(FilterBasic.get(Tag.VISIBLE))) {
maxTupleSet.add(new Tuple(e1, e2));
maxTupleSet.add(new Tuple(e2, e1));
}
}
}
}
}
return maxTupleSet;
}
Aggregations