quahog
quahog copied to clipboard
Clamd sometimes returns a NULL response; should be handled
Quahog sometimes receives a NULL response from clamd, and this makes PHP throw a notice:
Undefined offset: 1 in vendor/blurgroup/quahog/src/Quahog/Client.php on line 211
I just encountered this myself. Here's a simple way to reproduce:
$client->scanStream('asdf');
$client->scanStream('asdf');
The problem appears to be that clamd is not expecting multiple commands on the same connection. Thus, Quahog always fails when multiple commands are issued. Here's another example that produces a different error:
$client->ping();
$client->ping();
The fix is to issue an IDSESSION
command before anything else, and close it with END
. That's easier said than done, though, because then clamd performs the commands asynchronously.
From the clamd man:
IDSESSION, END
It is mandatory to prefix this command with n or z, and all
commands inside IDSESSION must be prefixed.
Start/end a clamd session. Within a session multiple SCAN,
INSTREAM, FILDES, VERSION, STATS commands can be sent on the
same socket without opening new connections. Replies from clamd
will be in the form '<id>: <response>' where <id> is the request
number (in ascii, starting from 1) and <response> is the usual
clamd reply. The reply lines have same delimiter as the
corresponding command had. Clamd will process the commands
asynchronously, and reply as soon as it has finished processing.
So it should be possible to just wait for the correct reply (or error). Or even better, introduce an async mode with non blocking sockets like the docs suggest:
Clamd requires clients to read all the replies it sent, before
sending more commands to prevent send() deadlocks. The
recommended way to implement a client that uses IDSESSION is
with non-blocking sockets, and a select()/poll() loop: whenever
send would block, sleep in select/poll until either you can
write more data, or read more replies. Note that using non-
blocking sockets without the select/poll loop and alternating
recv()/send() doesn't comply with clamd's requirements.
Is the bug still there