github.com/kooksee/kchain@v0.0.0-20180613035215-4aef51c04906/src/golang.org/x/sys/unix/syscall_linux_386.go (about) 1 // Copyright 2009 The Go Authors. All rights reserved. 2 // Use of this source code is governed by a BSD-style 3 // license that can be found in the LICENSE file. 4 5 // TODO(rsc): Rewrite all nn(SP) references into name+(nn-8)(FP) 6 // so that go vet can check that they are correct. 7 8 // +build 386,linux 9 10 package unix 11 12 import ( 13 "syscall" 14 "unsafe" 15 ) 16 17 func Getpagesize() int { return 4096 } 18 19 func TimespecToNsec(ts Timespec) int64 { return int64(ts.Sec)*1e9 + int64(ts.Nsec) } 20 21 func NsecToTimespec(nsec int64) (ts Timespec) { 22 ts.Sec = int32(nsec / 1e9) 23 ts.Nsec = int32(nsec % 1e9) 24 return 25 } 26 27 func NsecToTimeval(nsec int64) (tv Timeval) { 28 nsec += 999 // round up to microsecond 29 tv.Sec = int32(nsec / 1e9) 30 tv.Usec = int32(nsec % 1e9 / 1e3) 31 return 32 } 33 34 //sysnb pipe(p *[2]_C_int) (err error) 35 36 func Pipe(p []int) (err error) { 37 if len(p) != 2 { 38 return EINVAL 39 } 40 var pp [2]_C_int 41 err = pipe(&pp) 42 p[0] = int(pp[0]) 43 p[1] = int(pp[1]) 44 return 45 } 46 47 //sysnb pipe2(p *[2]_C_int, flags int) (err error) 48 49 func Pipe2(p []int, flags int) (err error) { 50 if len(p) != 2 { 51 return EINVAL 52 } 53 var pp [2]_C_int 54 err = pipe2(&pp, flags) 55 p[0] = int(pp[0]) 56 p[1] = int(pp[1]) 57 return 58 } 59 60 // 64-bit file system and 32-bit uid calls 61 // (386 default is 32-bit file system and 16-bit uid). 62 //sys Dup2(oldfd int, newfd int) (err error) 63 //sys Fadvise(fd int, offset int64, length int64, advice int) (err error) = SYS_FADVISE64_64 64 //sys Fchown(fd int, uid int, gid int) (err error) = SYS_FCHOWN32 65 //sys Fstat(fd int, stat *Stat_t) (err error) = SYS_FSTAT64 66 //sys Ftruncate(fd int, length int64) (err error) = SYS_FTRUNCATE64 67 //sysnb Getegid() (egid int) = SYS_GETEGID32 68 //sysnb Geteuid() (euid int) = SYS_GETEUID32 69 //sysnb Getgid() (gid int) = SYS_GETGID32 70 //sysnb Getuid() (uid int) = SYS_GETUID32 71 //sysnb InotifyInit() (fd int, err error) 72 //sys Ioperm(from int, num int, on int) (err error) 73 //sys Iopl(level int) (err error) 74 //sys Lchown(path string, uid int, gid int) (err error) = SYS_LCHOWN32 75 //sys Lstat(path string, stat *Stat_t) (err error) = SYS_LSTAT64 76 //sys Pread(fd int, p []byte, offset int64) (n int, err error) = SYS_PREAD64 77 //sys Pwrite(fd int, p []byte, offset int64) (n int, err error) = SYS_PWRITE64 78 //sys sendfile(outfd int, infd int, offset *int64, count int) (written int, err error) = SYS_SENDFILE64 79 //sys Setfsgid(gid int) (err error) = SYS_SETFSGID32 80 //sys Setfsuid(uid int) (err error) = SYS_SETFSUID32 81 //sysnb Setregid(rgid int, egid int) (err error) = SYS_SETREGID32 82 //sysnb Setresgid(rgid int, egid int, sgid int) (err error) = SYS_SETRESGID32 83 //sysnb Setresuid(ruid int, euid int, suid int) (err error) = SYS_SETRESUID32 84 //sysnb Setreuid(ruid int, euid int) (err error) = SYS_SETREUID32 85 //sys Splice(rfd int, roff *int64, wfd int, woff *int64, len int, flags int) (n int, err error) 86 //sys Stat(path string, stat *Stat_t) (err error) = SYS_STAT64 87 //sys SyncFileRange(fd int, off int64, n int64, flags int) (err error) 88 //sys Truncate(path string, length int64) (err error) = SYS_TRUNCATE64 89 //sysnb getgroups(n int, list *_Gid_t) (nn int, err error) = SYS_GETGROUPS32 90 //sysnb setgroups(n int, list *_Gid_t) (err error) = SYS_SETGROUPS32 91 //sys Select(nfd int, r *FdSet, w *FdSet, e *FdSet, timeout *Timeval) (n int, err error) = SYS__NEWSELECT 92 93 //sys mmap2(addr uintptr, length uintptr, prot int, flags int, fd int, pageOffset uintptr) (xaddr uintptr, err error) 94 //sys EpollWait(epfd int, events []EpollEvent, msec int) (n int, err error) 95 //sys Pause() (err error) 96 97 func mmap(addr uintptr, length uintptr, prot int, flags int, fd int, offset int64) (xaddr uintptr, err error) { 98 page := uintptr(offset / 4096) 99 if offset != int64(page)*4096 { 100 return 0, EINVAL 101 } 102 return mmap2(addr, length, prot, flags, fd, page) 103 } 104 105 type rlimit32 struct { 106 Cur uint32 107 Max uint32 108 } 109 110 //sysnb getrlimit(resource int, rlim *rlimit32) (err error) = SYS_GETRLIMIT 111 112 const rlimInf32 = ^uint32(0) 113 const rlimInf64 = ^uint64(0) 114 115 func Getrlimit(resource int, rlim *Rlimit) (err error) { 116 err = prlimit(0, resource, nil, rlim) 117 if err != ENOSYS { 118 return err 119 } 120 121 rl := rlimit32{} 122 err = getrlimit(resource, &rl) 123 if err != nil { 124 return 125 } 126 127 if rl.Cur == rlimInf32 { 128 rlim.Cur = rlimInf64 129 } else { 130 rlim.Cur = uint64(rl.Cur) 131 } 132 133 if rl.Max == rlimInf32 { 134 rlim.Max = rlimInf64 135 } else { 136 rlim.Max = uint64(rl.Max) 137 } 138 return 139 } 140 141 //sysnb setrlimit(resource int, rlim *rlimit32) (err error) = SYS_SETRLIMIT 142 143 func Setrlimit(resource int, rlim *Rlimit) (err error) { 144 err = prlimit(0, resource, rlim, nil) 145 if err != ENOSYS { 146 return err 147 } 148 149 rl := rlimit32{} 150 if rlim.Cur == rlimInf64 { 151 rl.Cur = rlimInf32 152 } else if rlim.Cur < uint64(rlimInf32) { 153 rl.Cur = uint32(rlim.Cur) 154 } else { 155 return EINVAL 156 } 157 if rlim.Max == rlimInf64 { 158 rl.Max = rlimInf32 159 } else if rlim.Max < uint64(rlimInf32) { 160 rl.Max = uint32(rlim.Max) 161 } else { 162 return EINVAL 163 } 164 165 return setrlimit(resource, &rl) 166 } 167 168 // Underlying system call writes to newoffset via pointer. 169 // Implemented in assembly to avoid allocation. 170 func seek(fd int, offset int64, whence int) (newoffset int64, err syscall.Errno) 171 172 func Seek(fd int, offset int64, whence int) (newoffset int64, err error) { 173 newoffset, errno := seek(fd, offset, whence) 174 if errno != 0 { 175 return 0, errno 176 } 177 return newoffset, nil 178 } 179 180 // Vsyscalls on amd64. 181 //sysnb Gettimeofday(tv *Timeval) (err error) 182 //sysnb Time(t *Time_t) (tt Time_t, err error) 183 184 //sys Utime(path string, buf *Utimbuf) (err error) 185 186 // On x86 Linux, all the socket calls go through an extra indirection, 187 // I think because the 5-register system call interface can't handle 188 // the 6-argument calls like sendto and recvfrom. Instead the 189 // arguments to the underlying system call are the number below 190 // and a pointer to an array of uintptr. We hide the pointer in the 191 // socketcall assembly to avoid allocation on every system call. 192 193 const ( 194 // see linux/net.h 195 _SOCKET = 1 196 _BIND = 2 197 _CONNECT = 3 198 _LISTEN = 4 199 _ACCEPT = 5 200 _GETSOCKNAME = 6 201 _GETPEERNAME = 7 202 _SOCKETPAIR = 8 203 _SEND = 9 204 _RECV = 10 205 _SENDTO = 11 206 _RECVFROM = 12 207 _SHUTDOWN = 13 208 _SETSOCKOPT = 14 209 _GETSOCKOPT = 15 210 _SENDMSG = 16 211 _RECVMSG = 17 212 _ACCEPT4 = 18 213 _RECVMMSG = 19 214 _SENDMMSG = 20 215 ) 216 217 func socketcall(call int, a0, a1, a2, a3, a4, a5 uintptr) (n int, err syscall.Errno) 218 func rawsocketcall(call int, a0, a1, a2, a3, a4, a5 uintptr) (n int, err syscall.Errno) 219 220 func accept(s int, rsa *RawSockaddrAny, addrlen *_Socklen) (fd int, err error) { 221 fd, e := socketcall(_ACCEPT, uintptr(s), uintptr(unsafe.Pointer(rsa)), uintptr(unsafe.Pointer(addrlen)), 0, 0, 0) 222 if e != 0 { 223 err = e 224 } 225 return 226 } 227 228 func accept4(s int, rsa *RawSockaddrAny, addrlen *_Socklen, flags int) (fd int, err error) { 229 fd, e := socketcall(_ACCEPT4, uintptr(s), uintptr(unsafe.Pointer(rsa)), uintptr(unsafe.Pointer(addrlen)), uintptr(flags), 0, 0) 230 if e != 0 { 231 err = e 232 } 233 return 234 } 235 236 func getsockname(s int, rsa *RawSockaddrAny, addrlen *_Socklen) (err error) { 237 _, e := rawsocketcall(_GETSOCKNAME, uintptr(s), uintptr(unsafe.Pointer(rsa)), uintptr(unsafe.Pointer(addrlen)), 0, 0, 0) 238 if e != 0 { 239 err = e 240 } 241 return 242 } 243 244 func getpeername(s int, rsa *RawSockaddrAny, addrlen *_Socklen) (err error) { 245 _, e := rawsocketcall(_GETPEERNAME, uintptr(s), uintptr(unsafe.Pointer(rsa)), uintptr(unsafe.Pointer(addrlen)), 0, 0, 0) 246 if e != 0 { 247 err = e 248 } 249 return 250 } 251 252 func socketpair(domain int, typ int, flags int, fd *[2]int32) (err error) { 253 _, e := rawsocketcall(_SOCKETPAIR, uintptr(domain), uintptr(typ), uintptr(flags), uintptr(unsafe.Pointer(fd)), 0, 0) 254 if e != 0 { 255 err = e 256 } 257 return 258 } 259 260 func bind(s int, addr unsafe.Pointer, addrlen _Socklen) (err error) { 261 _, e := socketcall(_BIND, uintptr(s), uintptr(addr), uintptr(addrlen), 0, 0, 0) 262 if e != 0 { 263 err = e 264 } 265 return 266 } 267 268 func connect(s int, addr unsafe.Pointer, addrlen _Socklen) (err error) { 269 _, e := socketcall(_CONNECT, uintptr(s), uintptr(addr), uintptr(addrlen), 0, 0, 0) 270 if e != 0 { 271 err = e 272 } 273 return 274 } 275 276 func socket(domain int, typ int, proto int) (fd int, err error) { 277 fd, e := rawsocketcall(_SOCKET, uintptr(domain), uintptr(typ), uintptr(proto), 0, 0, 0) 278 if e != 0 { 279 err = e 280 } 281 return 282 } 283 284 func getsockopt(s int, level int, name int, val unsafe.Pointer, vallen *_Socklen) (err error) { 285 _, e := socketcall(_GETSOCKOPT, uintptr(s), uintptr(level), uintptr(name), uintptr(val), uintptr(unsafe.Pointer(vallen)), 0) 286 if e != 0 { 287 err = e 288 } 289 return 290 } 291 292 func setsockopt(s int, level int, name int, val unsafe.Pointer, vallen uintptr) (err error) { 293 _, e := socketcall(_SETSOCKOPT, uintptr(s), uintptr(level), uintptr(name), uintptr(val), vallen, 0) 294 if e != 0 { 295 err = e 296 } 297 return 298 } 299 300 func recvfrom(s int, p []byte, flags int, from *RawSockaddrAny, fromlen *_Socklen) (n int, err error) { 301 var base uintptr 302 if len(p) > 0 { 303 base = uintptr(unsafe.Pointer(&p[0])) 304 } 305 n, e := socketcall(_RECVFROM, uintptr(s), base, uintptr(len(p)), uintptr(flags), uintptr(unsafe.Pointer(from)), uintptr(unsafe.Pointer(fromlen))) 306 if e != 0 { 307 err = e 308 } 309 return 310 } 311 312 func sendto(s int, p []byte, flags int, to unsafe.Pointer, addrlen _Socklen) (err error) { 313 var base uintptr 314 if len(p) > 0 { 315 base = uintptr(unsafe.Pointer(&p[0])) 316 } 317 _, e := socketcall(_SENDTO, uintptr(s), base, uintptr(len(p)), uintptr(flags), uintptr(to), uintptr(addrlen)) 318 if e != 0 { 319 err = e 320 } 321 return 322 } 323 324 func recvmsg(s int, msg *Msghdr, flags int) (n int, err error) { 325 n, e := socketcall(_RECVMSG, uintptr(s), uintptr(unsafe.Pointer(msg)), uintptr(flags), 0, 0, 0) 326 if e != 0 { 327 err = e 328 } 329 return 330 } 331 332 func sendmsg(s int, msg *Msghdr, flags int) (n int, err error) { 333 n, e := socketcall(_SENDMSG, uintptr(s), uintptr(unsafe.Pointer(msg)), uintptr(flags), 0, 0, 0) 334 if e != 0 { 335 err = e 336 } 337 return 338 } 339 340 func Listen(s int, n int) (err error) { 341 _, e := socketcall(_LISTEN, uintptr(s), uintptr(n), 0, 0, 0, 0) 342 if e != 0 { 343 err = e 344 } 345 return 346 } 347 348 func Shutdown(s, how int) (err error) { 349 _, e := socketcall(_SHUTDOWN, uintptr(s), uintptr(how), 0, 0, 0, 0) 350 if e != 0 { 351 err = e 352 } 353 return 354 } 355 356 func Fstatfs(fd int, buf *Statfs_t) (err error) { 357 _, _, e := Syscall(SYS_FSTATFS64, uintptr(fd), unsafe.Sizeof(*buf), uintptr(unsafe.Pointer(buf))) 358 if e != 0 { 359 err = e 360 } 361 return 362 } 363 364 func Statfs(path string, buf *Statfs_t) (err error) { 365 pathp, err := BytePtrFromString(path) 366 if err != nil { 367 return err 368 } 369 _, _, e := Syscall(SYS_STATFS64, uintptr(unsafe.Pointer(pathp)), unsafe.Sizeof(*buf), uintptr(unsafe.Pointer(buf))) 370 if e != 0 { 371 err = e 372 } 373 return 374 } 375 376 func (r *PtraceRegs) PC() uint64 { return uint64(uint32(r.Eip)) } 377 378 func (r *PtraceRegs) SetPC(pc uint64) { r.Eip = int32(pc) } 379 380 func (iov *Iovec) SetLen(length int) { 381 iov.Len = uint32(length) 382 } 383 384 func (msghdr *Msghdr) SetControllen(length int) { 385 msghdr.Controllen = uint32(length) 386 } 387 388 func (cmsg *Cmsghdr) SetLen(length int) { 389 cmsg.Len = uint32(length) 390 } 391 392 //sys poll(fds *PollFd, nfds int, timeout int) (n int, err error) 393 394 func Poll(fds []PollFd, timeout int) (n int, err error) { 395 if len(fds) == 0 { 396 return poll(nil, 0, timeout) 397 } 398 return poll(&fds[0], len(fds), timeout) 399 }