NetworkStats: more robust subtraction for deltas
This patch ensures that subtract() between two NetworkStats object will return a delta with no negative entries in all cases. When the stats delta contains some negative values, there are clamped to 0. Some logging is added when this happens. This is what's expected by NetworkStatsHistory#recordData(). Bug: 64365917 Test: runtest frameworks-net Change-Id: I16e97e73f600225f80e0ce517e80c07c6f399196
This commit is contained in:
@@ -672,36 +672,33 @@ public class NetworkStats implements Parcelable {
|
||||
entry.tag = left.tag[i];
|
||||
entry.metered = left.metered[i];
|
||||
entry.roaming = left.roaming[i];
|
||||
entry.rxBytes = left.rxBytes[i];
|
||||
entry.rxPackets = left.rxPackets[i];
|
||||
entry.txBytes = left.txBytes[i];
|
||||
entry.txPackets = left.txPackets[i];
|
||||
entry.operations = left.operations[i];
|
||||
|
||||
// find remote row that matches, and subtract
|
||||
final int j = right.findIndexHinted(entry.iface, entry.uid, entry.set, entry.tag,
|
||||
entry.metered, entry.roaming, i);
|
||||
if (j == -1) {
|
||||
// newly appearing row, return entire value
|
||||
entry.rxBytes = left.rxBytes[i];
|
||||
entry.rxPackets = left.rxPackets[i];
|
||||
entry.txBytes = left.txBytes[i];
|
||||
entry.txPackets = left.txPackets[i];
|
||||
entry.operations = left.operations[i];
|
||||
} else {
|
||||
// existing row, subtract remote value
|
||||
entry.rxBytes = left.rxBytes[i] - right.rxBytes[j];
|
||||
entry.rxPackets = left.rxPackets[i] - right.rxPackets[j];
|
||||
entry.txBytes = left.txBytes[i] - right.txBytes[j];
|
||||
entry.txPackets = left.txPackets[i] - right.txPackets[j];
|
||||
entry.operations = left.operations[i] - right.operations[j];
|
||||
if (j != -1) {
|
||||
// Found matching row, subtract remote value.
|
||||
entry.rxBytes -= right.rxBytes[j];
|
||||
entry.rxPackets -= right.rxPackets[j];
|
||||
entry.txBytes -= right.txBytes[j];
|
||||
entry.txPackets -= right.txPackets[j];
|
||||
entry.operations -= right.operations[j];
|
||||
}
|
||||
|
||||
if (entry.rxBytes < 0 || entry.rxPackets < 0 || entry.txBytes < 0
|
||||
|| entry.txPackets < 0 || entry.operations < 0) {
|
||||
if (observer != null) {
|
||||
observer.foundNonMonotonic(left, i, right, j, cookie);
|
||||
}
|
||||
entry.rxBytes = Math.max(entry.rxBytes, 0);
|
||||
entry.rxPackets = Math.max(entry.rxPackets, 0);
|
||||
entry.txBytes = Math.max(entry.txBytes, 0);
|
||||
entry.txPackets = Math.max(entry.txPackets, 0);
|
||||
entry.operations = Math.max(entry.operations, 0);
|
||||
if (entry.isNegative()) {
|
||||
if (observer != null) {
|
||||
observer.foundNonMonotonic(left, i, right, j, cookie);
|
||||
}
|
||||
entry.rxBytes = Math.max(entry.rxBytes, 0);
|
||||
entry.rxPackets = Math.max(entry.rxPackets, 0);
|
||||
entry.txBytes = Math.max(entry.txBytes, 0);
|
||||
entry.txPackets = Math.max(entry.txPackets, 0);
|
||||
entry.operations = Math.max(entry.operations, 0);
|
||||
}
|
||||
|
||||
result.addValues(entry);
|
||||
|
||||
Reference in New Issue
Block a user