They closed their socket without sending \n, yes. Shit happens in the real world; possibly encouraged by servers being generous in what they accept.
I guess I misread the code or your description of the protocol, sorry.
What are the tradeoffs of using sysread/syswrite vs. read/print? The obvious one is I have to implement my own line-oriented read for the first line of the protocol, which I have to read and parse. Is dropping down a level going to be of significant benefit, and if so in what?
I've been finding various strange returns from $sock->read(), including undef with $! empty. However, by taking a desperate leap and treating all errors except EINTR and EAGAIN as end-of-file, my proxy is now successfully passing data back and forth between test clients and real servers (next step will be to more aggressive test clients, and then real clients). For the proxy, treating a read error as EOF isn't really too bad a choice, clearly it's time to close that connection and terminate the proxy child!