kcp 0.1.0 → 0.1.1
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.
- checksums.yaml +4 -4
- data/ext/kcp/kcp_native.c +39 -20
- data/lib/kcp/version.rb +1 -1
- data/lib/kcp.rb +6 -0
- metadata +1 -1
checksums.yaml
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
---
|
|
2
2
|
SHA256:
|
|
3
|
-
metadata.gz:
|
|
4
|
-
data.tar.gz:
|
|
3
|
+
metadata.gz: c7802d290ec502e834ab5f7eb1e9b4c7a4f664b677ecae6c6f001fce6be4cd3c
|
|
4
|
+
data.tar.gz: 58fc1060c2be20897078deb312bfd4e671a5d5dd72b9656205ee2ccf8cc6fa31
|
|
5
5
|
SHA512:
|
|
6
|
-
metadata.gz:
|
|
7
|
-
data.tar.gz:
|
|
6
|
+
metadata.gz: f01a77107b1821d1c32818c403982799e5a97b0dd214d6f9b8cb7e6419f1eb597849d31456f76abecadb75317d2a1a29bd85f3ea8694d88dcf57e2c6699d12d7
|
|
7
|
+
data.tar.gz: 2261acc0d59efcb3b94267a0b523e24fa9b036aa5ba7e18f52a2a857194051a94c1a2004d4ba1a993b7141e76e7ca9bfcae828ee7098c91aaaba66e2382b7edc
|
data/ext/kcp/kcp_native.c
CHANGED
|
@@ -8,25 +8,36 @@
|
|
|
8
8
|
#include <stdlib.h>
|
|
9
9
|
#include <string.h>
|
|
10
10
|
|
|
11
|
+
typedef struct {
|
|
12
|
+
char *data;
|
|
13
|
+
int len;
|
|
14
|
+
} kcp_pkt;
|
|
15
|
+
|
|
11
16
|
typedef struct {
|
|
12
17
|
ikcpcb *kcp;
|
|
13
|
-
|
|
14
|
-
int
|
|
15
|
-
int
|
|
18
|
+
kcp_pkt *pkts;
|
|
19
|
+
int count;
|
|
20
|
+
int cap;
|
|
16
21
|
} kcp_ctx;
|
|
17
22
|
|
|
18
|
-
/*
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
23
|
+
/* shim_output 每个 KCP 报文(≤ mtu)单独入队,output() 一次只取一个包,
|
|
24
|
+
避免把多个 KCP 报文拼成一个大 blob,导致上层封成单个超大 UDP 数据报被
|
|
25
|
+
IP 分片(分片常被 NAT/防火墙丢弃,造成远端云主机连接异常)。 */
|
|
22
26
|
static int shim_output(const char *buf, int len, ikcpcb *kcp, void *user) {
|
|
23
27
|
kcp_ctx *ctx = (kcp_ctx *)user;
|
|
24
|
-
if (ctx->
|
|
25
|
-
|
|
26
|
-
|
|
28
|
+
if (ctx->count >= ctx->cap) {
|
|
29
|
+
int newcap = ctx->cap ? ctx->cap * 2 : 32;
|
|
30
|
+
kcp_pkt *npkts = (kcp_pkt *)realloc(ctx->pkts, newcap * sizeof(kcp_pkt));
|
|
31
|
+
if (!npkts) return -1;
|
|
32
|
+
ctx->pkts = npkts;
|
|
33
|
+
ctx->cap = newcap;
|
|
27
34
|
}
|
|
28
|
-
|
|
29
|
-
|
|
35
|
+
kcp_pkt *p = &ctx->pkts[ctx->count];
|
|
36
|
+
p->data = (char *)malloc(len);
|
|
37
|
+
if (!p->data) return -1;
|
|
38
|
+
memcpy(p->data, buf, len);
|
|
39
|
+
p->len = len;
|
|
40
|
+
ctx->count++;
|
|
30
41
|
return 0;
|
|
31
42
|
}
|
|
32
43
|
|
|
@@ -34,7 +45,8 @@ static void ctx_free(void *ptr) {
|
|
|
34
45
|
kcp_ctx *ctx = (kcp_ctx *)ptr;
|
|
35
46
|
if (ctx) {
|
|
36
47
|
if (ctx->kcp) ikcp_release(ctx->kcp);
|
|
37
|
-
free(ctx->
|
|
48
|
+
for (int i = 0; i < ctx->count; i++) free(ctx->pkts[i].data);
|
|
49
|
+
free(ctx->pkts);
|
|
38
50
|
free(ctx);
|
|
39
51
|
}
|
|
40
52
|
}
|
|
@@ -108,17 +120,23 @@ static VALUE m_kcp_flush(VALUE mod, VALUE self) {
|
|
|
108
120
|
|
|
109
121
|
static VALUE m_kcp_output(VALUE mod, VALUE self) {
|
|
110
122
|
kcp_ctx *ctx = get_ctx(self);
|
|
111
|
-
if (ctx->
|
|
112
|
-
/*
|
|
113
|
-
|
|
114
|
-
VALUE buf = rb_str_new(
|
|
115
|
-
|
|
116
|
-
|
|
123
|
+
if (ctx->count <= 0) return Qnil;
|
|
124
|
+
/* 一次只返回一个 KCP 报文(≤ mtu),避免上层拼成超长 UDP 数据报触发 IP 分片 */
|
|
125
|
+
kcp_pkt p = ctx->pkts[0];
|
|
126
|
+
VALUE buf = rb_str_new(p.data, p.len);
|
|
127
|
+
free(p.data);
|
|
128
|
+
ctx->count--;
|
|
129
|
+
if (ctx->count > 0) {
|
|
130
|
+
memmove(&ctx->pkts[0], &ctx->pkts[1], ctx->count * sizeof(kcp_pkt));
|
|
117
131
|
}
|
|
118
|
-
ctx->outlen -= n;
|
|
119
132
|
return buf;
|
|
120
133
|
}
|
|
121
134
|
|
|
135
|
+
static VALUE m_kcp_setmtu(VALUE mod, VALUE self, VALUE mtu) {
|
|
136
|
+
kcp_ctx *ctx = get_ctx(self);
|
|
137
|
+
return INT2NUM(ikcp_setmtu(ctx->kcp, NUM2INT(mtu)));
|
|
138
|
+
}
|
|
139
|
+
|
|
122
140
|
static VALUE m_kcp_waitsnd(VALUE mod, VALUE self) {
|
|
123
141
|
kcp_ctx *ctx = get_ctx(self);
|
|
124
142
|
return INT2NUM(ikcp_waitsnd(ctx->kcp));
|
|
@@ -133,5 +151,6 @@ void Init_kcp_native(void) {
|
|
|
133
151
|
rb_define_singleton_method(m, "kcp_update", m_kcp_update, 2);
|
|
134
152
|
rb_define_singleton_method(m, "kcp_flush", m_kcp_flush, 1);
|
|
135
153
|
rb_define_singleton_method(m, "kcp_output", m_kcp_output, 1);
|
|
154
|
+
rb_define_singleton_method(m, "kcp_setmtu", m_kcp_setmtu, 2);
|
|
136
155
|
rb_define_singleton_method(m, "kcp_waitsnd", m_kcp_waitsnd, 1);
|
|
137
156
|
}
|
data/lib/kcp/version.rb
CHANGED
data/lib/kcp.rb
CHANGED
|
@@ -57,6 +57,12 @@ module Kcp
|
|
|
57
57
|
KcpNative.kcp_output(@ctx)
|
|
58
58
|
end
|
|
59
59
|
|
|
60
|
+
# 设置 KCP 内部 MTU(默认 1400)。上层如 mnet 会额外加自己的 header + GCM tag,
|
|
61
|
+
# 需要把 MTU 调小,保证「KCP 包 + 外层封装」仍小于路径 MTU,避免 IP 分片。
|
|
62
|
+
def mtu=(mtu)
|
|
63
|
+
KcpNative.kcp_setmtu(@ctx, mtu)
|
|
64
|
+
end
|
|
65
|
+
|
|
60
66
|
# 发送队列里待发送的包数(>0 表示窗口已满、有积压)。
|
|
61
67
|
def waitsnd
|
|
62
68
|
KcpNative.kcp_waitsnd(@ctx)
|