CodeSOD: Efficiently Waiting

Alan was recently reviewing some of the scriptlets his company writes to publish their RPM installers. Some of the script quality has been… questionable in the past, so Alan wanted to do some code review.

In the uninstallation code, in the branch for AIX systems specifically, Alan found a block that needs to check that a service has successfully shut down. Since properly shutting down may take time, the check includes a pause- implemented in an unusual way.

until lssrc -s the-service-name-here | egrep 'inoperative|not'; do perl -e 'select(undef,undef,undef,.25)' done

This code calls into the Perl interpreter and executes the select command, which in this context wraps the select syscall, which is intended to allow a program to wait until a filehandle is available for I/O operations. In this case, the filehandle we're looking for is undef, so the only relevant parameter here is the last one- the timeout.

So this line waits for no file handle to be available, but no more than 0.25 seconds. It's a 250ms sleep. Which, notably, the AIX sleep utility doesn't support fractional seconds- so this is potentially 750ms more efficient than taking the obvious solution.

As Alan writes:

This code is obviously worried that re-testing for service shutdown once a second with a simple "sleep 1" might risk a serious waste of the user's time. It's just so much better not to be vulnerable to a 750ms window during which the user might be distracted by browsing a cat video. Naturally this is worth the creation of a dependency on a Perl interpreter which gets invoked in order to fake a millisecond sleep timer via (ab)use of a general I/O multiplexing facility!

[Advertisement] ProGet’s got you covered with security and access controls on your NuGet feeds. Learn more.

This post originally appeared on The Daily WTF.

Leave a Reply

Your email address will not be published.