]>
git.saurik.com Git - apple/launchd.git/blob - launchd/testing/missed-fds.c
2 * <rdar://problem/4389914> 8G1153: Cannot SSH into machine despite Remote Login being checked
8 #include <sys/socket.h>
9 #include <netinet/in.h>
19 static void do_parent(int thefd
);
20 static void do_child(int thefd
);
27 assert(socketpair(AF_UNIX
, SOCK_STREAM
, 0, sp
) != -1);
29 assert((p
= fork()) != -1);
32 assert(close(sp
[0]) != -1);
35 assert(close(sp
[1]) != -1);
45 struct sockaddr_in ina
;
48 memset(&ina
, 0, sizeof(ina
));
49 ina
.sin_family
= AF_INET
;
50 assert((fd
= socket(PF_INET
, SOCK_STREAM
, 0)) != -1);
51 assert(bind(fd
, (struct sockaddr
*)&ina
, sizeof(ina
)) != -1);
52 assert(listen(fd
, SOMAXCONN
) != -1);
57 static int total_fds_sent
= 0;
62 struct cmsghdr
*cm
= NULL
;
65 size_t sentctrllen
= 0;
66 int fdcnt
= (rand() % 223) + 1; /* 223 is prime */
69 memset(&mh
, 0, sizeof(mh
));
71 iov
.iov_base
= &fdcnt
;
72 iov
.iov_len
= sizeof(fdcnt
);
76 for (i
= 0; i
< fdcnt
; i
++) {
77 fds
[i
] = alloc_random_fd();
80 sentctrllen
= mh
.msg_controllen
= CMSG_SPACE(fdcnt
* sizeof(int));
82 mh
.msg_control
= cm
= alloca(mh
.msg_controllen
);
84 memset(cm
, 0, mh
.msg_controllen
);
86 cm
->cmsg_len
= CMSG_LEN(fdcnt
* sizeof(int));
87 cm
->cmsg_level
= SOL_SOCKET
;
88 cm
->cmsg_type
= SCM_RIGHTS
;
90 memcpy(CMSG_DATA(cm
), fds
, fdcnt
* sizeof(int));
92 if (sendmsg(thefd
, &mh
, 0) == -1) {
93 fprintf(stderr
, "Child: sendmsg(): %s\n", strerror(errno
));
94 fprintf(stderr
, "Child: Tried to send %d fds\n", fdcnt
);
95 fprintf(stderr
, "Child: Total FDs sent: %d\n", total_fds_sent
);
99 total_fds_sent
+= fdcnt
;
101 assert(sentctrllen
== mh
.msg_controllen
);
103 r
= read(thefd
, &i
, sizeof(i
));
107 for (i
= 0; i
< fdcnt
; i
++) {
108 assert(close(fds
[i
]) != -1);
120 static int total_fds_received
= 0;
123 fetch_and_check_fds(int thefd
)
125 struct cmsghdr
*cm
= alloca(4096);
128 int r
, i
, *fds
, fdcnt
= 0, sentfds
;
130 memset(&mh
, 0, sizeof(mh
));
132 iov
.iov_base
= &fdcnt
;
133 iov
.iov_len
= sizeof(fdcnt
);
137 mh
.msg_controllen
= 4096;
139 r
= recvmsg(thefd
, &mh
, 0);
142 assert(!(mh
.msg_flags
& MSG_CTRUNC
));
143 assert(mh
.msg_controllen
> 0);
145 fds
= (int *)CMSG_DATA(cm
);
146 sentfds
= (mh
.msg_controllen
- sizeof(struct cmsghdr
)) / sizeof(int);
148 if (sentfds
!= fdcnt
) {
149 fprintf(stderr
, "%d FDs sent, %d actually received.\n", fdcnt
, sentfds
);
153 total_fds_received
+= fdcnt
;
155 for (i
= 0; i
< fdcnt
; i
++) {
156 assert(close(fds
[i
]) != -1);
159 r
= write(thefd
, &fdcnt
, sizeof(fdcnt
));
172 EV_SET(&kev
, thefd
, EVFILT_READ
, EV_ADD
, 0, 0, NULL
);
174 assert((kq
= kqueue()) != -1);
175 assert(kevent(kq
, &kev
, 1, NULL
, 0, NULL
) != -1);
177 for (iter
= 0; ; iter
++) {
178 assert(kevent(kq
, NULL
, 0, &kev
, 1, NULL
) == 1);
179 assert(kev
.filter
== EVFILT_READ
);
180 if (!fetch_and_check_fds(thefd
))
184 fprintf(stderr
, "After %d iterations and %d FDs received, bug 4389914 still exists!\n", iter
, total_fds_received
);