Source file
src/syscall/syscall_linux.go
Documentation: syscall
1
2
3
4
5
6
7
8
9
10
11
12 package syscall
13
14 import "unsafe"
15
16 func rawSyscallNoError(trap, a1, a2, a3 uintptr) (r1, r2 uintptr)
17
18
21
22 func Access(path string, mode uint32) (err error) {
23 return Faccessat(_AT_FDCWD, path, mode, 0)
24 }
25
26 func Chmod(path string, mode uint32) (err error) {
27 return Fchmodat(_AT_FDCWD, path, mode, 0)
28 }
29
30 func Chown(path string, uid int, gid int) (err error) {
31 return Fchownat(_AT_FDCWD, path, uid, gid, 0)
32 }
33
34 func Creat(path string, mode uint32) (fd int, err error) {
35 return Open(path, O_CREAT|O_WRONLY|O_TRUNC, mode)
36 }
37
38 func isGroupMember(gid int) bool {
39 groups, err := Getgroups()
40 if err != nil {
41 return false
42 }
43
44 for _, g := range groups {
45 if g == gid {
46 return true
47 }
48 }
49 return false
50 }
51
52
53
54 func Faccessat(dirfd int, path string, mode uint32, flags int) (err error) {
55 if flags & ^(_AT_SYMLINK_NOFOLLOW|_AT_EACCESS) != 0 {
56 return EINVAL
57 }
58
59
60
61
62
63
64
65 if flags == 0 {
66 return faccessat(dirfd, path, mode)
67 }
68
69 var st Stat_t
70 if err := fstatat(dirfd, path, &st, flags&_AT_SYMLINK_NOFOLLOW); err != nil {
71 return err
72 }
73
74 mode &= 7
75 if mode == 0 {
76 return nil
77 }
78
79 var uid int
80 if flags&_AT_EACCESS != 0 {
81 uid = Geteuid()
82 } else {
83 uid = Getuid()
84 }
85
86 if uid == 0 {
87 if mode&1 == 0 {
88
89 return nil
90 }
91 if st.Mode&0111 != 0 {
92
93 return nil
94 }
95 return EACCES
96 }
97
98 var fmode uint32
99 if uint32(uid) == st.Uid {
100 fmode = (st.Mode >> 6) & 7
101 } else {
102 var gid int
103 if flags&_AT_EACCESS != 0 {
104 gid = Getegid()
105 } else {
106 gid = Getgid()
107 }
108
109 if uint32(gid) == st.Gid || isGroupMember(gid) {
110 fmode = (st.Mode >> 3) & 7
111 } else {
112 fmode = st.Mode & 7
113 }
114 }
115
116 if fmode&mode == mode {
117 return nil
118 }
119
120 return EACCES
121 }
122
123
124
125 func Fchmodat(dirfd int, path string, mode uint32, flags int) (err error) {
126
127
128
129 if flags&^_AT_SYMLINK_NOFOLLOW != 0 {
130 return EINVAL
131 } else if flags&_AT_SYMLINK_NOFOLLOW != 0 {
132 return EOPNOTSUPP
133 }
134 return fchmodat(dirfd, path, mode)
135 }
136
137
138
139 func Link(oldpath string, newpath string) (err error) {
140 return linkat(_AT_FDCWD, oldpath, _AT_FDCWD, newpath, 0)
141 }
142
143 func Mkdir(path string, mode uint32) (err error) {
144 return Mkdirat(_AT_FDCWD, path, mode)
145 }
146
147 func Mknod(path string, mode uint32, dev int) (err error) {
148 return Mknodat(_AT_FDCWD, path, mode, dev)
149 }
150
151 func Open(path string, mode int, perm uint32) (fd int, err error) {
152 return openat(_AT_FDCWD, path, mode|O_LARGEFILE, perm)
153 }
154
155
156
157 func Openat(dirfd int, path string, flags int, mode uint32) (fd int, err error) {
158 return openat(dirfd, path, flags|O_LARGEFILE, mode)
159 }
160
161
162
163 func Readlink(path string, buf []byte) (n int, err error) {
164 return readlinkat(_AT_FDCWD, path, buf)
165 }
166
167 func Rename(oldpath string, newpath string) (err error) {
168 return Renameat(_AT_FDCWD, oldpath, _AT_FDCWD, newpath)
169 }
170
171 func Rmdir(path string) error {
172 return unlinkat(_AT_FDCWD, path, _AT_REMOVEDIR)
173 }
174
175
176
177 func Symlink(oldpath string, newpath string) (err error) {
178 return symlinkat(oldpath, _AT_FDCWD, newpath)
179 }
180
181 func Unlink(path string) error {
182 return unlinkat(_AT_FDCWD, path, 0)
183 }
184
185
186
187 func Unlinkat(dirfd int, path string) error {
188 return unlinkat(dirfd, path, 0)
189 }
190
191 func Utimes(path string, tv []Timeval) (err error) {
192 if len(tv) != 2 {
193 return EINVAL
194 }
195 return utimes(path, (*[2]Timeval)(unsafe.Pointer(&tv[0])))
196 }
197
198
199
200 func UtimesNano(path string, ts []Timespec) (err error) {
201 if len(ts) != 2 {
202 return EINVAL
203 }
204 err = utimensat(_AT_FDCWD, path, (*[2]Timespec)(unsafe.Pointer(&ts[0])), 0)
205 if err != ENOSYS {
206 return err
207 }
208
209
210 var tv [2]Timeval
211 for i := 0; i < 2; i++ {
212 tv[i].Sec = ts[i].Sec
213 tv[i].Usec = ts[i].Nsec / 1000
214 }
215 return utimes(path, (*[2]Timeval)(unsafe.Pointer(&tv[0])))
216 }
217
218 func Futimesat(dirfd int, path string, tv []Timeval) (err error) {
219 if len(tv) != 2 {
220 return EINVAL
221 }
222 return futimesat(dirfd, path, (*[2]Timeval)(unsafe.Pointer(&tv[0])))
223 }
224
225 func Futimes(fd int, tv []Timeval) (err error) {
226
227
228 return Utimes("/proc/self/fd/"+itoa(fd), tv)
229 }
230
231 const ImplementsGetwd = true
232
233
234
235 func Getwd() (wd string, err error) {
236 var buf [PathMax]byte
237 n, err := Getcwd(buf[0:])
238 if err != nil {
239 return "", err
240 }
241
242 if n < 1 || n > len(buf) || buf[n-1] != 0 {
243 return "", EINVAL
244 }
245 return string(buf[0 : n-1]), nil
246 }
247
248 func Getgroups() (gids []int, err error) {
249 n, err := getgroups(0, nil)
250 if err != nil {
251 return nil, err
252 }
253 if n == 0 {
254 return nil, nil
255 }
256
257
258 if n < 0 || n > 1<<20 {
259 return nil, EINVAL
260 }
261
262 a := make([]_Gid_t, n)
263 n, err = getgroups(n, &a[0])
264 if err != nil {
265 return nil, err
266 }
267 gids = make([]int, n)
268 for i, v := range a[0:n] {
269 gids[i] = int(v)
270 }
271 return
272 }
273
274 func Setgroups(gids []int) (err error) {
275 if len(gids) == 0 {
276 return setgroups(0, nil)
277 }
278
279 a := make([]_Gid_t, len(gids))
280 for i, v := range gids {
281 a[i] = _Gid_t(v)
282 }
283 return setgroups(len(a), &a[0])
284 }
285
286 type WaitStatus uint32
287
288
289
290
291
292
293
294
295
296
297 const (
298 mask = 0x7F
299 core = 0x80
300 exited = 0x00
301 stopped = 0x7F
302 shift = 8
303 )
304
305 func (w WaitStatus) Exited() bool { return w&mask == exited }
306
307 func (w WaitStatus) Signaled() bool { return w&mask != stopped && w&mask != exited }
308
309 func (w WaitStatus) Stopped() bool { return w&0xFF == stopped }
310
311 func (w WaitStatus) Continued() bool { return w == 0xFFFF }
312
313 func (w WaitStatus) CoreDump() bool { return w.Signaled() && w&core != 0 }
314
315 func (w WaitStatus) ExitStatus() int {
316 if !w.Exited() {
317 return -1
318 }
319 return int(w>>shift) & 0xFF
320 }
321
322 func (w WaitStatus) Signal() Signal {
323 if !w.Signaled() {
324 return -1
325 }
326 return Signal(w & mask)
327 }
328
329 func (w WaitStatus) StopSignal() Signal {
330 if !w.Stopped() {
331 return -1
332 }
333 return Signal(w>>shift) & 0xFF
334 }
335
336 func (w WaitStatus) TrapCause() int {
337 if w.StopSignal() != SIGTRAP {
338 return -1
339 }
340 return int(w>>shift) >> 8
341 }
342
343
344
345 func Wait4(pid int, wstatus *WaitStatus, options int, rusage *Rusage) (wpid int, err error) {
346 var status _C_int
347 wpid, err = wait4(pid, &status, options, rusage)
348 if wstatus != nil {
349 *wstatus = WaitStatus(status)
350 }
351 return
352 }
353
354 func Mkfifo(path string, mode uint32) (err error) {
355 return Mknod(path, mode|S_IFIFO, 0)
356 }
357
358 func (sa *SockaddrInet4) sockaddr() (unsafe.Pointer, _Socklen, error) {
359 if sa.Port < 0 || sa.Port > 0xFFFF {
360 return nil, 0, EINVAL
361 }
362 sa.raw.Family = AF_INET
363 p := (*[2]byte)(unsafe.Pointer(&sa.raw.Port))
364 p[0] = byte(sa.Port >> 8)
365 p[1] = byte(sa.Port)
366 for i := 0; i < len(sa.Addr); i++ {
367 sa.raw.Addr[i] = sa.Addr[i]
368 }
369 return unsafe.Pointer(&sa.raw), SizeofSockaddrInet4, nil
370 }
371
372 func (sa *SockaddrInet6) sockaddr() (unsafe.Pointer, _Socklen, error) {
373 if sa.Port < 0 || sa.Port > 0xFFFF {
374 return nil, 0, EINVAL
375 }
376 sa.raw.Family = AF_INET6
377 p := (*[2]byte)(unsafe.Pointer(&sa.raw.Port))
378 p[0] = byte(sa.Port >> 8)
379 p[1] = byte(sa.Port)
380 sa.raw.Scope_id = sa.ZoneId
381 for i := 0; i < len(sa.Addr); i++ {
382 sa.raw.Addr[i] = sa.Addr[i]
383 }
384 return unsafe.Pointer(&sa.raw), SizeofSockaddrInet6, nil
385 }
386
387 func (sa *SockaddrUnix) sockaddr() (unsafe.Pointer, _Socklen, error) {
388 name := sa.Name
389 n := len(name)
390 if n > len(sa.raw.Path) {
391 return nil, 0, EINVAL
392 }
393 if n == len(sa.raw.Path) && name[0] != '@' {
394 return nil, 0, EINVAL
395 }
396 sa.raw.Family = AF_UNIX
397 for i := 0; i < n; i++ {
398 sa.raw.Path[i] = int8(name[i])
399 }
400
401 sl := _Socklen(2)
402 if n > 0 {
403 sl += _Socklen(n) + 1
404 }
405 if sa.raw.Path[0] == '@' {
406 sa.raw.Path[0] = 0
407
408 sl--
409 }
410
411 return unsafe.Pointer(&sa.raw), sl, nil
412 }
413
414 type SockaddrLinklayer struct {
415 Protocol uint16
416 Ifindex int
417 Hatype uint16
418 Pkttype uint8
419 Halen uint8
420 Addr [8]byte
421 raw RawSockaddrLinklayer
422 }
423
424 func (sa *SockaddrLinklayer) sockaddr() (unsafe.Pointer, _Socklen, error) {
425 if sa.Ifindex < 0 || sa.Ifindex > 0x7fffffff {
426 return nil, 0, EINVAL
427 }
428 sa.raw.Family = AF_PACKET
429 sa.raw.Protocol = sa.Protocol
430 sa.raw.Ifindex = int32(sa.Ifindex)
431 sa.raw.Hatype = sa.Hatype
432 sa.raw.Pkttype = sa.Pkttype
433 sa.raw.Halen = sa.Halen
434 for i := 0; i < len(sa.Addr); i++ {
435 sa.raw.Addr[i] = sa.Addr[i]
436 }
437 return unsafe.Pointer(&sa.raw), SizeofSockaddrLinklayer, nil
438 }
439
440 type SockaddrNetlink struct {
441 Family uint16
442 Pad uint16
443 Pid uint32
444 Groups uint32
445 raw RawSockaddrNetlink
446 }
447
448 func (sa *SockaddrNetlink) sockaddr() (unsafe.Pointer, _Socklen, error) {
449 sa.raw.Family = AF_NETLINK
450 sa.raw.Pad = sa.Pad
451 sa.raw.Pid = sa.Pid
452 sa.raw.Groups = sa.Groups
453 return unsafe.Pointer(&sa.raw), SizeofSockaddrNetlink, nil
454 }
455
456 func anyToSockaddr(rsa *RawSockaddrAny) (Sockaddr, error) {
457 switch rsa.Addr.Family {
458 case AF_NETLINK:
459 pp := (*RawSockaddrNetlink)(unsafe.Pointer(rsa))
460 sa := new(SockaddrNetlink)
461 sa.Family = pp.Family
462 sa.Pad = pp.Pad
463 sa.Pid = pp.Pid
464 sa.Groups = pp.Groups
465 return sa, nil
466
467 case AF_PACKET:
468 pp := (*RawSockaddrLinklayer)(unsafe.Pointer(rsa))
469 sa := new(SockaddrLinklayer)
470 sa.Protocol = pp.Protocol
471 sa.Ifindex = int(pp.Ifindex)
472 sa.Hatype = pp.Hatype
473 sa.Pkttype = pp.Pkttype
474 sa.Halen = pp.Halen
475 for i := 0; i < len(sa.Addr); i++ {
476 sa.Addr[i] = pp.Addr[i]
477 }
478 return sa, nil
479
480 case AF_UNIX:
481 pp := (*RawSockaddrUnix)(unsafe.Pointer(rsa))
482 sa := new(SockaddrUnix)
483 if pp.Path[0] == 0 {
484
485
486
487
488
489 pp.Path[0] = '@'
490 }
491
492
493
494
495
496
497 n := 0
498 for n < len(pp.Path) && pp.Path[n] != 0 {
499 n++
500 }
501 bytes := (*[len(pp.Path)]byte)(unsafe.Pointer(&pp.Path[0]))[0:n]
502 sa.Name = string(bytes)
503 return sa, nil
504
505 case AF_INET:
506 pp := (*RawSockaddrInet4)(unsafe.Pointer(rsa))
507 sa := new(SockaddrInet4)
508 p := (*[2]byte)(unsafe.Pointer(&pp.Port))
509 sa.Port = int(p[0])<<8 + int(p[1])
510 for i := 0; i < len(sa.Addr); i++ {
511 sa.Addr[i] = pp.Addr[i]
512 }
513 return sa, nil
514
515 case AF_INET6:
516 pp := (*RawSockaddrInet6)(unsafe.Pointer(rsa))
517 sa := new(SockaddrInet6)
518 p := (*[2]byte)(unsafe.Pointer(&pp.Port))
519 sa.Port = int(p[0])<<8 + int(p[1])
520 sa.ZoneId = pp.Scope_id
521 for i := 0; i < len(sa.Addr); i++ {
522 sa.Addr[i] = pp.Addr[i]
523 }
524 return sa, nil
525 }
526 return nil, EAFNOSUPPORT
527 }
528
529 func Accept(fd int) (nfd int, sa Sockaddr, err error) {
530 var rsa RawSockaddrAny
531 var len _Socklen = SizeofSockaddrAny
532 nfd, err = accept(fd, &rsa, &len)
533 if err != nil {
534 return
535 }
536 sa, err = anyToSockaddr(&rsa)
537 if err != nil {
538 Close(nfd)
539 nfd = 0
540 }
541 return
542 }
543
544 func Accept4(fd int, flags int) (nfd int, sa Sockaddr, err error) {
545 var rsa RawSockaddrAny
546 var len _Socklen = SizeofSockaddrAny
547 nfd, err = accept4(fd, &rsa, &len, flags)
548 if err != nil {
549 return
550 }
551 if len > SizeofSockaddrAny {
552 panic("RawSockaddrAny too small")
553 }
554 sa, err = anyToSockaddr(&rsa)
555 if err != nil {
556 Close(nfd)
557 nfd = 0
558 }
559 return
560 }
561
562 func Getsockname(fd int) (sa Sockaddr, err error) {
563 var rsa RawSockaddrAny
564 var len _Socklen = SizeofSockaddrAny
565 if err = getsockname(fd, &rsa, &len); err != nil {
566 return
567 }
568 return anyToSockaddr(&rsa)
569 }
570
571 func GetsockoptInet4Addr(fd, level, opt int) (value [4]byte, err error) {
572 vallen := _Socklen(4)
573 err = getsockopt(fd, level, opt, unsafe.Pointer(&value[0]), &vallen)
574 return value, err
575 }
576
577 func GetsockoptIPMreq(fd, level, opt int) (*IPMreq, error) {
578 var value IPMreq
579 vallen := _Socklen(SizeofIPMreq)
580 err := getsockopt(fd, level, opt, unsafe.Pointer(&value), &vallen)
581 return &value, err
582 }
583
584 func GetsockoptIPMreqn(fd, level, opt int) (*IPMreqn, error) {
585 var value IPMreqn
586 vallen := _Socklen(SizeofIPMreqn)
587 err := getsockopt(fd, level, opt, unsafe.Pointer(&value), &vallen)
588 return &value, err
589 }
590
591 func GetsockoptIPv6Mreq(fd, level, opt int) (*IPv6Mreq, error) {
592 var value IPv6Mreq
593 vallen := _Socklen(SizeofIPv6Mreq)
594 err := getsockopt(fd, level, opt, unsafe.Pointer(&value), &vallen)
595 return &value, err
596 }
597
598 func GetsockoptIPv6MTUInfo(fd, level, opt int) (*IPv6MTUInfo, error) {
599 var value IPv6MTUInfo
600 vallen := _Socklen(SizeofIPv6MTUInfo)
601 err := getsockopt(fd, level, opt, unsafe.Pointer(&value), &vallen)
602 return &value, err
603 }
604
605 func GetsockoptICMPv6Filter(fd, level, opt int) (*ICMPv6Filter, error) {
606 var value ICMPv6Filter
607 vallen := _Socklen(SizeofICMPv6Filter)
608 err := getsockopt(fd, level, opt, unsafe.Pointer(&value), &vallen)
609 return &value, err
610 }
611
612 func GetsockoptUcred(fd, level, opt int) (*Ucred, error) {
613 var value Ucred
614 vallen := _Socklen(SizeofUcred)
615 err := getsockopt(fd, level, opt, unsafe.Pointer(&value), &vallen)
616 return &value, err
617 }
618
619 func SetsockoptIPMreqn(fd, level, opt int, mreq *IPMreqn) (err error) {
620 return setsockopt(fd, level, opt, unsafe.Pointer(mreq), unsafe.Sizeof(*mreq))
621 }
622
623 func Recvmsg(fd int, p, oob []byte, flags int) (n, oobn int, recvflags int, from Sockaddr, err error) {
624 var msg Msghdr
625 var rsa RawSockaddrAny
626 msg.Name = (*byte)(unsafe.Pointer(&rsa))
627 msg.Namelen = uint32(SizeofSockaddrAny)
628 var iov Iovec
629 if len(p) > 0 {
630 iov.Base = &p[0]
631 iov.SetLen(len(p))
632 }
633 var dummy byte
634 if len(oob) > 0 {
635 if len(p) == 0 {
636 var sockType int
637 sockType, err = GetsockoptInt(fd, SOL_SOCKET, SO_TYPE)
638 if err != nil {
639 return
640 }
641
642 if sockType != SOCK_DGRAM {
643 iov.Base = &dummy
644 iov.SetLen(1)
645 }
646 }
647 msg.Control = &oob[0]
648 msg.SetControllen(len(oob))
649 }
650 msg.Iov = &iov
651 msg.Iovlen = 1
652 if n, err = recvmsg(fd, &msg, flags); err != nil {
653 return
654 }
655 oobn = int(msg.Controllen)
656 recvflags = int(msg.Flags)
657
658 if rsa.Addr.Family != AF_UNSPEC {
659 from, err = anyToSockaddr(&rsa)
660 }
661 return
662 }
663
664 func Sendmsg(fd int, p, oob []byte, to Sockaddr, flags int) (err error) {
665 _, err = SendmsgN(fd, p, oob, to, flags)
666 return
667 }
668
669 func SendmsgN(fd int, p, oob []byte, to Sockaddr, flags int) (n int, err error) {
670 var ptr unsafe.Pointer
671 var salen _Socklen
672 if to != nil {
673 var err error
674 ptr, salen, err = to.sockaddr()
675 if err != nil {
676 return 0, err
677 }
678 }
679 var msg Msghdr
680 msg.Name = (*byte)(ptr)
681 msg.Namelen = uint32(salen)
682 var iov Iovec
683 if len(p) > 0 {
684 iov.Base = &p[0]
685 iov.SetLen(len(p))
686 }
687 var dummy byte
688 if len(oob) > 0 {
689 if len(p) == 0 {
690 var sockType int
691 sockType, err = GetsockoptInt(fd, SOL_SOCKET, SO_TYPE)
692 if err != nil {
693 return 0, err
694 }
695
696 if sockType != SOCK_DGRAM {
697 iov.Base = &dummy
698 iov.SetLen(1)
699 }
700 }
701 msg.Control = &oob[0]
702 msg.SetControllen(len(oob))
703 }
704 msg.Iov = &iov
705 msg.Iovlen = 1
706 if n, err = sendmsg(fd, &msg, flags); err != nil {
707 return 0, err
708 }
709 if len(oob) > 0 && len(p) == 0 {
710 n = 0
711 }
712 return n, nil
713 }
714
715
716 func BindToDevice(fd int, device string) (err error) {
717 return SetsockoptString(fd, SOL_SOCKET, SO_BINDTODEVICE, device)
718 }
719
720
721
722 func ptracePeek(req int, pid int, addr uintptr, out []byte) (count int, err error) {
723
724
725
726
727
728
729 var buf [sizeofPtr]byte
730
731
732
733
734
735
736 n := 0
737 if addr%sizeofPtr != 0 {
738 err = ptrace(req, pid, addr-addr%sizeofPtr, uintptr(unsafe.Pointer(&buf[0])))
739 if err != nil {
740 return 0, err
741 }
742 n += copy(out, buf[addr%sizeofPtr:])
743 out = out[n:]
744 }
745
746
747 for len(out) > 0 {
748
749
750 err = ptrace(req, pid, addr+uintptr(n), uintptr(unsafe.Pointer(&buf[0])))
751 if err != nil {
752 return n, err
753 }
754 copied := copy(out, buf[0:])
755 n += copied
756 out = out[copied:]
757 }
758
759 return n, nil
760 }
761
762 func PtracePeekText(pid int, addr uintptr, out []byte) (count int, err error) {
763 return ptracePeek(PTRACE_PEEKTEXT, pid, addr, out)
764 }
765
766 func PtracePeekData(pid int, addr uintptr, out []byte) (count int, err error) {
767 return ptracePeek(PTRACE_PEEKDATA, pid, addr, out)
768 }
769
770 func ptracePoke(pokeReq int, peekReq int, pid int, addr uintptr, data []byte) (count int, err error) {
771
772
773
774
775 n := 0
776 if addr%sizeofPtr != 0 {
777 var buf [sizeofPtr]byte
778 err = ptrace(peekReq, pid, addr-addr%sizeofPtr, uintptr(unsafe.Pointer(&buf[0])))
779 if err != nil {
780 return 0, err
781 }
782 n += copy(buf[addr%sizeofPtr:], data)
783 word := *((*uintptr)(unsafe.Pointer(&buf[0])))
784 err = ptrace(pokeReq, pid, addr-addr%sizeofPtr, word)
785 if err != nil {
786 return 0, err
787 }
788 data = data[n:]
789 }
790
791
792 for len(data) > sizeofPtr {
793 word := *((*uintptr)(unsafe.Pointer(&data[0])))
794 err = ptrace(pokeReq, pid, addr+uintptr(n), word)
795 if err != nil {
796 return n, err
797 }
798 n += sizeofPtr
799 data = data[sizeofPtr:]
800 }
801
802
803 if len(data) > 0 {
804 var buf [sizeofPtr]byte
805 err = ptrace(peekReq, pid, addr+uintptr(n), uintptr(unsafe.Pointer(&buf[0])))
806 if err != nil {
807 return n, err
808 }
809 copy(buf[0:], data)
810 word := *((*uintptr)(unsafe.Pointer(&buf[0])))
811 err = ptrace(pokeReq, pid, addr+uintptr(n), word)
812 if err != nil {
813 return n, err
814 }
815 n += len(data)
816 }
817
818 return n, nil
819 }
820
821 func PtracePokeText(pid int, addr uintptr, data []byte) (count int, err error) {
822 return ptracePoke(PTRACE_POKETEXT, PTRACE_PEEKTEXT, pid, addr, data)
823 }
824
825 func PtracePokeData(pid int, addr uintptr, data []byte) (count int, err error) {
826 return ptracePoke(PTRACE_POKEDATA, PTRACE_PEEKDATA, pid, addr, data)
827 }
828
829 func PtraceGetRegs(pid int, regsout *PtraceRegs) (err error) {
830 return ptrace(PTRACE_GETREGS, pid, 0, uintptr(unsafe.Pointer(regsout)))
831 }
832
833 func PtraceSetRegs(pid int, regs *PtraceRegs) (err error) {
834 return ptrace(PTRACE_SETREGS, pid, 0, uintptr(unsafe.Pointer(regs)))
835 }
836
837 func PtraceSetOptions(pid int, options int) (err error) {
838 return ptrace(PTRACE_SETOPTIONS, pid, 0, uintptr(options))
839 }
840
841 func PtraceGetEventMsg(pid int) (msg uint, err error) {
842 var data _C_long
843 err = ptrace(PTRACE_GETEVENTMSG, pid, 0, uintptr(unsafe.Pointer(&data)))
844 msg = uint(data)
845 return
846 }
847
848 func PtraceCont(pid int, signal int) (err error) {
849 return ptrace(PTRACE_CONT, pid, 0, uintptr(signal))
850 }
851
852 func PtraceSyscall(pid int, signal int) (err error) {
853 return ptrace(PTRACE_SYSCALL, pid, 0, uintptr(signal))
854 }
855
856 func PtraceSingleStep(pid int) (err error) { return ptrace(PTRACE_SINGLESTEP, pid, 0, 0) }
857
858 func PtraceAttach(pid int) (err error) { return ptrace(PTRACE_ATTACH, pid, 0, 0) }
859
860 func PtraceDetach(pid int) (err error) { return ptrace(PTRACE_DETACH, pid, 0, 0) }
861
862
863
864 func Reboot(cmd int) (err error) {
865 return reboot(LINUX_REBOOT_MAGIC1, LINUX_REBOOT_MAGIC2, cmd, "")
866 }
867
868 func ReadDirent(fd int, buf []byte) (n int, err error) {
869 return Getdents(fd, buf)
870 }
871
872 func direntIno(buf []byte) (uint64, bool) {
873 return readInt(buf, unsafe.Offsetof(Dirent{}.Ino), unsafe.Sizeof(Dirent{}.Ino))
874 }
875
876 func direntReclen(buf []byte) (uint64, bool) {
877 return readInt(buf, unsafe.Offsetof(Dirent{}.Reclen), unsafe.Sizeof(Dirent{}.Reclen))
878 }
879
880 func direntNamlen(buf []byte) (uint64, bool) {
881 reclen, ok := direntReclen(buf)
882 if !ok {
883 return 0, false
884 }
885 return reclen - uint64(unsafe.Offsetof(Dirent{}.Name)), true
886 }
887
888
889
890 func Mount(source string, target string, fstype string, flags uintptr, data string) (err error) {
891
892
893 if data == "" {
894 return mount(source, target, fstype, flags, nil)
895 }
896 datap, err := BytePtrFromString(data)
897 if err != nil {
898 return err
899 }
900 return mount(source, target, fstype, flags, datap)
901 }
902
903
904
905
906
907
910
911
912
913
914
915
916
917
918
919
920
921
922
923
924
925
926
927
928
929
930 func Getpgrp() (pid int) {
931 pid, _ = Getpgid(0)
932 return
933 }
934
935
936
937
938
939
940
941
942
943
944
945
946
947
948
949
950
951
952
953
954
955
956
957
958
959
960
961
962
963
964
965 func Setuid(uid int) (err error) {
966 return EOPNOTSUPP
967 }
968
969 func Setgid(gid int) (err error) {
970 return EOPNOTSUPP
971 }
972
973
974
975
976
977
978
979
980
981
982
983
984
985
986
987
988
989
990
991
992 var mapper = &mmapper{
993 active: make(map[*byte][]byte),
994 mmap: mmap,
995 munmap: munmap,
996 }
997
998 func Mmap(fd int, offset int64, length int, prot int, flags int) (data []byte, err error) {
999 return mapper.Mmap(fd, offset, length, prot, flags)
1000 }
1001
1002 func Munmap(b []byte) (err error) {
1003 return mapper.Munmap(b)
1004 }
1005
1006
1007
1008
1009
1010
1011
1012
View as plain text