Skip to content

Set DOM polling interval based on the time at the start of the loop instead of the end - #757

Merged
rustiqly merged 1 commit into
sonic-net:masterfrom
nexthop-ai:aditya-polling-interval-fix
Mar 13, 2026
Merged

Set DOM polling interval based on the time at the start of the loop instead of the end#757
rustiqly merged 1 commit into
sonic-net:masterfrom
nexthop-ai:aditya-polling-interval-fix

Conversation

@aditya-nexthop

Copy link
Copy Markdown
Contributor

Description

During profiling we found that there was a significant period of time when transceiver information was not being updated.
Upon study, it was seen that for DOM_INFO_UPDATE_PERIOD_SECS after the last transceiver in the loop was polled, there were no updates.

Motivation and Context

fixes #756
This improves DOM polling performance of transceivers in xcvrd and correctly ensures that DOM_INFO_UPDATE_PERIOD_SECS time elapses between updating a specific transceiver.

How Has This Been Tested?

We did a CPU profiling without and with the change over a 10 min window just after xcvrd starts
Before:
image
After:
image

The CPU is more uniformly utilized after the change instead of staying idle when more than DOM_INFO_UPDATE_PERIOD_SECS has already passed since a specific transceiver was polled.

Additional Information (Optional)

@mssonicbld

Copy link
Copy Markdown
Collaborator

/azp run

@azure-pipelines

Copy link
Copy Markdown
Azure Pipelines successfully started running 1 pipeline(s).

@aditya-nexthop
aditya-nexthop force-pushed the aditya-polling-interval-fix branch from b20422c to 1f21007 Compare February 20, 2026 02:03
@mssonicbld

Copy link
Copy Markdown
Collaborator

/azp run

@azure-pipelines

Copy link
Copy Markdown
Azure Pipelines successfully started running 1 pipeline(s).

…nstead of the end.

Signed-off-by: aditya-nexthop <aditya@nexthop.ai>
@aditya-nexthop
aditya-nexthop force-pushed the aditya-polling-interval-fix branch from 1f21007 to c1e6d5f Compare February 20, 2026 02:04
@mssonicbld

Copy link
Copy Markdown
Collaborator

/azp run

@azure-pipelines

Copy link
Copy Markdown
Azure Pipelines successfully started running 1 pipeline(s).

Copilot AI left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pull request overview

This PR adjusts the xcvrd DOM monitoring loop scheduling so the next DOM polling window is calculated from the timestamp at the start of the loop iteration, instead of from the time after all ports have been processed. This aligns the effective polling period with DOM_INFO_UPDATE_PERIOD_SECS per the expectation in issue #756 and reduces idle gaps after a full polling pass.

Changes:

  • Capture now at the beginning of each DOM monitoring loop iteration.
  • Use that loop-start timestamp to determine whether an update is due and to compute next_periodic_db_update_time.

Comment on lines +275 to +276
now = datetime.datetime.now()
if next_periodic_db_update_time <= now:

Copilot AI Mar 10, 2026

Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The new scheduling logic depends on capturing now at the start of the loop and using it to compute next_periodic_db_update_time. There isn’t currently a unit test that asserts this behavior for a non-zero DOM_INFO_UPDATE_PERIOD_SECS (e.g., by mocking datetime.datetime.now() to simulate a long per-iteration processing time and verifying the next update time is based on the loop-start timestamp, not the loop-end timestamp). Adding such a test would help prevent regressions to the original timing bug.

Copilot generated this review using guidance from repository custom instructions.

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@aditya-nexthop do you want to add this test?

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Unit test added in PR #758 in commit 305a41e

@prgeor
prgeor requested a review from mihirpat1 March 10, 2026 22:29

@mihirpat1 mihirpat1 left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@aditya-nexthop @prgeor This change looks correct for fixing the interval anchoring. However, a broader question: if each port takes ~1s to update DOM data and there are 64 ports, the loop takes ~64s per iteration. With DOM_INFO_UPDATE_PERIOD_SECS potentially shorter than that, are we okay with the loop running back-to-back with no sleep/yield? Could there be a concern about starving other tasks or excessive CPU usage in that scenario?

