polyphony 0.59 → 0.62

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -25,6 +25,8 @@ void context_store_initialize(op_context_store_t *store) {
25
25
  store->last_id = 0;
26
26
  store->available = NULL;
27
27
  store->taken = NULL;
28
+ store->available_count = 0;
29
+ store->taken_count = 0;
28
30
  }
29
31
 
30
32
  inline op_context_t *context_store_acquire(op_context_store_t *store, enum op_type type) {
@@ -32,12 +34,12 @@ inline op_context_t *context_store_acquire(op_context_store_t *store, enum op_ty
32
34
  if (ctx) {
33
35
  if (ctx->next) ctx->next->prev = NULL;
34
36
  store->available = ctx->next;
37
+ store->available_count--;
35
38
  }
36
39
  else {
37
40
  ctx = malloc(sizeof(op_context_t));
38
41
  }
39
42
  ctx->id = (++store->last_id);
40
- // printf("acquire %p %d (%s)\n", ctx, ctx->id, op_type_to_str(type));
41
43
  ctx->prev = NULL;
42
44
  ctx->next = store->taken;
43
45
  if (store->taken) store->taken->prev = ctx;
@@ -49,6 +51,10 @@ inline op_context_t *context_store_acquire(op_context_store_t *store, enum op_ty
49
51
  ctx->ref_count = 2;
50
52
  ctx->result = 0;
51
53
 
54
+ store->taken_count++;
55
+
56
+ // printf("acquire %p %d (%s, ref_count: %d) taken: %d\n", ctx, ctx->id, op_type_to_str(type), ctx->ref_count, store->taken_count);
57
+
52
58
  return ctx;
53
59
  }
54
60
 
@@ -61,6 +67,9 @@ inline int context_store_release(op_context_store_t *store, op_context_t *ctx) {
61
67
  ctx->ref_count--;
62
68
  if (ctx->ref_count) return 0;
63
69
 
70
+ store->taken_count--;
71
+ store->available_count++;
72
+
64
73
  if (ctx->next) ctx->next->prev = ctx->prev;
65
74
  if (ctx->prev) ctx->prev->next = ctx->next;
66
75
  if (store->taken == ctx) store->taken = ctx->next;
@@ -22,7 +22,7 @@ typedef struct op_context {
22
22
  struct op_context *prev;
23
23
  struct op_context *next;
24
24
  enum op_type type: 16;
25
- unsigned int ref_count : 16;
25
+ unsigned int ref_count : 16;
26
26
  int id;
27
27
  int result;
28
28
  VALUE fiber;
@@ -31,8 +31,10 @@ typedef struct op_context {
31
31
 
32
32
  typedef struct op_context_store {
33
33
  int last_id;
34
- op_context_t *available;
35
- op_context_t *taken;
34
+ op_context_t *available;
35
+ op_context_t *taken;
36
+ int available_count;
37
+ int taken_count;
36
38
  } op_context_store_t;
37
39
 
38
40
  const char *op_type_to_str(enum op_type type);
@@ -164,6 +164,8 @@ inline VALUE Backend_poll(VALUE self, VALUE blocking) {
164
164
  Backend_t *backend;
165
165
  GetBackend(self, backend);
166
166
 
167
+ backend->base.poll_count++;
168
+
167
169
  COND_TRACE(&backend->base, 2, SYM_fiber_event_poll_enter, rb_fiber_current());
168
170
  backend->base.currently_polling = 1;
169
171
  ev_run(backend->ev_loop, blocking == Qtrue ? EVRUN_ONCE : EVRUN_NOWAIT);
@@ -211,15 +213,11 @@ VALUE Backend_wakeup(VALUE self) {
211
213
  return Qnil;
212
214
  }
213
215
 
214
- inline struct backend_stats Backend_stats(VALUE self) {
216
+ inline struct backend_stats backend_get_stats(VALUE self) {
215
217
  Backend_t *backend;
216
218
  GetBackend(self, backend);
217
219
 
218
- return (struct backend_stats){
219
- .scheduled_fibers = runqueue_len(&backend->base.runqueue),
220
- .waiting_fibers = 0,
221
- .pending_ops = backend->base.pending_count
222
- };
220
+ return backend_base_stats(&backend->base);
223
221
  }
224
222
 
225
223
  struct libev_io {
@@ -261,14 +259,20 @@ VALUE libev_wait_fd(Backend_t *backend, int fd, int events, int raise_exception)
261
259
  return switchpoint_result;
262
260
  }
263
261
 
264
- VALUE Backend_read(VALUE self, VALUE io, VALUE str, VALUE length, VALUE to_eof) {
262
+ VALUE Backend_read(VALUE self, VALUE io, VALUE str, VALUE length, VALUE to_eof, VALUE pos) {
265
263
  Backend_t *backend;
266
264
  struct libev_io watcher;
267
265
  rb_io_t *fptr;
268
266
  long dynamic_len = length == Qnil;
269
267
  long len = dynamic_len ? 4096 : NUM2INT(length);
270
- int shrinkable = io_setstrbuf(&str, len);
271
- char *buf = RSTRING_PTR(str);
268
+ long buf_pos = NUM2INT(pos);
269
+ if (str != Qnil) {
270
+ int current_len = RSTRING_LEN(str);
271
+ if (buf_pos < 0 || buf_pos > current_len) buf_pos = current_len;
272
+ }
273
+ else buf_pos = 0;
274
+ int shrinkable = io_setstrbuf(&str, buf_pos + len);
275
+ char *buf = RSTRING_PTR(str) + buf_pos;
272
276
  long total = 0;
273
277
  VALUE switchpoint_result = Qnil;
274
278
  int read_to_eof = RTEST(to_eof);
@@ -284,6 +288,7 @@ VALUE Backend_read(VALUE self, VALUE io, VALUE str, VALUE length, VALUE to_eof)
284
288
  OBJ_TAINT(str);
285
289
 
286
290
  while (1) {
291
+ backend->base.op_count++;
287
292
  ssize_t n = read(fptr->fd, buf, len - total);
288
293
  if (n < 0) {
289
294
  int e = errno;
@@ -304,9 +309,9 @@ VALUE Backend_read(VALUE self, VALUE io, VALUE str, VALUE length, VALUE to_eof)
304
309
  if (total == len) {
305
310
  if (!dynamic_len) break;
306
311
 
307
- rb_str_resize(str, total);
312
+ rb_str_resize(str, buf_pos + total);
308
313
  rb_str_modify_expand(str, len);
309
- buf = RSTRING_PTR(str) + total;
314
+ buf = RSTRING_PTR(str) + buf_pos + total;
310
315
  shrinkable = 0;
311
316
  len += len;
312
317
  }
@@ -314,7 +319,7 @@ VALUE Backend_read(VALUE self, VALUE io, VALUE str, VALUE length, VALUE to_eof)
314
319
  }
315
320
  }
316
321
 
317
- io_set_read_length(str, total, shrinkable);
322
+ io_set_read_length(str, buf_pos + total, shrinkable);
318
323
  io_enc_str(str, fptr);
319
324
 
320
325
  if (total == 0) return Qnil;
@@ -327,17 +332,17 @@ error:
327
332
  return RAISE_EXCEPTION(switchpoint_result);
328
333
  }
329
334
 
330
- VALUE Backend_recv(VALUE self, VALUE io, VALUE str, VALUE length) {
331
- return Backend_read(self, io, str, length, Qnil);
335
+ VALUE Backend_recv(VALUE self, VALUE io, VALUE str, VALUE length, VALUE pos) {
336
+ return Backend_read(self, io, str, length, Qnil, pos);
332
337
  }
333
338
 
334
- VALUE Backend_read_loop(VALUE self, VALUE io) {
339
+ VALUE Backend_read_loop(VALUE self, VALUE io, VALUE maxlen) {
335
340
  Backend_t *backend;
336
341
  struct libev_io watcher;
337
342
  rb_io_t *fptr;
338
343
  VALUE str;
339
344
  long total;
340
- long len = 8192;
345
+ long len = NUM2INT(maxlen);
341
346
  int shrinkable;
342
347
  char *buf;
343
348
  VALUE switchpoint_result = Qnil;
@@ -354,6 +359,7 @@ VALUE Backend_read_loop(VALUE self, VALUE io) {
354
359
  watcher.fiber = Qnil;
355
360
 
356
361
  while (1) {
362
+ backend->base.op_count++;
357
363
  ssize_t n = read(fptr->fd, buf, len);
358
364
  if (n < 0) {
359
365
  int e = errno;
@@ -406,6 +412,7 @@ VALUE Backend_feed_loop(VALUE self, VALUE io, VALUE receiver, VALUE method) {
406
412
  watcher.fiber = Qnil;
407
413
 
408
414
  while (1) {
415
+ backend->base.op_count++;
409
416
  ssize_t n = read(fptr->fd, buf, len);
410
417
  if (n < 0) {
411
418
  int e = errno;
@@ -453,6 +460,7 @@ VALUE Backend_write(VALUE self, VALUE io, VALUE str) {
453
460
  watcher.fiber = Qnil;
454
461
 
455
462
  while (left > 0) {
463
+ backend->base.op_count++;
456
464
  ssize_t n = write(fptr->fd, buf, left);
457
465
  if (n < 0) {
458
466
  int e = errno;
@@ -512,6 +520,7 @@ VALUE Backend_writev(VALUE self, VALUE io, int argc, VALUE *argv) {
512
520
  iov_ptr = iov;
513
521
 
514
522
  while (1) {
523
+ backend->base.op_count++;
515
524
  ssize_t n = writev(fptr->fd, iov_ptr, iov_count);
516
525
  if (n < 0) {
517
526
  int e = errno;
@@ -583,6 +592,7 @@ VALUE Backend_accept(VALUE self, VALUE server_socket, VALUE socket_class) {
583
592
  io_verify_blocking_mode(fptr, server_socket, Qfalse);
584
593
  watcher.fiber = Qnil;
585
594
  while (1) {
595
+ backend->base.op_count++;
586
596
  fd = accept(fptr->fd, &addr, &len);
587
597
  if (fd < 0) {
588
598
  int e = errno;
@@ -641,6 +651,7 @@ VALUE Backend_accept_loop(VALUE self, VALUE server_socket, VALUE socket_class) {
641
651
  watcher.fiber = Qnil;
642
652
 
643
653
  while (1) {
654
+ backend->base.op_count++;
644
655
  fd = accept(fptr->fd, &addr, &len);
645
656
  if (fd < 0) {
646
657
  int e = errno;
@@ -700,6 +711,7 @@ VALUE Backend_connect(VALUE self, VALUE sock, VALUE host, VALUE port) {
700
711
  addr.sin_addr.s_addr = inet_addr(host_buf);
701
712
  addr.sin_port = htons(NUM2INT(port));
702
713
 
714
+ backend->base.op_count++;
703
715
  int result = connect(fptr->fd, (struct sockaddr *)&addr, sizeof(addr));
704
716
  if (result < 0) {
705
717
  int e = errno;
@@ -740,6 +752,7 @@ VALUE Backend_send(VALUE self, VALUE io, VALUE str, VALUE flags) {
740
752
  watcher.fiber = Qnil;
741
753
 
742
754
  while (left > 0) {
755
+ backend->base.op_count++;
743
756
  ssize_t n = send(fptr->fd, buf, left, flags_int);
744
757
  if (n < 0) {
745
758
  int e = errno;
@@ -847,6 +860,7 @@ VALUE Backend_splice(VALUE self, VALUE src, VALUE dest, VALUE maxlen) {
847
860
 
848
861
  watcher.ctx.fiber = Qnil;
849
862
  while (1) {
863
+ backend->base.op_count++;
850
864
  len = splice(src_fptr->fd, 0, dest_fptr->fd, 0, NUM2INT(maxlen), 0);
851
865
  if (len < 0) {
852
866
  int e = errno;
@@ -898,6 +912,7 @@ VALUE Backend_splice_to_eof(VALUE self, VALUE src, VALUE dest, VALUE maxlen) {
898
912
 
899
913
  watcher.ctx.fiber = Qnil;
900
914
  while (1) {
915
+ backend->base.op_count++;
901
916
  len = splice(src_fptr->fd, 0, dest_fptr->fd, 0, NUM2INT(maxlen), 0);
902
917
  if (len < 0) {
903
918
  int e = errno;
@@ -957,6 +972,7 @@ VALUE Backend_fake_splice(VALUE self, VALUE src, VALUE dest, VALUE maxlen) {
957
972
  watcher.fiber = Qnil;
958
973
 
959
974
  while (1) {
975
+ backend->base.op_count++;
960
976
  ssize_t n = read(src_fptr->fd, buf, len);
961
977
  if (n < 0) {
962
978
  int e = errno;
@@ -972,6 +988,7 @@ VALUE Backend_fake_splice(VALUE self, VALUE src, VALUE dest, VALUE maxlen) {
972
988
  }
973
989
 
974
990
  while (left > 0) {
991
+ backend->base.op_count++;
975
992
  ssize_t n = write(dest_fptr->fd, buf, left);
976
993
  if (n < 0) {
977
994
  int e = errno;
@@ -1032,6 +1049,7 @@ VALUE Backend_fake_splice_to_eof(VALUE self, VALUE src, VALUE dest, VALUE maxlen
1032
1049
  while (1) {
1033
1050
  char *ptr = buf;
1034
1051
  while (1) {
1052
+ backend->base.op_count++;
1035
1053
  ssize_t n = read(src_fptr->fd, ptr, len);
1036
1054
  if (n < 0) {
1037
1055
  int e = errno;
@@ -1049,6 +1067,7 @@ VALUE Backend_fake_splice_to_eof(VALUE self, VALUE src, VALUE dest, VALUE maxlen
1049
1067
  }
1050
1068
 
1051
1069
  while (left > 0) {
1070
+ backend->base.op_count++;
1052
1071
  ssize_t n = write(dest_fptr->fd, ptr, left);
1053
1072
  if (n < 0) {
1054
1073
  int e = errno;
@@ -1088,6 +1107,7 @@ VALUE Backend_wait_io(VALUE self, VALUE io, VALUE write) {
1088
1107
  GetBackend(self, backend);
1089
1108
  GetOpenFile(io, fptr);
1090
1109
 
1110
+ backend->base.op_count++;
1091
1111
  return libev_wait_fd(backend, fptr->fd, events, 1);
1092
1112
  }
1093
1113
 
@@ -1111,6 +1131,7 @@ VALUE Backend_sleep(VALUE self, VALUE duration) {
1111
1131
  watcher.fiber = rb_fiber_current();
1112
1132
  ev_timer_init(&watcher.timer, Backend_timer_callback, NUM2DBL(duration), 0.);
1113
1133
  ev_timer_start(backend->ev_loop, &watcher.timer);
1134
+ backend->base.op_count++;
1114
1135
 
1115
1136
  switchpoint_result = backend_await((struct Backend_base *)backend);
1116
1137
 
@@ -1140,6 +1161,7 @@ noreturn VALUE Backend_timer_loop(VALUE self, VALUE interval) {
1140
1161
  VALUE switchpoint_result = Qnil;
1141
1162
  ev_timer_init(&watcher.timer, Backend_timer_callback, sleep_duration, 0.);
1142
1163
  ev_timer_start(backend->ev_loop, &watcher.timer);
1164
+ backend->base.op_count++;
1143
1165
  switchpoint_result = backend_await((struct Backend_base *)backend);
1144
1166
  ev_timer_stop(backend->ev_loop, &watcher.timer);
1145
1167
  RAISE_IF_EXCEPTION(switchpoint_result);
@@ -1191,6 +1213,7 @@ VALUE Backend_timeout(int argc,VALUE *argv, VALUE self) {
1191
1213
  watcher.resume_value = timeout;
1192
1214
  ev_timer_init(&watcher.timer, Backend_timeout_callback, NUM2DBL(duration), 0.);
1193
1215
  ev_timer_start(backend->ev_loop, &watcher.timer);
1216
+ backend->base.op_count++;
1194
1217
 
1195
1218
  struct Backend_timeout_ctx timeout_ctx = {backend, &watcher};
1196
1219
  result = rb_ensure(Backend_timeout_ensure_safe, Qnil, Backend_timeout_ensure, (VALUE)&timeout_ctx);
@@ -1213,6 +1236,7 @@ VALUE Backend_waitpid(VALUE self, VALUE pid) {
1213
1236
  if (fd >= 0) {
1214
1237
  Backend_t *backend;
1215
1238
  GetBackend(self, backend);
1239
+ backend->base.op_count++;
1216
1240
 
1217
1241
  VALUE resume_value = libev_wait_fd(backend, fd, EV_READ, 0);
1218
1242
  close(fd);
@@ -1256,6 +1280,7 @@ VALUE Backend_waitpid(VALUE self, VALUE pid) {
1256
1280
  watcher.fiber = rb_fiber_current();
1257
1281
  ev_child_init(&watcher.child, Backend_child_callback, NUM2INT(pid), 0);
1258
1282
  ev_child_start(backend->ev_loop, &watcher.child);
1283
+ backend->base.op_count++;
1259
1284
 
1260
1285
  switchpoint_result = backend_await((struct Backend_base *)backend);
1261
1286
 
@@ -1278,6 +1303,7 @@ VALUE Backend_wait_event(VALUE self, VALUE raise) {
1278
1303
 
1279
1304
  ev_async_init(&async, Backend_async_callback);
1280
1305
  ev_async_start(backend->ev_loop, &async);
1306
+ backend->base.op_count++;
1281
1307
 
1282
1308
  switchpoint_result = backend_await((struct Backend_base *)backend);
1283
1309
 
@@ -1341,6 +1367,7 @@ inline int splice_chunks_write(Backend_t *backend, int fd, VALUE str, struct lib
1341
1367
  int len = RSTRING_LEN(str);
1342
1368
  int left = len;
1343
1369
  while (left > 0) {
1370
+ backend->base.op_count++;
1344
1371
  ssize_t n = write(fd, buf, left);
1345
1372
  if (n < 0) {
1346
1373
  int err = errno;
@@ -1401,6 +1428,7 @@ VALUE Backend_splice_chunks(VALUE self, VALUE src, VALUE dest, VALUE prefix, VAL
1401
1428
  int chunk_len;
1402
1429
  // splice to pipe
1403
1430
  while (1) {
1431
+ backend->base.op_count++;
1404
1432
  chunk_len = splice(src_fptr->fd, 0, pipefd[1], 0, maxlen, 0);
1405
1433
  if (chunk_len < 0) {
1406
1434
  err = errno;
@@ -1426,6 +1454,7 @@ VALUE Backend_splice_chunks(VALUE self, VALUE src, VALUE dest, VALUE prefix, VAL
1426
1454
 
1427
1455
  int left = chunk_len;
1428
1456
  while (1) {
1457
+ backend->base.op_count++;
1429
1458
  int n = splice(pipefd[0], 0, dest_fptr->fd, 0, left, 0);
1430
1459
  if (n < 0) {
1431
1460
  err = errno;
@@ -1498,6 +1527,7 @@ void Init_Backend() {
1498
1527
  rb_define_method(cBackend, "post_fork", Backend_post_fork, 0);
1499
1528
  rb_define_method(cBackend, "trace", Backend_trace, -1);
1500
1529
  rb_define_method(cBackend, "trace_proc=", Backend_trace_proc_set, 1);
1530
+ rb_define_method(cBackend, "stats", Backend_stats, 0);
1501
1531
 
1502
1532
  rb_define_method(cBackend, "poll", Backend_poll, 1);
1503
1533
  rb_define_method(cBackend, "break", Backend_wakeup, 0);
@@ -1511,10 +1541,10 @@ void Init_Backend() {
1511
1541
  rb_define_method(cBackend, "accept_loop", Backend_accept_loop, 2);
1512
1542
  rb_define_method(cBackend, "connect", Backend_connect, 3);
1513
1543
  rb_define_method(cBackend, "feed_loop", Backend_feed_loop, 3);
1514
- rb_define_method(cBackend, "read", Backend_read, 4);
1515
- rb_define_method(cBackend, "read_loop", Backend_read_loop, 1);
1516
- rb_define_method(cBackend, "recv", Backend_recv, 3);
1517
- rb_define_method(cBackend, "recv_loop", Backend_read_loop, 1);
1544
+ rb_define_method(cBackend, "read", Backend_read, 5);
1545
+ rb_define_method(cBackend, "read_loop", Backend_read_loop, 2);
1546
+ rb_define_method(cBackend, "recv", Backend_recv, 4);
1547
+ rb_define_method(cBackend, "recv_loop", Backend_read_loop, 2);
1518
1548
  rb_define_method(cBackend, "recv_feed_loop", Backend_feed_loop, 3);
1519
1549
  rb_define_method(cBackend, "send", Backend_send, 3);
1520
1550
  rb_define_method(cBackend, "sendv", Backend_sendv, 3);
@@ -1540,6 +1570,8 @@ void Init_Backend() {
1540
1570
  SYM_send = ID2SYM(rb_intern("send"));
1541
1571
  SYM_splice = ID2SYM(rb_intern("splice"));
1542
1572
  SYM_write = ID2SYM(rb_intern("write"));
1573
+
1574
+ backend_setup_stats_symbols();
1543
1575
  }
1544
1576
 
1545
1577
  #endif // POLYPHONY_BACKEND_LIBEV
@@ -8,8 +8,8 @@ use_pidfd_open = false
8
8
  force_use_libev = ENV['POLYPHONY_USE_LIBEV'] != nil
9
9
  linux = RUBY_PLATFORM =~ /linux/
10
10
 
11
- if linux && `uname -sr` =~ /Linux 5\.([\d+])/
12
- kernel_minor_version = $1.gsub('.', '').to_i
11
+ if linux && `uname -sr` =~ /Linux 5\.(\d+)/
12
+ kernel_minor_version = $1.to_i
13
13
  use_liburing = !force_use_libev && kernel_minor_version >= 6
14
14
  use_pidfd_open = kernel_minor_version >= 3
15
15
  end
@@ -81,34 +81,6 @@ static VALUE Fiber_state(VALUE self) {
81
81
  return SYM_waiting;
82
82
  }
83
83
 
84
- VALUE Fiber_await(VALUE self) {
85
- VALUE result;
86
-
87
- // we compare with false, since a fiber that has not yet started will have
88
- // @running set to nil
89
- if (rb_ivar_get(self, ID_ivar_running) == Qfalse) {
90
- result = rb_ivar_get(self, ID_ivar_result);
91
- RAISE_IF_EXCEPTION(result);
92
- return result;
93
- }
94
-
95
- VALUE fiber = rb_fiber_current();
96
- VALUE waiting_fibers = rb_ivar_get(self, ID_ivar_waiting_fibers);
97
- if (waiting_fibers == Qnil) {
98
- waiting_fibers = rb_hash_new();
99
- rb_ivar_set(self, ID_ivar_waiting_fibers, waiting_fibers);
100
- }
101
- rb_hash_aset(waiting_fibers, fiber, Qtrue);
102
-
103
- VALUE backend = rb_ivar_get(rb_thread_current(), ID_ivar_backend);
104
- result = Backend_wait_event(backend, Qnil);
105
-
106
- rb_hash_delete(waiting_fibers, fiber);
107
- RAISE_IF_EXCEPTION(result);
108
- RB_GC_GUARD(result);
109
- return result;
110
- }
111
-
112
84
  VALUE Fiber_send(VALUE self, VALUE value) {
113
85
  VALUE mailbox = rb_ivar_get(self, ID_ivar_mailbox);
114
86
  if (mailbox == Qnil) {
@@ -125,7 +97,7 @@ VALUE Fiber_receive(VALUE self) {
125
97
  mailbox = rb_funcall(cQueue, ID_new, 0);
126
98
  rb_ivar_set(self, ID_ivar_mailbox, mailbox);
127
99
  }
128
- return Queue_shift(mailbox);
100
+ return Queue_shift(mailbox);
129
101
  }
130
102
 
131
103
  VALUE Fiber_mailbox(VALUE self) {
@@ -150,9 +122,6 @@ void Init_Fiber() {
150
122
  rb_define_method(cFiber, "state", Fiber_state, 0);
151
123
  rb_define_method(cFiber, "auto_watcher", Fiber_auto_watcher, 0);
152
124
 
153
- rb_define_method(cFiber, "await", Fiber_await, 0);
154
- rb_define_method(cFiber, "join", Fiber_await, 0);
155
-
156
125
  rb_define_method(cFiber, "<<", Fiber_send, 1);
157
126
  rb_define_method(cFiber, "send", Fiber_send, 1);
158
127
  rb_define_method(cFiber, "receive", Fiber_receive, 0);
@@ -58,20 +58,20 @@ VALUE Polyphony_backend_feed_loop(VALUE self, VALUE io, VALUE receiver, VALUE me
58
58
  return Backend_feed_loop(BACKEND(), io, receiver, method);
59
59
  }
60
60
 
61
- VALUE Polyphony_backend_read(VALUE self, VALUE io, VALUE str, VALUE length, VALUE to_eof) {
62
- return Backend_read(BACKEND(), io, str, length, to_eof);
61
+ VALUE Polyphony_backend_read(VALUE self, VALUE io, VALUE str, VALUE length, VALUE to_eof, VALUE pos) {
62
+ return Backend_read(BACKEND(), io, str, length, to_eof, pos);
63
63
  }
64
64
 
65
- VALUE Polyphony_backend_read_loop(VALUE self, VALUE io) {
66
- return Backend_read_loop(BACKEND(), io);
65
+ VALUE Polyphony_backend_read_loop(VALUE self, VALUE io, VALUE maxlen) {
66
+ return Backend_read_loop(BACKEND(), io, maxlen);
67
67
  }
68
68
 
69
- VALUE Polyphony_backend_recv(VALUE self, VALUE io, VALUE str, VALUE length) {
70
- return Backend_recv(BACKEND(), io, str, length);
69
+ VALUE Polyphony_backend_recv(VALUE self, VALUE io, VALUE str, VALUE length, VALUE pos) {
70
+ return Backend_recv(BACKEND(), io, str, length, pos);
71
71
  }
72
72
 
73
- VALUE Polyphony_backend_recv_loop(VALUE self, VALUE io) {
74
- return Backend_recv_loop(BACKEND(), io);
73
+ VALUE Polyphony_backend_recv_loop(VALUE self, VALUE io, VALUE maxlen) {
74
+ return Backend_recv_loop(BACKEND(), io, maxlen);
75
75
  }
76
76
 
77
77
  VALUE Polyphony_backend_recv_feed_loop(VALUE self, VALUE io, VALUE receiver, VALUE method) {
@@ -130,10 +130,10 @@ void Init_Polyphony() {
130
130
  rb_define_singleton_method(mPolyphony, "backend_accept_loop", Polyphony_backend_accept_loop, 2);
131
131
  rb_define_singleton_method(mPolyphony, "backend_connect", Polyphony_backend_connect, 3);
132
132
  rb_define_singleton_method(mPolyphony, "backend_feed_loop", Polyphony_backend_feed_loop, 3);
133
- rb_define_singleton_method(mPolyphony, "backend_read", Polyphony_backend_read, 4);
134
- rb_define_singleton_method(mPolyphony, "backend_read_loop", Polyphony_backend_read_loop, 1);
135
- rb_define_singleton_method(mPolyphony, "backend_recv", Polyphony_backend_recv, 3);
136
- rb_define_singleton_method(mPolyphony, "backend_recv_loop", Polyphony_backend_recv_loop, 1);
133
+ rb_define_singleton_method(mPolyphony, "backend_read", Polyphony_backend_read, 5);
134
+ rb_define_singleton_method(mPolyphony, "backend_read_loop", Polyphony_backend_read_loop, 2);
135
+ rb_define_singleton_method(mPolyphony, "backend_recv", Polyphony_backend_recv, 4);
136
+ rb_define_singleton_method(mPolyphony, "backend_recv_loop", Polyphony_backend_recv_loop, 2);
137
137
  rb_define_singleton_method(mPolyphony, "backend_recv_feed_loop", Polyphony_backend_recv_feed_loop, 3);
138
138
  rb_define_singleton_method(mPolyphony, "backend_send", Polyphony_backend_send, 3);
139
139
  rb_define_singleton_method(mPolyphony, "backend_sendv", Polyphony_backend_sendv, 3);