package mvd.jester.model; import java.util.LinkedHashSet; import java.util.Set; import org.jgrapht.experimental.dag.DirectedAcyclicGraph; import org.jgrapht.graph.DefaultEdge; public class DagTask implements Task { private DirectedAcyclicGraph jobDag; private final Set workloadDistribution; private final long workload; private final long criticalPath; private final long period; private final long deadline; private final long numberOfThreads; public DagTask(DirectedAcyclicGraph jobDag, long period, long numberOfThreads) { this.jobDag = jobDag; this.period = period; this.deadline = period; this.numberOfThreads = numberOfThreads; this.workload = DagUtils.calculateWorkload(this.jobDag); this.criticalPath = DagUtils.calculateCriticalPath(this.jobDag); this.workloadDistribution = DagUtils.calculateWorkloadDistribution(this.jobDag, this.criticalPath); } public double getUtilization() { return (double) workload / period; } /** * @return the deadline */ public long getDeadline() { return deadline; } /** * @return the jobDag */ public DirectedAcyclicGraph getJobDag() { return jobDag; } /** * @param jobDag the jobDag to set */ public void setJobDag(DirectedAcyclicGraph jobDag) { this.jobDag = jobDag; } /** * @return the period */ public long getPeriod() { return period; } /** * @return the workload */ public long getWorkload() { return workload; } /** * @return the criticalPath */ public long getCriticalPath() { return criticalPath; } /** * @return the workloadDistribution */ public Set getWorkloadDistribution() { return workloadDistribution; } @Override public long getMaximumParallelism() { long max = 0; for (Segment s : workloadDistribution) { if (max < s.getNumberOfJobs()) { max = s.getNumberOfJobs(); } } return max; } @Override public long getNumberOfThreads() { return numberOfThreads; } public static class DagUtils { public static long calculateWorkload(DirectedAcyclicGraph jobDag) { long workload = 0; for (Job job : jobDag) { workload += job.getWcet(); } return workload; } public static long calculateCriticalPath(DirectedAcyclicGraph jobDag) { long criticalPath = 0; for (Job job : jobDag) { Set edges = jobDag.incomingEdgesOf(job); long longestRelativeCompletionTime = 0; for (DefaultEdge e : edges) { Job source = jobDag.getEdgeSource(e); longestRelativeCompletionTime = longestRelativeCompletionTime >= source.getRelativeCompletionTime() ? longestRelativeCompletionTime : source.getRelativeCompletionTime(); } job.setRelativeCompletionTime(longestRelativeCompletionTime + job.getWcet()); criticalPath = job.getRelativeCompletionTime(); } return criticalPath; } public static LinkedHashSet calculateWorkloadDistribution( DirectedAcyclicGraph jobDag, long criticalPath) { LinkedHashSet segments = new LinkedHashSet<>(); long segmentDuration = 0; long segmentHeight = 1; for (long t = 0; t < criticalPath; ++t) { long currentHeight = 0; for (Job j : jobDag) { if (t >= j.getRelativeCompletionTime() - j.getWcet() && t < j.getRelativeCompletionTime()) { currentHeight++; } } if (currentHeight == segmentHeight) { segmentDuration++; } else { segments.add(new Segment(segmentDuration, segmentHeight)); segmentDuration = 1; segmentHeight = currentHeight; } } segments.add(new Segment(segmentDuration, segmentHeight)); return segments; } public static void createNFJGraph(DirectedAcyclicGraph jobDag) { Set joinNodes = new LinkedHashSet<>(); Set forkNodes = new LinkedHashSet<>(); for (Job j : jobDag) { if (jobDag.inDegreeOf(j) > 1) { joinNodes.add(j); } if (jobDag.outDegreeOf(j) > 1) { forkNodes.add(j); } } for (Job j : joinNodes) { for (Job f : forkNodes) { Set edges = jobDag.getAllEdges(f, j); // jobDag. } } } } }