CacheFlow: Using Maximum Flow to Bound Cache-Based Preemption Delays
Abstract
Cache-related preemption delay (CRPD) analysis bounds the additional execution time caused by cache evictions during preemptions. Tightly bounding CRPDs is challenging as there are many possible preemption patterns that can occur at runtime, and thus there has been continuous work over three decades to refine these bounds. This paper presents CacheFlow, a framework that formulates total CRPD as a maximum-flow problem. In the flow network, nodes and edge capacities can be constructed to model certain eviction patterns that can occur. Therefore, by (safely) removing nodes or edges, or reducing edge capacities, tighter CRPD bounds can be derived. This is demonstrated with different CacheFlow refinements, some of which include insights from prior analyses, as well as a refinement for simply periodic systems. An iterative max-flow formulation is also described to more efficiently integrate the max-flow solving in the context of standard fixed-priority response-time analysis. Experiments on synthetic task systems demonstrate significant schedulability improvements across a range of system configurations, while also having reasonable solving times.
Keywords and phrases:
Cache-related Preemption Delay, Real-Time Systems, Maximum FlowCopyright and License:
2012 ACM Subject Classification:
General and reference General conference proceedingsSupplementary Material:
Software (ECRTS 2026 Artifact Evaluation approved artifact): https://doi.org/10.4230/DARTS.12.2.7Editor:
Angeliki KritikakouSeries and Publisher:
Leibniz International Proceedings in Informatics, Schloss Dagstuhl – Leibniz-Zentrum für Informatik
1 Introduction
Processors employ caches to bridge the performance gap between processing elements and memory. When tasks are analyzed or run in isolation, caches can dramatically improve both average- and worst-case performance. However, in preemptively scheduled systems, cache affinity can be lost during a preemption, thereby causing additional cache misses and increased execution times. These effects can be quantified through cache-related preemption delay (CRPD) analysis, and subsequently incorporated into schedulability analysis to ensure that CRPDs do not cause deadline misses. In practice, CRPDs can be large, and their analysis pessimistic, yielding significant utilization loss.
Accurately bounding CRPD is challenging due to the combinatorial complexity of bounding all possible scheduling and preemption patterns. Early analysis methods focused on bounding the delay of a single preemption and multiplying it by the maximum number of preemptions. These foundational methods introduced the concepts of Evicting Cache Blocks (ECBs), which are memory blocks accessed by a preempting task that may overwrite the cache [9], and Useful Cache Blocks (UCBs), which are memory blocks that a preempted task has cached and will reuse later [14]. Combining these concepts yielded the ECB-Only and UCB-Only approaches, which bound the CRPD of a preemption by the number of ECBs of the preempting task or UCBs of the preempted task, respectively.
Further refinements observed that when a job is preempted multiple times by different tasks, the set of cache blocks evicted is bounded by the union of the preempting tasks’ ECBs (the ECB-Union approach), and similarly, the total number of useful cache blocks that can be reloaded is bounded by the union of the preempted tasks’ UCBs (the UCB-Union approach) [3]. These union-based methods were subsequently extended to more precisely account for the exact multiset of preemptions that can occur over an interval (the ECB-Multiset and UCB-Multiset approaches) [3]. More recently, preemption partitioning techniques have been introduced to tighten CRPD bounds by recognizing that the set of UCBs varies throughout a job’s execution, thereby avoiding the pessimistic assumption that every preemption evicts the global maximum number of UCBs [21]. To further manage this complexity, existing techniques rely on various insights to prune the set of preemptions or evictions that must be accounted for analytically.
CacheFlow.
In this work, we present a new framework that we call CacheFlow that enables these types of insights to be more easily composed to compute tighter CRPD bounds. We address the pessimism inherent in summing independent worst-case bounds by formulating the total CRPD as a max-flow problem over an analysis interval. CRPDs can be viewed as flow from preempting jobs and their corresponding ECBs, to preempted jobs, and their corresponding UCBs. We describe this new technique as a framework: the flow network can be constructed in a number of ways to exploit specific insights about the task system, such as adding or removing nodes from the flow network, or adjusting edge capacities.
Interval-based analysis.
A key advantage of this approach is that it shifts the focus from bounding CRPD on a per-job or per-task basis to bounding the total CRPD incurred across an entire analysis interval for all jobs in that interval. By considering the aggregate behavior of all jobs within a window of time, CacheFlow can account for constraints that are difficult to capture in traditional set-based analyses. This interval-based perspective allows for a more holistic accounting of cache usage and preemption patterns, further reducing the pessimism inherent in summing independent worst-case bounds.
Cache-block utility.
Previous CRPD analysis methods have leveraged information from cache and timing analysis that determined which cache blocks are useful, i.e., will be reused, and which cache blocks are evicting, or simply accessed during the job’s execution, possibly evicting cache lines of preempted jobs. In this work, we define the utility of a cache block, which generalizes these previous approaches. Specifically, the utility of a cache block bounds the total number of times that a cache block may be reused during a job’s execution, assuming it executes in isolation. Thus, if the utility of a cache block is zero (resp., non-zero), that cache block is an evicting (resp., useful) cache block. Cache utility allows us to further reduce pessimism in CRPD analysis, as the total CRPD accounted for due to a given cache block should not exceed its utility. This information can also be incorporated into our CacheFlow framework by adjusting the capacity of some edges in the flow network.
Contributions.
-
We introduce CacheFlow, a framework that formulates CRPD analysis as a max-flow problem over a network of job-level cache interactions. By bounding the total CRPD across a set of jobs – rather than summing per-job bounds – CacheFlow captures cross-job constraints that existing analyses cannot express.
-
We define cache-block utility, a generalization of the binary useful/evicting classification. Utility bounds the number of cache hits a block provides within a single job execution, allowing CacheFlow to tighten CRPD bounds by limiting flow through individual cache-block edges.
-
We present two network refinements – frequency constraints and aggregate task constraints – that embed the insights of prior analyses (UCB-Union-Multiset and ECB-Union-Multiset) as bottleneck nodes in the flow network.
-
We present an incremental algorithm that integrates CacheFlow into fixed-priority response-time analysis (RTA). The algorithm exploits the monotonic growth of the flow network across RTA iterations by reusing the residual graph, and includes an early-exit optimization that avoids computing the full max-flow when the CRPD budget is already exceeded.
-
We evaluate CacheFlow experimentally against prior uniprocessor CRPD analysis techniques, demonstrating significant improvements in schedulability across a range of system configurations.
2 Task Model
We consider a sporadic task system consisting of sporadic tasks scheduled on a uniprocessor. Each task is composed of a sequence of jobs, and is characterized by a minimum job inter-arrival time , relative deadline , and an execution time . is said to be released, or made available for execution, at , and must complete its execution requirement of at most before . is released at or after . We assume fixed-priority preemptive scheduling with distinct task priorities and no job suspensions. Tasks are indexed in priority order: has the highest priority and the lowest. We let denote the set of tasks with higher priority than , and the set of higher-priority jobs that can preempt during the interval . We let denote the set of lower-priority jobs that may be affected by (preempted by) during the same interval.
Cache-related preemption delay.
Consistent with prior work on CRPD analysis, we assume a single-level direct-mapped cache. When a job preempts a lower-priority job, may evict cache lines that the preempted job would have reused, causing additional cache misses upon resumption. The resulting delay is called cache-related preemption delay (CRPD). CRPD analysis relies on two sets derived from cache analysis: the evicting cache blocks of task , which are the cache blocks that may access (and thus potentially evict from the cache); and the useful cache blocks , which are the cache blocks that may have cached and would reuse absent a preemption. The block reload time, denoted , is the worst-case time to reload a single cache block from main memory.
Maximum-flow background.
A flow network is a directed graph with a designated source , a sink , and a capacity on each directed edge . A flow assigns a non-negative value to each edge such that flow is conserved at every internal vertex. The maximum-flow problem seeks the assignment that maximises the total flow from to ; by the max-flow/min-cut theorem this equals the minimum capacity cut separating from . Maximum flow is solvable in polynomial time (e.g., Dinic’s algorithm runs in ).
3 Flow-Based CRPD Analysis
Our CacheFlow framework is built upon the observation that CRPD can be modeled as a flow problem. We define a flow network where flow represents CRPD, and edge capacities represent constraints on CRPD. By computing the maximum flow through this network, we can determine the maximum CRPD over an analysis interval for all jobs in that interval. A simple example of such a flow network is shown in Fig. 1.
We next formally define the flow network . Each directed edge is written as a triple with source , destination , and capacity . Let be the source node, and the sink. Let denote the set of jobs that can be released within the interval . Let and be sets of vertices that correspond to the jobs in . We denote the preempting or culprit job node as and the preempted or victim job node as , corresponding to . Let and be sets of vertices that correspond to evicting (useful) cache blocks of each . We let (resp., ) denote the vertex corresponding to the evicting (useful) cache block of . Let ; the vertex sets , , , , and are pairwise disjoint by construction, as depicted in Fig. 1.
Intuitively, flow through the network represents CRPD. Each edge in the graph represents a possible CRPD opportunity. Computing the maximum flow through the network of possible CRPD interactions, we compute the maximum CRPD over the analysis interval. In the following discussion, we construct the edge set through reasoning about CRPD opportunities. We reason about subsets of separately. We begin with the first trivial edge subset.
Edge subset 1.
| (1) |
To begin, we do not constrain the flow from the source to each culprit vertex in . The capacity on each edge simply means there is no source-side cap: the maximum CRPD induced by each job is fully determined by downstream capacities (specifically, the cap on edges and the cap on edges).
Lemma 2.
Each evicting cache block of a job causes at most CRPD in total to the lower-priority jobs that preempts.
Proof.
We bound the CRPD that causes to its victims in , not the CRPD itself experiences. The cache set maps to holds at most one occupant; when first accesses , if that occupant is a victim the access evicts ’s -data and the victim will pay to reload once it resumes; otherwise no victim CRPD is caused. Under fixed-priority preemptive scheduling, cannot run again until completes, so reloads at most once regardless of any further evictions of the slot during ’s execution. Hence causes at most of CRPD per ECB across all victims it preempts.
From this lemma, we construct the following edge subset.
Edge subset 3.
| (2) |
This edge subset encodes the fact that each evicting cache block can cause at most CRPD.
Lemma 4.
An evicting cache block of job can only evict a useful cache block of a lower-priority job if .
Proof.
An evicting cache block can only evict data that maps to the same cache set, so can only evict cache blocks that map to the same set as . Furthermore, can only preempt lower-priority jobs, i.e., jobs . Finally, the eviction of causes a CRPD for only if would have been reused by absent the preemption, i.e., only if .
We can apply this result to construct the following edge set.
Edge subset 5.
| (3) |
This edge subset encodes the fact that an evicting cache block of a higher-priority job can only cause CRPD to a lower-priority job if the same memory block belongs to both and . In a direct-mapped cache, each memory block maps to a unique cache set, so the intersection is on memory-block identity and simultaneously implies the same cache-set mapping.
The previous edge sets are derived from similar observations as have been used to derive previous CRPD analysis techniques. The remaining edge sets are derived from new observations. Importantly, these new observations codify an interesting and important intersection between cache analysis and CRPD and schedulability analysis.
Quantifying Cache Utility
Before we define the remaining edge sets, we must first review relevant prior work on cache analysis. Useful cache blocks were originally defined by Lee et al. [14]. A cache block was said to be useful at program point if it may be cached at , and may subsequently be reused on at least one control-flow path starting at . This UCB definition leads to many cache blocks that may not be reused being classified as useful, which in turn leads to larger CRPD overheads. More recently, Altmeyer and Burguière [1] refined the UCB definition to include only definitely cached blocks. Under this modified definition a cache block is considered useful (or definitely cached) at if it must be cached at and along the path to its reuse, and may be reused on at least one control-flow path starting at . This refined UCB definition leads to fewer cache blocks being categorized as useful, which in turn leads to tighter CRPD bounds. Indeed, in our flow network, fewer blocks being UCBs often reduces the maximum flow, and thus the CRPD bound.
Altmeyer and Burguière [1] presented program analysis that determines for every program point which cache blocks are definitely cached. In subsequent CRPD analysis papers [14, 2, 3], the set of useful cache blocks for a task , denoted , was defined to be the set of blocks that are useful at any program point.
We leverage the definition of a definitely cached block in the following definition.
Definition 6.
A memory reference to block at program point is definitely a cache hit if is a definitely-cached useful cache block (DC-UCB) at .
Definition 7.
The utility of a memory block , denoted , is the maximum number of memory references within a job to block that are definitely cache hits.
Note that utility is defined per memory block: in a direct-mapped cache, different memory blocks that map to the same cache set may have different utility values.
Note that this definition of utility is strictly more expressive than prior definitions for useful cache blocks. Specifically, the set of DC-UCBs for a task is also equal to the set of all cache blocks with non-zero utility.
To tightly bound the utility of each cache block, we can consider the control-flow graph (CFG) of the task, and determine upon which execution path a cache block is definitely a cache hit the most number of times. This is akin to solving the longest-path problem, which is NP-hard. Notably, however, a timing-analysis tool must also solve a similar longest-path problem on the same CFG to determine a bound on the WCET.
In this work, we assume a bound on the utility of each cache block . This bound can be derived as described previously by considering the CFG, or through less-precise methods. For example, one could sum across all definitely cached instructions a bound on the number of times that instruction may be executed. Naïvely, one can always assume a bound of for each UCB as determined by previous analysis [14, 1]. Such a bound is safe, but may lead to more pessimistic CRPD bounds.
Given the definition of utility, a job cannot experience more than CRPD due to evictions of a single cache block . This observation gives us the following edge subset.
Edge subset 8.
| (4) |
Finally, we route flow from each victim vertex to the sink.
Edge subset 9.
| (5) |
For this baseline network, we let and . The maximum flow in this network is a safe bound on the maximum CRPD over an interval of length .
Example 10.
Consider three tasks with : () with and no UCBs; () with , , ; and () with and . We analyze in a window of , during which contributes two jobs (, ) and contributes one job ().
UCB-Union bound.
Summing per-task contributions independently: adds and adds , giving .
Max-flow bound.
The optimal max-flow solution routes units along four paths, each saturating one edge (capacity ): (1) : ’s first job evicts , reloaded by ; (2) : re-evicts , reloaded by ; (3) : evicts , reloaded by ; (4) : evicts , reloaded by .
Two structural properties explain the improvement from 6 to 4. First, the capacity of captures that each victim job reloads block at most once () regardless of how many culprits evict it. Although both jobs of evict block , the incoming capacity is saturated after one unit, so the second job () contributes nothing. Second, the capacity of captures that a single eviction causes CRPD to at most one victim – not to all lower-priority tasks simultaneously. In the nested preemption chain , ’s eviction of block causes to reload it (path 1), after which re-evicts , causing ’s reload (path 2). UCB-Union charges for both evictions of , but the capacity on forces its single unit of flow to route to , not , correctly accounting for the chained reload.
4 CacheFlow Refinements
With this simple max-flow formulation, we can compute a safe bound on the maximum CRPD over an interval of length . However, by leveraging additional structural properties of the task system or insights from other analyses, we can improve the tightness of the CRPD bound. In the following, we present two refinements to the max-flow formulation that improve the tightness of the CRPD bound. The first is for simply periodic or harmonic task systems, and the second is a refinement for sporadic task systems.
4.1 Simply Periodic Systems
The flow network defined above is constructed under the sporadic task model, in which the release times of jobs are unknown apart from the minimum inter-arrival constraint. As a result, every higher-priority job in is conservatively assumed to be able to preempt every lower-priority job, yielding many ECB–UCB edges in .
When release times are known, many of these potential preemptions are not possible. Fig. 2 illustrates a simply periodic task system in which some higher-priority and lower-priority jobs are released simultaneously. In such cases, the higher-priority job executes first and therefore does not preempt the lower-priority job. Consequently, there is no CRPD opportunity at that instant. These infeasible CRPD opportunities correspond to edges that the sporadic model would include in , but that can be safely removed when periodic releases are assumed.
A common special case arises in simply periodic systems, where each task releases jobs at exact multiples of its period.
Assumption 11.
Each task is simply periodic, and thus the job of is released at .
Under this assumption, the release time of every job is determined by the task parameters. A preemption of by a higher-priority job can only occur if is released during the execution window of : it must arrive strictly after ’s release (otherwise runs first, with no preemption) and before ’s absolute deadline (otherwise has already completed).
Lemma 12.
Under Assumption 11, job can preempt with only if
| (6) |
Proof.
If , then is released no later than . Since has higher priority, it begins executing at or before starts and does not preempt it. If , then must have completed (or missed its deadline) before is released, so again no preemption is possible.
This observation allows us to tighten the edge set by restricting it to preemption pairs that satisfy (6):
| (7) | ||||
Since , the resulting graph has fewer edges and therefore a max-flow value no larger than that of .
Corollary 13.
Under Assumption 11, the max-flow through is a safe CRPD bound and yields a schedulability test that dominates the sporadic CacheFlow test.
Proof.
Safety follows from the fact that every realizable preemption corresponds to an edge in ; no feasible CRPD scenario is excluded. Dominance follows because implies that the max-flow through is at most the max-flow through : any task set deemed schedulable by the sporadic CacheFlow test is also deemed schedulable by the periodic variant.
Example: harmonic periods.
In a simply periodic (harmonic) system, where each task’s period is an integer multiple of the next-shorter period, all tasks with the same period release simultaneously. By Lem. 12, jobs that are released at the same instant cannot preempt one another, so no ECB–UCB edges are added between them. More generally, jobs of tasks whose periods divide evenly into a common hyperperiod will have many aligned releases, each of which eliminates a set of edges from .
4.2 Frequency Constraints
The basic network allows every culprit job of a higher-priority task to contribute CRPD per overlapping cache block to every victim job, regardless of how many culprit jobs can actually preempt a given victim during its execution. This is equivalent to the UCB-Union approach: each ECB–UCB pair generates an independent edge in with no limit on how many times a single preempting task can affect a given victim job. By adding frequency constraints, we tighten the analysis by limiting the number of preemptions from each preempting task that can affect a given victim job.
Frequency vertices.
We introduce a new vertex set with one vertex for each preempting task , victim task (with ), victim job , and cache block . These frequency vertices are interposed between the ECB and UCB layers and serve as bottlenecks that limit the total flow from all culprit jobs of through cache block to victim job .
Modified edge set .
We replace with two new edge subsets. The first connects ECB nodes to frequency nodes:
| (8) |
The second connects frequency nodes to UCB nodes, with capacity governed by the preemption frequency:
| (9) |
where is the response time of task .
The key idea is that each frequency node aggregates all flow from ’s culprit jobs through cache block to victim job . The capacity of the outgoing edge in limits this aggregate flow to , reflecting the maximum number of preemptions from during ’s execution window. The updated flowgraph is shown in Fig. 4.
Lemma 14.
During the execution of a single job , at most jobs of a higher-priority task can preempt .
Proof.
A job executes for at most time units. Task releases at most one job per time units. Therefore, the maximum number of jobs that can be released – and hence preempt – during the execution window of is .
Soundness.
The replacement is a sound substitute for : every feasible CRPD scenario still corresponds to a feasible flow in the refined network. In any concrete execution, each cache block can be evicted at most once per preemption of by a job, contributing CRPD per eviction. With at most such preemptions, the total CRPD from to through block is at most – exactly the capacity of the corresponding edge. The frequency constraint therefore removes only infeasible flows in which more than preemptions from would affect victim job .
Dominance.
The frequency refinement captures the same constraint as the UCB-Union-Multiset approach [3] within the joint optimization framework of the flow network. In UCB-Union-Multiset, the CRPD contribution of each preempting task to a victim task is bounded by times the per-preemption CRPD. The frequency node enforces precisely this bound per victim job, per cache block. Combined with the per-block utility bound (), the refined network dominates UCB-Union-Multiset.
Aggregate preemption counts.
One might consider adding a further aggregation layer between the ECB and frequency vertices: a single node per (preempting task , victim task , cache block ) that limits the total flow from all culprit jobs of to all victim jobs of for block . Such a node would enforce the constraint that the total number of preemptions from to across all victim jobs is at most , which can be strictly less than the sum of per-job frequency factors . However, this constraint is already implicit in the network: the source side contains exactly culprit nodes for , each with a edge of capacity per block. The total flow originating from for any block is therefore at most , shared across all victim tasks. Since this budget is already enforced by the existing edge capacities, an explicit aggregation node would be redundant – the max-flow solver will discover the source-side bottleneck whenever .
4.3 Aggregate Task Constraints
The base network and the frequency refinement constrain CRPD at the job and block level: how much CRPD each evicting cache block can cause (Lem. 2), how many preemptions can occur within a victim’s execution window, and how much CRPD each useful cache block can absorb (utility). However, the network so far does not incorporate task-level bounds derived by prior analyses. In particular, the ECB-Union-Multiset analysis [3] bounds the total CRPD that a preempting task can cause, and the UCB-Union-Multiset analysis [3] bounds the total CRPD that a victim task can experience. These task-level bounds can be embedded as additional bottleneck nodes in the flow network, tightening the analysis without losing soundness.
Aggregate culprit vertices.
We introduce one vertex per preempting task and replace the Source–Culprit edges () with two layers:
| (10) | ||||
| (11) |
where is the ECB-Union-Multiset CRPD bound for task over an interval of length [3]. The capacity of the edge limits the total CRPD that all jobs of can collectively induce to at most what the ECB-Union-Multiset analysis assigns to .
Aggregate victim vertices.
Symmetrically, we introduce one vertex per victim task and replace the Victim–Sink edges () with:
| (12) | ||||
| (13) |
where is the total UCB-Union-Multiset CRPD bound for victim task summed over all preempting tasks.
Dominance.
With aggregate vertices, the flow network simultaneously constrains CRPD from two directions. On the source side, the total flow originating from task is at most , the ECB-Union-Multiset bound. On the sink side, the total flow absorbed by task is at most , the UCB-Union-Multiset bound. Since both constraints are enforced simultaneously within a single max-flow computation, the resulting CRPD bound is at least as tight as either analysis alone, and in general tighter because the network encodes finer-grained block- and job-level interactions within these aggregate limits.
Theorem 15.
CacheFlow with aggregate constraints dominates both ECB-Union-Multiset and UCB-Union-Multiset [3], and therefore also Combined-Union-Multiset.
Proof.
Let denote the max-flow through the refined network for interval . The capacity limits the total flow from task to at most . Summing over all preempting tasks: , the total ECB-Union-Multiset CRPD bound. By an identical argument on the sink side, . Hence the CacheFlow CRPD bound satisfies for all .
Since the CRPD bound at every iteration of the RTA fixed-point is at most the ECB-Union-Multiset bound and at most the UCB-Union-Multiset bound, the resulting response time is no larger than either. Because Combined-Union-Multiset takes at the response-time level, and CacheFlow yields and , it follows that .
5 Iterative Max-Flow for Response-Time Analysis
Runtime overhead and pseudo-polynomial complexity.
Compared to closed-form CRPD bounds, CacheFlow incurs additional computational cost because each step of the fixed-point response-time iteration requires solving a max-flow instance on the network . While this is more expensive than several prior approaches, the max-flow problem is solvable in polynomial time in the size of the constructed graph. To quantify this overhead in practice, we include in our evaluation the wall-clock analysis time per generated task system, reporting the total time spent across the RTA fixed-point loop and all max-flow invocations.
From a worst-case perspective, the overall test is pseudo-polynomial. The size of depends on the number of jobs in and the number of cache-block vertices (ECB/UCB, and frequency vertices in refined variants), which in turn depend on numeric parameters such as task periods and the candidate response time . As grows, additional jobs enter and the graph expands, increasing the cost of each max-flow solve. Since fixed-priority RTA is itself pseudo-polynomial in the same parameters, composing RTA with a polynomial-time max-flow solver yields an overall pseudo-polynomial schedulability test.
The graph defined above is parameterized by the interval length : the job set determines which culprit and victim nodes exist, and therefore which ECB and UCB nodes and edges are present. In fixed-priority response-time analysis (RTA), is the candidate response time that is iteratively refined in a fixed-point computation. As increases, can only grow – new jobs are released, but no previously released job leaves the analysis window. Consequently, expands monotonically with .
Theorem 16.
A task is schedulable under fixed-priority scheduling with CRPD if the fixed-point iteration
| (14) |
starting from the initial value converges to .
Proof.
The maximum flow through provides a safe upper bound on the total CRPD that can occur during an interval of length . Because all edge capacities are expressed in time units (multiples of ), the max-flow value directly gives the CRPD bound. The edge capacities encode exactly the constraints derived in Edge subsets 1–5: the per-block reload cost (Lem. 2), the cache-set matching requirement, and the per-block utility bound. Since every feasible CRPD scenario corresponds to a feasible flow through , the maximum flow is an upper bound on total CRPD. Standard RTA convergence arguments apply [12]: if the right-hand side of (14) is monotonically non-decreasing in and bounded, the iteration converges to a least fixed point.
Lemma 17.
The maximum flow through is monotonically non-decreasing in .
Proof.
As increases, jobs may be added to but never removed. Each new job adds a culprit vertex, a victim vertex, and corresponding ECB and UCB vertices, together with their incident edges. No existing vertices or edges are removed. Since the feasible region of the max-flow problem can only grow, the optimal flow value cannot decrease.
This monotonicity property is essential: it ensures that the demand function on the right-hand side of (14) is non-decreasing, which guarantees that the fixed-point iteration either converges or exceeds . Intuitively, because new jobs only add nodes and edges to and no existing vertex or edge is ever removed, the set of feasible flows can only expand as grows – so the maximum flow is monotone in , underpinning the convergence of Algorithm 1.
Monotonicity of refinements.
Each refinement from the previous section preserves monotonicity. For the periodic refinement, edge set can only gain edges as grows, since new jobs may enter and create new feasible preemption pairs, but no existing pair is invalidated. For frequency constraints, the frequency factor depends on , which is non-decreasing across RTA iterations; hence the capacity of every edge can only grow. For aggregate task constraints, the ECB-Union-Multiset bound and the UCB-Union-Multiset bound are both non-decreasing in , so the and capacities can only grow. When the candidate response time increases during the RTA iteration, the edge capacities are updated by adding the difference between the new and old bounds to the residual capacity. In all cases, no existing vertices or edges are removed, so Lem. 17 and the incremental algorithm apply without modification.
Incremental algorithm.
The monotonic growth of suggests an efficient incremental strategy. Rather than rebuilding the graph and solving from scratch at each iteration, we extend the residual graph from the previous iteration and compute only the additional flow contributed by newly added nodes and edges. Algorithm 1 presents this approach.
The key insight is that the max-flow solver operates on the residual graph from the previous iteration. Because existing edges and their residual capacities are preserved, the solver need only search for augmenting paths through the newly added portion of the graph. The accumulated flow gives the total CRPD bound at each step.
Early exit.
At each iteration, the algorithm computes a budget: the maximum additional CRPD that the system can tolerate at the current candidate response time . When is below the budget, the remaining slack is passed as a flow limit to the solver (line 12), which stops as soon as the limit is reached. When already meets or exceeds the budget, the solver is still invoked without a restrictive limit (line 13) to ensure that the total flow reflects any new augmenting paths introduced by newly added nodes and edges. This is necessary for correctness: without it, could remain stale, causing the iteration to converge prematurely to an unsafe value.
Complexity.
The size of the flow network is pseudo-polynomial in the task parameters: the number of vertices and edges depends on the number of jobs , which grows with the numeric parameter . Since max-flow is solvable in polynomial time in the size of the network, and fixed-priority RTA is itself pseudo-polynomial, the overall schedulability test is pseudo-polynomial. In practice, warm-starting the solver from the previous iteration’s residual graph and the early-exit optimization described above keep runtimes well within practical bounds, as shown in the evaluation.
6 Experimental Evaluation
We evaluate CacheFlow experimentally along two axes: effectiveness, measured as the fraction of generated task systems deemed schedulable, and analysis cost, measured as wall-clock runtime of the schedulability test. We first describe our experimental setup, including the design space, sampling methodology, and compared analyses (Sec. 6.1). We then present schedulability results for sporadic task systems across a range of block reload times (Sec. 6.2–Sec. 6.3), including a dedicated evaluation of the periodic refinement on harmonic task systems. Finally, we report analysis runtime as a function of task-set size to demonstrate that CacheFlow remains practically tractable (Sec. 6.4).
6.1 Experimental Setup
We evaluate CacheFlow using synthetically generated sporadic task systems under uniprocessor fixed-priority scheduling. Each experiment point is defined by the Cartesian product of the parameters listed below, and each plotted datum reports the mean across independently generated task systems at the corresponding parameter point.
Design space.
We vary the target system utilization , and the number of tasks . Task periods are drawn from a log-uniform distribution (logunif). We model a direct-mapped cache with sets, and consider three block reload times . To explore a range of cache behaviors, we vary (i) cache_util from 5 to 30 in steps of 5, which controls the size/strength of useful-cache behavior in the generated cache-block sets, and (ii) the reuse parameter , which controls the likelihood and/or degree to which useful blocks are reused following a preemption (and hence can contribute CRPD). Table 1 summarizes the evaluated design space.
| Parameter | Values |
|---|---|
| Processors () | |
| System utilization () | |
| Number of tasks () | |
| Period distribution | logunif |
| Cache sets () | |
| Block reload time () | |
| Cache utility (cache_util) | |
| Reuse (reuse) |
Sampling and confidence.
For each design point, we generate at least 30 task systems and up to 1000 task systems, using a fixed random seed (12345) for reproducibility. We stop sampling early once the 95% confidence interval of the estimated mean schedulability is sufficiently tight (maximum confidence interval width 0.05), otherwise we sample up to the maximum. We report mean schedulability (fraction of schedulable task systems) and, where indicated, the median wall-clock analysis time per task system (including the full RTA fixed-point iteration and all max-flow solves).
Compared analyses.
We compare CacheFlow against standard CRPD baselines (e.g., ECB-only, UCB-only, union and multiset variants) as well as our flow-based variants, using identical task-system instances across all tests.
We also include the Preemption Partitioning Version 1 (PP-VER1) analysis of Marković et al. [21], which decomposes preemptions into partitions and computes a tighter per-partition CRPD bound. Note that the original evaluation of [21] uses a per-task parameter , the maximum number of UCBs at any single program point, derived from static binary analysis. This program-point-level information is strictly finer than the task-level ECB/UCB sets used by all other compared analyses (including CacheFlow). To ensure a fair comparison at the same level of abstraction, our implementation substitutes for , retaining the partitioning structure while relying only on task-level cache-block sets.
Flow-based variants.
We evaluate four configurations of CacheFlow. FLOW is the base max-flow construction under the sporadic task model. FLOW-PERIODIC augments the base model with the strictly periodic refinement (Sec. 4.1), pruning ECB–UCB edges that correspond to preemptions that cannot occur when release times are known. FLOW-CAPPED adds task-level frequency (multiset-style) constraints (Sec. 4.3) that bound the total CRPD that each preempting task can induce and each victim task can absorb over the analysis window. Finally, FLOW-PERIODIC-CAPPED combines both refinements, yielding the tightest flow-based bound when tasks are strictly periodic and task-level caps are enabled. Max-flow instances are solved using Dinic’s algorithm (implemented in the artifact’s src/dinic.rs); a push-relabel variant is included as a cross-check. Both algorithms are applied to the same residual graph via the incremental algorithm (Algorithm 1).
6.2 Schedulability Improvement
Fig. 6 and Fig. 7 show mean schedulability as a function of system utilization for two block reload times (BRT). As expected, schedulability decreases monotonically as utilization increases, and the separation between analyses becomes more pronounced in the mid-to-high utilization regime.
At BRT (Fig. 6), the flow-based variants dominate the baselines across most of the utilization sweep, with the strongest improvements visible between roughly , where CRPD begins to dominate but the system is not yet trivially overloaded. At BRT (Fig. 7), all CRPD-aware tests become more pessimistic, and schedulability drops earlier, but the relative ordering of the methods is preserved: the best-performing flow variants retain schedulability at higher utilizations than prior union- and multiset-based bounds.
6.3 Effect of Block Reload Time
Block reload time () directly scales the cost of each cache-related preemption: when is small, each eviction incurs only a minor penalty, and hence the difference between tight and pessimistic CRPD bounds has limited impact on schedulability. This trend is reflected in Fig. 8: for and , all CRPD-aware analyses (flow and non-flow baselines) are closer to each other across most utilizations, and the schedulability loss due to CRPD appears only in the high-utilization region. The advantage is less significant than at the higher values shown previously.
As increases, the CRPD term becomes a dominant contributor to response-time bounds, and reducing pessimism in CRPD estimation translates into a visibly larger schedulability advantage. This explains why the separation between CacheFlow ’s flow-based variants and prior union/multiset bounds grows in the higher- experiments (e.g., and in Fig. 6–Fig. 7): tighter modeling of which evictions can actually occur yields a larger reduction in the overall interference term when each eviction is expensive.
Harmonic periodic task sets.
To stress-test the periodic refinement in a setting where release-time alignment is common, we additionally evaluate CacheFlow on harmonic task systems, where each period is an integer multiple of the next-shorter period. In such systems, many jobs release simultaneously, which triggers the periodic pruning rule (Lem. 12) and removes a substantial fraction of infeasible preemption edges. One might therefore expect the remaining advantage of flow-based analysis to diminish.
Fig. 9 shows results for two block reload times. At BRT (left), CRPD is relatively inexpensive and most analyses track closely until high utilizations. At BRT (right), CRPD dominates earlier and the separation between methods becomes more pronounced. In both cases, however, the best-performing flow-based variants (notably the periodic/capped flow variants) retain a consistent schedulability advantage over union- and multiset-based baselines across the mid-to-high utilization range. This indicates that, beyond eliminating infeasible preemptions via periodic filtering, jointly optimizing feasible CRPD interactions at the block/job level continues to reduce pessimism relative to prior closed-form bounds.
6.4 Analysis Cost vs. Large Task-Set Size
Fig. 10 reports the mean analysis time per generated task system for larger task sets (). The plotted values are computed from the raw CSV measurements by grouping all task systems with the same task-set size and averaging the runtime for each analysis technique.
A key observation is that analysis time does not increase significantly as the task-set size grows from 20 to 50. While flow-based variants are naturally more expensive than closed-form baselines, their runtime growth across this range is modest, and the absolute costs remain practical. In particular, even in the largest task sets considered, the flow-based analyses complete in seconds per task system rather than minutes or hours.
The COMBINED-UNION-MULTISET baseline, despite being a closed-form analysis, incurs notably higher runtime than expected because it runs both ECB-Union-Multiset and UCB-Union-Multiset in full and takes their minimum. Each multiset construction requires sorting a per-preemption CRPD cost array and summing the largest entries, a step that is super-linear in the number of jobs in the analysis window. Running both variants and then selecting the minimum therefore approximately doubles the per-iteration work compared to either variant alone, while the flow-based variants exploit warm-starting and early-exit to amortize their cost across RTA iterations.
This demonstrates that CacheFlow is applicable as an offline schedulability test: it provides tighter CRPD bounds without requiring prohibitively long per-system evaluation time.
7 Related Work
We survey prior work on CRPD analysis and the use of optimization techniques in real-time systems analysis, highlighting how CacheFlow differs from and improves upon existing approaches.
CRPD analysis foundations.
CRPD analysis dates back to Lee et al. [14], who defined useful cache blocks (UCBs) and evicting cache blocks (ECBs) and showed how to incorporate CRPD into fixed-priority response-time analysis. Busquets-Mataix et al. [9] proposed an ECB-Only approach that bounds CRPD using only the evicting cache blocks of the preempting task. Altmeyer and Burguière [1] refined the UCB definition by restricting it to definitely-cached blocks (DC-UCBs), significantly reducing the number of blocks classified as useful and thereby tightening CRPD bounds.
Building on these foundations, Altmeyer, Davis, and Maiza [2, 3] systematically formalized four approaches to CRPD analysis: ECB-Only, UCB-Only, ECB-Union, and UCB-Union. They established dominance relationships among these approaches and showed that the ECB-based and UCB-based families are incomparable – neither strictly dominates the other in all cases. Their journal paper [3] further introduced multiset variants (ECB-Union-Multiset and UCB-Union-Multiset) that compute a sorted multiset of per-preemption CRPD costs and sum the largest entries, yielding tighter bounds than multiplying the worst-case per-preemption cost by the number of preemptions.
All of the above approaches bound CRPD on a per-job or per-preemption basis and then aggregate over multiple preemptions. In contrast, CacheFlow bounds the total CRPD across a set of jobs holistically by encoding cross-job constraints in a flow network. This allows CacheFlow to exploit structural constraints – such as the fact that a single ECB can cause at most total CRPD across all victims – that per-job analyses cannot capture.
Tighter CRPD bounds.
Several works have sought to tighten CRPD bounds beyond the four classic approaches. Altmeyer, Maiza, and Reineke [4] introduced resilience analysis, a quantitative cache property that measures how many accesses a cache block can survive before being evicted in a set-associative cache. Resilience refines CRPD analysis for LRU caches by accounting for associativity. Our notion of cache-block utility is related in spirit but captures a different property: whereas resilience measures robustness against eviction, utility quantifies the total reuse benefit of a cache block, i.e., the maximum number of accesses to a block that are definitely cache hits.
Kleinsorge, Falk, and Marwedel [13] proposed a synergetic approach that jointly considers the cache states of the preempting and preempted tasks, achieving tighter bounds than analyzing each in isolation. Rashid et al. [24, 23] observed that not all UCBs are evicted on every preemption when cache persistence is considered and integrated cache persistence analysis with CRPD analysis. Stock, Hahn, and Reineke [26] later showed how to make cache persistence analysis exact. Marković et al. [21] proposed preemption partitioning, which assigns each preemption point to a specific higher-priority task and computes a tighter per-task CRPD bound accordingly.
These refinements are complementary to CacheFlow: the per-job or per-block CRPD information they produce can be incorporated as edge capacities in our flow network. Specifically, persistence-aware analysis refines the inputs to CRPD analysis – the useful-block sets and their per-block reload counts – rather than the algorithm that aggregates them. CacheFlow consumes such refinements directly: tighter UCB sets reduce the number of edges, and a per-block utility derived from persistence analysis tightens capacities. We therefore view persistence- and resilience-aware analyses as complementary to, and composable with, our framework. However, none of them formulates CRPD as an optimization problem or considers cross-job interactions the way a flow network does.
CRPD under different scheduling policies and architectures.
Lunniss et al. [18] extended CRPD analysis to EDF scheduling by bounding per-task CRPD over an interval. Our work builds directly on this interval-based formulation but bounds the total CRPD across all tasks in the interval, further reducing pessimism. The same group also compared FP and EDF scheduling accounting for CRPD [16], considered hierarchical scheduling [17], and, with Davis and Dobrin, analyzed preemption thresholds [8].
On the architecture side, Zhang and Koutsoukos [27] addressed CRPD in multi-level inclusive cache hierarchies, Fischer and Falk [11] tackled non-inclusive hierarchies, and Ballabriga et al. [5] considered FIFO replacement policies using ILP. Shah et al. [25] provided an experimental evaluation of existing CRPD-aware analysis techniques. The ECB and UCB sets used as inputs to all compared analyses are standard outputs of cache analysis: binary cache analyses such as those in [14, 1] and commercial tools (e.g., AbsInt’s aiT) derive these sets from control-flow graphs and binary executables. Benchmark suites such as TACLeBench and Mälardalen have been used in this manner (e.g., Shah et al. [25]), providing a clear path to applying CacheFlow to real workloads. Altmeyer et al. [10] proposed a compositional framework for multicore response-time analysis incorporating CRPD. Nguyen et al. [22] used cache-awareness to improve offline scheduling decisions. For a comprehensive survey, we refer the reader to Lv et al. [19] for static cache analysis and Maiza et al. [20] for multicore timing verification.
Optimization techniques in real-time analysis.
The use of network flow and mathematical programming in real-time systems analysis has methodological precedent, though not in CRPD analysis. Bonifaci, Marchetti-Spaccamela, and Stiller [6] used network flow to construct a constant-factor feasibility test for multiprocessor scheduling, where flow represents the allocation of computational work to processors. Brandenburg [7] used linear programming to derive tight blocking bounds for semaphore protocols under partitioned fixed-priority scheduling. Li and Malik [15] pioneered the implicit path enumeration technique (IPET), using integer linear programming to compute WCET bounds.
CacheFlow shares the philosophy of formulating a timing-analysis problem as a combinatorial optimization problem, but differs in what the optimization captures. In [6], flow represents work allocation; in [7], LP variables represent blocking scenarios. In CacheFlow, flow through the network represents CRPD. The max-flow/min-cut formulation naturally encodes constraints that span multiple jobs – for instance, the constraint that a single ECB can cause at most total CRPD across all jobs it preempts – which cannot be expressed in per-job analyses.
8 Conclusion
We presented CacheFlow, a framework that formulates CRPD analysis as a maximum-flow problem over a network of job-level cache interactions, bounding the total CRPD across an analysis interval rather than summing independent per-job bounds. We introduced cache-block utility to generalize the binary useful/evicting classification, described three network refinements (periodic edge pruning, nesting constraints, and aggregate task constraints), and proved that CacheFlow dominates Combined-Union-Multiset. An incremental algorithm integrates max-flow solving into fixed-priority response-time analysis by reusing the residual graph across iterations. Experiments demonstrated significant schedulability improvements with practical analysis times.
References
- [1] Sebastian Altmeyer and Claire Burguiere. A new notion of useful cache block to improve the bounds of cache-related preemption delay. In Proceedings of the 2009 21st Euromicro Conference on Real-Time Systems, ECRTS ’09, pages 109–118, USA, 2009. IEEE Computer Society. doi:10.1109/ECRTS.2009.21.
- [2] Sebastian Altmeyer, Robert I. Davis, and Claire Maiza. Cache related pre-emption delay aware response time analysis for fixed priority pre-emptive systems. In 2011 IEEE 32nd Real-Time Systems Symposium, pages 261–271, 2011. doi:10.1109/RTSS.2011.31.
- [3] Sebastian Altmeyer, Robert I. Davis, and Claire Maiza. Improved cache related pre-emption delay aware response time analysis for fixed priority pre-emptive systems. Real-Time Systems, 48(5):499–526, 2012. doi:10.1007/s11241-012-9152-2.
- [4] Sebastian Altmeyer, Claire Maiza, and Jan Reineke. Resilience analysis: tightening the crpd bound for set-associative caches. In Proceedings of the ACM SIGPLAN/SIGBED 2010 Conference on Languages, Compilers, and Tools for Embedded Systems, LCTES ’10, pages 153–162, New York, NY, USA, 2010. Association for Computing Machinery. doi:10.1145/1755888.1755911.
- [5] Clément Ballabriga, Lee Kee Chong, and Abhik Roychoudhury. Cache-related preemption delay analysis for fifo caches. In Proceedings of the 2014 SIGPLAN/SIGBED Conference on Languages, Compilers and Tools for Embedded Systems, LCTES ’14, pages 33–42, New York, NY, USA, 2014. Association for Computing Machinery. doi:10.1145/2597809.2597814.
- [6] Vincenzo Bonifaci, Alberto Marchetti-Spaccamela, and Sebastian Stiller. A constant-approximate feasibility test for multiprocessor real-time scheduling. Algorithmica, 62(3–4):1034–1049, 2012. doi:10.1007/s00453-011-9497-2.
- [7] Björn B. Brandenburg. Improved analysis and evaluation of real-time semaphore protocols for p-fp scheduling. In 2013 IEEE 19th Real-Time and Embedded Technology and Applications Symposium (RTAS), pages 141–152, 2013. doi:10.1109/RTAS.2013.6531087.
- [8] Reinder J. Bril, Sebastian Altmeyer, Martijn M. Heuvel, Robert I. Davis, and Moris Behnam. Fixed priority scheduling with pre-emption thresholds and cache-related pre-emption delays: integrated analysis and evaluation. Real-Time Syst., 53(4):403–466, 2017. doi:10.1007/s11241-016-9266-z.
- [9] Jose.V. Busquets-Mataix, Juan.J. Serrano, Rafael. Ors, Pedro. Gil, and Andy. Wellings. Adding instruction cache effect to schedulability analysis of preemptive real-time systems. In Proceedings Real-Time Technology and Applications, pages 204–212, 1996. doi:10.1109/RTTAS.1996.509537.
- [10] Robert I. Davis, Sebastian Altmeyer, Leandro S. Indrusiak, Claire Maiza, Vincent Nelis, and Jan Reineke. An extensible framework for multicore response time analysis. Real-Time Syst., 54(3):607–661, 2018. doi:10.1007/s11241-017-9285-4.
- [11] Thilo Leon Fischer and Heiko Falk. Towards analysing cache-related preemption delay in non-inclusive cache hierarchies. ACM Trans. Embed. Comput. Syst., 24(1), 2024. doi:10.1145/3695768.
- [12] M. Joseph and P. Pandya. Finding response times in a real-time system. The Computer Journal, 29(5):390–395, January 1986. doi:10.1093/comjnl/29.5.390.
- [13] Jan C. Kleinsorge, Heiko Falk, and Peter Marwedel. A synergetic approach to accurate analysis of cache-related preemption delay. In Proceedings of the Ninth ACM International Conference on Embedded Software, EMSOFT ’11, pages 329–338, New York, NY, USA, 2011. Association for Computing Machinery. doi:10.1145/2038642.2038693.
- [14] Chang-Gun Lee, Hoosun Hahn, Yang-Min Seo, Sang Lyul Min, Rhan Ha, Seongsoo Hong, Chang Yun Park, Minsuk Lee, and Chong Sang Kim. Analysis of cache-related preemption delay in fixed-priority preemptive scheduling. IEEE Transactions on Computers, 47(6):700–713, 1998. doi:10.1109/12.689649.
- [15] Yau-Tsun Steven Li and Sharad Malik. Performance analysis of embedded software using implicit path enumeration. SIGPLAN Not., 30(11):88–98, 1995. doi:10.1145/216633.216666.
- [16] Will Lunniss, Sebastian Altmeyer, and Robert I. Davis. A Comparison between Fixed Priority and EDF Scheduling accounting for Cache Related Pre-emption Delays. Leibniz Transactions on Embedded Systems, 1(1):01:1–01:24, 2014. doi:10.4230/LITES-v001-i001-a001.
- [17] Will Lunniss, Sebastian Altmeyer, Giuseppe Lipari, and Robert I. Davis. Cache related pre-emption delays in hierarchical scheduling. Real-Time Syst., 52(2):201–238, 2016. doi:10.1007/s11241-015-9228-x.
- [18] Will Lunniss, Sebastian Altmeyer, Claire Maiza, and Robert I. Davis. Integrating cache related pre-emption delay analysis into edf scheduling. In 2013 IEEE 19th Real-Time and Embedded Technology and Applications Symposium (RTAS), pages 75–84, 2013. doi:10.1109/RTAS.2013.6531081.
- [19] Mingsong Lv, Nan Guan, Jan Reineke, Reinhard Wilhelm, and Wang Yi. A Survey on Static Cache Analysis for Real-Time Systems. Leibniz Transactions on Embedded Systems, 3(1):05:1–05:48, 2016. doi:10.4230/LITES-v003-i001-a005.
- [20] Claire Maiza, Hamza Rihani, Juan M. Rivas, Joël Goossens, Sebastian Altmeyer, and Robert I. Davis. A survey of timing verification techniques for multi-core real-time systems. ACM Comput. Surv., 52(3), 2019. doi:10.1145/3323212.
- [21] Filip Marković, Jan Carlson, Sebastian Altmeyer, and Radu Dobrin. Improving the Accuracy of Cache-Aware Response Time Analysis Using Preemption Partitioning. In Marcus Völp, editor, 32nd Euromicro Conference on Real-Time Systems (ECRTS 2020), volume 165 of Leibniz International Proceedings in Informatics (LIPIcs), pages 5:1–5:23, Dagstuhl, Germany, 2020. Schloss Dagstuhl – Leibniz-Zentrum für Informatik. doi:10.4230/LIPIcs.ECRTS.2020.5.
- [22] Viet Anh Nguyen, Damien Hardy, and Isabelle Puaut. Cache-conscious offline real-time task scheduling for multi-core processors. In ECRTS ’17, 2017. doi:10.1007/s11241-019-09333-z.
- [23] Syed Aftab Rashid, Geoffrey Nelissen, Sebastian Altmeyer, Robert I. Davis, and Eduardo Tovar. Integrated analysis of cache related preemption delays and cache persistence reload overheads. In RTSS ’17, pages 188–198, 2017. doi:10.1109/RTSS.2017.00025.
- [24] Syed Aftab Rashid, Geoffrey Nelissen, Damien Hardy, Benny Akesson, Isabelle Puaut, and Eduardo Tovar. Cache-persistence-aware response-time analysis for fixed-priority preemptive systems. In 2016 28th Euromicro Conference on Real-Time Systems (ECRTS), pages 262–272, 2016. doi:10.1109/ECRTS.2016.25.
- [25] Darshit Shah, Sebastian Hahn, and Jan Reineke. Experimental evaluation of cache-related preemption delay aware timing analysis. In 18th International Workshop on Worst-Case Execution Time Analysis (WCET), 2018.
- [26] Gregory Stock, Sebastian Hahn, and Jan Reineke. Cache persistence analysis: Finally exact. CoRR, abs/1909.04374, 2019. arXiv:1909.04374.
- [27] Zhenkai Zhang and Xenofon Koutsoukos. Cache-related preemption delay analysis for multi-level inclusive caches. In Proceedings of the 13th International Conference on Embedded Software, EMSOFT ’16, New York, NY, USA, 2016. Association for Computing Machinery. doi:10.1145/2968478.2968481.
