zeromq / cppzmq

Header-only C++ binding for libzmq
http://www.zeromq.org
MIT License
1.94k stars 757 forks source link

EINTR #525

Open xR3b0rn opened 2 years ago

xR3b0rn commented 2 years ago

When blocking system calls are interrupted by a user installed signal handler, Linux will abort the execution of the system call and returns EINTR.

The current implementation of recv in cppzmq only checks for EAGAIN, if zmq_recv returns something else, cppzmq throws an errro. I.e. cppzmq will throw an error when an user installed signal handler interrupts a blocking system call such as e.g. recv.

This behaviour is very annoying if you want clean up some stuff when an signal is sent.

A current workarround could be to catch the error and compare the error string. However, this feels not much like C++, so here are 3 proposals to improve this:

  1. Throw a different error in order to make it possible to distinguish the different kinds of errors
  2. Don't throw in case of EINTR and put the information into the result of cppzmq's recv-function
  3. Treat EINTR the same way EAGAIN is treated: Ignore it and return {}
gummif commented 2 years ago

The exception thrown is zmq::error_t, and has member function num() that can be used to get the error code, is that what you mean in 1 or something else?

xR3b0rn commented 2 years ago

I have to admit I was not aware of the num-function, however this does not differ much from my string comparsion approach, since I still have to catch the error, check the num and if it is not EINTR I have to rethrow. I think this is bad practice.

Hence I suggest to introduce a new type of error if 1. is preferred in order to make it possible to catch only the error I want to catch.