Skip to content
This repository has been archived by the owner on Apr 19, 2023. It is now read-only.

Commit

Permalink
Support logs longer than 71.6 minutes (track 32-bit time field rollover)
Browse files Browse the repository at this point in the history
  • Loading branch information
thenickdude committed Nov 27, 2016
1 parent 7a940b6 commit 1f4c46c
Show file tree
Hide file tree
Showing 3 changed files with 77 additions and 49 deletions.
2 changes: 2 additions & 0 deletions js/flightlog.js
Original file line number Diff line number Diff line change
Expand Up @@ -401,6 +401,8 @@ function FlightLog(logData) {
parser.resetDataState();

//Prime the parser with the previous state we get from the flightlog index, so it can base deltas off that data
parser.setTimeRolloverAccumulator(iframeDirectory.initialTimeRolloverAccumulator[chunkIndex]);

if (iframeDirectory.initialGPSHome) {
parser.setGPSHomeHistory(iframeDirectory.initialGPSHome[chunkIndex]);
}
Expand Down
7 changes: 2 additions & 5 deletions js/flightlog_index.js
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,6 @@ function FlightLogIndex(logData) {
var
that = this,
logBeginOffsets = false,
logCount = false,
intraframeDirectories = false;

function buildLogOffsetsIndex() {
Expand Down Expand Up @@ -46,19 +45,17 @@ function FlightLogIndex(logData) {
initialIMU: [],
initialSlow: [],
initialGPSHome: [],
initialTimeRolloverAccumulator: [],
hasEvent: [],
minTime: false,
maxTime: false
},

imu = new IMU(),
gyroADC, accSmooth, magADC,

iframeCount = 0,
motorFields = [],
matches,
throttleTotal,
eventInThisChunk = null,
parsedHeader,
sawEndMarker = false;

Expand Down Expand Up @@ -122,6 +119,7 @@ function FlightLogIndex(logData) {
// Log the beginning of the new chunk
intraIndex.times.push(frameTime);
intraIndex.offsets.push(frameOffset);
intraIndex.initialTimeRolloverAccumulator.push(frameTime - (frameTime >>> 0) /* i.e. frameTime with the lower 32-bits masked out */);

if (motorFields.length) {
throttleTotal = 0;
Expand Down Expand Up @@ -218,7 +216,6 @@ function FlightLogIndex(logData) {
var
lastTime, lastLastTime,
lastOffset, lastLastOffset,
lastThrottle,

sourceIndex = intraframeDirectories[i],

Expand Down
117 changes: 73 additions & 44 deletions js/flightlog_parser.js
Original file line number Diff line number Diff line change
Expand Up @@ -217,6 +217,9 @@ var FlightLogParser = function(logData) {
// Details about the last main frame that was successfully parsed
lastMainFrameIteration,
lastMainFrameTime,

// When 32-bit time values roll over to zero, we add 2^32 to this accumulator so it can be added to the time:
timeRolloverAccumulator = 0,

//The actual log data stream we're reading:
stream;
Expand Down Expand Up @@ -453,51 +456,74 @@ var FlightLogParser = function(logData) {
}
}
}

function castTo32BitUnsigned(val) {
return val >>> 0;
}

function applyTimeRollover() {
if (lastMainFrameTime != -1) {
if (
// If we appeared to travel backwards in time (modulo 32 bits)...
(castTo32BitUnsigned(mainHistory[0][FlightLogParser.prototype.FLIGHT_LOG_FIELD_INDEX_TIME]) < castTo32BitUnsigned(lastMainFrameTime))
// But we actually just incremented a reasonable amount (modulo 32-bits)...
&& castTo32BitUnsigned(castTo32BitUnsigned(mainHistory[0][FlightLogParser.prototype.FLIGHT_LOG_FIELD_INDEX_TIME]) - castTo32BitUnsigned(lastMainFrameTime)) < MAXIMUM_TIME_JUMP_BETWEEN_FRAMES
) {
// 32-bit time counter has wrapped, so add 2^32 to the timestamp
timeRolloverAccumulator += 0x100000000;
}
}

mainHistory[0][FlightLogParser.prototype.FLIGHT_LOG_FIELD_INDEX_TIME] = castTo32BitUnsigned(mainHistory[0][FlightLogParser.prototype.FLIGHT_LOG_FIELD_INDEX_TIME]) + timeRolloverAccumulator;
}

function validateMainFrameValues() {
// Check that iteration count and time didn't move backwards, and didn't move forward too much.
return (
mainHistory[0][FlightLogParser.prototype.FLIGHT_LOG_FIELD_INDEX_ITERATION] >= lastMainFrameIteration
&& mainHistory[0][FlightLogParser.prototype.FLIGHT_LOG_FIELD_INDEX_ITERATION] < lastMainFrameIteration + MAXIMUM_ITERATION_JUMP_BETWEEN_FRAMES
&& mainHistory[0][FlightLogParser.prototype.FLIGHT_LOG_FIELD_INDEX_TIME] >= lastMainFrameTime
&& mainHistory[0][FlightLogParser.prototype.FLIGHT_LOG_FIELD_INDEX_TIME] < lastMainFrameTime + MAXIMUM_TIME_JUMP_BETWEEN_FRAMES
);
}

function completeIntraframe(frameType, frameStart, frameEnd, raw) {
var acceptFrame = true;
applyTimeRollover();

// Only attempt to validate the frame values if we have something to check it against
if (!raw && lastMainFrameIteration != -1 && !validateMainFrameValues()) {
invalidateMainStream();
} else {
mainStreamIsValid = true;
}

// Do we have a previous frame to use as a reference to validate field values against?
if (!raw && lastMainFrameIteration != -1) {
/*
* Check that iteration count and time didn't move backwards, and didn't move forward too much.
*/
acceptFrame =
mainHistory[0][FlightLogParser.prototype.FLIGHT_LOG_FIELD_INDEX_ITERATION] >= lastMainFrameIteration
&& mainHistory[0][FlightLogParser.prototype.FLIGHT_LOG_FIELD_INDEX_ITERATION] < lastMainFrameIteration + MAXIMUM_ITERATION_JUMP_BETWEEN_FRAMES
&& mainHistory[0][FlightLogParser.prototype.FLIGHT_LOG_FIELD_INDEX_TIME] >= lastMainFrameTime
&& mainHistory[0][FlightLogParser.prototype.FLIGHT_LOG_FIELD_INDEX_TIME] < lastMainFrameTime + MAXIMUM_TIME_JUMP_BETWEEN_FRAMES;
}

if (acceptFrame) {
if (mainStreamIsValid) {
that.stats.intentionallyAbsentIterations += countIntentionallySkippedFramesTo(mainHistory[0][FlightLogParser.prototype.FLIGHT_LOG_FIELD_INDEX_ITERATION]);

lastMainFrameIteration = mainHistory[0][FlightLogParser.prototype.FLIGHT_LOG_FIELD_INDEX_ITERATION];
lastMainFrameTime = mainHistory[0][FlightLogParser.prototype.FLIGHT_LOG_FIELD_INDEX_TIME];

mainStreamIsValid = true;


updateFieldStatistics(frameType, mainHistory[0]);
} else {
invalidateMainStream();
}

if (that.onFrameReady)
that.onFrameReady(mainStreamIsValid, mainHistory[0], frameType, frameStart, frameEnd - frameStart);

// Rotate history buffers

// Both the previous and previous-previous states become the I-frame, because we can't look further into the past than the I-frame
mainHistory[1] = mainHistory[0];
mainHistory[2] = mainHistory[0];

// And advance the current frame into an empty space ready to be filled
if (mainHistory[0] == mainHistoryRing[0])
mainHistory[0] = mainHistoryRing[1];
else if (mainHistory[0] == mainHistoryRing[1])
mainHistory[0] = mainHistoryRing[2];
else
mainHistory[0] = mainHistoryRing[0];
if (mainStreamIsValid) {
// Rotate history buffers

// Both the previous and previous-previous states become the I-frame, because we can't look further into the past than the I-frame
mainHistory[1] = mainHistory[0];
mainHistory[2] = mainHistory[0];

// And advance the current frame into an empty space ready to be filled
if (mainHistory[0] == mainHistoryRing[0])
mainHistory[0] = mainHistoryRing[1];
else if (mainHistory[0] == mainHistoryRing[1])
mainHistory[0] = mainHistoryRing[2];
else
mainHistory[0] = mainHistoryRing[0];
}
}

/**
Expand Down Expand Up @@ -642,16 +668,13 @@ var FlightLogParser = function(logData) {
}

function completeInterframe(frameType, frameStart, frameEnd, raw) {
// Reject this frame if the time or iteration count jumped too far
if (mainStreamIsValid && !raw
&& (
mainHistory[0][FlightLogParser.prototype.FLIGHT_LOG_FIELD_INDEX_TIME] > lastMainFrameTime + MAXIMUM_TIME_JUMP_BETWEEN_FRAMES
|| mainHistory[0][FlightLogParser.prototype.FLIGHT_LOG_FIELD_INDEX_ITERATION] > lastMainFrameIteration + MAXIMUM_ITERATION_JUMP_BETWEEN_FRAMES
)) {
mainStreamIsValid = false;
}

if (mainStreamIsValid) {
applyTimeRollover();

if (mainStreamIsValid && !raw && !validateMainFrameValues()) {
invalidateMainStream();
}

if (mainStreamIsValid) {
lastMainFrameIteration = mainHistory[0][FlightLogParser.prototype.FLIGHT_LOG_FIELD_INDEX_ITERATION];
lastMainFrameTime = mainHistory[0][FlightLogParser.prototype.FLIGHT_LOG_FIELD_INDEX_TIME];

Expand Down Expand Up @@ -865,7 +888,7 @@ var FlightLogParser = function(logData) {

switch (eventType) {
case FlightLogEvent.SYNC_BEEP:
lastEvent.data.time = stream.readUnsignedVB();
lastEvent.data.time = stream.readUnsignedVB() + timeRolloverAccumulator;
lastEvent.time = lastEvent.data.time;
break;
case FlightLogEvent.AUTOTUNE_CYCLE_START:
Expand Down Expand Up @@ -921,7 +944,7 @@ var FlightLogParser = function(logData) {
break;
case FlightLogEvent.LOGGING_RESUME:
lastEvent.data.logIteration = stream.readUnsignedVB();
lastEvent.data.currentTime = stream.readUnsignedVB();
lastEvent.data.currentTime = stream.readUnsignedVB() + timeRolloverAccumulator;
break;
case FlightLogEvent.LOG_END:
var endMessage = stream.readString(END_OF_LOG_MESSAGE.length);
Expand Down Expand Up @@ -952,6 +975,8 @@ var FlightLogParser = function(logData) {

lastMainFrameIteration = -1;
lastMainFrameTime = -1;

timeRolloverAccumulator = 0;

invalidateMainStream();
gpsHomeIsValid = false;
Expand Down Expand Up @@ -1073,6 +1098,9 @@ var FlightLogParser = function(logData) {
}
};

this.setTimeRolloverAccumulator = function(newTimeRolloverAccumulator) {
timeRolloverAccumulator = newTimeRolloverAccumulator;
};

/**
* Continue the current parse by scanning the given range of offsets for data. To begin an independent parse,
Expand Down Expand Up @@ -1111,6 +1139,7 @@ var FlightLogParser = function(logData) {
sizeCount: new Int32Array(256), /* int32 arrays are zero-filled, handy! */
validCount: 0,
corruptCount: 0,
desyncCount: 0,
field: []
};
}
Expand Down

0 comments on commit 1f4c46c

Please sign in to comment.