Relation between eofTimestampUs and tscEofTimestampUs

DRIVE OS Version: 7.0.3

Issue Description:

I am attempting to retrieve camera image timestamps using the dwSensorCamera_getImageTimestamps() API. According to the documentation, this function should populate a dwImageTimestamps structure containing various timestamp fields.

However, the eofTimestampUs value does not appear to be in microseconds, as it progresses approximately 32 times faster than the system time obtained via dwContext_getCurrentTime(). It seems to behave more like a combination of epoch time and TSC (timestamp counter) count.

We observed the following relationship:

eofTimestampUs ≈ epoch_time_at_system_boot + tscEofTimestampUs

To investigate this further, we modified the sample_camera application, specifically the CameraCustomSimpleApp::onRenderHelper() function, as shown in the attached snippet:


Code Modification: CameraCustomSimpleApp::onRenderHelper

// Render received texture
{
    dwVector2f range{};
    range.x = imageGL->prop.width;
    range.y = imageGL->prop.height;
    CHECK_DW_ERROR(dwRenderEngine_setCoordinateRange2D(range, m_renderEngine));
    CHECK_DW_ERROR(dwRenderEngine_renderImage2D(imageGL, {0, 0, range.x, range.y}, m_renderEngine));
    dwRenderEngine_setColor(m_colorPerPort[0], m_renderEngine);

    dwTime_t dw_ts;
    dwContext_getCurrentTime(&dw_ts, m_context);

    dwTime_t timestamp;
    dwImage_getTimestamp(&timestamp, img);

    dwImageTimestamps imageTimestamps{};
    dwSensorCamera_getImageTimestamps(&imageTimestamps, frame);

    dwTime_t getImageTimestamp_ts;
    dwSensorCamera_getTimestamp(&getImageTimestamp_ts, frame);

    conv.observeFrameTscEofUs(imageTimestamps.tscEofTimestampUs);

    auto epoch_time_at_system_boot = imageTimestamps.eofTimestampUs - imageTimestamps.tscEofTimestampUs;
    auto epoch_ctx_to_tsc_offset = static_cast<double>(dw_ts - offset);
    auto time_elapsed_per_count = epoch_ctx_to_tsc_offset / static_cast<double>(imageTimestamps.tscEofTimestampUs);
    auto tsc_to_elapsed_time = static_cast<double>(imageTimestamps.tscEofTimestampUs) * time_elapsed_per_count;

    std::cout << "Current from dwContext_getCurrentTime: " << dw_ts
              << " epoch_time_at_system_boot: " << epoch_time_at_system_boot
              << " eof: " << std::setprecision(10) << tsc_to_elapsed_time / 1e6
              << " time_elapsed_per_count: " << std::setprecision(10) << time_elapsed_per_count
              << std::endl;

    std::string tileString = "Camera:" + std::to_string(cameraIndex) + " Time:" +
                             std::to_string(timestamp / 1000000) + "." +
                             std::to_string(timestamp % 1000000);

    CHECK_DW_ERROR(dwRenderEngine_setFont(DW_RENDER_ENGINE_FONT_VERDANA_16, m_renderEngine));
    CHECK_DW_ERROR(dwRenderEngine_renderText2D(tileString.c_str(), {25, 80}, m_renderEngine));

    m_screenshot->processScreenshotTrig();
}

Analysis

Essentially, we aim to calculate the time difference between the current epoch time from dwContext_getCurrentTime() and the derived epoch_time_at_system_boot, then compare that with tscEofTimestampUs * time_elapsed_per_count.

Based on Timestamping GPIO , the time_elapsed_per_count value appears to be approximately 32ns on Jetson Orin. Our computed value is around 31.25ns, except for the first few frames when starting the sample_camera.

Example outputs:

