Advertisement
xiaoy1

Untitled

May 15th, 2025
25
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
text 94.31 KB | None | 0 0
  1. // autogenerated by syzkaller (https://github.com/google/syzkaller)
  2.  
  3. #define _GNU_SOURCE
  4.  
  5. #include <arpa/inet.h>
  6. #include <dirent.h>
  7. #include <endian.h>
  8. #include <errno.h>
  9. #include <fcntl.h>
  10. #include <net/if.h>
  11. #include <net/if_arp.h>
  12. #include <netinet/in.h>
  13. #include <pthread.h>
  14. #include <sched.h>
  15. #include <setjmp.h>
  16. #include <signal.h>
  17. #include <stdarg.h>
  18. #include <stdbool.h>
  19. #include <stddef.h>
  20. #include <stdint.h>
  21. #include <stdio.h>
  22. #include <stdlib.h>
  23. #include <string.h>
  24. #include <sys/ioctl.h>
  25. #include <sys/mman.h>
  26. #include <sys/mount.h>
  27. #include <sys/prctl.h>
  28. #include <sys/resource.h>
  29. #include <sys/socket.h>
  30. #include <sys/stat.h>
  31. #include <sys/syscall.h>
  32. #include <sys/time.h>
  33. #include <sys/types.h>
  34. #include <sys/uio.h>
  35. #include <sys/wait.h>
  36. #include <time.h>
  37. #include <unistd.h>
  38.  
  39. #include <linux/capability.h>
  40. #include <linux/futex.h>
  41. #include <linux/genetlink.h>
  42. #include <linux/if_addr.h>
  43. #include <linux/if_ether.h>
  44. #include <linux/if_link.h>
  45. #include <linux/if_tun.h>
  46. #include <linux/in6.h>
  47. #include <linux/ip.h>
  48. #include <linux/loop.h>
  49. #include <linux/neighbour.h>
  50. #include <linux/net.h>
  51. #include <linux/netlink.h>
  52. #include <linux/rtnetlink.h>
  53. #include <linux/tcp.h>
  54. #include <linux/veth.h>
  55.  
  56. #ifndef __NR_memfd_create
  57. #define __NR_memfd_create 319
  58. #endif
  59.  
  60. static unsigned long long procid;
  61.  
  62. static __thread int clone_ongoing;
  63. static __thread int skip_segv;
  64. static __thread jmp_buf segv_env;
  65.  
  66. static void segv_handler(int sig, siginfo_t* info, void* ctx)
  67. {
  68. if (__atomic_load_n(&clone_ongoing, __ATOMIC_RELAXED) != 0) {
  69. exit(sig);
  70. }
  71. uintptr_t addr = (uintptr_t)info->si_addr;
  72. const uintptr_t prog_start = 1 << 20;
  73. const uintptr_t prog_end = 100 << 20;
  74. int skip = __atomic_load_n(&skip_segv, __ATOMIC_RELAXED) != 0;
  75. int valid = addr < prog_start || addr > prog_end;
  76. if (skip && valid) {
  77. _longjmp(segv_env, 1);
  78. }
  79. exit(sig);
  80. }
  81.  
  82. static void install_segv_handler(void)
  83. {
  84. struct sigaction sa;
  85. memset(&sa, 0, sizeof(sa));
  86. sa.sa_handler = SIG_IGN;
  87. syscall(SYS_rt_sigaction, 0x20, &sa, NULL, 8);
  88. syscall(SYS_rt_sigaction, 0x21, &sa, NULL, 8);
  89. memset(&sa, 0, sizeof(sa));
  90. sa.sa_sigaction = segv_handler;
  91. sa.sa_flags = SA_NODEFER | SA_SIGINFO;
  92. sigaction(SIGSEGV, &sa, NULL);
  93. sigaction(SIGBUS, &sa, NULL);
  94. }
  95.  
  96. #define NONFAILING(...) \
  97. ({ \
  98. int ok = 1; \
  99. __atomic_fetch_add(&skip_segv, 1, __ATOMIC_SEQ_CST); \
  100. if (_setjmp(segv_env) == 0) { \
  101. __VA_ARGS__; \
  102. } else \
  103. ok = 0; \
  104. __atomic_fetch_sub(&skip_segv, 1, __ATOMIC_SEQ_CST); \
  105. ok; \
  106. })
  107.  
  108. static void sleep_ms(uint64_t ms)
  109. {
  110. usleep(ms * 1000);
  111. }
  112.  
  113. static uint64_t current_time_ms(void)
  114. {
  115. struct timespec ts;
  116. if (clock_gettime(CLOCK_MONOTONIC, &ts))
  117. exit(1);
  118. return (uint64_t)ts.tv_sec * 1000 + (uint64_t)ts.tv_nsec / 1000000;
  119. }
  120.  
  121. static void use_temporary_dir(void)
  122. {
  123. char tmpdir_template[] = "./syzkaller.XXXXXX";
  124. char* tmpdir = mkdtemp(tmpdir_template);
  125. if (!tmpdir)
  126. exit(1);
  127. if (chmod(tmpdir, 0777))
  128. exit(1);
  129. if (chdir(tmpdir))
  130. exit(1);
  131. }
  132.  
  133. static void thread_start(void* (*fn)(void*), void* arg)
  134. {
  135. pthread_t th;
  136. pthread_attr_t attr;
  137. pthread_attr_init(&attr);
  138. pthread_attr_setstacksize(&attr, 128 << 10);
  139. int i = 0;
  140. for (; i < 100; i++) {
  141. if (pthread_create(&th, &attr, fn, arg) == 0) {
  142. pthread_attr_destroy(&attr);
  143. return;
  144. }
  145. if (errno == EAGAIN) {
  146. usleep(50);
  147. continue;
  148. }
  149. break;
  150. }
  151. exit(1);
  152. }
  153.  
  154. typedef struct {
  155. int state;
  156. } event_t;
  157.  
  158. static void event_init(event_t* ev)
  159. {
  160. ev->state = 0;
  161. }
  162.  
  163. static void event_reset(event_t* ev)
  164. {
  165. ev->state = 0;
  166. }
  167.  
  168. static void event_set(event_t* ev)
  169. {
  170. if (ev->state)
  171. exit(1);
  172. __atomic_store_n(&ev->state, 1, __ATOMIC_RELEASE);
  173. syscall(SYS_futex, &ev->state, FUTEX_WAKE | FUTEX_PRIVATE_FLAG, 1000000);
  174. }
  175.  
  176. static void event_wait(event_t* ev)
  177. {
  178. while (!__atomic_load_n(&ev->state, __ATOMIC_ACQUIRE))
  179. syscall(SYS_futex, &ev->state, FUTEX_WAIT | FUTEX_PRIVATE_FLAG, 0, 0);
  180. }
  181.  
  182. static int event_isset(event_t* ev)
  183. {
  184. return __atomic_load_n(&ev->state, __ATOMIC_ACQUIRE);
  185. }
  186.  
  187. static int event_timedwait(event_t* ev, uint64_t timeout)
  188. {
  189. uint64_t start = current_time_ms();
  190. uint64_t now = start;
  191. for (;;) {
  192. uint64_t remain = timeout - (now - start);
  193. struct timespec ts;
  194. ts.tv_sec = remain / 1000;
  195. ts.tv_nsec = (remain % 1000) * 1000 * 1000;
  196. syscall(SYS_futex, &ev->state, FUTEX_WAIT | FUTEX_PRIVATE_FLAG, 0, &ts);
  197. if (__atomic_load_n(&ev->state, __ATOMIC_ACQUIRE))
  198. return 1;
  199. now = current_time_ms();
  200. if (now - start > timeout)
  201. return 0;
  202. }
  203. }
  204.  
  205. static bool write_file(const char* file, const char* what, ...)
  206. {
  207. char buf[1024];
  208. va_list args;
  209. va_start(args, what);
  210. vsnprintf(buf, sizeof(buf), what, args);
  211. va_end(args);
  212. buf[sizeof(buf) - 1] = 0;
  213. int len = strlen(buf);
  214. int fd = open(file, O_WRONLY | O_CLOEXEC);
  215. if (fd == -1)
  216. return false;
  217. if (write(fd, buf, len) != len) {
  218. int err = errno;
  219. close(fd);
  220. errno = err;
  221. return false;
  222. }
  223. close(fd);
  224. return true;
  225. }
  226.  
  227. struct nlmsg {
  228. char* pos;
  229. int nesting;
  230. struct nlattr* nested[8];
  231. char buf[4096];
  232. };
  233.  
  234. static void netlink_init(struct nlmsg* nlmsg, int typ, int flags,
  235. const void* data, int size)
  236. {
  237. memset(nlmsg, 0, sizeof(*nlmsg));
  238. struct nlmsghdr* hdr = (struct nlmsghdr*)nlmsg->buf;
  239. hdr->nlmsg_type = typ;
  240. hdr->nlmsg_flags = NLM_F_REQUEST | NLM_F_ACK | flags;
  241. memcpy(hdr + 1, data, size);
  242. nlmsg->pos = (char*)(hdr + 1) + NLMSG_ALIGN(size);
  243. }
  244.  
  245. static void netlink_attr(struct nlmsg* nlmsg, int typ, const void* data,
  246. int size)
  247. {
  248. struct nlattr* attr = (struct nlattr*)nlmsg->pos;
  249. attr->nla_len = sizeof(*attr) + size;
  250. attr->nla_type = typ;
  251. if (size > 0)
  252. memcpy(attr + 1, data, size);
  253. nlmsg->pos += NLMSG_ALIGN(attr->nla_len);
  254. }
  255.  
  256. static void netlink_nest(struct nlmsg* nlmsg, int typ)
  257. {
  258. struct nlattr* attr = (struct nlattr*)nlmsg->pos;
  259. attr->nla_type = typ;
  260. nlmsg->pos += sizeof(*attr);
  261. nlmsg->nested[nlmsg->nesting++] = attr;
  262. }
  263.  
  264. static void netlink_done(struct nlmsg* nlmsg)
  265. {
  266. struct nlattr* attr = nlmsg->nested[--nlmsg->nesting];
  267. attr->nla_len = nlmsg->pos - (char*)attr;
  268. }
  269.  
  270. static int netlink_send_ext(struct nlmsg* nlmsg, int sock, uint16_t reply_type,
  271. int* reply_len, bool dofail)
  272. {
  273. if (nlmsg->pos > nlmsg->buf + sizeof(nlmsg->buf) || nlmsg->nesting)
  274. exit(1);
  275. struct nlmsghdr* hdr = (struct nlmsghdr*)nlmsg->buf;
  276. hdr->nlmsg_len = nlmsg->pos - nlmsg->buf;
  277. struct sockaddr_nl addr;
  278. memset(&addr, 0, sizeof(addr));
  279. addr.nl_family = AF_NETLINK;
  280. ssize_t n = sendto(sock, nlmsg->buf, hdr->nlmsg_len, 0,
  281. (struct sockaddr*)&addr, sizeof(addr));
  282. if (n != (ssize_t)hdr->nlmsg_len) {
  283. if (dofail)
  284. exit(1);
  285. return -1;
  286. }
  287. n = recv(sock, nlmsg->buf, sizeof(nlmsg->buf), 0);
  288. if (reply_len)
  289. *reply_len = 0;
  290. if (n < 0) {
  291. if (dofail)
  292. exit(1);
  293. return -1;
  294. }
  295. if (n < (ssize_t)sizeof(struct nlmsghdr)) {
  296. errno = EINVAL;
  297. if (dofail)
  298. exit(1);
  299. return -1;
  300. }
  301. if (hdr->nlmsg_type == NLMSG_DONE)
  302. return 0;
  303. if (reply_len && hdr->nlmsg_type == reply_type) {
  304. *reply_len = n;
  305. return 0;
  306. }
  307. if (n < (ssize_t)(sizeof(struct nlmsghdr) + sizeof(struct nlmsgerr))) {
  308. errno = EINVAL;
  309. if (dofail)
  310. exit(1);
  311. return -1;
  312. }
  313. if (hdr->nlmsg_type != NLMSG_ERROR) {
  314. errno = EINVAL;
  315. if (dofail)
  316. exit(1);
  317. return -1;
  318. }
  319. errno = -((struct nlmsgerr*)(hdr + 1))->error;
  320. return -errno;
  321. }
  322.  
  323. static int netlink_send(struct nlmsg* nlmsg, int sock)
  324. {
  325. return netlink_send_ext(nlmsg, sock, 0, NULL, true);
  326. }
  327.  
  328. static int netlink_query_family_id(struct nlmsg* nlmsg, int sock,
  329. const char* family_name, bool dofail)
  330. {
  331. struct genlmsghdr genlhdr;
  332. memset(&genlhdr, 0, sizeof(genlhdr));
  333. genlhdr.cmd = CTRL_CMD_GETFAMILY;
  334. netlink_init(nlmsg, GENL_ID_CTRL, 0, &genlhdr, sizeof(genlhdr));
  335. netlink_attr(nlmsg, CTRL_ATTR_FAMILY_NAME, family_name,
  336. strnlen(family_name, GENL_NAMSIZ - 1) + 1);
  337. int n = 0;
  338. int err = netlink_send_ext(nlmsg, sock, GENL_ID_CTRL, &n, dofail);
  339. if (err < 0) {
  340. return -1;
  341. }
  342. uint16_t id = 0;
  343. struct nlattr* attr = (struct nlattr*)(nlmsg->buf + NLMSG_HDRLEN +
  344. NLMSG_ALIGN(sizeof(genlhdr)));
  345. for (; (char*)attr < nlmsg->buf + n;
  346. attr = (struct nlattr*)((char*)attr + NLMSG_ALIGN(attr->nla_len))) {
  347. if (attr->nla_type == CTRL_ATTR_FAMILY_ID) {
  348. id = *(uint16_t*)(attr + 1);
  349. break;
  350. }
  351. }
  352. if (!id) {
  353. errno = EINVAL;
  354. return -1;
  355. }
  356. recv(sock, nlmsg->buf, sizeof(nlmsg->buf), 0);
  357. return id;
  358. }
  359.  
  360. static int netlink_next_msg(struct nlmsg* nlmsg, unsigned int offset,
  361. unsigned int total_len)
  362. {
  363. struct nlmsghdr* hdr = (struct nlmsghdr*)(nlmsg->buf + offset);
  364. if (offset == total_len || offset + hdr->nlmsg_len > total_len)
  365. return -1;
  366. return hdr->nlmsg_len;
  367. }
  368.  
  369. static void netlink_add_device_impl(struct nlmsg* nlmsg, const char* type,
  370. const char* name, bool up)
  371. {
  372. struct ifinfomsg hdr;
  373. memset(&hdr, 0, sizeof(hdr));
  374. if (up)
  375. hdr.ifi_flags = hdr.ifi_change = IFF_UP;
  376. netlink_init(nlmsg, RTM_NEWLINK, NLM_F_EXCL | NLM_F_CREATE, &hdr,
  377. sizeof(hdr));
  378. if (name)
  379. netlink_attr(nlmsg, IFLA_IFNAME, name, strlen(name));
  380. netlink_nest(nlmsg, IFLA_LINKINFO);
  381. netlink_attr(nlmsg, IFLA_INFO_KIND, type, strlen(type));
  382. }
  383.  
  384. static void netlink_add_device(struct nlmsg* nlmsg, int sock, const char* type,
  385. const char* name)
  386. {
  387. netlink_add_device_impl(nlmsg, type, name, false);
  388. netlink_done(nlmsg);
  389. int err = netlink_send(nlmsg, sock);
  390. if (err < 0) {
  391. }
  392. }
  393.  
  394. static void netlink_add_veth(struct nlmsg* nlmsg, int sock, const char* name,
  395. const char* peer)
  396. {
  397. netlink_add_device_impl(nlmsg, "veth", name, false);
  398. netlink_nest(nlmsg, IFLA_INFO_DATA);
  399. netlink_nest(nlmsg, VETH_INFO_PEER);
  400. nlmsg->pos += sizeof(struct ifinfomsg);
  401. netlink_attr(nlmsg, IFLA_IFNAME, peer, strlen(peer));
  402. netlink_done(nlmsg);
  403. netlink_done(nlmsg);
  404. netlink_done(nlmsg);
  405. int err = netlink_send(nlmsg, sock);
  406. if (err < 0) {
  407. }
  408. }
  409.  
  410. static void netlink_add_xfrm(struct nlmsg* nlmsg, int sock, const char* name)
  411. {
  412. netlink_add_device_impl(nlmsg, "xfrm", name, true);
  413. netlink_nest(nlmsg, IFLA_INFO_DATA);
  414. int if_id = 1;
  415. netlink_attr(nlmsg, 2, &if_id, sizeof(if_id));
  416. netlink_done(nlmsg);
  417. netlink_done(nlmsg);
  418. int err = netlink_send(nlmsg, sock);
  419. if (err < 0) {
  420. }
  421. }
  422.  
  423. static void netlink_add_hsr(struct nlmsg* nlmsg, int sock, const char* name,
  424. const char* slave1, const char* slave2)
  425. {
  426. netlink_add_device_impl(nlmsg, "hsr", name, false);
  427. netlink_nest(nlmsg, IFLA_INFO_DATA);
  428. int ifindex1 = if_nametoindex(slave1);
  429. netlink_attr(nlmsg, IFLA_HSR_SLAVE1, &ifindex1, sizeof(ifindex1));
  430. int ifindex2 = if_nametoindex(slave2);
  431. netlink_attr(nlmsg, IFLA_HSR_SLAVE2, &ifindex2, sizeof(ifindex2));
  432. netlink_done(nlmsg);
  433. netlink_done(nlmsg);
  434. int err = netlink_send(nlmsg, sock);
  435. if (err < 0) {
  436. }
  437. }
  438.  
  439. static void netlink_add_linked(struct nlmsg* nlmsg, int sock, const char* type,
  440. const char* name, const char* link)
  441. {
  442. netlink_add_device_impl(nlmsg, type, name, false);
  443. netlink_done(nlmsg);
  444. int ifindex = if_nametoindex(link);
  445. netlink_attr(nlmsg, IFLA_LINK, &ifindex, sizeof(ifindex));
  446. int err = netlink_send(nlmsg, sock);
  447. if (err < 0) {
  448. }
  449. }
  450.  
  451. static void netlink_add_vlan(struct nlmsg* nlmsg, int sock, const char* name,
  452. const char* link, uint16_t id, uint16_t proto)
  453. {
  454. netlink_add_device_impl(nlmsg, "vlan", name, false);
  455. netlink_nest(nlmsg, IFLA_INFO_DATA);
  456. netlink_attr(nlmsg, IFLA_VLAN_ID, &id, sizeof(id));
  457. netlink_attr(nlmsg, IFLA_VLAN_PROTOCOL, &proto, sizeof(proto));
  458. netlink_done(nlmsg);
  459. netlink_done(nlmsg);
  460. int ifindex = if_nametoindex(link);
  461. netlink_attr(nlmsg, IFLA_LINK, &ifindex, sizeof(ifindex));
  462. int err = netlink_send(nlmsg, sock);
  463. if (err < 0) {
  464. }
  465. }
  466.  
  467. static void netlink_add_macvlan(struct nlmsg* nlmsg, int sock, const char* name,
  468. const char* link)
  469. {
  470. netlink_add_device_impl(nlmsg, "macvlan", name, false);
  471. netlink_nest(nlmsg, IFLA_INFO_DATA);
  472. uint32_t mode = MACVLAN_MODE_BRIDGE;
  473. netlink_attr(nlmsg, IFLA_MACVLAN_MODE, &mode, sizeof(mode));
  474. netlink_done(nlmsg);
  475. netlink_done(nlmsg);
  476. int ifindex = if_nametoindex(link);
  477. netlink_attr(nlmsg, IFLA_LINK, &ifindex, sizeof(ifindex));
  478. int err = netlink_send(nlmsg, sock);
  479. if (err < 0) {
  480. }
  481. }
  482.  
  483. static void netlink_add_geneve(struct nlmsg* nlmsg, int sock, const char* name,
  484. uint32_t vni, struct in_addr* addr4,
  485. struct in6_addr* addr6)
  486. {
  487. netlink_add_device_impl(nlmsg, "geneve", name, false);
  488. netlink_nest(nlmsg, IFLA_INFO_DATA);
  489. netlink_attr(nlmsg, IFLA_GENEVE_ID, &vni, sizeof(vni));
  490. if (addr4)
  491. netlink_attr(nlmsg, IFLA_GENEVE_REMOTE, addr4, sizeof(*addr4));
  492. if (addr6)
  493. netlink_attr(nlmsg, IFLA_GENEVE_REMOTE6, addr6, sizeof(*addr6));
  494. netlink_done(nlmsg);
  495. netlink_done(nlmsg);
  496. int err = netlink_send(nlmsg, sock);
  497. if (err < 0) {
  498. }
  499. }
  500.  
  501. #define IFLA_IPVLAN_FLAGS 2
  502. #define IPVLAN_MODE_L3S 2
  503. #undef IPVLAN_F_VEPA
  504. #define IPVLAN_F_VEPA 2
  505.  
  506. static void netlink_add_ipvlan(struct nlmsg* nlmsg, int sock, const char* name,
  507. const char* link, uint16_t mode, uint16_t flags)
  508. {
  509. netlink_add_device_impl(nlmsg, "ipvlan", name, false);
  510. netlink_nest(nlmsg, IFLA_INFO_DATA);
  511. netlink_attr(nlmsg, IFLA_IPVLAN_MODE, &mode, sizeof(mode));
  512. netlink_attr(nlmsg, IFLA_IPVLAN_FLAGS, &flags, sizeof(flags));
  513. netlink_done(nlmsg);
  514. netlink_done(nlmsg);
  515. int ifindex = if_nametoindex(link);
  516. netlink_attr(nlmsg, IFLA_LINK, &ifindex, sizeof(ifindex));
  517. int err = netlink_send(nlmsg, sock);
  518. if (err < 0) {
  519. }
  520. }
  521.  
  522. static void netlink_device_change(struct nlmsg* nlmsg, int sock,
  523. const char* name, bool up, const char* master,
  524. const void* mac, int macsize,
  525. const char* new_name)
  526. {
  527. struct ifinfomsg hdr;
  528. memset(&hdr, 0, sizeof(hdr));
  529. if (up)
  530. hdr.ifi_flags = hdr.ifi_change = IFF_UP;
  531. hdr.ifi_index = if_nametoindex(name);
  532. netlink_init(nlmsg, RTM_NEWLINK, 0, &hdr, sizeof(hdr));
  533. if (new_name)
  534. netlink_attr(nlmsg, IFLA_IFNAME, new_name, strlen(new_name));
  535. if (master) {
  536. int ifindex = if_nametoindex(master);
  537. netlink_attr(nlmsg, IFLA_MASTER, &ifindex, sizeof(ifindex));
  538. }
  539. if (macsize)
  540. netlink_attr(nlmsg, IFLA_ADDRESS, mac, macsize);
  541. int err = netlink_send(nlmsg, sock);
  542. if (err < 0) {
  543. }
  544. }
  545.  
  546. static int netlink_add_addr(struct nlmsg* nlmsg, int sock, const char* dev,
  547. const void* addr, int addrsize)
  548. {
  549. struct ifaddrmsg hdr;
  550. memset(&hdr, 0, sizeof(hdr));
  551. hdr.ifa_family = addrsize == 4 ? AF_INET : AF_INET6;
  552. hdr.ifa_prefixlen = addrsize == 4 ? 24 : 120;
  553. hdr.ifa_scope = RT_SCOPE_UNIVERSE;
  554. hdr.ifa_index = if_nametoindex(dev);
  555. netlink_init(nlmsg, RTM_NEWADDR, NLM_F_CREATE | NLM_F_REPLACE, &hdr,
  556. sizeof(hdr));
  557. netlink_attr(nlmsg, IFA_LOCAL, addr, addrsize);
  558. netlink_attr(nlmsg, IFA_ADDRESS, addr, addrsize);
  559. return netlink_send(nlmsg, sock);
  560. }
  561.  
  562. static void netlink_add_addr4(struct nlmsg* nlmsg, int sock, const char* dev,
  563. const char* addr)
  564. {
  565. struct in_addr in_addr;
  566. inet_pton(AF_INET, addr, &in_addr);
  567. int err = netlink_add_addr(nlmsg, sock, dev, &in_addr, sizeof(in_addr));
  568. if (err < 0) {
  569. }
  570. }
  571.  
  572. static void netlink_add_addr6(struct nlmsg* nlmsg, int sock, const char* dev,
  573. const char* addr)
  574. {
  575. struct in6_addr in6_addr;
  576. inet_pton(AF_INET6, addr, &in6_addr);
  577. int err = netlink_add_addr(nlmsg, sock, dev, &in6_addr, sizeof(in6_addr));
  578. if (err < 0) {
  579. }
  580. }
  581.  
  582. static struct nlmsg nlmsg;
  583.  
  584. #define DEVLINK_FAMILY_NAME "devlink"
  585.  
  586. #define DEVLINK_CMD_PORT_GET 5
  587. #define DEVLINK_ATTR_BUS_NAME 1
  588. #define DEVLINK_ATTR_DEV_NAME 2
  589. #define DEVLINK_ATTR_NETDEV_NAME 7
  590.  
  591. static struct nlmsg nlmsg2;
  592.  
  593. static void initialize_devlink_ports(const char* bus_name, const char* dev_name,
  594. const char* netdev_prefix)
  595. {
  596. struct genlmsghdr genlhdr;
  597. int len, total_len, id, err, offset;
  598. uint16_t netdev_index;
  599. int sock = socket(AF_NETLINK, SOCK_RAW, NETLINK_GENERIC);
  600. if (sock == -1)
  601. exit(1);
  602. int rtsock = socket(AF_NETLINK, SOCK_RAW, NETLINK_ROUTE);
  603. if (rtsock == -1)
  604. exit(1);
  605. id = netlink_query_family_id(&nlmsg, sock, DEVLINK_FAMILY_NAME, true);
  606. if (id == -1)
  607. goto error;
  608. memset(&genlhdr, 0, sizeof(genlhdr));
  609. genlhdr.cmd = DEVLINK_CMD_PORT_GET;
  610. netlink_init(&nlmsg, id, NLM_F_DUMP, &genlhdr, sizeof(genlhdr));
  611. netlink_attr(&nlmsg, DEVLINK_ATTR_BUS_NAME, bus_name, strlen(bus_name) + 1);
  612. netlink_attr(&nlmsg, DEVLINK_ATTR_DEV_NAME, dev_name, strlen(dev_name) + 1);
  613. err = netlink_send_ext(&nlmsg, sock, id, &total_len, true);
  614. if (err < 0) {
  615. goto error;
  616. }
  617. offset = 0;
  618. netdev_index = 0;
  619. while ((len = netlink_next_msg(&nlmsg, offset, total_len)) != -1) {
  620. struct nlattr* attr = (struct nlattr*)(nlmsg.buf + offset + NLMSG_HDRLEN +
  621. NLMSG_ALIGN(sizeof(genlhdr)));
  622. for (; (char*)attr < nlmsg.buf + offset + len;
  623. attr = (struct nlattr*)((char*)attr + NLMSG_ALIGN(attr->nla_len))) {
  624. if (attr->nla_type == DEVLINK_ATTR_NETDEV_NAME) {
  625. char* port_name;
  626. char netdev_name[IFNAMSIZ];
  627. port_name = (char*)(attr + 1);
  628. snprintf(netdev_name, sizeof(netdev_name), "%s%d", netdev_prefix,
  629. netdev_index);
  630. netlink_device_change(&nlmsg2, rtsock, port_name, true, 0, 0, 0,
  631. netdev_name);
  632. break;
  633. }
  634. }
  635. offset += len;
  636. netdev_index++;
  637. }
  638. error:
  639. close(rtsock);
  640. close(sock);
  641. }
  642.  
  643. #define DEV_IPV4 "172.20.20.%d"
  644. #define DEV_IPV6 "fe80::%02x"
  645. #define DEV_MAC 0x00aaaaaaaaaa
  646.  
  647. static void netdevsim_add(unsigned int addr, unsigned int port_count)
  648. {
  649. write_file("/sys/bus/netdevsim/del_device", "%u", addr);
  650. if (write_file("/sys/bus/netdevsim/new_device", "%u %u", addr, port_count)) {
  651. char buf[32];
  652. snprintf(buf, sizeof(buf), "netdevsim%d", addr);
  653. initialize_devlink_ports("netdevsim", buf, "netdevsim");
  654. }
  655. }
  656.  
  657. #define WG_GENL_NAME "wireguard"
  658. enum wg_cmd {
  659. WG_CMD_GET_DEVICE,
  660. WG_CMD_SET_DEVICE,
  661. };
  662. enum wgdevice_attribute {
  663. WGDEVICE_A_UNSPEC,
  664. WGDEVICE_A_IFINDEX,
  665. WGDEVICE_A_IFNAME,
  666. WGDEVICE_A_PRIVATE_KEY,
  667. WGDEVICE_A_PUBLIC_KEY,
  668. WGDEVICE_A_FLAGS,
  669. WGDEVICE_A_LISTEN_PORT,
  670. WGDEVICE_A_FWMARK,
  671. WGDEVICE_A_PEERS,
  672. };
  673. enum wgpeer_attribute {
  674. WGPEER_A_UNSPEC,
  675. WGPEER_A_PUBLIC_KEY,
  676. WGPEER_A_PRESHARED_KEY,
  677. WGPEER_A_FLAGS,
  678. WGPEER_A_ENDPOINT,
  679. WGPEER_A_PERSISTENT_KEEPALIVE_INTERVAL,
  680. WGPEER_A_LAST_HANDSHAKE_TIME,
  681. WGPEER_A_RX_BYTES,
  682. WGPEER_A_TX_BYTES,
  683. WGPEER_A_ALLOWEDIPS,
  684. WGPEER_A_PROTOCOL_VERSION,
  685. };
  686. enum wgallowedip_attribute {
  687. WGALLOWEDIP_A_UNSPEC,
  688. WGALLOWEDIP_A_FAMILY,
  689. WGALLOWEDIP_A_IPADDR,
  690. WGALLOWEDIP_A_CIDR_MASK,
  691. };
  692.  
  693. static void netlink_wireguard_setup(void)
  694. {
  695. const char ifname_a[] = "wg0";
  696. const char ifname_b[] = "wg1";
  697. const char ifname_c[] = "wg2";
  698. const char private_a[] =
  699. "\xa0\x5c\xa8\x4f\x6c\x9c\x8e\x38\x53\xe2\xfd\x7a\x70\xae\x0f\xb2\x0f\xa1"
  700. "\x52\x60\x0c\xb0\x08\x45\x17\x4f\x08\x07\x6f\x8d\x78\x43";
  701. const char private_b[] =
  702. "\xb0\x80\x73\xe8\xd4\x4e\x91\xe3\xda\x92\x2c\x22\x43\x82\x44\xbb\x88\x5c"
  703. "\x69\xe2\x69\xc8\xe9\xd8\x35\xb1\x14\x29\x3a\x4d\xdc\x6e";
  704. const char private_c[] =
  705. "\xa0\xcb\x87\x9a\x47\xf5\xbc\x64\x4c\x0e\x69\x3f\xa6\xd0\x31\xc7\x4a\x15"
  706. "\x53\xb6\xe9\x01\xb9\xff\x2f\x51\x8c\x78\x04\x2f\xb5\x42";
  707. const char public_a[] =
  708. "\x97\x5c\x9d\x81\xc9\x83\xc8\x20\x9e\xe7\x81\x25\x4b\x89\x9f\x8e\xd9\x25"
  709. "\xae\x9f\x09\x23\xc2\x3c\x62\xf5\x3c\x57\xcd\xbf\x69\x1c";
  710. const char public_b[] =
  711. "\xd1\x73\x28\x99\xf6\x11\xcd\x89\x94\x03\x4d\x7f\x41\x3d\xc9\x57\x63\x0e"
  712. "\x54\x93\xc2\x85\xac\xa4\x00\x65\xcb\x63\x11\xbe\x69\x6b";
  713. const char public_c[] =
  714. "\xf4\x4d\xa3\x67\xa8\x8e\xe6\x56\x4f\x02\x02\x11\x45\x67\x27\x08\x2f\x5c"
  715. "\xeb\xee\x8b\x1b\xf5\xeb\x73\x37\x34\x1b\x45\x9b\x39\x22";
  716. const uint16_t listen_a = 20001;
  717. const uint16_t listen_b = 20002;
  718. const uint16_t listen_c = 20003;
  719. const uint16_t af_inet = AF_INET;
  720. const uint16_t af_inet6 = AF_INET6;
  721. const struct sockaddr_in endpoint_b_v4 = {
  722. .sin_family = AF_INET,
  723. .sin_port = htons(listen_b),
  724. .sin_addr = {htonl(INADDR_LOOPBACK)}};
  725. const struct sockaddr_in endpoint_c_v4 = {
  726. .sin_family = AF_INET,
  727. .sin_port = htons(listen_c),
  728. .sin_addr = {htonl(INADDR_LOOPBACK)}};
  729. struct sockaddr_in6 endpoint_a_v6 = {.sin6_family = AF_INET6,
  730. .sin6_port = htons(listen_a)};
  731. endpoint_a_v6.sin6_addr = in6addr_loopback;
  732. struct sockaddr_in6 endpoint_c_v6 = {.sin6_family = AF_INET6,
  733. .sin6_port = htons(listen_c)};
  734. endpoint_c_v6.sin6_addr = in6addr_loopback;
  735. const struct in_addr first_half_v4 = {0};
  736. const struct in_addr second_half_v4 = {(uint32_t)htonl(128 << 24)};
  737. const struct in6_addr first_half_v6 = {{{0}}};
  738. const struct in6_addr second_half_v6 = {{{0x80}}};
  739. const uint8_t half_cidr = 1;
  740. const uint16_t persistent_keepalives[] = {1, 3, 7, 9, 14, 19};
  741. struct genlmsghdr genlhdr = {.cmd = WG_CMD_SET_DEVICE, .version = 1};
  742. int sock;
  743. int id, err;
  744. sock = socket(AF_NETLINK, SOCK_RAW, NETLINK_GENERIC);
  745. if (sock == -1) {
  746. return;
  747. }
  748. id = netlink_query_family_id(&nlmsg, sock, WG_GENL_NAME, true);
  749. if (id == -1)
  750. goto error;
  751. netlink_init(&nlmsg, id, 0, &genlhdr, sizeof(genlhdr));
  752. netlink_attr(&nlmsg, WGDEVICE_A_IFNAME, ifname_a, strlen(ifname_a) + 1);
  753. netlink_attr(&nlmsg, WGDEVICE_A_PRIVATE_KEY, private_a, 32);
  754. netlink_attr(&nlmsg, WGDEVICE_A_LISTEN_PORT, &listen_a, 2);
  755. netlink_nest(&nlmsg, NLA_F_NESTED | WGDEVICE_A_PEERS);
  756. netlink_nest(&nlmsg, NLA_F_NESTED | 0);
  757. netlink_attr(&nlmsg, WGPEER_A_PUBLIC_KEY, public_b, 32);
  758. netlink_attr(&nlmsg, WGPEER_A_ENDPOINT, &endpoint_b_v4,
  759. sizeof(endpoint_b_v4));
  760. netlink_attr(&nlmsg, WGPEER_A_PERSISTENT_KEEPALIVE_INTERVAL,
  761. &persistent_keepalives[0], 2);
  762. netlink_nest(&nlmsg, NLA_F_NESTED | WGPEER_A_ALLOWEDIPS);
  763. netlink_nest(&nlmsg, NLA_F_NESTED | 0);
  764. netlink_attr(&nlmsg, WGALLOWEDIP_A_FAMILY, &af_inet, 2);
  765. netlink_attr(&nlmsg, WGALLOWEDIP_A_IPADDR, &first_half_v4,
  766. sizeof(first_half_v4));
  767. netlink_attr(&nlmsg, WGALLOWEDIP_A_CIDR_MASK, &half_cidr, 1);
  768. netlink_done(&nlmsg);
  769. netlink_nest(&nlmsg, NLA_F_NESTED | 0);
  770. netlink_attr(&nlmsg, WGALLOWEDIP_A_FAMILY, &af_inet6, 2);
  771. netlink_attr(&nlmsg, WGALLOWEDIP_A_IPADDR, &first_half_v6,
  772. sizeof(first_half_v6));
  773. netlink_attr(&nlmsg, WGALLOWEDIP_A_CIDR_MASK, &half_cidr, 1);
  774. netlink_done(&nlmsg);
  775. netlink_done(&nlmsg);
  776. netlink_done(&nlmsg);
  777. netlink_nest(&nlmsg, NLA_F_NESTED | 0);
  778. netlink_attr(&nlmsg, WGPEER_A_PUBLIC_KEY, public_c, 32);
  779. netlink_attr(&nlmsg, WGPEER_A_ENDPOINT, &endpoint_c_v6,
  780. sizeof(endpoint_c_v6));
  781. netlink_attr(&nlmsg, WGPEER_A_PERSISTENT_KEEPALIVE_INTERVAL,
  782. &persistent_keepalives[1], 2);
  783. netlink_nest(&nlmsg, NLA_F_NESTED | WGPEER_A_ALLOWEDIPS);
  784. netlink_nest(&nlmsg, NLA_F_NESTED | 0);
  785. netlink_attr(&nlmsg, WGALLOWEDIP_A_FAMILY, &af_inet, 2);
  786. netlink_attr(&nlmsg, WGALLOWEDIP_A_IPADDR, &second_half_v4,
  787. sizeof(second_half_v4));
  788. netlink_attr(&nlmsg, WGALLOWEDIP_A_CIDR_MASK, &half_cidr, 1);
  789. netlink_done(&nlmsg);
  790. netlink_nest(&nlmsg, NLA_F_NESTED | 0);
  791. netlink_attr(&nlmsg, WGALLOWEDIP_A_FAMILY, &af_inet6, 2);
  792. netlink_attr(&nlmsg, WGALLOWEDIP_A_IPADDR, &second_half_v6,
  793. sizeof(second_half_v6));
  794. netlink_attr(&nlmsg, WGALLOWEDIP_A_CIDR_MASK, &half_cidr, 1);
  795. netlink_done(&nlmsg);
  796. netlink_done(&nlmsg);
  797. netlink_done(&nlmsg);
  798. netlink_done(&nlmsg);
  799. err = netlink_send(&nlmsg, sock);
  800. if (err < 0) {
  801. }
  802. netlink_init(&nlmsg, id, 0, &genlhdr, sizeof(genlhdr));
  803. netlink_attr(&nlmsg, WGDEVICE_A_IFNAME, ifname_b, strlen(ifname_b) + 1);
  804. netlink_attr(&nlmsg, WGDEVICE_A_PRIVATE_KEY, private_b, 32);
  805. netlink_attr(&nlmsg, WGDEVICE_A_LISTEN_PORT, &listen_b, 2);
  806. netlink_nest(&nlmsg, NLA_F_NESTED | WGDEVICE_A_PEERS);
  807. netlink_nest(&nlmsg, NLA_F_NESTED | 0);
  808. netlink_attr(&nlmsg, WGPEER_A_PUBLIC_KEY, public_a, 32);
  809. netlink_attr(&nlmsg, WGPEER_A_ENDPOINT, &endpoint_a_v6,
  810. sizeof(endpoint_a_v6));
  811. netlink_attr(&nlmsg, WGPEER_A_PERSISTENT_KEEPALIVE_INTERVAL,
  812. &persistent_keepalives[2], 2);
  813. netlink_nest(&nlmsg, NLA_F_NESTED | WGPEER_A_ALLOWEDIPS);
  814. netlink_nest(&nlmsg, NLA_F_NESTED | 0);
  815. netlink_attr(&nlmsg, WGALLOWEDIP_A_FAMILY, &af_inet, 2);
  816. netlink_attr(&nlmsg, WGALLOWEDIP_A_IPADDR, &first_half_v4,
  817. sizeof(first_half_v4));
  818. netlink_attr(&nlmsg, WGALLOWEDIP_A_CIDR_MASK, &half_cidr, 1);
  819. netlink_done(&nlmsg);
  820. netlink_nest(&nlmsg, NLA_F_NESTED | 0);
  821. netlink_attr(&nlmsg, WGALLOWEDIP_A_FAMILY, &af_inet6, 2);
  822. netlink_attr(&nlmsg, WGALLOWEDIP_A_IPADDR, &first_half_v6,
  823. sizeof(first_half_v6));
  824. netlink_attr(&nlmsg, WGALLOWEDIP_A_CIDR_MASK, &half_cidr, 1);
  825. netlink_done(&nlmsg);
  826. netlink_done(&nlmsg);
  827. netlink_done(&nlmsg);
  828. netlink_nest(&nlmsg, NLA_F_NESTED | 0);
  829. netlink_attr(&nlmsg, WGPEER_A_PUBLIC_KEY, public_c, 32);
  830. netlink_attr(&nlmsg, WGPEER_A_ENDPOINT, &endpoint_c_v4,
  831. sizeof(endpoint_c_v4));
  832. netlink_attr(&nlmsg, WGPEER_A_PERSISTENT_KEEPALIVE_INTERVAL,
  833. &persistent_keepalives[3], 2);
  834. netlink_nest(&nlmsg, NLA_F_NESTED | WGPEER_A_ALLOWEDIPS);
  835. netlink_nest(&nlmsg, NLA_F_NESTED | 0);
  836. netlink_attr(&nlmsg, WGALLOWEDIP_A_FAMILY, &af_inet, 2);
  837. netlink_attr(&nlmsg, WGALLOWEDIP_A_IPADDR, &second_half_v4,
  838. sizeof(second_half_v4));
  839. netlink_attr(&nlmsg, WGALLOWEDIP_A_CIDR_MASK, &half_cidr, 1);
  840. netlink_done(&nlmsg);
  841. netlink_nest(&nlmsg, NLA_F_NESTED | 0);
  842. netlink_attr(&nlmsg, WGALLOWEDIP_A_FAMILY, &af_inet6, 2);
  843. netlink_attr(&nlmsg, WGALLOWEDIP_A_IPADDR, &second_half_v6,
  844. sizeof(second_half_v6));
  845. netlink_attr(&nlmsg, WGALLOWEDIP_A_CIDR_MASK, &half_cidr, 1);
  846. netlink_done(&nlmsg);
  847. netlink_done(&nlmsg);
  848. netlink_done(&nlmsg);
  849. netlink_done(&nlmsg);
  850. err = netlink_send(&nlmsg, sock);
  851. if (err < 0) {
  852. }
  853. netlink_init(&nlmsg, id, 0, &genlhdr, sizeof(genlhdr));
  854. netlink_attr(&nlmsg, WGDEVICE_A_IFNAME, ifname_c, strlen(ifname_c) + 1);
  855. netlink_attr(&nlmsg, WGDEVICE_A_PRIVATE_KEY, private_c, 32);
  856. netlink_attr(&nlmsg, WGDEVICE_A_LISTEN_PORT, &listen_c, 2);
  857. netlink_nest(&nlmsg, NLA_F_NESTED | WGDEVICE_A_PEERS);
  858. netlink_nest(&nlmsg, NLA_F_NESTED | 0);
  859. netlink_attr(&nlmsg, WGPEER_A_PUBLIC_KEY, public_a, 32);
  860. netlink_attr(&nlmsg, WGPEER_A_ENDPOINT, &endpoint_a_v6,
  861. sizeof(endpoint_a_v6));
  862. netlink_attr(&nlmsg, WGPEER_A_PERSISTENT_KEEPALIVE_INTERVAL,
  863. &persistent_keepalives[4], 2);
  864. netlink_nest(&nlmsg, NLA_F_NESTED | WGPEER_A_ALLOWEDIPS);
  865. netlink_nest(&nlmsg, NLA_F_NESTED | 0);
  866. netlink_attr(&nlmsg, WGALLOWEDIP_A_FAMILY, &af_inet, 2);
  867. netlink_attr(&nlmsg, WGALLOWEDIP_A_IPADDR, &first_half_v4,
  868. sizeof(first_half_v4));
  869. netlink_attr(&nlmsg, WGALLOWEDIP_A_CIDR_MASK, &half_cidr, 1);
  870. netlink_done(&nlmsg);
  871. netlink_nest(&nlmsg, NLA_F_NESTED | 0);
  872. netlink_attr(&nlmsg, WGALLOWEDIP_A_FAMILY, &af_inet6, 2);
  873. netlink_attr(&nlmsg, WGALLOWEDIP_A_IPADDR, &first_half_v6,
  874. sizeof(first_half_v6));
  875. netlink_attr(&nlmsg, WGALLOWEDIP_A_CIDR_MASK, &half_cidr, 1);
  876. netlink_done(&nlmsg);
  877. netlink_done(&nlmsg);
  878. netlink_done(&nlmsg);
  879. netlink_nest(&nlmsg, NLA_F_NESTED | 0);
  880. netlink_attr(&nlmsg, WGPEER_A_PUBLIC_KEY, public_b, 32);
  881. netlink_attr(&nlmsg, WGPEER_A_ENDPOINT, &endpoint_b_v4,
  882. sizeof(endpoint_b_v4));
  883. netlink_attr(&nlmsg, WGPEER_A_PERSISTENT_KEEPALIVE_INTERVAL,
  884. &persistent_keepalives[5], 2);
  885. netlink_nest(&nlmsg, NLA_F_NESTED | WGPEER_A_ALLOWEDIPS);
  886. netlink_nest(&nlmsg, NLA_F_NESTED | 0);
  887. netlink_attr(&nlmsg, WGALLOWEDIP_A_FAMILY, &af_inet, 2);
  888. netlink_attr(&nlmsg, WGALLOWEDIP_A_IPADDR, &second_half_v4,
  889. sizeof(second_half_v4));
  890. netlink_attr(&nlmsg, WGALLOWEDIP_A_CIDR_MASK, &half_cidr, 1);
  891. netlink_done(&nlmsg);
  892. netlink_nest(&nlmsg, NLA_F_NESTED | 0);
  893. netlink_attr(&nlmsg, WGALLOWEDIP_A_FAMILY, &af_inet6, 2);
  894. netlink_attr(&nlmsg, WGALLOWEDIP_A_IPADDR, &second_half_v6,
  895. sizeof(second_half_v6));
  896. netlink_attr(&nlmsg, WGALLOWEDIP_A_CIDR_MASK, &half_cidr, 1);
  897. netlink_done(&nlmsg);
  898. netlink_done(&nlmsg);
  899. netlink_done(&nlmsg);
  900. netlink_done(&nlmsg);
  901. err = netlink_send(&nlmsg, sock);
  902. if (err < 0) {
  903. }
  904.  
  905. error:
  906. close(sock);
  907. }
  908.  
  909. static void initialize_netdevices(void)
  910. {
  911. char netdevsim[16];
  912. sprintf(netdevsim, "netdevsim%d", (int)procid);
  913. struct {
  914. const char* type;
  915. const char* dev;
  916. } devtypes[] = {
  917. {"ip6gretap", "ip6gretap0"}, {"bridge", "bridge0"}, {"vcan", "vcan0"},
  918. {"bond", "bond0"}, {"team", "team0"}, {"dummy", "dummy0"},
  919. {"nlmon", "nlmon0"}, {"caif", "caif0"}, {"batadv", "batadv0"},
  920. {"vxcan", "vxcan1"}, {"veth", 0}, {"wireguard", "wg0"},
  921. {"wireguard", "wg1"}, {"wireguard", "wg2"},
  922. };
  923. const char* devmasters[] = {"bridge", "bond", "team", "batadv"};
  924. struct {
  925. const char* name;
  926. int macsize;
  927. bool noipv6;
  928. } devices[] = {
  929. {"lo", ETH_ALEN},
  930. {"sit0", 0},
  931. {"bridge0", ETH_ALEN},
  932. {"vcan0", 0, true},
  933. {"tunl0", 0},
  934. {"gre0", 0},
  935. {"gretap0", ETH_ALEN},
  936. {"ip_vti0", 0},
  937. {"ip6_vti0", 0},
  938. {"ip6tnl0", 0},
  939. {"ip6gre0", 0},
  940. {"ip6gretap0", ETH_ALEN},
  941. {"erspan0", ETH_ALEN},
  942. {"bond0", ETH_ALEN},
  943. {"veth0", ETH_ALEN},
  944. {"veth1", ETH_ALEN},
  945. {"team0", ETH_ALEN},
  946. {"veth0_to_bridge", ETH_ALEN},
  947. {"veth1_to_bridge", ETH_ALEN},
  948. {"veth0_to_bond", ETH_ALEN},
  949. {"veth1_to_bond", ETH_ALEN},
  950. {"veth0_to_team", ETH_ALEN},
  951. {"veth1_to_team", ETH_ALEN},
  952. {"veth0_to_hsr", ETH_ALEN},
  953. {"veth1_to_hsr", ETH_ALEN},
  954. {"hsr0", 0},
  955. {"dummy0", ETH_ALEN},
  956. {"nlmon0", 0},
  957. {"vxcan0", 0, true},
  958. {"vxcan1", 0, true},
  959. {"caif0", ETH_ALEN},
  960. {"batadv0", ETH_ALEN},
  961. {netdevsim, ETH_ALEN},
  962. {"xfrm0", ETH_ALEN},
  963. {"veth0_virt_wifi", ETH_ALEN},
  964. {"veth1_virt_wifi", ETH_ALEN},
  965. {"virt_wifi0", ETH_ALEN},
  966. {"veth0_vlan", ETH_ALEN},
  967. {"veth1_vlan", ETH_ALEN},
  968. {"vlan0", ETH_ALEN},
  969. {"vlan1", ETH_ALEN},
  970. {"macvlan0", ETH_ALEN},
  971. {"macvlan1", ETH_ALEN},
  972. {"ipvlan0", ETH_ALEN},
  973. {"ipvlan1", ETH_ALEN},
  974. {"veth0_macvtap", ETH_ALEN},
  975. {"veth1_macvtap", ETH_ALEN},
  976. {"macvtap0", ETH_ALEN},
  977. {"macsec0", ETH_ALEN},
  978. {"veth0_to_batadv", ETH_ALEN},
  979. {"veth1_to_batadv", ETH_ALEN},
  980. {"batadv_slave_0", ETH_ALEN},
  981. {"batadv_slave_1", ETH_ALEN},
  982. {"geneve0", ETH_ALEN},
  983. {"geneve1", ETH_ALEN},
  984. {"wg0", 0},
  985. {"wg1", 0},
  986. {"wg2", 0},
  987. };
  988. int sock = socket(AF_NETLINK, SOCK_RAW, NETLINK_ROUTE);
  989. if (sock == -1)
  990. exit(1);
  991. unsigned i;
  992. for (i = 0; i < sizeof(devtypes) / sizeof(devtypes[0]); i++)
  993. netlink_add_device(&nlmsg, sock, devtypes[i].type, devtypes[i].dev);
  994. for (i = 0; i < sizeof(devmasters) / (sizeof(devmasters[0])); i++) {
  995. char master[32], slave0[32], veth0[32], slave1[32], veth1[32];
  996. sprintf(slave0, "%s_slave_0", devmasters[i]);
  997. sprintf(veth0, "veth0_to_%s", devmasters[i]);
  998. netlink_add_veth(&nlmsg, sock, slave0, veth0);
  999. sprintf(slave1, "%s_slave_1", devmasters[i]);
  1000. sprintf(veth1, "veth1_to_%s", devmasters[i]);
  1001. netlink_add_veth(&nlmsg, sock, slave1, veth1);
  1002. sprintf(master, "%s0", devmasters[i]);
  1003. netlink_device_change(&nlmsg, sock, slave0, false, master, 0, 0, NULL);
  1004. netlink_device_change(&nlmsg, sock, slave1, false, master, 0, 0, NULL);
  1005. }
  1006. netlink_add_xfrm(&nlmsg, sock, "xfrm0");
  1007. netlink_device_change(&nlmsg, sock, "bridge_slave_0", true, 0, 0, 0, NULL);
  1008. netlink_device_change(&nlmsg, sock, "bridge_slave_1", true, 0, 0, 0, NULL);
  1009. netlink_add_veth(&nlmsg, sock, "hsr_slave_0", "veth0_to_hsr");
  1010. netlink_add_veth(&nlmsg, sock, "hsr_slave_1", "veth1_to_hsr");
  1011. netlink_add_hsr(&nlmsg, sock, "hsr0", "hsr_slave_0", "hsr_slave_1");
  1012. netlink_device_change(&nlmsg, sock, "hsr_slave_0", true, 0, 0, 0, NULL);
  1013. netlink_device_change(&nlmsg, sock, "hsr_slave_1", true, 0, 0, 0, NULL);
  1014. netlink_add_veth(&nlmsg, sock, "veth0_virt_wifi", "veth1_virt_wifi");
  1015. netlink_add_linked(&nlmsg, sock, "virt_wifi", "virt_wifi0",
  1016. "veth1_virt_wifi");
  1017. netlink_add_veth(&nlmsg, sock, "veth0_vlan", "veth1_vlan");
  1018. netlink_add_vlan(&nlmsg, sock, "vlan0", "veth0_vlan", 0, htons(ETH_P_8021Q));
  1019. netlink_add_vlan(&nlmsg, sock, "vlan1", "veth0_vlan", 1, htons(ETH_P_8021AD));
  1020. netlink_add_macvlan(&nlmsg, sock, "macvlan0", "veth1_vlan");
  1021. netlink_add_macvlan(&nlmsg, sock, "macvlan1", "veth1_vlan");
  1022. netlink_add_ipvlan(&nlmsg, sock, "ipvlan0", "veth0_vlan", IPVLAN_MODE_L2, 0);
  1023. netlink_add_ipvlan(&nlmsg, sock, "ipvlan1", "veth0_vlan", IPVLAN_MODE_L3S,
  1024. IPVLAN_F_VEPA);
  1025. netlink_add_veth(&nlmsg, sock, "veth0_macvtap", "veth1_macvtap");
  1026. netlink_add_linked(&nlmsg, sock, "macvtap", "macvtap0", "veth0_macvtap");
  1027. netlink_add_linked(&nlmsg, sock, "macsec", "macsec0", "veth1_macvtap");
  1028. char addr[32];
  1029. sprintf(addr, DEV_IPV4, 14 + 10);
  1030. struct in_addr geneve_addr4;
  1031. if (inet_pton(AF_INET, addr, &geneve_addr4) <= 0)
  1032. exit(1);
  1033. struct in6_addr geneve_addr6;
  1034. if (inet_pton(AF_INET6, "fc00::01", &geneve_addr6) <= 0)
  1035. exit(1);
  1036. netlink_add_geneve(&nlmsg, sock, "geneve0", 0, &geneve_addr4, 0);
  1037. netlink_add_geneve(&nlmsg, sock, "geneve1", 1, 0, &geneve_addr6);
  1038. netdevsim_add((int)procid, 4);
  1039. netlink_wireguard_setup();
  1040. for (i = 0; i < sizeof(devices) / (sizeof(devices[0])); i++) {
  1041. char addr[32];
  1042. sprintf(addr, DEV_IPV4, i + 10);
  1043. netlink_add_addr4(&nlmsg, sock, devices[i].name, addr);
  1044. if (!devices[i].noipv6) {
  1045. sprintf(addr, DEV_IPV6, i + 10);
  1046. netlink_add_addr6(&nlmsg, sock, devices[i].name, addr);
  1047. }
  1048. uint64_t macaddr = DEV_MAC + ((i + 10ull) << 40);
  1049. netlink_device_change(&nlmsg, sock, devices[i].name, true, 0, &macaddr,
  1050. devices[i].macsize, NULL);
  1051. }
  1052. close(sock);
  1053. }
  1054. static void initialize_netdevices_init(void)
  1055. {
  1056. int sock = socket(AF_NETLINK, SOCK_RAW, NETLINK_ROUTE);
  1057. if (sock == -1)
  1058. exit(1);
  1059. struct {
  1060. const char* type;
  1061. int macsize;
  1062. bool noipv6;
  1063. bool noup;
  1064. } devtypes[] = {
  1065. {"nr", 7, true},
  1066. {"rose", 5, true, true},
  1067. };
  1068. unsigned i;
  1069. for (i = 0; i < sizeof(devtypes) / sizeof(devtypes[0]); i++) {
  1070. char dev[32], addr[32];
  1071. sprintf(dev, "%s%d", devtypes[i].type, (int)procid);
  1072. sprintf(addr, "172.30.%d.%d", i, (int)procid + 1);
  1073. netlink_add_addr4(&nlmsg, sock, dev, addr);
  1074. if (!devtypes[i].noipv6) {
  1075. sprintf(addr, "fe88::%02x:%02x", i, (int)procid + 1);
  1076. netlink_add_addr6(&nlmsg, sock, dev, addr);
  1077. }
  1078. int macsize = devtypes[i].macsize;
  1079. uint64_t macaddr = 0xbbbbbb +
  1080. ((unsigned long long)i << (8 * (macsize - 2))) +
  1081. (procid << (8 * (macsize - 1)));
  1082. netlink_device_change(&nlmsg, sock, dev, !devtypes[i].noup, 0, &macaddr,
  1083. macsize, NULL);
  1084. }
  1085. close(sock);
  1086. }
  1087.  
  1088. #define MAX_FDS 30
  1089.  
  1090. //% This code is derived from puff.{c,h}, found in the zlib development. The
  1091. //% original files come with the following copyright notice:
  1092.  
  1093. //% Copyright (C) 2002-2013 Mark Adler, all rights reserved
  1094. //% version 2.3, 21 Jan 2013
  1095. //% This software is provided 'as-is', without any express or implied
  1096. //% warranty. In no event will the author be held liable for any damages
  1097. //% arising from the use of this software.
  1098. //% Permission is granted to anyone to use this software for any purpose,
  1099. //% including commercial applications, and to alter it and redistribute it
  1100. //% freely, subject to the following restrictions:
  1101. //% 1. The origin of this software must not be misrepresented; you must not
  1102. //% claim that you wrote the original software. If you use this software
  1103. //% in a product, an acknowledgment in the product documentation would be
  1104. //% appreciated but is not required.
  1105. //% 2. Altered source versions must be plainly marked as such, and must not be
  1106. //% misrepresented as being the original software.
  1107. //% 3. This notice may not be removed or altered from any source distribution.
  1108. //% Mark Adler [email protected]
  1109.  
  1110. //% BEGIN CODE DERIVED FROM puff.{c,h}
  1111.  
  1112. #define MAXBITS 15
  1113. #define MAXLCODES 286
  1114. #define MAXDCODES 30
  1115. #define MAXCODES (MAXLCODES + MAXDCODES)
  1116. #define FIXLCODES 288
  1117.  
  1118. struct puff_state {
  1119. unsigned char* out;
  1120. unsigned long outlen;
  1121. unsigned long outcnt;
  1122. const unsigned char* in;
  1123. unsigned long inlen;
  1124. unsigned long incnt;
  1125. int bitbuf;
  1126. int bitcnt;
  1127. jmp_buf env;
  1128. };
  1129. static int puff_bits(struct puff_state* s, int need)
  1130. {
  1131. long val = s->bitbuf;
  1132. while (s->bitcnt < need) {
  1133. if (s->incnt == s->inlen)
  1134. longjmp(s->env, 1);
  1135. val |= (long)(s->in[s->incnt++]) << s->bitcnt;
  1136. s->bitcnt += 8;
  1137. }
  1138. s->bitbuf = (int)(val >> need);
  1139. s->bitcnt -= need;
  1140. return (int)(val & ((1L << need) - 1));
  1141. }
  1142. static int puff_stored(struct puff_state* s)
  1143. {
  1144. s->bitbuf = 0;
  1145. s->bitcnt = 0;
  1146. if (s->incnt + 4 > s->inlen)
  1147. return 2;
  1148. unsigned len = s->in[s->incnt++];
  1149. len |= s->in[s->incnt++] << 8;
  1150. if (s->in[s->incnt++] != (~len & 0xff) ||
  1151. s->in[s->incnt++] != ((~len >> 8) & 0xff))
  1152. return -2;
  1153. if (s->incnt + len > s->inlen)
  1154. return 2;
  1155. if (s->outcnt + len > s->outlen)
  1156. return 1;
  1157. for (; len--; s->outcnt++, s->incnt++) {
  1158. if (s->in[s->incnt])
  1159. s->out[s->outcnt] = s->in[s->incnt];
  1160. }
  1161. return 0;
  1162. }
  1163. struct puff_huffman {
  1164. short* count;
  1165. short* symbol;
  1166. };
  1167. static int puff_decode(struct puff_state* s, const struct puff_huffman* h)
  1168. {
  1169. int first = 0;
  1170. int index = 0;
  1171. int bitbuf = s->bitbuf;
  1172. int left = s->bitcnt;
  1173. int code = first = index = 0;
  1174. int len = 1;
  1175. short* next = h->count + 1;
  1176. while (1) {
  1177. while (left--) {
  1178. code |= bitbuf & 1;
  1179. bitbuf >>= 1;
  1180. int count = *next++;
  1181. if (code - count < first) {
  1182. s->bitbuf = bitbuf;
  1183. s->bitcnt = (s->bitcnt - len) & 7;
  1184. return h->symbol[index + (code - first)];
  1185. }
  1186. index += count;
  1187. first += count;
  1188. first <<= 1;
  1189. code <<= 1;
  1190. len++;
  1191. }
  1192. left = (MAXBITS + 1) - len;
  1193. if (left == 0)
  1194. break;
  1195. if (s->incnt == s->inlen)
  1196. longjmp(s->env, 1);
  1197. bitbuf = s->in[s->incnt++];
  1198. if (left > 8)
  1199. left = 8;
  1200. }
  1201. return -10;
  1202. }
  1203. static int puff_construct(struct puff_huffman* h, const short* length, int n)
  1204. {
  1205. int len;
  1206. for (len = 0; len <= MAXBITS; len++)
  1207. h->count[len] = 0;
  1208. int symbol;
  1209. for (symbol = 0; symbol < n; symbol++)
  1210. (h->count[length[symbol]])++;
  1211. if (h->count[0] == n)
  1212. return 0;
  1213. int left = 1;
  1214. for (len = 1; len <= MAXBITS; len++) {
  1215. left <<= 1;
  1216. left -= h->count[len];
  1217. if (left < 0)
  1218. return left;
  1219. }
  1220. short offs[MAXBITS + 1];
  1221. offs[1] = 0;
  1222. for (len = 1; len < MAXBITS; len++)
  1223. offs[len + 1] = offs[len] + h->count[len];
  1224. for (symbol = 0; symbol < n; symbol++)
  1225. if (length[symbol] != 0)
  1226. h->symbol[offs[length[symbol]]++] = symbol;
  1227. return left;
  1228. }
  1229. static int puff_codes(struct puff_state* s, const struct puff_huffman* lencode,
  1230. const struct puff_huffman* distcode)
  1231. {
  1232. static const short lens[29] = {3, 4, 5, 6, 7, 8, 9, 10, 11, 13,
  1233. 15, 17, 19, 23, 27, 31, 35, 43, 51, 59,
  1234. 67, 83, 99, 115, 131, 163, 195, 227, 258};
  1235. static const short lext[29] = {0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 2, 2, 2,
  1236. 2, 3, 3, 3, 3, 4, 4, 4, 4, 5, 5, 5, 5, 0};
  1237. static const short dists[30] = {
  1238. 1, 2, 3, 4, 5, 7, 9, 13, 17, 25,
  1239. 33, 49, 65, 97, 129, 193, 257, 385, 513, 769,
  1240. 1025, 1537, 2049, 3073, 4097, 6145, 8193, 12289, 16385, 24577};
  1241. static const short dext[30] = {0, 0, 0, 0, 1, 1, 2, 2, 3, 3,
  1242. 4, 4, 5, 5, 6, 6, 7, 7, 8, 8,
  1243. 9, 9, 10, 10, 11, 11, 12, 12, 13, 13};
  1244. int symbol;
  1245. do {
  1246. symbol = puff_decode(s, lencode);
  1247. if (symbol < 0)
  1248. return symbol;
  1249. if (symbol < 256) {
  1250. if (s->outcnt == s->outlen)
  1251. return 1;
  1252. if (symbol)
  1253. s->out[s->outcnt] = symbol;
  1254. s->outcnt++;
  1255. } else if (symbol > 256) {
  1256. symbol -= 257;
  1257. if (symbol >= 29)
  1258. return -10;
  1259. int len = lens[symbol] + puff_bits(s, lext[symbol]);
  1260. symbol = puff_decode(s, distcode);
  1261. if (symbol < 0)
  1262. return symbol;
  1263. unsigned dist = dists[symbol] + puff_bits(s, dext[symbol]);
  1264. if (dist > s->outcnt)
  1265. return -11;
  1266. if (s->outcnt + len > s->outlen)
  1267. return 1;
  1268. while (len--) {
  1269. if (dist <= s->outcnt && s->out[s->outcnt - dist])
  1270. s->out[s->outcnt] = s->out[s->outcnt - dist];
  1271. s->outcnt++;
  1272. }
  1273. }
  1274. } while (symbol != 256);
  1275. return 0;
  1276. }
  1277. static int puff_fixed(struct puff_state* s)
  1278. {
  1279. static int virgin = 1;
  1280. static short lencnt[MAXBITS + 1], lensym[FIXLCODES];
  1281. static short distcnt[MAXBITS + 1], distsym[MAXDCODES];
  1282. static struct puff_huffman lencode, distcode;
  1283. if (virgin) {
  1284. lencode.count = lencnt;
  1285. lencode.symbol = lensym;
  1286. distcode.count = distcnt;
  1287. distcode.symbol = distsym;
  1288. short lengths[FIXLCODES];
  1289. int symbol;
  1290. for (symbol = 0; symbol < 144; symbol++)
  1291. lengths[symbol] = 8;
  1292. for (; symbol < 256; symbol++)
  1293. lengths[symbol] = 9;
  1294. for (; symbol < 280; symbol++)
  1295. lengths[symbol] = 7;
  1296. for (; symbol < FIXLCODES; symbol++)
  1297. lengths[symbol] = 8;
  1298. puff_construct(&lencode, lengths, FIXLCODES);
  1299. for (symbol = 0; symbol < MAXDCODES; symbol++)
  1300. lengths[symbol] = 5;
  1301. puff_construct(&distcode, lengths, MAXDCODES);
  1302. virgin = 0;
  1303. }
  1304. return puff_codes(s, &lencode, &distcode);
  1305. }
  1306. static int puff_dynamic(struct puff_state* s)
  1307. {
  1308. static const short order[19] = {16, 17, 18, 0, 8, 7, 9, 6, 10, 5,
  1309. 11, 4, 12, 3, 13, 2, 14, 1, 15};
  1310. int nlen = puff_bits(s, 5) + 257;
  1311. int ndist = puff_bits(s, 5) + 1;
  1312. int ncode = puff_bits(s, 4) + 4;
  1313. if (nlen > MAXLCODES || ndist > MAXDCODES)
  1314. return -3;
  1315. short lengths[MAXCODES];
  1316. int index;
  1317. for (index = 0; index < ncode; index++)
  1318. lengths[order[index]] = puff_bits(s, 3);
  1319. for (; index < 19; index++)
  1320. lengths[order[index]] = 0;
  1321. short lencnt[MAXBITS + 1], lensym[MAXLCODES];
  1322. struct puff_huffman lencode = {lencnt, lensym};
  1323. int err = puff_construct(&lencode, lengths, 19);
  1324. if (err != 0)
  1325. return -4;
  1326. index = 0;
  1327. while (index < nlen + ndist) {
  1328. int symbol;
  1329. int len;
  1330. symbol = puff_decode(s, &lencode);
  1331. if (symbol < 0)
  1332. return symbol;
  1333. if (symbol < 16)
  1334. lengths[index++] = symbol;
  1335. else {
  1336. len = 0;
  1337. if (symbol == 16) {
  1338. if (index == 0)
  1339. return -5;
  1340. len = lengths[index - 1];
  1341. symbol = 3 + puff_bits(s, 2);
  1342. } else if (symbol == 17)
  1343. symbol = 3 + puff_bits(s, 3);
  1344. else
  1345. symbol = 11 + puff_bits(s, 7);
  1346. if (index + symbol > nlen + ndist)
  1347. return -6;
  1348. while (symbol--)
  1349. lengths[index++] = len;
  1350. }
  1351. }
  1352. if (lengths[256] == 0)
  1353. return -9;
  1354. err = puff_construct(&lencode, lengths, nlen);
  1355. if (err && (err < 0 || nlen != lencode.count[0] + lencode.count[1]))
  1356. return -7;
  1357. short distcnt[MAXBITS + 1], distsym[MAXDCODES];
  1358. struct puff_huffman distcode = {distcnt, distsym};
  1359. err = puff_construct(&distcode, lengths + nlen, ndist);
  1360. if (err && (err < 0 || ndist != distcode.count[0] + distcode.count[1]))
  1361. return -8;
  1362. return puff_codes(s, &lencode, &distcode);
  1363. }
  1364. static int puff(unsigned char* dest, unsigned long* destlen,
  1365. const unsigned char* source, unsigned long sourcelen)
  1366. {
  1367. struct puff_state s = {
  1368. .out = dest,
  1369. .outlen = *destlen,
  1370. .outcnt = 0,
  1371. .in = source,
  1372. .inlen = sourcelen,
  1373. .incnt = 0,
  1374. .bitbuf = 0,
  1375. .bitcnt = 0,
  1376. };
  1377. int err;
  1378. if (setjmp(s.env) != 0)
  1379. err = 2;
  1380. else {
  1381. int last;
  1382. do {
  1383. last = puff_bits(&s, 1);
  1384. int type = puff_bits(&s, 2);
  1385. err = type == 0 ? puff_stored(&s)
  1386. : (type == 1 ? puff_fixed(&s)
  1387. : (type == 2 ? puff_dynamic(&s) : -1));
  1388. if (err != 0)
  1389. break;
  1390. } while (!last);
  1391. }
  1392. *destlen = s.outcnt;
  1393. return err;
  1394. }
  1395.  
  1396. //% END CODE DERIVED FROM puff.{c,h}
  1397.  
  1398. #define ZLIB_HEADER_WIDTH 2
  1399.  
  1400. static int puff_zlib_to_file(const unsigned char* source,
  1401. unsigned long sourcelen, int dest_fd)
  1402. {
  1403. if (sourcelen < ZLIB_HEADER_WIDTH)
  1404. return 0;
  1405. source += ZLIB_HEADER_WIDTH;
  1406. sourcelen -= ZLIB_HEADER_WIDTH;
  1407. const unsigned long max_destlen = 132 << 20;
  1408. void* ret = mmap(0, max_destlen, PROT_WRITE | PROT_READ,
  1409. MAP_PRIVATE | MAP_ANON, -1, 0);
  1410. if (ret == MAP_FAILED)
  1411. return -1;
  1412. unsigned char* dest = (unsigned char*)ret;
  1413. unsigned long destlen = max_destlen;
  1414. int err = puff(dest, &destlen, source, sourcelen);
  1415. if (err) {
  1416. munmap(dest, max_destlen);
  1417. errno = -err;
  1418. return -1;
  1419. }
  1420. if (write(dest_fd, dest, destlen) != (ssize_t)destlen) {
  1421. munmap(dest, max_destlen);
  1422. return -1;
  1423. }
  1424. return munmap(dest, max_destlen);
  1425. }
  1426.  
  1427. static int setup_loop_device(unsigned char* data, unsigned long size,
  1428. const char* loopname, int* loopfd_p)
  1429. {
  1430. int err = 0, loopfd = -1;
  1431. int memfd = syscall(__NR_memfd_create, "syzkaller", 0);
  1432. if (memfd == -1) {
  1433. err = errno;
  1434. goto error;
  1435. }
  1436. if (puff_zlib_to_file(data, size, memfd)) {
  1437. err = errno;
  1438. goto error_close_memfd;
  1439. }
  1440. loopfd = open(loopname, O_RDWR);
  1441. if (loopfd == -1) {
  1442. err = errno;
  1443. goto error_close_memfd;
  1444. }
  1445. if (ioctl(loopfd, LOOP_SET_FD, memfd)) {
  1446. if (errno != EBUSY) {
  1447. err = errno;
  1448. goto error_close_loop;
  1449. }
  1450. ioctl(loopfd, LOOP_CLR_FD, 0);
  1451. usleep(1000);
  1452. if (ioctl(loopfd, LOOP_SET_FD, memfd)) {
  1453. err = errno;
  1454. goto error_close_loop;
  1455. }
  1456. }
  1457. close(memfd);
  1458. *loopfd_p = loopfd;
  1459. return 0;
  1460.  
  1461. error_close_loop:
  1462. close(loopfd);
  1463. error_close_memfd:
  1464. close(memfd);
  1465. error:
  1466. errno = err;
  1467. return -1;
  1468. }
  1469.  
  1470. static void reset_loop_device(const char* loopname)
  1471. {
  1472. int loopfd = open(loopname, O_RDWR);
  1473. if (loopfd == -1) {
  1474. return;
  1475. }
  1476. if (ioctl(loopfd, LOOP_CLR_FD, 0)) {
  1477. }
  1478. close(loopfd);
  1479. }
  1480.  
  1481. static long syz_mount_image(volatile long fsarg, volatile long dir,
  1482. volatile long flags, volatile long optsarg,
  1483. volatile long change_dir,
  1484. volatile unsigned long size, volatile long image)
  1485. {
  1486. unsigned char* data = (unsigned char*)image;
  1487. int res = -1, err = 0, need_loop_device = !!size;
  1488. char* mount_opts = (char*)optsarg;
  1489. char* target = (char*)dir;
  1490. char* fs = (char*)fsarg;
  1491. char* source = NULL;
  1492. char loopname[64];
  1493. if (need_loop_device) {
  1494. int loopfd;
  1495. memset(loopname, 0, sizeof(loopname));
  1496. snprintf(loopname, sizeof(loopname), "/dev/loop%llu", procid);
  1497. if (setup_loop_device(data, size, loopname, &loopfd) == -1)
  1498. return -1;
  1499. close(loopfd);
  1500. source = loopname;
  1501. }
  1502. mkdir(target, 0777);
  1503. char opts[256];
  1504. memset(opts, 0, sizeof(opts));
  1505. if (strlen(mount_opts) > (sizeof(opts) - 32)) {
  1506. }
  1507. strncpy(opts, mount_opts, sizeof(opts) - 32);
  1508. if (strcmp(fs, "iso9660") == 0) {
  1509. flags |= MS_RDONLY;
  1510. } else if (strncmp(fs, "ext", 3) == 0) {
  1511. bool has_remount_ro = false;
  1512. char* remount_ro_start = strstr(opts, "errors=remount-ro");
  1513. if (remount_ro_start != NULL) {
  1514. char after = *(remount_ro_start + strlen("errors=remount-ro"));
  1515. char before = remount_ro_start == opts ? '\0' : *(remount_ro_start - 1);
  1516. has_remount_ro = ((before == '\0' || before == ',') &&
  1517. (after == '\0' || after == ','));
  1518. }
  1519. if (strstr(opts, "errors=panic") || !has_remount_ro)
  1520. strcat(opts, ",errors=continue");
  1521. } else if (strcmp(fs, "xfs") == 0) {
  1522. strcat(opts, ",nouuid");
  1523. }
  1524. res = mount(source, target, fs, flags, opts);
  1525. if (res == -1) {
  1526. err = errno;
  1527. goto error_clear_loop;
  1528. }
  1529. res = open(target, O_RDONLY | O_DIRECTORY);
  1530. if (res == -1) {
  1531. err = errno;
  1532. goto error_clear_loop;
  1533. }
  1534. if (change_dir) {
  1535. res = chdir(target);
  1536. if (res == -1) {
  1537. err = errno;
  1538. }
  1539. }
  1540.  
  1541. error_clear_loop:
  1542. if (need_loop_device)
  1543. reset_loop_device(loopname);
  1544. errno = err;
  1545. return res;
  1546. }
  1547.  
  1548. #define XT_TABLE_SIZE 1536
  1549. #define XT_MAX_ENTRIES 10
  1550.  
  1551. struct xt_counters {
  1552. uint64_t pcnt, bcnt;
  1553. };
  1554.  
  1555. struct ipt_getinfo {
  1556. char name[32];
  1557. unsigned int valid_hooks;
  1558. unsigned int hook_entry[5];
  1559. unsigned int underflow[5];
  1560. unsigned int num_entries;
  1561. unsigned int size;
  1562. };
  1563.  
  1564. struct ipt_get_entries {
  1565. char name[32];
  1566. unsigned int size;
  1567. uint64_t entrytable[XT_TABLE_SIZE / sizeof(uint64_t)];
  1568. };
  1569.  
  1570. struct ipt_replace {
  1571. char name[32];
  1572. unsigned int valid_hooks;
  1573. unsigned int num_entries;
  1574. unsigned int size;
  1575. unsigned int hook_entry[5];
  1576. unsigned int underflow[5];
  1577. unsigned int num_counters;
  1578. struct xt_counters* counters;
  1579. uint64_t entrytable[XT_TABLE_SIZE / sizeof(uint64_t)];
  1580. };
  1581.  
  1582. struct ipt_table_desc {
  1583. const char* name;
  1584. struct ipt_getinfo info;
  1585. struct ipt_replace replace;
  1586. };
  1587.  
  1588. static struct ipt_table_desc ipv4_tables[] = {
  1589. {.name = "filter"}, {.name = "nat"}, {.name = "mangle"},
  1590. {.name = "raw"}, {.name = "security"},
  1591. };
  1592.  
  1593. static struct ipt_table_desc ipv6_tables[] = {
  1594. {.name = "filter"}, {.name = "nat"}, {.name = "mangle"},
  1595. {.name = "raw"}, {.name = "security"},
  1596. };
  1597.  
  1598. #define IPT_BASE_CTL 64
  1599. #define IPT_SO_SET_REPLACE (IPT_BASE_CTL)
  1600. #define IPT_SO_GET_INFO (IPT_BASE_CTL)
  1601. #define IPT_SO_GET_ENTRIES (IPT_BASE_CTL + 1)
  1602.  
  1603. struct arpt_getinfo {
  1604. char name[32];
  1605. unsigned int valid_hooks;
  1606. unsigned int hook_entry[3];
  1607. unsigned int underflow[3];
  1608. unsigned int num_entries;
  1609. unsigned int size;
  1610. };
  1611.  
  1612. struct arpt_get_entries {
  1613. char name[32];
  1614. unsigned int size;
  1615. uint64_t entrytable[XT_TABLE_SIZE / sizeof(uint64_t)];
  1616. };
  1617.  
  1618. struct arpt_replace {
  1619. char name[32];
  1620. unsigned int valid_hooks;
  1621. unsigned int num_entries;
  1622. unsigned int size;
  1623. unsigned int hook_entry[3];
  1624. unsigned int underflow[3];
  1625. unsigned int num_counters;
  1626. struct xt_counters* counters;
  1627. uint64_t entrytable[XT_TABLE_SIZE / sizeof(uint64_t)];
  1628. };
  1629.  
  1630. struct arpt_table_desc {
  1631. const char* name;
  1632. struct arpt_getinfo info;
  1633. struct arpt_replace replace;
  1634. };
  1635.  
  1636. static struct arpt_table_desc arpt_tables[] = {
  1637. {.name = "filter"},
  1638. };
  1639.  
  1640. #define ARPT_BASE_CTL 96
  1641. #define ARPT_SO_SET_REPLACE (ARPT_BASE_CTL)
  1642. #define ARPT_SO_GET_INFO (ARPT_BASE_CTL)
  1643. #define ARPT_SO_GET_ENTRIES (ARPT_BASE_CTL + 1)
  1644.  
  1645. static void checkpoint_iptables(struct ipt_table_desc* tables, int num_tables,
  1646. int family, int level)
  1647. {
  1648. int fd = socket(family, SOCK_STREAM, IPPROTO_TCP);
  1649. if (fd == -1) {
  1650. switch (errno) {
  1651. case EAFNOSUPPORT:
  1652. case ENOPROTOOPT:
  1653. case ENOENT:
  1654. return;
  1655. }
  1656. exit(1);
  1657. }
  1658. for (int i = 0; i < num_tables; i++) {
  1659. struct ipt_table_desc* table = &tables[i];
  1660. strcpy(table->info.name, table->name);
  1661. strcpy(table->replace.name, table->name);
  1662. socklen_t optlen = sizeof(table->info);
  1663. if (getsockopt(fd, level, IPT_SO_GET_INFO, &table->info, &optlen)) {
  1664. switch (errno) {
  1665. case EPERM:
  1666. case ENOENT:
  1667. case ENOPROTOOPT:
  1668. continue;
  1669. }
  1670. exit(1);
  1671. }
  1672. if (table->info.size > sizeof(table->replace.entrytable))
  1673. exit(1);
  1674. if (table->info.num_entries > XT_MAX_ENTRIES)
  1675. exit(1);
  1676. struct ipt_get_entries entries;
  1677. memset(&entries, 0, sizeof(entries));
  1678. strcpy(entries.name, table->name);
  1679. entries.size = table->info.size;
  1680. optlen = sizeof(entries) - sizeof(entries.entrytable) + table->info.size;
  1681. if (getsockopt(fd, level, IPT_SO_GET_ENTRIES, &entries, &optlen))
  1682. exit(1);
  1683. table->replace.valid_hooks = table->info.valid_hooks;
  1684. table->replace.num_entries = table->info.num_entries;
  1685. table->replace.size = table->info.size;
  1686. memcpy(table->replace.hook_entry, table->info.hook_entry,
  1687. sizeof(table->replace.hook_entry));
  1688. memcpy(table->replace.underflow, table->info.underflow,
  1689. sizeof(table->replace.underflow));
  1690. memcpy(table->replace.entrytable, entries.entrytable, table->info.size);
  1691. }
  1692. close(fd);
  1693. }
  1694.  
  1695. static void reset_iptables(struct ipt_table_desc* tables, int num_tables,
  1696. int family, int level)
  1697. {
  1698. int fd = socket(family, SOCK_STREAM, IPPROTO_TCP);
  1699. if (fd == -1) {
  1700. switch (errno) {
  1701. case EAFNOSUPPORT:
  1702. case ENOPROTOOPT:
  1703. case ENOENT:
  1704. return;
  1705. }
  1706. exit(1);
  1707. }
  1708. for (int i = 0; i < num_tables; i++) {
  1709. struct ipt_table_desc* table = &tables[i];
  1710. if (table->info.valid_hooks == 0)
  1711. continue;
  1712. struct ipt_getinfo info;
  1713. memset(&info, 0, sizeof(info));
  1714. strcpy(info.name, table->name);
  1715. socklen_t optlen = sizeof(info);
  1716. if (getsockopt(fd, level, IPT_SO_GET_INFO, &info, &optlen))
  1717. exit(1);
  1718. if (memcmp(&table->info, &info, sizeof(table->info)) == 0) {
  1719. struct ipt_get_entries entries;
  1720. memset(&entries, 0, sizeof(entries));
  1721. strcpy(entries.name, table->name);
  1722. entries.size = table->info.size;
  1723. optlen = sizeof(entries) - sizeof(entries.entrytable) + entries.size;
  1724. if (getsockopt(fd, level, IPT_SO_GET_ENTRIES, &entries, &optlen))
  1725. exit(1);
  1726. if (memcmp(table->replace.entrytable, entries.entrytable,
  1727. table->info.size) == 0)
  1728. continue;
  1729. }
  1730. struct xt_counters counters[XT_MAX_ENTRIES];
  1731. table->replace.num_counters = info.num_entries;
  1732. table->replace.counters = counters;
  1733. optlen = sizeof(table->replace) - sizeof(table->replace.entrytable) +
  1734. table->replace.size;
  1735. if (setsockopt(fd, level, IPT_SO_SET_REPLACE, &table->replace, optlen))
  1736. exit(1);
  1737. }
  1738. close(fd);
  1739. }
  1740.  
  1741. static void checkpoint_arptables(void)
  1742. {
  1743. int fd = socket(AF_INET, SOCK_STREAM, IPPROTO_TCP);
  1744. if (fd == -1) {
  1745. switch (errno) {
  1746. case EAFNOSUPPORT:
  1747. case ENOPROTOOPT:
  1748. case ENOENT:
  1749. return;
  1750. }
  1751. exit(1);
  1752. }
  1753. for (unsigned i = 0; i < sizeof(arpt_tables) / sizeof(arpt_tables[0]); i++) {
  1754. struct arpt_table_desc* table = &arpt_tables[i];
  1755. strcpy(table->info.name, table->name);
  1756. strcpy(table->replace.name, table->name);
  1757. socklen_t optlen = sizeof(table->info);
  1758. if (getsockopt(fd, SOL_IP, ARPT_SO_GET_INFO, &table->info, &optlen)) {
  1759. switch (errno) {
  1760. case EPERM:
  1761. case ENOENT:
  1762. case ENOPROTOOPT:
  1763. continue;
  1764. }
  1765. exit(1);
  1766. }
  1767. if (table->info.size > sizeof(table->replace.entrytable))
  1768. exit(1);
  1769. if (table->info.num_entries > XT_MAX_ENTRIES)
  1770. exit(1);
  1771. struct arpt_get_entries entries;
  1772. memset(&entries, 0, sizeof(entries));
  1773. strcpy(entries.name, table->name);
  1774. entries.size = table->info.size;
  1775. optlen = sizeof(entries) - sizeof(entries.entrytable) + table->info.size;
  1776. if (getsockopt(fd, SOL_IP, ARPT_SO_GET_ENTRIES, &entries, &optlen))
  1777. exit(1);
  1778. table->replace.valid_hooks = table->info.valid_hooks;
  1779. table->replace.num_entries = table->info.num_entries;
  1780. table->replace.size = table->info.size;
  1781. memcpy(table->replace.hook_entry, table->info.hook_entry,
  1782. sizeof(table->replace.hook_entry));
  1783. memcpy(table->replace.underflow, table->info.underflow,
  1784. sizeof(table->replace.underflow));
  1785. memcpy(table->replace.entrytable, entries.entrytable, table->info.size);
  1786. }
  1787. close(fd);
  1788. }
  1789.  
  1790. static void reset_arptables()
  1791. {
  1792. int fd = socket(AF_INET, SOCK_STREAM, IPPROTO_TCP);
  1793. if (fd == -1) {
  1794. switch (errno) {
  1795. case EAFNOSUPPORT:
  1796. case ENOPROTOOPT:
  1797. case ENOENT:
  1798. return;
  1799. }
  1800. exit(1);
  1801. }
  1802. for (unsigned i = 0; i < sizeof(arpt_tables) / sizeof(arpt_tables[0]); i++) {
  1803. struct arpt_table_desc* table = &arpt_tables[i];
  1804. if (table->info.valid_hooks == 0)
  1805. continue;
  1806. struct arpt_getinfo info;
  1807. memset(&info, 0, sizeof(info));
  1808. strcpy(info.name, table->name);
  1809. socklen_t optlen = sizeof(info);
  1810. if (getsockopt(fd, SOL_IP, ARPT_SO_GET_INFO, &info, &optlen))
  1811. exit(1);
  1812. if (memcmp(&table->info, &info, sizeof(table->info)) == 0) {
  1813. struct arpt_get_entries entries;
  1814. memset(&entries, 0, sizeof(entries));
  1815. strcpy(entries.name, table->name);
  1816. entries.size = table->info.size;
  1817. optlen = sizeof(entries) - sizeof(entries.entrytable) + entries.size;
  1818. if (getsockopt(fd, SOL_IP, ARPT_SO_GET_ENTRIES, &entries, &optlen))
  1819. exit(1);
  1820. if (memcmp(table->replace.entrytable, entries.entrytable,
  1821. table->info.size) == 0)
  1822. continue;
  1823. } else {
  1824. }
  1825. struct xt_counters counters[XT_MAX_ENTRIES];
  1826. table->replace.num_counters = info.num_entries;
  1827. table->replace.counters = counters;
  1828. optlen = sizeof(table->replace) - sizeof(table->replace.entrytable) +
  1829. table->replace.size;
  1830. if (setsockopt(fd, SOL_IP, ARPT_SO_SET_REPLACE, &table->replace, optlen))
  1831. exit(1);
  1832. }
  1833. close(fd);
  1834. }
  1835.  
  1836. #define NF_BR_NUMHOOKS 6
  1837. #define EBT_TABLE_MAXNAMELEN 32
  1838. #define EBT_CHAIN_MAXNAMELEN 32
  1839. #define EBT_BASE_CTL 128
  1840. #define EBT_SO_SET_ENTRIES (EBT_BASE_CTL)
  1841. #define EBT_SO_GET_INFO (EBT_BASE_CTL)
  1842. #define EBT_SO_GET_ENTRIES (EBT_SO_GET_INFO + 1)
  1843. #define EBT_SO_GET_INIT_INFO (EBT_SO_GET_ENTRIES + 1)
  1844. #define EBT_SO_GET_INIT_ENTRIES (EBT_SO_GET_INIT_INFO + 1)
  1845.  
  1846. struct ebt_replace {
  1847. char name[EBT_TABLE_MAXNAMELEN];
  1848. unsigned int valid_hooks;
  1849. unsigned int nentries;
  1850. unsigned int entries_size;
  1851. struct ebt_entries* hook_entry[NF_BR_NUMHOOKS];
  1852. unsigned int num_counters;
  1853. struct ebt_counter* counters;
  1854. char* entries;
  1855. };
  1856.  
  1857. struct ebt_entries {
  1858. unsigned int distinguisher;
  1859. char name[EBT_CHAIN_MAXNAMELEN];
  1860. unsigned int counter_offset;
  1861. int policy;
  1862. unsigned int nentries;
  1863. char data[0] __attribute__((aligned(__alignof__(struct ebt_replace))));
  1864. };
  1865.  
  1866. struct ebt_table_desc {
  1867. const char* name;
  1868. struct ebt_replace replace;
  1869. char entrytable[XT_TABLE_SIZE];
  1870. };
  1871.  
  1872. static struct ebt_table_desc ebt_tables[] = {
  1873. {.name = "filter"},
  1874. {.name = "nat"},
  1875. {.name = "broute"},
  1876. };
  1877.  
  1878. static void checkpoint_ebtables(void)
  1879. {
  1880. int fd = socket(AF_INET, SOCK_STREAM, IPPROTO_TCP);
  1881. if (fd == -1) {
  1882. switch (errno) {
  1883. case EAFNOSUPPORT:
  1884. case ENOPROTOOPT:
  1885. case ENOENT:
  1886. return;
  1887. }
  1888. exit(1);
  1889. }
  1890. for (size_t i = 0; i < sizeof(ebt_tables) / sizeof(ebt_tables[0]); i++) {
  1891. struct ebt_table_desc* table = &ebt_tables[i];
  1892. strcpy(table->replace.name, table->name);
  1893. socklen_t optlen = sizeof(table->replace);
  1894. if (getsockopt(fd, SOL_IP, EBT_SO_GET_INIT_INFO, &table->replace,
  1895. &optlen)) {
  1896. switch (errno) {
  1897. case EPERM:
  1898. case ENOENT:
  1899. case ENOPROTOOPT:
  1900. continue;
  1901. }
  1902. exit(1);
  1903. }
  1904. if (table->replace.entries_size > sizeof(table->entrytable))
  1905. exit(1);
  1906. table->replace.num_counters = 0;
  1907. table->replace.entries = table->entrytable;
  1908. optlen = sizeof(table->replace) + table->replace.entries_size;
  1909. if (getsockopt(fd, SOL_IP, EBT_SO_GET_INIT_ENTRIES, &table->replace,
  1910. &optlen))
  1911. exit(1);
  1912. }
  1913. close(fd);
  1914. }
  1915.  
  1916. static void reset_ebtables()
  1917. {
  1918. int fd = socket(AF_INET, SOCK_STREAM, IPPROTO_TCP);
  1919. if (fd == -1) {
  1920. switch (errno) {
  1921. case EAFNOSUPPORT:
  1922. case ENOPROTOOPT:
  1923. case ENOENT:
  1924. return;
  1925. }
  1926. exit(1);
  1927. }
  1928. for (unsigned i = 0; i < sizeof(ebt_tables) / sizeof(ebt_tables[0]); i++) {
  1929. struct ebt_table_desc* table = &ebt_tables[i];
  1930. if (table->replace.valid_hooks == 0)
  1931. continue;
  1932. struct ebt_replace replace;
  1933. memset(&replace, 0, sizeof(replace));
  1934. strcpy(replace.name, table->name);
  1935. socklen_t optlen = sizeof(replace);
  1936. if (getsockopt(fd, SOL_IP, EBT_SO_GET_INFO, &replace, &optlen))
  1937. exit(1);
  1938. replace.num_counters = 0;
  1939. table->replace.entries = 0;
  1940. for (unsigned h = 0; h < NF_BR_NUMHOOKS; h++)
  1941. table->replace.hook_entry[h] = 0;
  1942. if (memcmp(&table->replace, &replace, sizeof(table->replace)) == 0) {
  1943. char entrytable[XT_TABLE_SIZE];
  1944. memset(&entrytable, 0, sizeof(entrytable));
  1945. replace.entries = entrytable;
  1946. optlen = sizeof(replace) + replace.entries_size;
  1947. if (getsockopt(fd, SOL_IP, EBT_SO_GET_ENTRIES, &replace, &optlen))
  1948. exit(1);
  1949. if (memcmp(table->entrytable, entrytable, replace.entries_size) == 0)
  1950. continue;
  1951. }
  1952. for (unsigned j = 0, h = 0; h < NF_BR_NUMHOOKS; h++) {
  1953. if (table->replace.valid_hooks & (1 << h)) {
  1954. table->replace.hook_entry[h] =
  1955. (struct ebt_entries*)table->entrytable + j;
  1956. j++;
  1957. }
  1958. }
  1959. table->replace.entries = table->entrytable;
  1960. optlen = sizeof(table->replace) + table->replace.entries_size;
  1961. if (setsockopt(fd, SOL_IP, EBT_SO_SET_ENTRIES, &table->replace, optlen))
  1962. exit(1);
  1963. }
  1964. close(fd);
  1965. }
  1966.  
  1967. static void checkpoint_net_namespace(void)
  1968. {
  1969. checkpoint_ebtables();
  1970. checkpoint_arptables();
  1971. checkpoint_iptables(ipv4_tables, sizeof(ipv4_tables) / sizeof(ipv4_tables[0]),
  1972. AF_INET, SOL_IP);
  1973. checkpoint_iptables(ipv6_tables, sizeof(ipv6_tables) / sizeof(ipv6_tables[0]),
  1974. AF_INET6, SOL_IPV6);
  1975. }
  1976.  
  1977. static void reset_net_namespace(void)
  1978. {
  1979. reset_ebtables();
  1980. reset_arptables();
  1981. reset_iptables(ipv4_tables, sizeof(ipv4_tables) / sizeof(ipv4_tables[0]),
  1982. AF_INET, SOL_IP);
  1983. reset_iptables(ipv6_tables, sizeof(ipv6_tables) / sizeof(ipv6_tables[0]),
  1984. AF_INET6, SOL_IPV6);
  1985. }
  1986.  
  1987. static void setup_gadgetfs();
  1988. static void setup_binderfs();
  1989. static void setup_fusectl();
  1990. static void sandbox_common_mount_tmpfs(void)
  1991. {
  1992. write_file("/proc/sys/fs/mount-max", "100000");
  1993. if (mkdir("./syz-tmp", 0777))
  1994. exit(1);
  1995. if (mount("", "./syz-tmp", "tmpfs", 0, NULL))
  1996. exit(1);
  1997. if (mkdir("./syz-tmp/newroot", 0777))
  1998. exit(1);
  1999. if (mkdir("./syz-tmp/newroot/dev", 0700))
  2000. exit(1);
  2001. unsigned bind_mount_flags = MS_BIND | MS_REC | MS_PRIVATE;
  2002. if (mount("/dev", "./syz-tmp/newroot/dev", NULL, bind_mount_flags, NULL))
  2003. exit(1);
  2004. if (mkdir("./syz-tmp/newroot/proc", 0700))
  2005. exit(1);
  2006. if (mount("syz-proc", "./syz-tmp/newroot/proc", "proc", 0, NULL))
  2007. exit(1);
  2008. if (mkdir("./syz-tmp/newroot/selinux", 0700))
  2009. exit(1);
  2010. const char* selinux_path = "./syz-tmp/newroot/selinux";
  2011. if (mount("/selinux", selinux_path, NULL, bind_mount_flags, NULL)) {
  2012. if (errno != ENOENT)
  2013. exit(1);
  2014. if (mount("/sys/fs/selinux", selinux_path, NULL, bind_mount_flags, NULL) &&
  2015. errno != ENOENT)
  2016. exit(1);
  2017. }
  2018. if (mkdir("./syz-tmp/newroot/sys", 0700))
  2019. exit(1);
  2020. if (mount("/sys", "./syz-tmp/newroot/sys", 0, bind_mount_flags, NULL))
  2021. exit(1);
  2022. if (mount("/sys/kernel/debug", "./syz-tmp/newroot/sys/kernel/debug", NULL,
  2023. bind_mount_flags, NULL) &&
  2024. errno != ENOENT)
  2025. exit(1);
  2026. if (mount("/sys/fs/smackfs", "./syz-tmp/newroot/sys/fs/smackfs", NULL,
  2027. bind_mount_flags, NULL) &&
  2028. errno != ENOENT)
  2029. exit(1);
  2030. if (mount("/proc/sys/fs/binfmt_misc",
  2031. "./syz-tmp/newroot/proc/sys/fs/binfmt_misc", NULL, bind_mount_flags,
  2032. NULL) &&
  2033. errno != ENOENT)
  2034. exit(1);
  2035. if (mkdir("./syz-tmp/newroot/syz-inputs", 0700))
  2036. exit(1);
  2037. if (mount("/syz-inputs", "./syz-tmp/newroot/syz-inputs", NULL,
  2038. bind_mount_flags | MS_RDONLY, NULL) &&
  2039. errno != ENOENT)
  2040. exit(1);
  2041. if (mkdir("./syz-tmp/pivot", 0777))
  2042. exit(1);
  2043. if (syscall(SYS_pivot_root, "./syz-tmp", "./syz-tmp/pivot")) {
  2044. if (chdir("./syz-tmp"))
  2045. exit(1);
  2046. } else {
  2047. if (chdir("/"))
  2048. exit(1);
  2049. if (umount2("./pivot", MNT_DETACH))
  2050. exit(1);
  2051. }
  2052. if (chroot("./newroot"))
  2053. exit(1);
  2054. if (chdir("/"))
  2055. exit(1);
  2056. setup_gadgetfs();
  2057. setup_binderfs();
  2058. setup_fusectl();
  2059. }
  2060.  
  2061. static void setup_gadgetfs()
  2062. {
  2063. if (mkdir("/dev/gadgetfs", 0777)) {
  2064. }
  2065. if (mount("gadgetfs", "/dev/gadgetfs", "gadgetfs", 0, NULL)) {
  2066. }
  2067. }
  2068.  
  2069. static void setup_fusectl()
  2070. {
  2071. if (mount(0, "/sys/fs/fuse/connections", "fusectl", 0, 0)) {
  2072. }
  2073. }
  2074.  
  2075. static void setup_binderfs()
  2076. {
  2077. if (mkdir("/dev/binderfs", 0777)) {
  2078. }
  2079. if (mount("binder", "/dev/binderfs", "binder", 0, NULL)) {
  2080. }
  2081. }
  2082.  
  2083. static void loop();
  2084.  
  2085. static void sandbox_common()
  2086. {
  2087. prctl(PR_SET_PDEATHSIG, SIGKILL, 0, 0, 0);
  2088. if (getppid() == 1)
  2089. exit(1);
  2090. struct rlimit rlim;
  2091. rlim.rlim_cur = rlim.rlim_max = (200 << 20);
  2092. setrlimit(RLIMIT_AS, &rlim);
  2093. rlim.rlim_cur = rlim.rlim_max = 32 << 20;
  2094. setrlimit(RLIMIT_MEMLOCK, &rlim);
  2095. rlim.rlim_cur = rlim.rlim_max = 136 << 20;
  2096. setrlimit(RLIMIT_FSIZE, &rlim);
  2097. rlim.rlim_cur = rlim.rlim_max = 1 << 20;
  2098. setrlimit(RLIMIT_STACK, &rlim);
  2099. rlim.rlim_cur = rlim.rlim_max = 128 << 20;
  2100. setrlimit(RLIMIT_CORE, &rlim);
  2101. rlim.rlim_cur = rlim.rlim_max = 256;
  2102. setrlimit(RLIMIT_NOFILE, &rlim);
  2103. if (unshare(CLONE_NEWNS)) {
  2104. }
  2105. if (mount(NULL, "/", NULL, MS_REC | MS_PRIVATE, NULL)) {
  2106. }
  2107. if (unshare(CLONE_NEWIPC)) {
  2108. }
  2109. if (unshare(0x02000000)) {
  2110. }
  2111. if (unshare(CLONE_NEWUTS)) {
  2112. }
  2113. if (unshare(CLONE_SYSVSEM)) {
  2114. }
  2115. typedef struct {
  2116. const char* name;
  2117. const char* value;
  2118. } sysctl_t;
  2119. static const sysctl_t sysctls[] = {
  2120. {"/proc/sys/kernel/shmmax", "16777216"},
  2121. {"/proc/sys/kernel/shmall", "536870912"},
  2122. {"/proc/sys/kernel/shmmni", "1024"},
  2123. {"/proc/sys/kernel/msgmax", "8192"},
  2124. {"/proc/sys/kernel/msgmni", "1024"},
  2125. {"/proc/sys/kernel/msgmnb", "1024"},
  2126. {"/proc/sys/kernel/sem", "1024 1048576 500 1024"},
  2127. };
  2128. unsigned i;
  2129. for (i = 0; i < sizeof(sysctls) / sizeof(sysctls[0]); i++)
  2130. write_file(sysctls[i].name, sysctls[i].value);
  2131. }
  2132.  
  2133. static int wait_for_loop(int pid)
  2134. {
  2135. if (pid < 0)
  2136. exit(1);
  2137. int status = 0;
  2138. while (waitpid(-1, &status, __WALL) != pid) {
  2139. }
  2140. return WEXITSTATUS(status);
  2141. }
  2142.  
  2143. static void drop_caps(void)
  2144. {
  2145. struct __user_cap_header_struct cap_hdr = {};
  2146. struct __user_cap_data_struct cap_data[2] = {};
  2147. cap_hdr.version = _LINUX_CAPABILITY_VERSION_3;
  2148. cap_hdr.pid = getpid();
  2149. if (syscall(SYS_capget, &cap_hdr, &cap_data))
  2150. exit(1);
  2151. const int drop = (1 << CAP_SYS_PTRACE) | (1 << CAP_SYS_NICE);
  2152. cap_data[0].effective &= ~drop;
  2153. cap_data[0].permitted &= ~drop;
  2154. cap_data[0].inheritable &= ~drop;
  2155. if (syscall(SYS_capset, &cap_hdr, &cap_data))
  2156. exit(1);
  2157. }
  2158.  
  2159. static int do_sandbox_none(void)
  2160. {
  2161. if (unshare(CLONE_NEWPID)) {
  2162. }
  2163. int pid = fork();
  2164. if (pid != 0)
  2165. return wait_for_loop(pid);
  2166. sandbox_common();
  2167. drop_caps();
  2168. initialize_netdevices_init();
  2169. if (unshare(CLONE_NEWNET)) {
  2170. }
  2171. write_file("/proc/sys/net/ipv4/ping_group_range", "0 65535");
  2172. initialize_netdevices();
  2173. sandbox_common_mount_tmpfs();
  2174. loop();
  2175. exit(1);
  2176. }
  2177.  
  2178. #define FS_IOC_SETFLAGS _IOW('f', 2, long)
  2179. static void remove_dir(const char* dir)
  2180. {
  2181. int iter = 0;
  2182. DIR* dp = 0;
  2183. const int umount_flags = MNT_FORCE | UMOUNT_NOFOLLOW;
  2184.  
  2185. retry:
  2186. while (umount2(dir, umount_flags) == 0) {
  2187. }
  2188. dp = opendir(dir);
  2189. if (dp == NULL) {
  2190. if (errno == EMFILE) {
  2191. exit(1);
  2192. }
  2193. exit(1);
  2194. }
  2195. struct dirent* ep = 0;
  2196. while ((ep = readdir(dp))) {
  2197. if (strcmp(ep->d_name, ".") == 0 || strcmp(ep->d_name, "..") == 0)
  2198. continue;
  2199. char filename[FILENAME_MAX];
  2200. snprintf(filename, sizeof(filename), "%s/%s", dir, ep->d_name);
  2201. while (umount2(filename, umount_flags) == 0) {
  2202. }
  2203. struct stat st;
  2204. if (lstat(filename, &st))
  2205. exit(1);
  2206. if (S_ISDIR(st.st_mode)) {
  2207. remove_dir(filename);
  2208. continue;
  2209. }
  2210. int i;
  2211. for (i = 0;; i++) {
  2212. if (unlink(filename) == 0)
  2213. break;
  2214. if (errno == EPERM) {
  2215. int fd = open(filename, O_RDONLY);
  2216. if (fd != -1) {
  2217. long flags = 0;
  2218. if (ioctl(fd, FS_IOC_SETFLAGS, &flags) == 0) {
  2219. }
  2220. close(fd);
  2221. continue;
  2222. }
  2223. }
  2224. if (errno == EROFS) {
  2225. break;
  2226. }
  2227. if (errno != EBUSY || i > 100)
  2228. exit(1);
  2229. if (umount2(filename, umount_flags))
  2230. exit(1);
  2231. }
  2232. }
  2233. closedir(dp);
  2234. for (int i = 0;; i++) {
  2235. if (rmdir(dir) == 0)
  2236. break;
  2237. if (i < 100) {
  2238. if (errno == EPERM) {
  2239. int fd = open(dir, O_RDONLY);
  2240. if (fd != -1) {
  2241. long flags = 0;
  2242. if (ioctl(fd, FS_IOC_SETFLAGS, &flags) == 0) {
  2243. }
  2244. close(fd);
  2245. continue;
  2246. }
  2247. }
  2248. if (errno == EROFS) {
  2249. break;
  2250. }
  2251. if (errno == EBUSY) {
  2252. if (umount2(dir, umount_flags))
  2253. exit(1);
  2254. continue;
  2255. }
  2256. if (errno == ENOTEMPTY) {
  2257. if (iter < 100) {
  2258. iter++;
  2259. goto retry;
  2260. }
  2261. }
  2262. }
  2263. exit(1);
  2264. }
  2265. }
  2266.  
  2267. static void kill_and_wait(int pid, int* status)
  2268. {
  2269. kill(-pid, SIGKILL);
  2270. kill(pid, SIGKILL);
  2271. for (int i = 0; i < 100; i++) {
  2272. if (waitpid(-1, status, WNOHANG | __WALL) == pid)
  2273. return;
  2274. usleep(1000);
  2275. }
  2276. DIR* dir = opendir("/sys/fs/fuse/connections");
  2277. if (dir) {
  2278. for (;;) {
  2279. struct dirent* ent = readdir(dir);
  2280. if (!ent)
  2281. break;
  2282. if (strcmp(ent->d_name, ".") == 0 || strcmp(ent->d_name, "..") == 0)
  2283. continue;
  2284. char abort[300];
  2285. snprintf(abort, sizeof(abort), "/sys/fs/fuse/connections/%s/abort",
  2286. ent->d_name);
  2287. int fd = open(abort, O_WRONLY);
  2288. if (fd == -1) {
  2289. continue;
  2290. }
  2291. if (write(fd, abort, 1) < 0) {
  2292. }
  2293. close(fd);
  2294. }
  2295. closedir(dir);
  2296. } else {
  2297. }
  2298. while (waitpid(-1, status, __WALL) != pid) {
  2299. }
  2300. }
  2301.  
  2302. static void setup_loop()
  2303. {
  2304. checkpoint_net_namespace();
  2305. }
  2306.  
  2307. static void reset_loop()
  2308. {
  2309. char buf[64];
  2310. snprintf(buf, sizeof(buf), "/dev/loop%llu", procid);
  2311. int loopfd = open(buf, O_RDWR);
  2312. if (loopfd != -1) {
  2313. ioctl(loopfd, LOOP_CLR_FD, 0);
  2314. close(loopfd);
  2315. }
  2316. reset_net_namespace();
  2317. }
  2318.  
  2319. static void setup_test()
  2320. {
  2321. prctl(PR_SET_PDEATHSIG, SIGKILL, 0, 0, 0);
  2322. setpgrp();
  2323. write_file("/proc/self/oom_score_adj", "1000");
  2324. if (symlink("/dev/binderfs", "./binderfs")) {
  2325. }
  2326. }
  2327.  
  2328. static void close_fds()
  2329. {
  2330. for (int fd = 3; fd < MAX_FDS; fd++)
  2331. close(fd);
  2332. }
  2333.  
  2334. static void setup_sysctl()
  2335. {
  2336. int cad_pid = fork();
  2337. if (cad_pid < 0)
  2338. exit(1);
  2339. if (cad_pid == 0) {
  2340. for (;;)
  2341. sleep(100);
  2342. }
  2343. char tmppid[32];
  2344. snprintf(tmppid, sizeof(tmppid), "%d", cad_pid);
  2345. struct {
  2346. const char* name;
  2347. const char* data;
  2348. } files[] = {
  2349. {"/sys/kernel/debug/x86/nmi_longest_ns", "10000000000"},
  2350. {"/proc/sys/kernel/hung_task_check_interval_secs", "20"},
  2351. {"/proc/sys/net/core/bpf_jit_kallsyms", "1"},
  2352. {"/proc/sys/net/core/bpf_jit_harden", "0"},
  2353. {"/proc/sys/kernel/kptr_restrict", "0"},
  2354. {"/proc/sys/kernel/softlockup_all_cpu_backtrace", "1"},
  2355. {"/proc/sys/fs/mount-max", "100"},
  2356. {"/proc/sys/vm/oom_dump_tasks", "0"},
  2357. {"/proc/sys/debug/exception-trace", "0"},
  2358. {"/proc/sys/kernel/printk", "7 4 1 3"},
  2359. {"/proc/sys/kernel/keys/gc_delay", "1"},
  2360. {"/proc/sys/vm/oom_kill_allocating_task", "1"},
  2361. {"/proc/sys/kernel/ctrl-alt-del", "0"},
  2362. {"/proc/sys/kernel/cad_pid", tmppid},
  2363. };
  2364. for (size_t i = 0; i < sizeof(files) / sizeof(files[0]); i++) {
  2365. if (!write_file(files[i].name, files[i].data)) {
  2366. }
  2367. }
  2368. kill(cad_pid, SIGKILL);
  2369. while (waitpid(cad_pid, NULL, 0) != cad_pid)
  2370. ;
  2371. }
  2372.  
  2373. struct thread_t {
  2374. int created, call;
  2375. event_t ready, done;
  2376. };
  2377.  
  2378. static struct thread_t threads[16];
  2379. static void execute_call(int call);
  2380. static int running;
  2381.  
  2382. static void* thr(void* arg)
  2383. {
  2384. struct thread_t* th = (struct thread_t*)arg;
  2385. for (;;) {
  2386. event_wait(&th->ready);
  2387. event_reset(&th->ready);
  2388. execute_call(th->call);
  2389. __atomic_fetch_sub(&running, 1, __ATOMIC_RELAXED);
  2390. event_set(&th->done);
  2391. }
  2392. return 0;
  2393. }
  2394.  
  2395. static void execute_one(void)
  2396. {
  2397. if (write(1, "executing program\n", sizeof("executing program\n") - 1)) {
  2398. }
  2399. int i, call, thread;
  2400. for (call = 0; call < 13; call++) {
  2401. for (thread = 0; thread < (int)(sizeof(threads) / sizeof(threads[0]));
  2402. thread++) {
  2403. struct thread_t* th = &threads[thread];
  2404. if (!th->created) {
  2405. th->created = 1;
  2406. event_init(&th->ready);
  2407. event_init(&th->done);
  2408. event_set(&th->done);
  2409. thread_start(thr, th);
  2410. }
  2411. if (!event_isset(&th->done))
  2412. continue;
  2413. event_reset(&th->done);
  2414. th->call = call;
  2415. __atomic_fetch_add(&running, 1, __ATOMIC_RELAXED);
  2416. event_set(&th->ready);
  2417. if (call == 0 || call == 2 || call == 10)
  2418. break;
  2419. event_timedwait(&th->done,
  2420. 50 + (call == 0 ? 4000 : 0) + (call == 1 ? 4000 : 0));
  2421. break;
  2422. }
  2423. }
  2424. for (i = 0; i < 100 && __atomic_load_n(&running, __ATOMIC_RELAXED); i++)
  2425. sleep_ms(1);
  2426. close_fds();
  2427. }
  2428.  
  2429. static void execute_one(void);
  2430.  
  2431. #define WAIT_FLAGS __WALL
  2432.  
  2433. static void loop(void)
  2434. {
  2435. setup_loop();
  2436. int iter = 0;
  2437. for (;; iter++) {
  2438. char cwdbuf[32];
  2439. sprintf(cwdbuf, "./%d", iter);
  2440. if (mkdir(cwdbuf, 0777))
  2441. exit(1);
  2442. reset_loop();
  2443. int pid = fork();
  2444. if (pid < 0)
  2445. exit(1);
  2446. if (pid == 0) {
  2447. if (chdir(cwdbuf))
  2448. exit(1);
  2449. setup_test();
  2450. execute_one();
  2451. exit(0);
  2452. }
  2453. int status = 0;
  2454. uint64_t start = current_time_ms();
  2455. for (;;) {
  2456. sleep_ms(10);
  2457. if (waitpid(-1, &status, WNOHANG | WAIT_FLAGS) == pid)
  2458. break;
  2459. if (current_time_ms() - start < 5000)
  2460. continue;
  2461. kill_and_wait(pid, &status);
  2462. break;
  2463. }
  2464. remove_dir(cwdbuf);
  2465. }
  2466. }
  2467.  
  2468. uint64_t r[3] = {0xffffffffffffffff, 0xffffffffffffffff, 0xffffffffffffffff};
  2469.  
  2470. void execute_call(int call)
  2471. {
  2472. intptr_t res = 0;
  2473. switch (call) {
  2474. case 0:
  2475. NONFAILING(memcpy((void*)0x200000000000, "ext4\000", 5));
  2476. NONFAILING(memcpy((void*)0x200000000280, "./bus\000", 6));
  2477. NONFAILING(memcpy((void*)0x200000000440, "dax=always", 10));
  2478. NONFAILING(*(uint8_t*)0x20000000044a = 0x2c);
  2479. NONFAILING(memcpy((void*)0x20000000044b, "journal_ioprio", 14));
  2480. NONFAILING(*(uint8_t*)0x200000000459 = 0x3d);
  2481. NONFAILING(sprintf((char*)0x20000000045a, "0x%016llx", (long long)2));
  2482. NONFAILING(*(uint8_t*)0x20000000046c = 0x2c);
  2483. NONFAILING(memcpy((void*)0x20000000046d, "mb_optimize_scan", 16));
  2484. NONFAILING(*(uint8_t*)0x20000000047d = 0x3d);
  2485. NONFAILING(sprintf((char*)0x20000000047e, "0x%016llx", (long long)1));
  2486. NONFAILING(*(uint8_t*)0x200000000490 = 0x2c);
  2487. NONFAILING(memcpy((void*)0x200000000491, "lazytime", 8));
  2488. NONFAILING(*(uint8_t*)0x200000000499 = 0x2c);
  2489. NONFAILING(memcpy((void*)0x20000000049a, "i_version", 9));
  2490. NONFAILING(*(uint8_t*)0x2000000004a3 = 0x2c);
  2491. NONFAILING(memcpy((void*)0x2000000004a4, "data_err=ignore", 15));
  2492. NONFAILING(*(uint8_t*)0x2000000004b3 = 0x2c);
  2493. NONFAILING(*(uint8_t*)0x2000000004b4 = 0);
  2494. NONFAILING(memcpy(
  2495. (void*)0x200000000500,
  2496. "\x78\x9c\xec\xdb\xcf\x4f\x1c\x55\x1c\x00\xf0\xef\xcc\x02\x95\xfe\x10"
  2497. "\xac\xf5\x47\x69\x55\xb4\x1a\x89\x3f\xa0\xd0\xaa\x3d\x78\xd1\x68\xe2"
  2498. "\x41\x13\x13\x3d\xd4\x23\x02\x6d\xb0\xdb\x62\x0a\x26\xb6\x21\x8a\xc6"
  2499. "\xd4\xa3\x69\xe2\xdd\x78\x34\xf1\x2f\xf0\xa4\x17\xa3\x9e\x4c\xbc\xea"
  2500. "\xdd\x34\x69\x0c\x97\x56\x4f\x6b\x66\x77\x06\x96\x65\x97\x02\x5d\x58"
  2501. "\xed\x7e\x3e\xc9\xb4\xef\xcd\xbc\xcd\x7b\xdf\x7d\xf3\x76\xdf\x9b\xc7"
  2502. "\x06\xd0\xb5\x86\xb3\x7f\x92\x88\xfd\x11\xf1\x7b\x44\x0c\xd4\xb2\x6b"
  2503. "\x0b\x0c\xd7\xfe\xbb\xb9\xbc\x38\xf5\xf7\xf2\xe2\x54\x12\x95\xca\x5b"
  2504. "\x7f\x25\xd5\x72\x37\x96\x17\xa7\x8a\xa2\xc5\xeb\xf6\xe5\x99\x91\x34"
  2505. "\x22\xfd\x2c\x89\x23\x4d\xea\x9d\xbf\x74\xf9\xdc\x64\xb9\x3c\x73\x31"
  2506. "\xcf\x8f\x2d\x9c\x7f\x7f\x6c\xfe\xd2\xe5\x67\x67\xcf\x4f\x9e\x9d\x39"
  2507. "\x3b\x73\x61\xe2\xd4\xa9\x93\x27\xc6\x5f\x78\x7e\xe2\xb9\xb6\xc4\x99"
  2508. "\xc5\x75\x63\xe8\xa3\xb9\xa3\x87\x5f\x7b\xe7\xea\x1b\x53\xa7\xaf\xbe"
  2509. "\xfb\xf3\xb7\x49\x11\x7f\x43\x1c\x6d\x32\xbc\xd1\xc5\x27\x2a\x95\x36"
  2510. "\x57\xd7\x59\x07\xea\xd2\x49\x4f\x07\x1b\xc2\x96\x94\x22\x22\xeb\xae"
  2511. "\xde\xea\xf8\x1f\x88\x52\xac\x76\xde\x40\xbc\xfa\x69\x47\x1b\x07\xec"
  2512. "\xa8\x4a\xae\xc5\xe5\xa5\x0a\x70\x07\x4b\xa2\xd3\x2d\x00\x3a\xa3\xf8"
  2513. "\xa2\xcf\xd6\xbf\xc5\xb1\x7b\xb3\x8f\xce\xbb\xfe\x52\x6d\x01\x94\xc5"
  2514. "\x7d\x33\x3f\x6a\x57\x7a\x22\xcd\xcb\xf4\x36\xac\x6f\xdb\x69\x38\x22"
  2515. "\x4e\x2f\xfd\xf3\x55\x76\xc4\xce\x3c\x87\x00\x00\x58\xe3\xfb\x6c\xfe"
  2516. "\xf3\x4c\xb3\xf9\x5f\x1a\xf7\xd7\x95\xbb\x3b\xdf\x43\x19\x8c\x88\x7b"
  2517. "\x22\xe2\x60\x44\xdc\x1b\x11\x87\x22\xe2\xbe\x88\x6a\xd9\x07\x22\xe2"
  2518. "\xc1\x2d\xd6\xdf\xb8\x49\xb2\x7e\xfe\x93\x5e\xdb\x56\x60\x9b\x94\xcd"
  2519. "\xff\x5e\xcc\xf7\xb6\xd6\xce\xff\x8a\xd9\x5f\x0c\x96\xf2\xdc\x81\x6a"
  2520. "\xfc\xbd\xc9\x99\xd9\xf2\xcc\xf1\xfc\x3d\x19\x89\xde\x3d\x59\x7e\x7c"
  2521. "\x83\x3a\x7e\x78\xe5\xb7\x2f\x5a\x5d\xab\x9f\xff\x65\x47\x56\x7f\x31"
  2522. "\x17\xcc\xdb\x71\xad\x67\xcf\xda\xd7\x4c\x4f\x2e\x4c\xde\x4e\xcc\xf5"
  2523. "\xae\x7f\x12\x31\xd4\xd3\x2c\xfe\x64\x65\x27\x20\x89\x88\xc3\x11\x31"
  2524. "\xb4\xcd\x3a\x66\x9f\xfa\xe6\x68\xab\x6b\xb7\x8e\x7f\x03\x6d\xd8\x67"
  2525. "\xaa\x7c\x1d\xf1\x64\xad\xff\x97\xa2\x21\xfe\x42\xb2\xf1\xfe\xe4\xd8"
  2526. "\x5d\x51\x9e\x39\x3e\x56\xdc\x15\xeb\xfd\xf2\xeb\x95\x37\x5b\xd5\x7f"
  2527. "\x5b\xf1\xb7\x41\xd6\xff\x7b\x9b\xde\xff\x2b\xf1\x0f\x26\xf5\xfb\xb5"
  2528. "\xf3\x5b\xaf\xe3\xca\x1f\x9f\xb7\x5c\xd3\x6c\xf7\xfe\xef\x4b\xde\xae"
  2529. "\xa6\xfb\xf2\x73\x1f\x4e\x2e\x2c\x5c\x1c\x8f\xe8\x4b\x5e\xaf\x35\xba"
  2530. "\xfe\xfc\xc4\xea\x6b\x8b\x7c\x51\x3e\x8b\x7f\xe4\x58\xf3\xf1\x7f\x30"
  2531. "\x56\xdf\x89\x23\x11\x91\xdd\xc4\x0f\x45\xc4\xc3\x11\xf1\x48\xde\xf6"
  2532. "\x47\x23\xe2\xb1\x88\x38\xb6\x41\xfc\x3f\xbd\xfc\xf8\x7b\xdb\x8f\x7f"
  2533. "\x67\x65\xf1\x4f\x6f\xa9\xff\x57\x13\x7d\xd1\x78\xa6\x79\xa2\x74\xee"
  2534. "\xc7\xef\xd6\x54\x3a\xb8\x95\xf8\xb3\xfe\x3f\x59\x4d\x8d\xe4\x67\x36"
  2535. "\xf3\xf9\xb7\x99\x76\x6d\xef\x6e\x06\x00\x00\x80\xff\x9f\x34\x22\xf6"
  2536. "\x47\x92\x8e\xae\xa4\xd3\x74\x74\xb4\xf6\x37\xfc\x87\x62\x6f\x5a\x9e"
  2537. "\x9b\x5f\x78\xfa\xcc\xdc\x07\x17\xa6\x6b\xbf\x11\x18\x8c\xde\xb4\x78"
  2538. "\xd2\x35\x50\xf7\x3c\x74\x3c\x5f\xd6\x17\xf9\x89\x86\xfc\x89\xfc\xb9"
  2539. "\xf1\x97\xa5\xfe\x6a\x7e\x74\x6a\xae\x3c\xdd\xe9\xe0\xa1\xcb\xed\x6b"
  2540. "\x31\xfe\x33\x7f\x96\x3a\xdd\x3a\x60\xc7\xf9\xbd\x16\x74\x2f\xe3\x1f"
  2541. "\xba\x97\xf1\x0f\xdd\xcb\xf8\x87\xee\xd5\x64\xfc\xf7\x77\xa2\x1d\xc0"
  2542. "\xee\x6b\xf6\xfd\xff\x71\x07\xda\x01\xec\xbe\x86\xf1\x6f\xdb\x0f\xba"
  2543. "\x88\xf5\x3f\x74\x2f\xe3\x1f\xba\x97\xf1\x0f\x5d\x69\xbe\x3f\x6e\xfd"
  2544. "\x23\x79\x09\x89\x75\x89\x48\xff\x13\xcd\x90\xd8\xa1\x44\xa7\x3f\x99"
  2545. "\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00"
  2546. "\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00"
  2547. "\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00"
  2548. "\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00"
  2549. "\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00"
  2550. "\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00"
  2551. "\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00"
  2552. "\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00"
  2553. "\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00"
  2554. "\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00"
  2555. "\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00"
  2556. "\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00"
  2557. "\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00"
  2558. "\x00\x00\x00\x00\x00\x00\x00\xda\xe3\xdf\x00\x00\x00\xff\xff\x08\x33"
  2559. "\xea\xc4",
  2560. 1073));
  2561. NONFAILING(syz_mount_image(
  2562. /*fs=*/0x200000000000, /*dir=*/0x200000000280,
  2563. /*flags=MS_PRIVATE|MS_POSIXACL|MS_REC|MS_RELATIME|MS_NODEV|0x80*/
  2564. 0x254084, /*opts=*/0x200000000440, /*chdir=*/1, /*size=*/0x431,
  2565. /*img=*/0x200000000500));
  2566. break;
  2567. case 1:
  2568. NONFAILING(memcpy((void*)0x200000000040, "ext4\000", 5));
  2569. NONFAILING(memcpy((void*)0x2000000000c0, "./file0\000", 8));
  2570. NONFAILING(*(uint8_t*)0x200000000300 = 0);
  2571. NONFAILING(memcpy(
  2572. (void*)0x200000000800,
  2573. "\x78\x9c\xec\xdd\xcd\x6b\x1c\xe5\x1f\x00\xf0\xef\x6c\x92\x26\xbf\xb4"
  2574. "\x3f\x13\x41\xd0\x7a\x0a\x08\x1a\xa8\xdd\x98\x1a\x5b\x05\x0f\x15\x0f"
  2575. "\x22\x58\x28\xe8\xd9\x74\xd9\x6c\x43\xcd\x26\x5b\xb2\x9b\xd2\x84\x40"
  2576. "\x2d\x22\x78\x11\x54\x3c\x08\x7a\xe9\xd9\x97\x7a\xf3\xea\xcb\x55\xff"
  2577. "\x0b\x0f\xd2\x52\x35\x2d\x56\x3c\x48\x64\x36\xb3\xed\xb6\xd9\x4d\x13"
  2578. "\x9b\x6c\x52\xf7\xf3\x81\xa7\x7d\x9e\x99\x67\xf3\xcc\x77\x9f\x99\x79"
  2579. "\x9e\xdd\x19\x76\x02\xe8\x5a\x23\xe9\x3f\xb9\x88\x83\x11\xf1\x41\x12"
  2580. "\x31\x94\x2d\x4f\x22\xa2\xaf\x9e\xeb\x8d\x38\xbe\x56\xef\xe6\xca\x72"
  2581. "\x31\x4d\x49\xac\xae\xbe\xfe\x5b\x52\xaf\x73\x63\x65\xb9\x18\x4d\xaf"
  2582. "\x49\xed\xcf\x0a\x8f\x45\xc4\xf7\xef\x46\x1c\xca\x25\xeb\xda\xad\x2e"
  2583. "\x2e\xcd\x14\xca\xe5\xd2\x7c\x56\x1e\xab\xcd\x9e\x1d\xab\x2e\x2e\x1d"
  2584. "\x3e\x33\x5b\x98\x2e\x4d\x97\xe6\x8e\x8e\x4f\x4c\x1c\x39\xf6\xdc\xb1"
  2585. "\xa3\xdb\x17\xeb\x1f\x3f\x2d\x1d\xb8\xfa\xe1\x2b\x4f\x7d\x75\xfc\xaf"
  2586. "\x77\x1e\xbd\xfc\xfe\x0f\x49\x1c\x8f\x03\xd9\xba\xe6\x38\xb6\xcb\x48"
  2587. "\x8c\x64\xef\x49\x5f\xfa\x16\xde\xe1\xe5\xed\x6e\x6c\x97\xad\xef\x61"
  2588. "\x1e\x04\xb9\x88\xe8\x59\x3b\xca\xe3\x60\x0c\x45\x4f\x3d\x07\x00\xfc"
  2589. "\x97\x5d\x88\x88\x55\x00\xa0\xcb\x24\xc6\x7f\x00\xe8\x32\x8d\xef\x01"
  2590. "\x6e\xac\x2c\x17\x1b\x69\x77\xbf\x91\xe8\xac\x6b\x2f\x45\xc4\xc0\x5a"
  2591. "\xfc\x8d\xeb\x9b\x6b\x6b\x7a\xb3\x6b\x76\x03\xf5\xeb\xa0\x83\x37\x92"
  2592. "\x3b\xae\x8c\x24\x11\x31\xbc\x0d\xed\x8f\x44\xc4\x67\xdf\xbc\xf9\x45"
  2593. "\x9a\x62\x87\xae\x43\x02\xb4\xf2\xf6\xc5\x88\x38\x35\x3c\xb2\xfe\xfc"
  2594. "\x9f\xac\xbb\x67\x61\xab\x9e\xd9\x44\x9d\x91\xbb\xca\xce\x7f\xd0\x39"
  2595. "\xdf\xa6\xf3\x9f\xe7\x5b\xcd\xff\x72\xb7\xe6\x3f\xd1\x62\xfe\xd3\xdf"
  2596. "\xe2\xd8\xfd\x37\xee\x7d\xfc\xe7\xae\x6c\x43\x33\x6d\xa5\xf3\xbf\x17"
  2597. "\x9b\xee\x6d\xbb\xd9\x14\x7f\x66\xb8\x27\x2b\xfd\xbf\x3e\xe7\xeb\x4b"
  2598. "\x4e\x9f\x29\x97\xd2\x73\xdb\x43\x11\x31\x1a\x7d\xfd\x69\x79\x7c\x83"
  2599. "\x36\x46\xaf\xff\x7d\xbd\xdd\xba\xe6\xf9\xdf\xef\x1f\xbd\xf5\x79\xda"
  2600. "\x7e\xfa\xff\xed\x1a\xb9\x2b\xbd\xfd\x77\xbe\x66\xaa\x50\x2b\xdc\x4f"
  2601. "\xcc\xcd\xae\x5d\x8c\x78\xbc\xb7\x55\xfc\xc9\xad\xfe\x4f\xda\xcc\x7f"
  2602. "\x4f\x6e\xb2\x8d\x57\x5f\x78\xef\xd3\x76\xeb\xd2\xf8\xd3\x78\x1b\x69"
  2603. "\x7d\xfc\x3b\x6b\xf5\x52\xc4\x93\x2d\xfb\xff\xf6\x1d\x6d\xc9\x86\xf7"
  2604. "\x27\x8e\xd5\x77\x87\xb1\xc6\x4e\xd1\xc2\xd7\x3f\x7f\x32\xd8\xae\xfd"
  2605. "\xe6\xfe\x4f\x53\xda\x7e\xe3\xb3\x40\x27\xa4\xfd\x3f\xb8\x71\xfc\xc3"
  2606. "\x49\xf3\xfd\x9a\xd5\xad\xb7\xf1\xe3\xa5\xa1\xef\xda\xad\x6b\x19\xff"
  2607. "\x85\xe6\x1a\xad\xf7\xff\x7d\xc9\x1b\xf5\xfc\xbe\x6c\xd9\xf9\x42\xad"
  2608. "\x36\x3f\x1e\xb1\x2f\x79\x6d\xfd\xf2\x23\xb7\x5f\xdb\x28\x37\xea\xa7"
  2609. "\xf1\x8f\x3e\xd1\xfa\xf8\xdf\x68\xff\x4f\x3f\x13\x9e\xda\x64\xfc\xbd"
  2610. "\x57\x7f\xfd\x72\x4b\xf1\x77\xb8\xff\xa7\xb6\xd4\xff\x5b\xcf\x5c\xbe"
  2611. "\x39\xd3\xd3\xae\xfd\x7b\xc7\x9f\xf6\xff\x44\x3d\x37\x9a\x2d\xd9\xcc"
  2612. "\xf9\x6f\xb3\x1b\x78\x3f\xef\x1d\x00\x00\x00\x00\x00\x00\x00\x00\x00"
  2613. "\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x6c\x56\x2e\x22\x0e\x44\x92"
  2614. "\xcb\xdf\xca\xe7\x72\xf9\xfc\xda\x33\xbc\x1f\x89\xc1\x5c\xb9\x52\xad"
  2615. "\x1d\x3a\x5d\x59\x98\x9b\x8a\xfa\xb3\xb2\x87\xa3\x2f\xd7\xf8\xa9\xcb"
  2616. "\xa1\xa6\xdf\x43\x1d\xcf\x7e\x0f\xbf\x51\x3e\x72\x57\xf9\xd9\x88\x78"
  2617. "\x38\x22\x3e\xee\xff\x5f\xbd\x9c\x2f\x56\xca\x53\xbb\x1d\x3c\x00\x00"
  2618. "\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00"
  2619. "\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x64\xf6\xb7\x79\xfe"
  2620. "\x7f\xea\x97\xfe\xdd\xde\x3a\x00\x60\xc7\x0c\xec\xf6\x06\x00\x00\x1d"
  2621. "\x67\xfc\x07\x80\xee\x63\xfc\x07\x80\xee\x63\xfc\x07\x80\xee\x63\xfc"
  2622. "\x07\x80\xee\x63\xfc\x07\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00"
  2623. "\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00"
  2624. "\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00"
  2625. "\x00\x00\x00\x00\x00\x60\x87\x9d\x3c\x71\x22\x4d\xab\x7f\xae\x2c\x17"
  2626. "\xd3\xf2\xd4\xb9\xc5\x85\x99\xca\xb9\xc3\x53\xa5\xea\x4c\x7e\x76\xa1"
  2627. "\x98\x2f\x56\xe6\xcf\xe6\xa7\x2b\x95\xe9\x72\x29\x5f\xac\xcc\xde\xeb"
  2628. "\xef\x95\x2b\x95\xb3\x13\x31\xb7\x70\x7e\xac\x56\xaa\xd6\xc6\xaa\x8b"
  2629. "\x4b\x93\xb3\x95\x85\xb9\xda\xe4\x99\xd9\xc2\x74\x69\xb2\xd4\xd7\x91"
  2630. "\xa8\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00"
  2631. "\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x60\x6b"
  2632. "\xaa\x8b\x4b\x33\x85\x72\xb9\x34\xdf\x9d\x99\x81\xd8\x13\x9b\x21\xd3"
  2633. "\xc1\xcc\xe4\xe8\xd3\xc9\x1e\xd8\x8c\xbd\x9e\xd9\xed\x33\x13\x00\x00"
  2634. "\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00"
  2635. "\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00"
  2636. "\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00"
  2637. "\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00"
  2638. "\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00"
  2639. "\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00"
  2640. "\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00"
  2641. "\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00"
  2642. "\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00"
  2643. "\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00"
  2644. "\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00"
  2645. "\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00"
  2646. "\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00"
  2647. "\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00"
  2648. "\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00"
  2649. "\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00"
  2650. "\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00"
  2651. "\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00"
  2652. "\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00"
  2653. "\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00"
  2654. "\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00"
  2655. "\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00"
  2656. "\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00"
  2657. "\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00"
  2658. "\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00"
  2659. "\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00"
  2660. "\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00"
  2661. "\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00"
  2662. "\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00"
  2663. "\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00"
  2664. "\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00"
  2665. "\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00"
  2666. "\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00"
  2667. "\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00"
  2668. "\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00"
  2669. "\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00"
  2670. "\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00"
  2671. "\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00"
  2672. "\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00"
  2673. "\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00"
  2674. "\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00"
  2675. "\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00"
  2676. "\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00"
  2677. "\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00"
  2678. "\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00"
  2679. "\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00"
  2680. "\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00"
  2681. "\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00"
  2682. "\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00"
  2683. "\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00"
  2684. "\x00\x00\x00\xc0\x83\xe1\x9f\x00\x00\x00\xff\xff\x4a\x6a\x27\x06",
  2685. 1903));
  2686. NONFAILING(syz_mount_image(
  2687. /*fs=*/0x200000000040, /*dir=*/0x2000000000c0,
  2688. /*flags=MS_SYNCHRONOUS|MS_NOSUID|MS_NODIRATIME|MS_NOATIME*/ 0xc12,
  2689. /*opts=*/0x200000000300, /*chdir=*/1, /*size=*/0x76f,
  2690. /*img=*/0x200000000800));
  2691. break;
  2692. case 2:
  2693. NONFAILING(*(uint64_t*)0x200000000100 = -1);
  2694. NONFAILING(*(uint64_t*)0x200000000108 = -1);
  2695. syscall(__NR_setrlimit, /*res=RLIMIT_FSIZE*/ 1ul,
  2696. /*rlim=*/0x200000000100ul);
  2697. break;
  2698. case 3:
  2699. NONFAILING(memcpy((void*)0x2000000002c0, "./bus\000", 6));
  2700. res = syscall(
  2701. __NR_open, /*file=*/0x2000000002c0ul,
  2702. /*flags=O_SYNC|O_NOCTTY|O_NOATIME|O_CREAT|O_CLOEXEC|0x2*/ 0x1c1142ul,
  2703. /*mode=*/0ul);
  2704. if (res != -1)
  2705. r[0] = res;
  2706. break;
  2707. case 4:
  2708. NONFAILING(memset((void*)0x2000000001c0, 32, 1));
  2709. syscall(__NR_pwrite64, /*fd=*/r[0], /*buf=*/0x2000000001c0ul, /*count=*/1ul,
  2710. /*pos=*/0x4010040bffdul);
  2711. break;
  2712. case 5:
  2713. NONFAILING(memcpy((void*)0x200000000380, "/dev/loop", 9));
  2714. NONFAILING(*(uint8_t*)0x200000000389 = 0x30 + procid * 1);
  2715. NONFAILING(*(uint8_t*)0x20000000038a = 0);
  2716. NONFAILING(memcpy((void*)0x200000000140, "./bus\000", 6));
  2717. syscall(__NR_mount, /*src=*/0x200000000380ul, /*dst=*/0x200000000140ul,
  2718. /*type=*/0ul, /*flags=MS_BIND*/ 0x1000ul, /*data=*/0ul);
  2719. break;
  2720. case 6:
  2721. NONFAILING(memcpy((void*)0x200000000400, "./bus\000", 6));
  2722. res = syscall(__NR_open, /*file=*/0x200000000400ul,
  2723. /*flags=O_SYNC|O_NOCTTY|O_NOATIME|O_RDWR|0x3c*/ 0x14113eul,
  2724. /*mode=*/0ul);
  2725. if (res != -1)
  2726. r[1] = res;
  2727. break;
  2728. case 7:
  2729. res = syscall(__NR_socket, /*domain=*/0xaul, /*type=*/1ul, /*proto=*/0);
  2730. if (res != -1)
  2731. r[2] = res;
  2732. break;
  2733. case 8:
  2734. syscall(__NR_setsockopt, /*fd=*/r[2], /*level=*/6,
  2735. /*optname=TCP_FASTOPEN_NO_COOKIE*/ 0x22, /*optval=*/0ul,
  2736. /*optlen=*/0ul);
  2737. break;
  2738. case 9:
  2739. syscall(__NR_connect, /*fd=*/r[2], /*addr=*/0ul, /*addrlen=*/0ul);
  2740. break;
  2741. case 10:
  2742. NONFAILING(memcpy((void*)0x200000000100, "#! ", 3));
  2743. NONFAILING(*(uint8_t*)0x200000000103 = 0xa);
  2744. syscall(__NR_write, /*fd=*/r[1], /*data=*/0x200000000100ul,
  2745. /*len=*/0x208e24bul);
  2746. break;
  2747. case 11:
  2748. syscall(__NR_close, /*fd=*/4);
  2749. break;
  2750. case 12:
  2751. syscall(__NR_readlink, /*path=*/0ul, /*buf=*/0ul, /*siz=*/0ul);
  2752. break;
  2753. }
  2754. }
  2755. int main(void)
  2756. {
  2757. syscall(__NR_mmap, /*addr=*/0x1ffffffff000ul, /*len=*/0x1000ul, /*prot=*/0ul,
  2758. /*flags=MAP_FIXED|MAP_ANONYMOUS|MAP_PRIVATE*/ 0x32ul, /*fd=*/-1,
  2759. /*offset=*/0ul);
  2760. syscall(__NR_mmap, /*addr=*/0x200000000000ul, /*len=*/0x1000000ul,
  2761. /*prot=PROT_WRITE|PROT_READ|PROT_EXEC*/ 7ul,
  2762. /*flags=MAP_FIXED|MAP_ANONYMOUS|MAP_PRIVATE*/ 0x32ul, /*fd=*/-1,
  2763. /*offset=*/0ul);
  2764. syscall(__NR_mmap, /*addr=*/0x200001000000ul, /*len=*/0x1000ul, /*prot=*/0ul,
  2765. /*flags=MAP_FIXED|MAP_ANONYMOUS|MAP_PRIVATE*/ 0x32ul, /*fd=*/-1,
  2766. /*offset=*/0ul);
  2767. setup_sysctl();
  2768. const char* reason;
  2769. (void)reason;
  2770. install_segv_handler();
  2771. for (procid = 0; procid < 8; procid++) {
  2772. if (fork() == 0) {
  2773. use_temporary_dir();
  2774. do_sandbox_none();
  2775. }
  2776. }
  2777. sleep(1000000);
  2778. return 0;
  2779. }
  2780.  
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement