Hi Noah,
Can you elaborate on how you’re evaluating the differences between the timestamps going in and coming out? Are you comparing the timestamp the camera watermarked the image with, with the time in the camera title bar in playback? Are you comparing the timestamp in the titlebar with the time shown on the timeline at the bottom?
Hopefully someone will correct me if I’m wrong but my understanding is that we typically use a combination of the Recording Server’s system time, and the time code’s provided by the camera, to resolve a timestamp for each frame.
I don’t think all cameras provide any, or any useful time code in the RTP stream (some don’t use RTP for example), so the actual implementation can vary by device, but the idea is that when the Recording Server starts the stream, the first frame is timestamped as “T0 plus 0 milliseconds” where T0 is the Recording Server system time. Then the next frame has a time code indicating 33ms has elapsed since the last frame it sent, so it gets stamped with T0 + 33ms. The advantage is that if there is significant latency/jitter, and maybe 200ms elapses between receiving two frames, then we get a bunch of frames within a couple milliseconds, we can use the RTP timecode to spread those frames out based on when the camera produced them, not when we actually received them.
The timestamp in the camera title bar will typically be different than the timestamp in the image, and again different than the timestamp in the timeline navigation bar. Here’s what it all means:
- The timestamp in the titlebar for each individual camera is the absolute timestamp record for the image being displayed according to the recording server.
- The timestamp in the image is the camera’s opinion on the time when that image frame was encoded, and before it was put on the wire to the Recording Server. This should ideally be within a few milliseconds of the Recording Server’s record, but can vary even up to a couple of seconds depending on the situation.
- The timestamp in the timeline navigation bar is the requested time, and the images provided for each camera in the view will be as close to that requested time as possible, but you might not have an image at that exact millisecond, so you’ll be shown the nearest image to that point in time.
I am comparing the frame timestamps that I get out of Corporate when I’m streaming live and the frames I get when querying for a range of timestamps. So in both cases, the data (I assume) is coming from the recorder. I would have expected the query range to produce frames with the same timestamps as the live stream, but they do not, which make me curious about how the frames are stored in the recorder. Are they kept as frames or constituted in some other compressed GOP format, which can only approximate the original frames? I’ve already worked around this issue, but I am curious as to what is actually happening.
The live images are delivered as they are received and I suspect they have a timestamp based completely on the time the recording server received the image, whereas when we store the image, a timestamp is resolved based on the strategy I mentioned above.
How are you comparing the live image timestamp with the same image in playback, and what is the variance you’re seeing?
Are you pulling a live image programatically, storing the image and the timestamp provided by the recording server, then looking for that exact image in playback? Just trying to understand how to produce the same results that you’re getting.
I’m using protocol integration, pulling the live data over the TCP connection and storing the timestamp data. When I recall frames, I compare the frames I get to the stored values. The variance can be 20-30 ms and sometimes more. It’s not consistently one way or the other, so I was wondering how the data is being stored in the recorder - whether it is kept as individual frames or glommed together into GOPs. I’m streaming 1080P @ 10 FPS and seeing ~ 160GB per day per camera of storage, which implies some sort of glomming.
If I did the math right, and you’re recording 100% of the time, that is 15 Mibps which seems really high for an H.264 stream.
But that doesn’t have much to do with how it’s stored unless there was a whole lot of of header/trailer added to the records.
We do store GOPs together in a record, and many GOPs would be stored in each BLK file in the media database, but I’m not sure how that is relevant to the original question as this is all abstracted away. In the end, the difference you’re seeing is probably due to the fact that the live data is passed straight on to the live viewers before being put in the database, and the timestamp used in the database is probably not resolved until later in the pipeline, so the live stream timestamp is likely just going to be “DateTime.UtcNow” while the stored image timestamp will be resolved using system time and RTP time code information whenever possible.