@aditya-nexthop

Copy link
Copy Markdown
Contributor Author

@aditya-nexthop @prgeor This change looks correct for fixing the interval anchoring. However, a broader question: if each port takes ~1s to update DOM data and there are 64 ports, the loop takes ~64s per iteration. With DOM_INFO_UPDATE_PERIOD_SECS potentially shorter than that, are we okay with the loop running back-to-back with no sleep/yield? Could there be a concern about starving other tasks or excessive CPU usage in that scenario?

Hi @mihirpat1, as per #758 the wait is primarily due to the time waiting for select to timeout.

We don't need to merge this PR if we merge #758 as #758 includes these changes.
I thought it useful to review the effect of this change as well as #758 independently to understand the impact.

I will close this PR once #758 merges.

@prgeor

prgeor commented Mar 11, 2026

Copy link
Copy Markdown
Collaborator

@aditya-nexthop @prgeor This change looks correct for fixing the interval anchoring. However, a broader question: if each port takes ~1s to update DOM data and there are 64 ports, the loop takes ~64s per iteration. With DOM_INFO_UPDATE_PERIOD_SECS potentially shorter than that, are we okay with the loop running back-to-back with no sleep/yield? Could there be a concern about starving other tasks or excessive CPU usage in that scenario?

@mihirpat1 in that case we may have to define DOM_INFO_UPDATE_PERIOD_SECS per platform basis? As the polling period of default 60 seconds does NOT work universally?

@mihirpat1

Copy link
Copy Markdown
Contributor

@aditya-nexthop @prgeor This change looks correct for fixing the interval anchoring. However, a broader question: if each port takes ~1s to update DOM data and there are 64 ports, the loop takes ~64s per iteration. With DOM_INFO_UPDATE_PERIOD_SECS potentially shorter than that, are we okay with the loop running back-to-back with no sleep/yield? Could there be a concern about starving other tasks or excessive CPU usage in that scenario?

@mihirpat1 in that case we may have to define DOM_INFO_UPDATE_PERIOD_SECS per platform basis? As the polling period of default 60 seconds does NOT work universally?

@prgeor That's correct - defining it per platform can help in addressing this.

@prgeor

prgeor commented Mar 12, 2026

Copy link
Copy Markdown
Collaborator

@aditya-nexthop can you make this a platform adjusted variable? DOM_INFO_UPDATE_PERIOD_SECS

@aditya-nexthop

Copy link
Copy Markdown
Contributor Author

@aditya-nexthop can you make this a platform adjusted variable? DOM_INFO_UPDATE_PERIOD_SECS

Yes, that's a good idea, created #774 to work on this in a new PR.

