Skip to content

Commit 841442b

Browse files
authored
network: implement net_select() for the Wii (#192)
poll() is generally more efficient and does not have a limitation on the number of file descriptors, but many libraries and programs out there still use select(), so let's make it easier to port them too.
1 parent 8b2e6bc commit 841442b

1 file changed

Lines changed: 48 additions & 2 deletions

File tree

libogc/network_wii.c

Lines changed: 48 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1062,8 +1062,54 @@ s32 net_close(s32 s)
10621062

10631063
s32 net_select(s32 maxfdp1, fd_set *readset, fd_set *writeset, fd_set *exceptset, struct timeval *timeout)
10641064
{
1065-
// not yet implemented
1066-
return -EINVAL;
1065+
struct pollsd sds[FD_SETSIZE];
1066+
int i, n_sds = 0;
1067+
s32 timeout_msecs;
1068+
s32 ret;
1069+
1070+
memset(sds, 0, sizeof(sds));
1071+
for (i = 0; i < maxfdp1; i++) {
1072+
bool watched = false;
1073+
1074+
if (readset && FD_ISSET(i, readset)) {
1075+
sds[n_sds].events |= POLLIN;
1076+
watched = true;
1077+
}
1078+
if (writeset && FD_ISSET(i, writeset)) {
1079+
sds[n_sds].events |= POLLOUT;
1080+
watched = true;
1081+
}
1082+
if (exceptset && FD_ISSET(i, exceptset)) {
1083+
sds[n_sds].events |= POLLPRI;
1084+
watched = true;
1085+
}
1086+
1087+
if (watched) {
1088+
sds[n_sds++].socket = i;
1089+
}
1090+
}
1091+
1092+
timeout_msecs = timeout->tv_sec * 1000 + timeout->tv_usec / 1000;
1093+
ret = net_poll(sds, n_sds, timeout_msecs);
1094+
if (ret <= 0) return ret;
1095+
1096+
ret = 0; /* Return the total number of 1 bits in the three fd sets */
1097+
for (i = 0; i < n_sds; i++) {
1098+
u8 fd = sds[i].socket;
1099+
if (sds[i].events & POLLIN) {
1100+
if (sds[i].revents & POLLIN) ret++;
1101+
else FD_CLR(fd, readset);
1102+
}
1103+
if (sds[i].events & POLLOUT) {
1104+
if (sds[i].revents & POLLOUT) ret++;
1105+
else FD_CLR(fd, writeset);
1106+
}
1107+
if (sds[i].events & POLLPRI) {
1108+
if (sds[i].revents & (POLLERR | POLLPRI | POLLHUP)) ret++;
1109+
else FD_CLR(fd, exceptset);
1110+
}
1111+
}
1112+
return ret;
10671113
}
10681114

10691115
s32 net_setsockopt(s32 s, u32 level, u32 optname, const void *optval, socklen_t optlen)

0 commit comments

Comments
 (0)