IV. Desarrollo
4.7 Riesgos Laborales
4.7.1 Riesgos de seguridad industrial
4.7.1.2 Equipos de Protección personal
In this section, we will describe of the main Kecleon optimization passes and how they exploit the runtime information gathered during the previous steps to generate an optimized data plane.
7.4.3.1 Dead Code Elimination Pass (DCE)
The goal of the Kecleon dynamic DCE pass is equivalent to the correspond- ing DCE pass used in most of the compiler optimization phases; it prunes “dead” branches and instructions that are considered unreachable at compilation time.
3The instrumented tables can also have entries that are not contained in the original map; this
information is also beneficial to the optimization passes that may optimize the code for the most common case.
4Kecleon does not know that the map value is a “bitvector”, it just substitutes value in the
code and tries to find a better path using the already existing compiler (LLVM) optimization passes.
7 – Kecleon: A Dynamic Compiler and Optimizer for Software Network Data Planes
Algorithm 5: Kecleon Dynamic DCE algorithm
Input: IRM (Module), IR of the original program Input: P (Plugin), Reference to target Kecleon plugin Function DynDCEPass:
1 forall IRConf Instr in IRM do
2 runtime_val ← P.GetConfigValue(IRConf Instr)
3 if runtime_val.size() > 1 then 4 foreach val in runtime_val do
5 P.IRBuilder.PropagateValueSet(val, IRConfInstr) else 6 P.IRBuilder.PropagateSingleValue (runtime_val, IRConf Instr) 7 RunConstantPropagationPass(IRM ) 8 RunConstantFoldingPass(IRM ) 9 RunDCEPass(IRM ) 10 return IRM
This pass works as described in Algorithm 5. As the first step (line 2), the algo- rithm scans the entire set of IR instructions to find the one marked as configuration (as described in Section 7.4.1). Then, it interrogates the back-end plugin to re- trieve the runtime values for the associated configuration variable. It is important to note that the exported variables can assume different values and types; it is the role of the Kecleon back-end plugin to provide the required information according to the defined plugin interface. For example, if a configuration variable is a list, a parameter is_list is stored into the internal Kecleon data structures during the analysis step; then, the various optimization passes can use this information to act differently based on their goal. As the second step (line 3-6), the algo- rithm substitutes the original configuration instruction with the runtime value (or set of values). Then, it can directly call the existing compiler passes to automati- cally perform Constant Propagation, Constant Folding, and Dead Code Elimination (line 7-9) that will eliminate the unreachable code.
The DCE Pass mentioned above can remove redundancy in the NF code, but there are some scenarios where it cannot be fully applied. It may happen that, after the propagation of the configuration, only a subset of the paths into the code is subjected to the dead code elimination. Within the current state, Kecleon is not able to recognize this scenario, given the path-insensitive type of analysis that is applied. A solution would be to use symbolic execution methods to perform a path-aware DCE, then merge the results of each path to generate the final output. Although not currently implemented, this extension is part of the future work.
7 – Kecleon: A Dynamic Compiler and Optimizer for Software Network Data Planes
Algorithm 6: Kecleon Dynamic DSS algorithm
Input: IRM (Module), IR of the original program Input: P (Plugin), Reference to target Kecleon plugin Function DynDSSPass:
1 forall IRT ableInstr in IRM do
2 tid ← IRM.RetrieveTID(IRT ableInstr)
3 inf o ← P.GetTableInfo(tid)
4 values ← P.GetTableValues(tid)
5 if IsDSSFeasible(inf o, values) then
6 new_inf o = ApplyDSSToTable(inf o)
7 P.CheckCostFunction(new_info, info)
8 P.IRBuilder.CreateNewTable(new_info, IRT ableInstr)
9 return IRM
7.4.3.2 Data Structure Specialization Pass (DSS)
The Kecleon DSS Pass is in charge of analyzing the runtime content of the MATs used by the NF data plane and modify their layout, size, or algorithm to the one that better performs under the given runtime conditions.
For example, knowing which field of a key in a Longest Prefix Match (LPM) table indicates the prefix, under specific circumstances (e.g., all entries have the same prefix) the Kecleon DSS could automatically convert the LPM table into a hash table. Algorithm 6 shows the behavior of this pass.
It starts by extracting the runtime values from the map using the Table Identifier (TID) taken by the previous analysis pass and retrieved from the debug information associated with the IR instruction. Then, depending on the runtime values, it decides if the data structure content matches a possible transformation. If a cost
function is given, Kecleon first checks if the new change may provide the expected
performance benefits; otherwise, the transformation is discarded. For frameworks that offer a clear definition of the data structures and their implementations, their associated cost function can be automatically deducted using static analysis or symbolic execution methods [124], [126], instead of requiring a manual effort from the plugin developer.
Note: Today, many NFs are stateful, where packet processing updates states that,
in turn, influences the packet data path. Changing the data structure used by the data plane of a NF may be dangerous if the table is modified within the data plane itself. If the newly inserted entries invalidate the assumption used by the DSS Pass when it has performed the optimization, we may corrupt the original application semantic. As a consequence, Kecleon applies the DSS Pass only to tables that are not modified in the data plane (the DSS Analysis Pass can recognize this situation). A change in those tables can happen only from the control plane, and, in this
7 – Kecleon: A Dynamic Compiler and Optimizer for Software Network Data Planes
scenario, Kecleon triggers the execution of the optimization pipeline to re-evaluate the feasibility of the optimization.
7.4.3.3 Cached Computation (CC) Pass
The CC Pass can be seen as a further specialization of the DSS pass, where together with the runtime MAT values also the results of the instrumented MAT are used. The results of the instrumentation give a hint to the different optimization passes about the most common paths into the code or the most used entries in a MAT. The Cached Computation (CC) Pass can reduce the overhead given by specific memory accesses by, as the name suggests, caching the computation of the most accessed entries within the code itself or in other, more efficient, tables. For example, a simple lookup operation in a large MAT may be in charge of 70% of the overall overhead of the NF, causing a lot of cache misses, even if the number of matched entries (taken from the runtime instrumentation) represent only the 5% of the overall number of entries in the table. The CC Pass can take the 5% of the most used entries within the MAT table and compile them directly in the code, by pre-computing the result of the MAT lookup for those entries. A parameter controls the maximum number of entries under which a table is directly compiled. The pre-computation depends on the original layout of the compiled table and the type of variable used for the lookup. For example, the cached entries within a hash table are converted into a series of switch-case matching the single key value used in the lookup, or a hash of this value for complex entries5. In the latter case, a
pre-computed collision-free hash (among the other cached values) is used to access to the pre-computed variable. In the same way, for an LPM table of IP addresses, we could derive from the instrumentation a set of most-accessed IPs, whose lookup result can be pre-computed and cached within the code, using the same procedure described before.
Avoid inconsistency of cached entries. When the Kecleon CC Pass caches
some entries directly in the code it needs to ensure that a subsequent modification in the table, which may happen both from the control plane and the data plane for non-configuration MAT, is reflected immediately in the cached code that should then use the updated information instead of the old (directly compiled in the code) one. That means that packets coming after the update should be immediately redi- rected to the original code branch (i.e., performing regular table lookup) instead of accessing the cached information. Triggering the execution of the Kecleon opti- mization pipeline every time an update is found would result on new packets coming
5With complex entries we indicate variables that contains more than one primitive value (e.g.,
7 – Kecleon: A Dynamic Compiler and Optimizer for Software Network Data Planes
immediately after the update to match the old cached version until Kecleon emits a new pipeline, breaking one of the main Kecleon assumption to keep the original data plane semantic untouched.
To avoid this issue, Kecleon makes use of guards. A guard is a control variable (or a specific MAT) that contains the version of the currently cached computation that is compiled in the code; before accessing the CC, the NF data plane checks if the value contained in the guard matches the one of the compiled version - if not, it falls back to the “default” path, which corresponds to the original NF data plane. The update of the guard is done atomically before the map associated with it is modified (of course, if the update does not impact the cached entries, the guard is not modified), and the way it is done depends on the given target platform.
For example, in the eBPF plugin implementation, the guard map is implemented as an additional PER_CPU_ARRAY table with a single entry containing the current version of the code. Then, an additional kprobe is attached to the bpf_map_update helper; therefore, when an update is performed, the Kecleon eBPF program at- tached to the kprobe is executed and it updates the guard consequently, guarantee- ing the consistency of the original data plane. Of course, the use of guards increases the overhead of the NF since it wastes some CPU cycles to check its version before accessing the cached entries. We have measured its cost in Section 7.6.