| OLD | NEW |
| 1 // Copyright (c) 2014, the Fletch project authors. Please see the AUTHORS file | 1 // Copyright (c) 2014, the Fletch project authors. Please see the AUTHORS file |
| 2 // for details. All rights reserved. Use of this source code is governed by a | 2 // for details. All rights reserved. Use of this source code is governed by a |
| 3 // BSD-style license that can be found in the LICENSE.md file. | 3 // BSD-style license that can be found in the LICENSE.md file. |
| 4 | 4 |
| 5 part of system; | 5 part of system; |
| 6 | 6 |
| 7 const int AF_INET = 2; | 7 const int AF_INET = 2; |
| 8 const int AF_INET6 = 10; | 8 const int AF_INET6 = 10; |
| 9 | 9 |
| 10 const int SOCK_STREAM = 1; | 10 const int SOCK_STREAM = 1; |
| (...skipping 38 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 49 int get _addrlenOffset => 16; | 49 int get _addrlenOffset => 16; |
| 50 | 50 |
| 51 int get ai_flags => getInt32(0); | 51 int get ai_flags => getInt32(0); |
| 52 int get ai_family => getInt32(4); | 52 int get ai_family => getInt32(4); |
| 53 void set ai_family(int value) { setInt32(4, value); } | 53 void set ai_family(int value) { setInt32(4, value); } |
| 54 int get ai_socktype => getInt32(8); | 54 int get ai_socktype => getInt32(8); |
| 55 int get ai_protocol => getInt32(12); | 55 int get ai_protocol => getInt32(12); |
| 56 | 56 |
| 57 int get ai_addrlen => getInt32(_addrlenOffset); | 57 int get ai_addrlen => getInt32(_addrlenOffset); |
| 58 | 58 |
| 59 Foreign get ai_addr; | 59 ForeignMemory get ai_addr; |
| 60 get ai_canonname; | 60 get ai_canonname; |
| 61 AddrInfo get ai_next; | 61 AddrInfo get ai_next; |
| 62 } | 62 } |
| 63 | 63 |
| 64 abstract class PosixSystem implements System { | 64 abstract class PosixSystem implements System { |
| 65 static final Foreign _accept = Foreign.lookup("accept"); | 65 static final ForeignFunction _accept = |
| 66 static final Foreign _access = Foreign.lookup("access"); | 66 ForeignLibrary.main.lookup("accept"); |
| 67 static final Foreign _bind = Foreign.lookup("bind"); | 67 static final ForeignFunction _access = |
| 68 static final Foreign _close = Foreign.lookup("close"); | 68 ForeignLibrary.main.lookup("access"); |
| 69 static final Foreign _connect = Foreign.lookup("connect"); | 69 static final ForeignFunction _bind = |
| 70 static final Foreign _fcntl = Foreign.lookup("fcntl"); | 70 ForeignLibrary.main.lookup("bind"); |
| 71 static final Foreign _freeaddrinfo = Foreign.lookup("freeaddrinfo"); | 71 static final ForeignFunction _close = |
| 72 static final Foreign _getaddrinfo = Foreign.lookup("getaddrinfo"); | 72 ForeignLibrary.main.lookup("close"); |
| 73 static final Foreign _getsockname = Foreign.lookup("getsockname"); | 73 static final ForeignFunction _connect = |
| 74 static final Foreign _ioctl = Foreign.lookup("ioctl"); | 74 ForeignLibrary.main.lookup("connect"); |
| 75 static final Foreign _listen = Foreign.lookup("listen"); | 75 static final ForeignFunction _fcntl = |
| 76 static final Foreign _memcpy = Foreign.lookup("memcpy"); | 76 ForeignLibrary.main.lookup("fcntl"); |
| 77 static final Foreign _mkstemp = Foreign.lookup("mkstemp"); | 77 static final ForeignFunction _freeaddrinfo = |
| 78 static final Foreign _nanosleep = Foreign.lookup("nanosleep"); | 78 ForeignLibrary.main.lookup("freeaddrinfo"); |
| 79 static final Foreign _read = Foreign.lookup("read"); | 79 static final ForeignFunction _getaddrinfo = |
| 80 static final Foreign _setsockopt = Foreign.lookup("setsockopt"); | 80 ForeignLibrary.main.lookup("getaddrinfo"); |
| 81 static final Foreign _shutdown = Foreign.lookup("shutdown"); | 81 static final ForeignFunction _getsockname = |
| 82 static final Foreign _socket = Foreign.lookup("socket"); | 82 ForeignLibrary.main.lookup("getsockname"); |
| 83 static final Foreign _unlink = Foreign.lookup("unlink"); | 83 static final ForeignFunction _ioctl = |
| 84 static final Foreign _write = Foreign.lookup("write"); | 84 ForeignLibrary.main.lookup("ioctl"); |
| 85 static final ForeignFunction _listen = |
| 86 ForeignLibrary.main.lookup("listen"); |
| 87 static final ForeignFunction _memcpy = |
| 88 ForeignLibrary.main.lookup("memcpy"); |
| 89 static final ForeignFunction _mkstemp = |
| 90 ForeignLibrary.main.lookup("mkstemp"); |
| 91 static final ForeignFunction _nanosleep = |
| 92 ForeignLibrary.main.lookup("nanosleep"); |
| 93 static final ForeignFunction _read = |
| 94 ForeignLibrary.main.lookup("read"); |
| 95 static final ForeignFunction _setsockopt = |
| 96 ForeignLibrary.main.lookup("setsockopt"); |
| 97 static final ForeignFunction _shutdown = |
| 98 ForeignLibrary.main.lookup("shutdown"); |
| 99 static final ForeignFunction _socket = |
| 100 ForeignLibrary.main.lookup("socket"); |
| 101 static final ForeignFunction _unlink = |
| 102 ForeignLibrary.main.lookup("unlink"); |
| 103 static final ForeignFunction _write = |
| 104 ForeignLibrary.main.lookup("write"); |
| 85 | 105 |
| 86 int get FIONREAD; | 106 int get FIONREAD; |
| 87 | 107 |
| 88 int get SOL_SOCKET; | 108 int get SOL_SOCKET; |
| 89 | 109 |
| 90 int get SO_REUSEADDR; | 110 int get SO_REUSEADDR; |
| 91 | 111 |
| 92 Foreign get _open; | 112 ForeignFunction get _open; |
| 93 Foreign get _lseek; | 113 ForeignFunction get _lseek; |
| 94 | 114 |
| 95 int socket() { | 115 int socket() { |
| 96 return _retry(() => _socket.icall$3(AF_INET, SOCK_STREAM, 0)); | 116 return _retry(() => _socket.icall$3(AF_INET, SOCK_STREAM, 0)); |
| 97 } | 117 } |
| 98 | 118 |
| 99 InternetAddress lookup(String host) { | 119 InternetAddress lookup(String host) { |
| 100 Foreign node = new Foreign.fromString(host); | 120 ForeignMemory node = new ForeignMemory.fromString(host); |
| 101 // TODO(ajohnsen): Actually apply hints. | 121 // TODO(ajohnsen): Actually apply hints. |
| 102 AddrInfo hints = new AddrInfo(); | 122 AddrInfo hints = new AddrInfo(); |
| 103 // TODO(ajohnsen): Allow IPv6 results. | 123 // TODO(ajohnsen): Allow IPv6 results. |
| 104 hints.ai_family = AF_INET; | 124 hints.ai_family = AF_INET; |
| 105 Struct result = new Struct(1); | 125 Struct result = new Struct(1); |
| 106 int status = _retry(() => _getaddrinfo.icall$4(node, | 126 int status = _retry(() => _getaddrinfo.icall$4(node, |
| 107 Foreign.NULL, | 127 ForeignPointer.NULL, |
| 108 hints, | 128 hints, |
| 109 result)); | 129 result)); |
| 110 AddrInfo start = new AddrInfo.fromAddress(result.getField(0)); | 130 AddrInfo start = new AddrInfo.fromAddress(result.getField(0)); |
| 111 AddrInfo info = start; | 131 AddrInfo info = start; |
| 112 var address; | 132 var address; |
| 113 while (info.value != 0) { | 133 while (info.address != 0) { |
| 114 int length; | 134 int length; |
| 115 int offset; | 135 int offset; |
| 116 // Loop until we find the right type. | 136 // Loop until we find the right type. |
| 117 if (info.ai_family == AF_INET) { | 137 if (info.ai_family == AF_INET) { |
| 118 length = 4; | 138 length = 4; |
| 119 offset = 4; | 139 offset = 4; |
| 120 } else if (info.ai_family == AF_INET6) { | 140 } else if (info.ai_family == AF_INET6) { |
| 121 length = 16; | 141 length = 16; |
| 122 offset = 8; | 142 offset = 8; |
| 123 } else { | 143 } else { |
| 124 info = info.ai_next; | 144 info = info.ai_next; |
| 125 continue; | 145 continue; |
| 126 } | 146 } |
| 127 Foreign addr = info.ai_addr; | 147 ForeignMemory addr = info.ai_addr; |
| 128 List<int> bytes = new List<int>(length); | 148 List<int> bytes = new List<int>(length); |
| 129 addr.copyBytesToList(bytes, offset, offset + length, 0); | 149 addr.copyBytesToList(bytes, offset, offset + length, 0); |
| 130 address = new _InternetAddress(bytes); | 150 address = new _InternetAddress(bytes); |
| 131 break; | 151 break; |
| 132 } | 152 } |
| 133 _freeaddrinfo.icall$1(start); | 153 _freeaddrinfo.icall$1(start); |
| 134 node.free(); | 154 node.free(); |
| 135 hints.free(); | 155 hints.free(); |
| 136 result.free(); | 156 result.free(); |
| 137 if (status != 0) throw "Failed to call 'getaddrinfo': ${errno()}"; | 157 if (status != 0) throw "Failed to call 'getaddrinfo': ${errno()}"; |
| 138 return address; | 158 return address; |
| 139 } | 159 } |
| 140 | 160 |
| 141 int open(String path, bool write, bool append) { | 161 int open(String path, bool write, bool append) { |
| 142 int flags = O_RDONLY; | 162 int flags = O_RDONLY; |
| 143 if (write || append) { | 163 if (write || append) { |
| 144 flags = O_RDWR | O_CREAT; | 164 flags = O_RDWR | O_CREAT; |
| 145 if (append) flags = flags | O_TRUNC; | 165 if (append) flags = flags | O_TRUNC; |
| 146 } | 166 } |
| 147 flags |= O_CLOEXEC; | 167 flags |= O_CLOEXEC; |
| 148 Foreign cPath = new Foreign.fromString(path); | 168 ForeignMemory cPath = new ForeignMemory.fromString(path); |
| 149 int fd = _retry(() => _open.icall$2(cPath, flags)); | 169 int fd = _retry(() => _open.icall$2(cPath, flags)); |
| 150 cPath.free(); | 170 cPath.free(); |
| 151 return fd; | 171 return fd; |
| 152 } | 172 } |
| 153 | 173 |
| 154 int lseek(int fd, int offset, int whence) { | 174 int lseek(int fd, int offset, int whence) { |
| 155 return _retry(() => _lseek.Lcall$wLw(fd, offset, whence)); | 175 return _retry(() => _lseek.Lcall$wLw(fd, offset, whence)); |
| 156 } | 176 } |
| 157 | 177 |
| 158 TempFile mkstemp(String path) { | 178 TempFile mkstemp(String path) { |
| 159 Foreign cPath = new Foreign.fromString(path + "XXXXXX"); | 179 ForeignMemory cPath = new ForeignMemory.fromString(path + "XXXXXX"); |
| 160 int result = _retry(() => _mkstemp.icall$1(cPath)); | 180 int result = _retry(() => _mkstemp.icall$1(cPath)); |
| 161 if (result != -1) { | 181 if (result != -1) { |
| 162 var bytes = new List(cPath.length - 1); | 182 var bytes = new List(cPath.length - 1); |
| 163 cPath.copyBytesToList(bytes, 0, cPath.length - 1, 0); | 183 cPath.copyBytesToList(bytes, 0, cPath.length - 1, 0); |
| 164 path = new String.fromCharCodes(bytes); | 184 path = new String.fromCharCodes(bytes); |
| 165 } | 185 } |
| 166 cPath.free(); | 186 cPath.free(); |
| 167 return new TempFile(result, path); | 187 return new TempFile(result, path); |
| 168 } | 188 } |
| 169 | 189 |
| 170 int access(String path) { | 190 int access(String path) { |
| 171 Foreign cPath = new Foreign.fromString(path); | 191 ForeignMemory cPath = new ForeignMemory.fromString(path); |
| 172 int result = _retry(() => _access.icall$2(cPath, 0)); | 192 int result = _retry(() => _access.icall$2(cPath, 0)); |
| 173 cPath.free(); | 193 cPath.free(); |
| 174 return result; | 194 return result; |
| 175 } | 195 } |
| 176 | 196 |
| 177 int unlink(String path) { | 197 int unlink(String path) { |
| 178 Foreign cPath = new Foreign.fromString(path); | 198 ForeignMemory cPath = new ForeignMemory.fromString(path); |
| 179 int result = _retry(() => _unlink.icall$1(cPath)); | 199 int result = _retry(() => _unlink.icall$1(cPath)); |
| 180 cPath.free(); | 200 cPath.free(); |
| 181 return result; | 201 return result; |
| 182 } | 202 } |
| 183 | 203 |
| 184 int bind(int fd, _InternetAddress address, int port) { | 204 int bind(int fd, _InternetAddress address, int port) { |
| 185 Foreign sockaddr = _createSocketAddress(address, port); | 205 ForeignMemory sockaddr = _createSocketAddress(address, port); |
| 186 int status = _retry(() => _bind.icall$3(fd, sockaddr, sockaddr.length)); | 206 int status = _retry(() => _bind.icall$3(fd, sockaddr, sockaddr.length)); |
| 187 sockaddr.free(); | 207 sockaddr.free(); |
| 188 return status; | 208 return status; |
| 189 } | 209 } |
| 190 | 210 |
| 191 int listen(int fd) { | 211 int listen(int fd) { |
| 192 return _retry(() => _listen.icall$2(fd, 128)); | 212 return _retry(() => _listen.icall$2(fd, 128)); |
| 193 } | 213 } |
| 194 | 214 |
| 195 int setsockopt(int fd, int level, int optname, int value) { | 215 int setsockopt(int fd, int level, int optname, int value) { |
| 196 Struct32 opt = new Struct32(1); | 216 Struct32 opt = new Struct32(1); |
| 197 opt.setField(0, value); | 217 opt.setField(0, value); |
| 198 int result = _retry(() => _setsockopt.icall$5(fd, | 218 int result = _retry(() => _setsockopt.icall$5(fd, |
| 199 level, | 219 level, |
| 200 optname, | 220 optname, |
| 201 opt, | 221 opt, |
| 202 opt.length)); | 222 opt.length)); |
| 203 opt.free(); | 223 opt.free(); |
| 204 return result; | 224 return result; |
| 205 } | 225 } |
| 206 | 226 |
| 207 int accept(int fd) { | 227 int accept(int fd) { |
| 208 return _retry(() => _accept.icall$3(fd, Foreign.NULL, Foreign.NULL)); | 228 return _retry(() => _accept.icall$3(fd, ForeignPointer.NULL, |
| 229 ForeignPointer.NULL)); |
| 209 } | 230 } |
| 210 | 231 |
| 211 int port(int fd) { | 232 int port(int fd) { |
| 212 const int LENGTH = 28; | 233 const int LENGTH = 28; |
| 213 var sockaddr = new Foreign.allocated(LENGTH); | 234 var sockaddr = new ForeignMemory.allocated(LENGTH); |
| 214 var addrlen = new Foreign.allocated(4); | 235 var addrlen = new ForeignMemory.allocated(4); |
| 215 addrlen.setInt32(0, LENGTH); | 236 addrlen.setInt32(0, LENGTH); |
| 216 int status = _retry(() => _getsockname.icall$3(fd, sockaddr, addrlen)); | 237 int status = _retry(() => _getsockname.icall$3(fd, sockaddr, addrlen)); |
| 217 int port = -1; | 238 int port = -1; |
| 218 if (status == 0) { | 239 if (status == 0) { |
| 219 port = sockaddr.getUint8(2) << 8; | 240 port = sockaddr.getUint8(2) << 8; |
| 220 port |= sockaddr.getUint8(3); | 241 port |= sockaddr.getUint8(3); |
| 221 } | 242 } |
| 222 sockaddr.free(); | 243 sockaddr.free(); |
| 223 addrlen.free(); | 244 addrlen.free(); |
| 224 return port; | 245 return port; |
| 225 } | 246 } |
| 226 | 247 |
| 227 int connect(int fd, _InternetAddress address, int port) { | 248 int connect(int fd, _InternetAddress address, int port) { |
| 228 Foreign sockaddr = _createSocketAddress(address, port); | 249 ForeignMemory sockaddr = _createSocketAddress(address, port); |
| 229 int status = _retry(() => _connect.icall$3(fd, sockaddr, sockaddr.length)); | 250 int status = _retry(() => _connect.icall$3(fd, sockaddr, sockaddr.length)); |
| 230 sockaddr.free(); | 251 sockaddr.free(); |
| 231 return status; | 252 return status; |
| 232 } | 253 } |
| 233 | 254 |
| 234 int setBlocking(int fd, bool blocking) { | 255 int setBlocking(int fd, bool blocking) { |
| 235 int flags = _retry(() => _fcntl.icall$3(fd, F_GETFL, 0)); | 256 int flags = _retry(() => _fcntl.icall$3(fd, F_GETFL, 0)); |
| 236 if (flags == -1) return -1; | 257 if (flags == -1) return -1; |
| 237 if (blocking) { | 258 if (blocking) { |
| 238 flags &= ~O_NONBLOCK; | 259 flags &= ~O_NONBLOCK; |
| (...skipping 11 matching lines...) Expand all Loading... |
| 250 Struct result = new Struct(1); | 271 Struct result = new Struct(1); |
| 251 int status = _retry(() => _ioctl.icall$3(fd, FIONREAD, result)); | 272 int status = _retry(() => _ioctl.icall$3(fd, FIONREAD, result)); |
| 252 int available = result.getWord(0); | 273 int available = result.getWord(0); |
| 253 result.free(); | 274 result.free(); |
| 254 if (status == -1) return status; | 275 if (status == -1) return status; |
| 255 return available; | 276 return available; |
| 256 } | 277 } |
| 257 | 278 |
| 258 int read(int fd, var buffer, int offset, int length) { | 279 int read(int fd, var buffer, int offset, int length) { |
| 259 _rangeCheck(buffer, offset, length); | 280 _rangeCheck(buffer, offset, length); |
| 260 var address = buffer.getForeign().value + offset; | 281 var address = buffer.getForeign().address + offset; |
| 261 return _retry(() => _read.icall$3(fd, address, length)); | 282 return _retry(() => _read.icall$3(fd, address, length)); |
| 262 } | 283 } |
| 263 | 284 |
| 264 int write(int fd, var buffer, int offset, int length) { | 285 int write(int fd, var buffer, int offset, int length) { |
| 265 _rangeCheck(buffer, offset, length); | 286 _rangeCheck(buffer, offset, length); |
| 266 var address = buffer.getForeign().value + offset; | 287 var address = buffer.getForeign().address + offset; |
| 267 return _retry(() => _write.icall$3(fd, address, length)); | 288 return _retry(() => _write.icall$3(fd, address, length)); |
| 268 } | 289 } |
| 269 | 290 |
| 270 void memcpy(var dest, | 291 void memcpy(var dest, |
| 271 int destOffset, | 292 int destOffset, |
| 272 var src, | 293 var src, |
| 273 int srcOffset, | 294 int srcOffset, |
| 274 int length) { | 295 int length) { |
| 275 var destAddress = dest.getForeign().value + destOffset; | 296 var destAddress = dest.getForeign().address + destOffset; |
| 276 var srcAddress = src.getForeign().value + srcOffset; | 297 var srcAddress = src.getForeign().address + srcOffset; |
| 277 _memcpy.icall$3(destAddress, srcAddress, length); | 298 _memcpy.icall$3(destAddress, srcAddress, length); |
| 278 } | 299 } |
| 279 | 300 |
| 280 int shutdown(int fd, int how) { | 301 int shutdown(int fd, int how) { |
| 281 return _retry(() => _shutdown.icall$2(fd, how)); | 302 return _retry(() => _shutdown.icall$2(fd, how)); |
| 282 } | 303 } |
| 283 | 304 |
| 284 int close(int fd) { | 305 int close(int fd) { |
| 285 return _retry(() => _close.icall$1(fd)); | 306 return _retry(() => _close.icall$1(fd)); |
| 286 } | 307 } |
| (...skipping 10 matching lines...) Expand all Loading... |
| 297 Errno errno() { | 318 Errno errno() { |
| 298 return Errno.from(Foreign.errno); | 319 return Errno.from(Foreign.errno); |
| 299 } | 320 } |
| 300 | 321 |
| 301 static void _rangeCheck(ByteBuffer buffer, int offset, int length) { | 322 static void _rangeCheck(ByteBuffer buffer, int offset, int length) { |
| 302 if (buffer.lengthInBytes < offset + length) { | 323 if (buffer.lengthInBytes < offset + length) { |
| 303 throw new IndexError(length, buffer); | 324 throw new IndexError(length, buffer); |
| 304 } | 325 } |
| 305 } | 326 } |
| 306 | 327 |
| 307 Foreign _createSocketAddress(_InternetAddress address, int port) { | 328 ForeignMemory _createSocketAddress(_InternetAddress address, int port) { |
| 308 var bytes = address._bytes; | 329 var bytes = address._bytes; |
| 309 Foreign sockaddr; | 330 ForeignMemory sockaddr; |
| 310 int length; | 331 int length; |
| 311 if (bytes.length == 4) { | 332 if (bytes.length == 4) { |
| 312 length = 16; | 333 length = 16; |
| 313 sockaddr = new Foreign.allocated(length); | 334 sockaddr = new ForeignMemory.allocated(length); |
| 314 sockaddr.setUint16(0, AF_INET); | 335 sockaddr.setUint16(0, AF_INET); |
| 315 sockaddr.copyBytesFromList(bytes, 4, 8, 0); | 336 sockaddr.copyBytesFromList(bytes, 4, 8, 0); |
| 316 } else if (bytes.length == 16) { | 337 } else if (bytes.length == 16) { |
| 317 length = 28; | 338 length = 28; |
| 318 sockaddr = new Foreign.allocated(length); | 339 sockaddr = new ForeignMemory.allocated(length); |
| 319 sockaddr.setUint16(0, AF_INET6); | 340 sockaddr.setUint16(0, AF_INET6); |
| 320 sockaddr.copyBytesFromList(bytes, 8, 24, 0); | 341 sockaddr.copyBytesFromList(bytes, 8, 24, 0); |
| 321 } else { | 342 } else { |
| 322 throw "Invalid InternetAddress"; | 343 throw "Invalid InternetAddress"; |
| 323 } | 344 } |
| 324 // Set port in Network Byte Order. | 345 // Set port in Network Byte Order. |
| 325 sockaddr.setUint8(2, port >> 8); | 346 sockaddr.setUint8(2, port >> 8); |
| 326 sockaddr.setUint8(3, port & 0xFF); | 347 sockaddr.setUint8(3, port & 0xFF); |
| 327 return sockaddr; | 348 return sockaddr; |
| 328 } | 349 } |
| 329 | 350 |
| 330 int _retry(Function f) { | 351 int _retry(Function f) { |
| 331 int value; | 352 int value; |
| 332 while ((value = f()) == -1) { | 353 while ((value = f()) == -1) { |
| 333 if (Foreign.errno != Errno.EINTR) break; | 354 if (Foreign.errno != Errno.EINTR) break; |
| 334 } | 355 } |
| 335 return value; | 356 return value; |
| 336 } | 357 } |
| 337 } | 358 } |
| OLD | NEW |