我想获得一个信号处理程序在C ++中工作,并不知道如何使用某些类的属性。
信号处理程序在接收到SIGIO信号时触发,我需要检查它是否是正确的套接字。
我所需要做的就是能够访问专用socket_
和public received()
。
namespace sigh { template<typename SomeType> class WorkWithSignals { public: void received( unsigned char* data, size_t len, unsigned int from ); private: static void sigio_handler ( int sig, siginfo_t* siginfo, void* empty ); int socket_; }; extern "C" { void sigio_handler ( int sig, siginfo_t* siginfo, void* empty ) { if (siginfo->si_fd == ***socket_*** ) ***received*** (); } } }
除此之外,我尝试在定义sigio_handler
之前定义一个静态结构variables,并将其填充到sigio_handler
之后定义的类构造函数中,但是sigio_handler
抱怨说它不在范围之内。
任何指针?
你不能从静态方法访问成员变量(只有没有对象)。 你也可以使你的socket_
一个静态变量,并通过WorkWithSignals<...>::socket_
引用它。
信号处理程序是一个静态方法,所以它不绑定到你的类的任何实例。
sigaction手册页包含段落(与siginfo_t参数有关):
* SIGPOLL/SIGIO fills in si_band and si_fd. The si_band event is a bit mask containing the same values as are filled in the revents field by poll(2). The si_fd field indicates the file descriptor for which the I/O event occurred.
假设你想继续使用当前的基于信号的设计(poll()可能更简单),我会建议一个静态的文件描述符映射到WorkWithSignals类的实例。
然后在静态信号处理程序中,查找与给定文件描述符(您的socket_字段)相关的实例,然后调用非静态方法来完成特定对象所需的工作。
到WorkWithSignals添加的decl
static std::map<int, WorkWithSignals*> object_registry_;
和源文件中需要的def。 在注册信号处理程序之前,通过添加到地图来管理地图中的成员身份,并在销毁对象之前从地图中删除。 然后:
void sigio_handler ( int sig, siginfo_t* siginfo, void* empty ) { std::map<int, WorkWithSignals*>::iterator it = object_registry_.find(siginfo->si_fd); if(it == object_registry_.end()) // handle error case assert(false); // Check that si_band is masked with the read flag as in the poll() call (look for revents) WorkWithSignals* obj = it->second; obj->received(); }