@rustiqly
rustiqly merged commit b85fff3 into sonic-net:master Mar 13, 2026
10 checks passed
@aditya-nexthop
aditya-nexthop deleted the aditya-polling-interval-fix branch March 13, 2026 20:38
mssonicbld added a commit that referenced this pull request Jul 29, 2026
…r transceiver DOM polling (#864)

<!-- Provide a general summary of your changes in the Title above -->

#### Description
This PR optimizes the DOM (Digital Optical Monitoring) polling loop in xcvrd by improving port update event handling and reducing unnecessary wait times. The changes include:

1. **Refactored port update handling** - Extracted port update event processing into a dedicated `check_port_update()` method for better code organization and reusability
2. **Optimized timeout strategy** - Introduced two-tier timeout mechanism:
 - 1000ms timeout when waiting for port updates before DOM polling begins and after when it completes until the next polling cycle
 - 100ms timeout during DOM polling to minimize delays while still handling port events
3. **Improved loop structure** - Restructured the main loop to handle port updates before entering the DOM polling phase, preventing unnecessary blocking
4. **Added comprehensive unit tests** - Created tests covering various scenarios including multiple ports, timing edge cases, and stop event handling

fixes #759 and builds on #757

#### Motivation and Context
Before the change, the DOM monitoring loop would wait up to 1 second (`SELECT_TIMEOUT_MSECS`) for port update events during each iteration of the physical port loop. This caused significant delays in DOM data collection, especially on systems with many ports.

**Problem:** With the 1-second timeout being called for every physical port, the DOM polling could take an excessive amount of time to complete, delaying DOM polling updates.

**Solution:** By separating port update handling from DOM polling and using a shorter 100ms timeout during the polling phase, the loop can complete much faster while still being responsive to port change events. The 1-second timeout is only used when explicitly waiting for port updates before starting the next DOM polling cycle.

#### How Has This Been Tested?
1. **Unit Tests Added** - Comprehensive test coverage for the new `check_port_update()` method including:
 - Scenario with no link change affected ports
 - Link change affected port with past timestamp (should trigger immediate update)
 - Link change affected port with future timestamp (should defer update)
 - Multiple ports with mixed ready/not-ready states
 - Stop event handling during processing

2. **CPU usage profiling**: Measured for 10 minutes after restarting `xcvrd` on a switch fully populated with optical transceivers.
- Before the change (includes changes from #757)
<img width="937" height="257" alt="image" src="https://github.com/user-attachments/assets/224dca27-c0fa-4059-b7b1-fdcd9a4ed66e" />
- After the change
<img width="934" height="249" alt="image" src="https://github.com/user-attachments/assets/8efa3d40-1e25-45c8-a48a-088d55ff34c3" />

The CPU usage is slightly higher during active polling as it spends less time waiting (100ms) between interfaces and then the loop spends time waiting for port change updates in 1s chunks.

3. **Measuring actual DOM update times**
- Before change: We are not able to poll every 60 seconds (takes 90 sec+) on a switch fully populated with optical transceivers
```
$ while true; do sonic-db-dump -n STATE_DB -y -k "TRANSCEIVER_DOM_SENSOR|Ethernet112" | grep last_update_time; sleep 10; done | uniq
 "last_update_time": "Tue Feb 24 19:25:57 2026",
 "last_update_time": "Tue Feb 24 19:27:32 2026",
 "last_update_time": "Tue Feb 24 19:29:06 2026",
 "last_update_time": "Tue Feb 24 19:30:40 2026",
 "last_update_time": "Tue Feb 24 19:32:13 2026",
 "last_update_time": "Tue Feb 24 19:33:47 2026",
```
- After change: Updates happen every 60 seconds for a specified interface
```
$ while true; do sonic-db-dump -n STATE_DB -y -k "TRANSCEIVER_DOM_SENSOR|Ethernet112" | grep last_update_time; sleep 10; done | uniq
 "last_update_time": "Tue Feb 24 19:17:09 2026",
 "last_update_time": "Tue Feb 24 19:18:10 2026",
 "last_update_time": "Tue Feb 24 19:19:10 2026",
 "last_update_time": "Tue Feb 24 19:20:10 2026",
 "last_update_time": "Tue Feb 24 19:21:11 2026",
 "last_update_time": "Tue Feb 24 19:22:11 2026",
```

#### Additional Information (Optional)
**Key Technical Changes:**
- New constants: `PORT_UPDATE_EVENT_SELECT_TIMEOUT_MSECS` (1000ms) and `PORT_UPDATE_EVENT_SELECT_TIMEOUT_FAST_MSECS` (100ms)
- Modified `PortChangeObserver.handle_port_update_event()` to accept a configurable timeout parameter
- The periodic update interval calculation now uses `dom_loop_start_time` to maintain consistent intervals regardless of loop execution time

**Backward Compatibility:** This change is fully backward compatible and does not affect the external API or configuration.

#### Tested branch
- [x] master
- [x] 202605: already in Nexthop's internal 202605 branch

Signed-off-by: Sonic Build Admin <sonicbld@microsoft.com>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

DomInfoUpdateTask polling period DOM_INFO_UPDATE_PERIOD_SECS improperly delays polling

6 participants