Current from dwContext_getCurrentTime: 1772476860821523 epoch_time_at_system_boot: 1772410458011147 eof: 66402.81038 time_elapsed_per_count: 1.000000422
Current from dwContext_getCurrentTime: 1772476860834283 epoch_time_at_system_boot: 1772410456977792 eof: 66403.85649 time_elapsed_per_count: 1.000000112
Current from dwContext_getCurrentTime: 1772476860868382 epoch_time_at_system_boot: 1772410455944458 eof: 66404.92392 time_elapsed_per_count: 1.000000124
Current from dwContext_getCurrentTime: 1772476860900552 epoch_time_at_system_boot: 1772410454911090 eof: 66405.98946 time_elapsed_per_count: 1.000000107
Current from dwContext_getCurrentTime: 1772476860935078 epoch_time_at_system_boot: 1772474785705951 eof: 2075.229127 time_elapsed_per_count: 0.03125013318
Current from dwContext_getCurrentTime: 1772476860967139 epoch_time_at_system_boot: 1772474785705951 eof: 2075.261188 time_elapsed_per_count: 0.03125011402
Current from dwContext_getCurrentTime: 1772476861000496 epoch_time_at_system_boot: 1772474785705951 eof: 2075.294545 time_elapsed_per_count: 0.03125011438
Current from dwContext_getCurrentTime: 1772476861033837 epoch_time_at_system_boot: 1772474785705951 eof: 2075.327886 time_elapsed_per_count: 0.03125011449
Current from dwContext_getCurrentTime: 1772476861068678 epoch_time_at_system_boot: 1772474785705951 eof: 2075.362727 time_elapsed_per_count: 0.03125013719
Current from dwContext_getCurrentTime: 1772476861100487 epoch_time_at_system_boot: 1772474785705951 eof: 2075.394536 time_elapsed_per_count: 0.03125011424
Current from dwContext_getCurrentTime: 1772476861133829 epoch_time_at_system_boot: 1772474785705951 eof: 2075.427878 time_elapsed_per_count: 0.03125011436
Current from dwContext_getCurrentTime: 1772476861167113 epoch_time_at_system_boot: 1772474785705951 eof: 2075.461162 time_elapsed_per_count: 0.03125011362
Current from dwContext_getCurrentTime: 1772476861200442 epoch_time_at_system_boot: 1772474785705951 eof: 2075.494491 time_elapsed_per_count: 0.03125011355
Current from dwContext_getCurrentTime: 1772476861233832 epoch_time_at_system_boot: 1772474785705951 eof: 2075.527881 time_elapsed_per_count: 0.0312501144
Current from dwContext_getCurrentTime: 1772476861267099 epoch_time_at_system_boot: 1772474785705951 eof: 2075.561148 time_elapsed_per_count: 0.0312501134
Current from dwContext_getCurrentTime: 1772476861300437 epoch_time_at_system_boot: 1772474785705951 eof: 2075.594486 time_elapsed_per_count: 0.03125011347


Question

Could you confirm if this is the correct interpretation of the eofTimestampUs field in DRIVE OS 7.0.3?
According to the documentation, eofTimestampUs should be in microseconds, and dwImage_getTimestamp return delay by 2 minutes timestamp - #25 by deng.shigang does get microseconds from using same API as we do.

Is there any time synchronization configuration we might have missed?

Rig file we used

{
    "version": 8,
    "rig": {
        "vehicleio": [],
        "sensors": [
            {
                "parameter": "camera-name=V1SIM728MPRU4120HD1, deserializer=MAX96724_Fusa_nv,interface=csi-gh,CPHY-mode=1,link=0,skip-eeprom=1,output-format=processed,file-buffer-size=16777216",
                "name": "camera:sample0",
                "properties": {
                    "height": "2168",
                    "Model": "ftheta",
                    "width": "3848",
                    "polynomial-type": "pixeldistance-to-angle",
                    "cy": "1096.686646",
                    "polynomial": "0.00000000000000 5.35356812179089e-4 4.99266072928606e-10 4.27370422037554e-12 -6.68245573791717e-16",
                    "cx": "1927.764404"
                },
                "nominalSensor2Rig_FLU": {
                    "roll-pitch-yaw": [
                        0.0,
                        0.0,
                        0.0
                    ],
                    "t": [
                        1.86210000514984,
                        -0.193900004029274,
                        1.31649994850159
                    ]
                },
                "protocol": "camera.gmsl"
            }
        ],
        "vehicle": {
            "valid": false
        }
    }
}
~        

Dear @MeowMeow ,
The current timestamp are TSC timestamps?
Let me repro the issue and share observation.

@SivaRamaKrishnaNV is there any update or do you need other information? :)

Have you been able to reproduce the observations @SivaRamaKrishnaNV ?

I will repro this week and update you.

Dear @MeowMeow ,
Could you share the full sample log?

CameraCustomSimpleApp.cpp.txt (42.5 KB)

log_0317.txt (331.7 KB)
I have uploaded the log and the modified sample code.
Please let me know if you need anything else!

Could you please share dwContext_getCurrentTime, tscEofTimestampUs, eofTimestampUs values in log?

CameraCustomSimpleApp.cpp.txt (42.8 KB)

log_0318.txt (1.0 MB)
like this?
So in our case the dwContext_getCurrentTime ~= (eofTimestampUs - tscEofTimestampUs) + eofTimestampUs * 0.03125

Can you share the log with single camera in rig file.

log_0320.txt (184.2 KB)

Here it is! Sorry for the inconvenience.

Dear @MeowMeow ,
I could reproduced the issue. Noticed that there is issue with eofTimestampUs timestamp conversion. It is fixed in future release.