Class: Event::Backend::EPoll
- Inherits:
-
Object
- Object
- Event::Backend::EPoll
- Defined in:
- ext/event/backend/epoll.c
Instance Method Summary collapse
- #initialize(loop) ⇒ Object constructor
- #io_wait(fiber, io, events) ⇒ Object
- #select(duration) ⇒ Object
Constructor Details
#initialize(loop) ⇒ Object
81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 |
# File 'ext/event/backend/epoll.c', line 81
VALUE Event_Backend_EPoll_initialize(VALUE self, VALUE loop) {
struct Event_Backend_EPoll *data = NULL;
TypedData_Get_Struct(self, struct Event_Backend_EPoll, &Event_Backend_EPoll_Type, data);
data->loop = loop;
int result = epoll_create1(EPOLL_CLOEXEC);
if (result == -1) {
rb_sys_fail("epoll_create");
} else {
data->descriptor = result;
rb_update_max_fd(data->descriptor);
}
return self;
}
|
Instance Method Details
#io_wait(fiber, io, events) ⇒ Object
154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 |
# File 'ext/event/backend/epoll.c', line 154
VALUE Event_Backend_EPoll_io_wait(VALUE self, VALUE fiber, VALUE io, VALUE events) {
struct Event_Backend_EPoll *data = NULL;
TypedData_Get_Struct(self, struct Event_Backend_EPoll, &Event_Backend_EPoll_Type, data);
struct epoll_event event = {0};
int descriptor = NUM2INT(rb_funcall(io, id_fileno, 0));
int duplicate = -1;
event.events = epoll_flags_from_events(NUM2INT(events));
event.data.ptr = (void*)fiber;
// fprintf(stderr, "<- fiber=%p descriptor=%d\n", (void*)fiber, descriptor);
// A better approach is to batch all changes:
int result = epoll_ctl(data->descriptor, EPOLL_CTL_ADD, descriptor, &event);
if (result == -1 && errno == EEXIST) {
// The file descriptor was already inserted into epoll.
duplicate = descriptor = dup(descriptor);
rb_update_max_fd(duplicate);
if (descriptor == -1)
rb_sys_fail("dup");
result = epoll_ctl(data->descriptor, EPOLL_CTL_ADD, descriptor, &event);
}
if (result == -1) {
rb_sys_fail("epoll_ctl");
}
struct io_wait_arguments io_wait_arguments = {
.data = data,
.descriptor = descriptor,
.duplicate = duplicate
};
return rb_ensure(io_wait_transfer, (VALUE)&io_wait_arguments, io_wait_ensure, (VALUE)&io_wait_arguments);
}
|
#select(duration) ⇒ Object
215 216 217 218 219 220 221 222 223 224 225 226 227 228 229 230 231 232 233 234 235 236 237 |
# File 'ext/event/backend/epoll.c', line 215
VALUE Event_Backend_EPoll_select(VALUE self, VALUE duration) {
struct Event_Backend_EPoll *data = NULL;
TypedData_Get_Struct(self, struct Event_Backend_EPoll, &Event_Backend_EPoll_Type, data);
struct epoll_event events[EPOLL_MAX_EVENTS];
int count = epoll_wait(data->descriptor, events, EPOLL_MAX_EVENTS, make_timeout(duration));
if (count == -1) {
rb_sys_fail("epoll_wait");
}
for (int i = 0; i < count; i += 1) {
VALUE fiber = (VALUE)events[i].data.ptr;
VALUE result = INT2NUM(events[i].events);
// fprintf(stderr, "-> fiber=%p descriptor=%d\n", (void*)fiber, events[i].data.fd);
rb_funcall(fiber, id_transfer, 1, result);
}
return INT2NUM(count);
}
|