Skip to content

odhcpd: fix infinite loop on recvmsg error - #403

Open
pandax381 wants to merge 1 commit into
openwrt:masterfrom
pandax381:fix_recvmsg_error_handling
Open

odhcpd: fix infinite loop on recvmsg error#403
pandax381 wants to merge 1 commit into
openwrt:masterfrom
pandax381:fix_recvmsg_error_handling

Conversation

@pandax381

Copy link
Copy Markdown

Description

This PR fixes an issue where odhcpd can enter an infinite loop and consume 100% CPU when recvmsg() encounters an error other than EAGAIN (such as EBADF).

Background

We observed that the odhcpd process was pinning a specific CPU core at 100% utilization.

Investigating the running process with strace revealed that recvmsg() was being called continuously in a tight loop, relentlessly returning EBADF (Bad file descriptor) because the file descriptor had become invalid (-1).

strace -f -c output:

% time     seconds  usecs/call     calls    errors syscall
------ ----------- ----------- --------- --------- ----------------
100.00    1.069867           1    762638    762638 recvmsg
------ ----------- ----------- --------- --------- ----------------
100.00    1.069867           1    762638    762638 total

strace -f -e trace=recvmsg output:

recvmsg(-1, {msg_namelen=28}, MSG_DONTWAIT) = -1 EBADF (Bad file descriptor)
recvmsg(-1, {msg_namelen=28}, MSG_DONTWAIT) = -1 EBADF (Bad file descriptor)
recvmsg(-1, {msg_namelen=28}, MSG_DONTWAIT) = -1 EBADF (Bad file descriptor)
...

The root cause was that when recvmsg() failed with a non-EAGAIN error, the loop inside odhcpd_receive_packets() would continue indefinitely instead of breaking out.

Changes

  • Modify the error handling in odhcpd_receive_packets() to also break out of the loop when a non-EAGAIN error occurs.
  • Add unexpected recvmsg failure logging via error().
  • Handle EINTR by continuing the loop to prevent premature termination on signal interrupts.

When recvmsg() encounters an error other than EAGAIN, the loop
previously continued indefinitely, causing an infinite loop. Fix this by
also breaking out of the loop when a non-EAGAIN error occurs. Also add
error logging for unexpected recvmsg failures and EINTR handling.

Signed-off-by: YAMAMOTO Masaya <pandax381@gmail.com>
@pandax381

Copy link
Copy Markdown
Author

@Noltari Sorry to ping you directly — would you have a moment to review this when you get a chance? Happy to make any changes if needed. Thanks!

@pandax381

Copy link
Copy Markdown
Author

@hauke Sorry to reach out directly. Would you have a moment to take a look at this, or point me to the right person to review it? Happy to make any changes if needed. Thanks!

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.

1 participant