summaryrefslogtreecommitdiff
path: root/icmpd.c
diff options
context:
space:
mode:
Diffstat (limited to 'icmpd.c')
-rw-r--r--icmpd.c59
1 files changed, 48 insertions, 11 deletions
diff --git a/icmpd.c b/icmpd.c
index e3127c7..1cfc051 100644
--- a/icmpd.c
+++ b/icmpd.c
@@ -14,20 +14,21 @@
struct icmpd {
- struct mt_mutex mut; // for this struct
+ // CONSTANTS
- bool isserver; // constant
+ bool isserver;
+ uint32_t other_addr; // IPv4 address of other party
+ int id; // id for messages, -1 if not set
+ int signal_out, signal_in; // 1 byte can be read from signal_out for every message received
- // IPv4 address of other party
- uint32_t other_addr; // constant
+ // VARIABLES
- bool outstanding; // server: whether an echo request hasn't been matched yet
+ struct mt_mutex mut; // for the variables in this struct
- // id for messages, -1 if not set
- int id; // constant
+ bool outstanding; // server: whether an echo request hasn't been matched yet
- // Client: seqnum can change before every send
- // Server: seqnum is the sequence number of the last-received ECHO
+ // client: seqnum can change before every send
+ // server: seqnum is the sequence number of the last-received ECHO
// value is -1 if not set
int seqnum;
};
@@ -338,6 +339,9 @@ static void* thread_entry(void *arg) {
recvqu[recvqu_len].msg.seqnum = msg.seqnum;
recvqu_len++;
+ char c = 42;
+ assert(writeall(d->signal_in, &c, 1) == 1);
+
fprintf(stderr, "server recv: recvqu_len = %zu\n", recvqu_len);
}
@@ -391,6 +395,9 @@ static void* thread_entry(void *arg) {
recvqu[recvqu_len].msg.seqnum = msg.seqnum;
recvqu_len++;
+ char c = 42;
+ assert(writeall(d->signal_in, &c, 1) == 1);
+
fprintf(stderr, "client recv: recvqu_len = %zu\n", recvqu_len);
mt_mutex_lock(&d->mut);
@@ -437,12 +444,17 @@ static struct icmpd* icmpd_create_base(int id, bool isserver, uint32_t other_add
struct icmpd *d = malloc(sizeof(struct icmpd));
mt_mutex_init(&d->mut);
- d->id = id;
- d->seqnum = -1;
d->isserver = isserver;
d->other_addr = other_addr;
+ d->id = id;
+ d->seqnum = -1;
d->outstanding = false;
+ int pp[2];
+ assert(pipe(pp) == 0);
+ d->signal_in = pp[1];
+ d->signal_out = pp[0];
+
send_message(host_out, MSG_NEWCONN, &d, sizeof d);
return d;
@@ -471,6 +483,7 @@ void icmpd_server_set_outstanding(struct icmpd *d, int seqnum) {
}
bool icmpd_peek(struct icmpd *d) {
+#if 0
send_message(host_out, MSG_PEEK, &d, sizeof d);
struct msg_in msg = recv_message(host_in);
assert(msg.hdr.type == MSG_PEEK_ANS);
@@ -478,10 +491,30 @@ bool icmpd_peek(struct icmpd *d) {
bool ret = ((uint8_t*)msg.data)[0];
free(msg.data);
return ret;
+#else
+ fd_set inset;
+ FD_ZERO(&inset);
+ FD_SET(d->signal_out, &inset);
+ while (true) {
+ struct timeval tv;
+ tv.tv_sec = tv.tv_usec = 0;
+ int ret = select(d->signal_out + 1, &inset, NULL, NULL, &tv);
+ if (ret < 0) {
+ if (errno == EINTR) continue;
+ perror("select");
+ assert(false);
+ }
+ return ret > 0;
+ }
+#endif
}
struct icmpd_received icmpd_recv(struct icmpd *d) {
send_message(host_out, MSG_RECV, &d, sizeof d);
+
+ char c;
+ assert(readall(d->signal_out, &c, 1) == 1);
+
struct msg_in msg = recv_message(host_in);
assert(msg.hdr.type == MSG_RECV_ANS);
@@ -500,3 +533,7 @@ void icmpd_send(struct icmpd *d, const void *data, size_t length) {
send_message(host_out, MSG_SEND, &form, sizeof form);
}
+
+int icmpd_get_select_fd(struct icmpd *d) {
+ return d->signal_out;
+}