+ private int sys_setsockopt(int fdn, int level, int name, int valaddr, int len) throws ReadFaultException, ErrnoException {
+ SocketFD fd = getSocketFD(fdn);
+ switch(level) {
+ case SOL_SOCKET:
+ switch(name) {
+ case SO_REUSEADDR:
+ case SO_KEEPALIVE: {
+ if(len != 4) return -EINVAL;
+ int val = memRead(valaddr);
+ if(val != 0) fd.options |= name;
+ else fd.options &= ~name;
+ fd.setOptions();
+ return 0;
+ }
+ default:
+ if(STDERR_DIAG) System.err.println("Unknown setsockopt name passed: " + name);
+ return -ENOPROTOOPT;
+ }
+ default:
+ if(STDERR_DIAG) System.err.println("Unknown setsockopt leve passed: " + level);
+ return -ENOPROTOOPT;
+ }
+ }
+
+ private int sys_getsockopt(int fdn, int level, int name, int valaddr, int lenaddr) throws ErrnoException, FaultException {
+ SocketFD fd = getSocketFD(fdn);
+ switch(level) {
+ case SOL_SOCKET:
+ switch(name) {
+ case SO_REUSEADDR:
+ case SO_KEEPALIVE: {
+ int len = memRead(lenaddr);
+ if(len < 4) return -EINVAL;
+ int val = (fd.options & name) != 0 ? 1 : 0;
+ memWrite(valaddr,val);
+ memWrite(lenaddr,4);
+ return 0;
+ }
+ default:
+ if(STDERR_DIAG) System.err.println("Unknown setsockopt name passed: " + name);
+ return -ENOPROTOOPT;
+ }
+ default:
+ if(STDERR_DIAG) System.err.println("Unknown setsockopt leve passed: " + level);
+ return -ENOPROTOOPT;
+ }
+ }
+
+ private int sys_bind(int fdn, int addr, int namelen) throws FaultException, ErrnoException {
+ SocketFD fd = getSocketFD(fdn);
+
+ if(fd.type() == SocketFD.TYPE_STREAM && fd.o != null) return -EISCONN;
+ int word1 = memRead(addr);
+ if( ((word1 >>> 16)&0xff) != AF_INET) return -EAFNOSUPPORT;
+ int port = word1 & 0xffff;
+ InetAddress inetAddr = null;
+ if(memRead(addr+4) != 0) {
+ byte[] ip = new byte[4];
+ copyin(addr+4,ip,4);
+
+ try {
+ inetAddr = Platform.inetAddressFromBytes(ip);
+ } catch(UnknownHostException e) {
+ return -EADDRNOTAVAIL;
+ }
+ }
+
+ switch(fd.type()) {
+ case SocketFD.TYPE_STREAM: {
+ fd.bindAddr = inetAddr;
+ fd.bindPort = port;
+ return 0;
+ }
+ case SocketFD.TYPE_DGRAM: {
+ DatagramSocket s = (DatagramSocket) fd.o;
+ if(s != null) s.close();
+ try {
+ fd.o = inetAddr != null ? new DatagramSocket(port,inetAddr) : new DatagramSocket(port);
+ } catch(IOException e) {
+ return -EADDRINUSE;
+ }
+ return 0;
+ }
+ default:
+ throw new Error("should never happen");
+ }
+ }
+
+ private int sys_listen(int fdn, int backlog) throws ErrnoException {
+ SocketFD fd = getSocketFD(fdn);
+ if(fd.type() != SocketFD.TYPE_STREAM) return -EOPNOTSUPP;
+ if(fd.o != null) return -EISCONN;
+ if(fd.bindPort < 0) return -EOPNOTSUPP;
+