struct utcp_connection *c;
int dir = 3;
bool running = true;
+double dropin;
+double dropout;
-int do_recv(struct utcp_connection *c, void *data, size_t len) {
+ssize_t do_recv(struct utcp_connection *c, const void *data, size_t len) {
if(!data || !len) {
- if(errno)
+ if(errno) {
fprintf(stderr, "Error: %s\n", strerror(errno));
- else {
+ dir = 0;
+ } else {
dir &= ~2;
fprintf(stderr, "Connection closed by peer\n");
}
- return 0;
+ return -1;
}
- return write(0, data, len);
+ return write(1, data, len);
}
void do_accept(struct utcp_connection *nc, uint16_t port) {
c = nc;
}
-int do_send(struct utcp *utcp, void *data, size_t len) {
+ssize_t do_send(struct utcp *utcp, const void *data, size_t len) {
int s = *(int *)utcp->priv;
- return send(s, data, len, MSG_DONTWAIT);
+ if(drand48() >= dropout)
+ return send(s, data, len, MSG_DONTWAIT);
+ else
+ return len;
}
int main(int argc, char *argv[]) {
srand(time(NULL));
+ srand48(time(NULL));
if(argc < 2 || argc > 3)
return 1;
bool server = argc == 2;
bool connected = false;
+ dropin = atof(getenv("DROPIN") ?: "0");
+ dropout = atof(getenv("DROPOUT") ?: "0");
+
struct addrinfo *ai;
struct addrinfo hint = {
.ai_flags = server ? AI_PASSIVE : 0,
connected = true;
}
+ freeaddrinfo(ai);
+
struct utcp *u = utcp_init(server ? do_accept : NULL, NULL, do_send, &s);
if(!u)
return 1;
+ utcp_set_mtu(u, 1300);
+ utcp_set_user_timeout(u, 10);
+
if(!server)
c = utcp_connect(u, 1, do_recv, NULL);
{.fd = s, .events = POLLIN | POLLERR | POLLHUP},
};
- char buf[1024];
+ char buf[102400];
+ int timeout = utcp_timeout(u);
while(dir) {
- int r = poll(fds, 2, 1000);
- if(!r) {
- utcp_timeout(u);
- continue;
- }
+ poll(fds, 2, timeout);
if(fds[0].revents) {
int len = read(0, buf, sizeof buf);
if(fds[1].revents) {
struct sockaddr_storage ss;
- socklen_t sl;
+ socklen_t sl = sizeof ss;
int len = recvfrom(s, buf, sizeof buf, MSG_DONTWAIT, (struct sockaddr *)&ss, &sl);
if(len <= 0)
break;
if(!connected)
if(!connect(s, (struct sockaddr *)&ss, sl))
connected = true;
- utcp_recv(u, buf, len);
+ if(drand48() >= dropin)
+ utcp_recv(u, buf, len);
}
+
+ timeout = utcp_timeout(u);
};
utcp_close(c);