diff options
author | Dobroslaw Kijowski | 2021-03-26 20:14:42 +0100 |
---|---|---|
committer | Dobroslaw Kijowski | 2021-03-26 20:14:42 +0100 |
commit | 7a22fb06e7c4fc217cda23837bc8a4e29feb3d42 (patch) | |
tree | 973525fd9a22cb5ade91834f2ebd8ac322307571 | |
download | aur-7a22fb06e7c4fc217cda23837bc8a4e29feb3d42.tar.gz |
relayd: initial package recipe
* This is last version from OpenWrt's master branch.
* Contains needed files from libubox to make it standalone.
-rw-r--r-- | .SRCINFO | 26 | ||||
-rw-r--r-- | 0001-libubox-import-list-uloop-utils-.h-uloop-epoll-.c.patch | 1332 | ||||
-rw-r--r-- | 0002-CMakeLists.txt-adjust-to-compile-with-inline-uloop.patch | 27 | ||||
-rw-r--r-- | 0003-relayd.h-fix-includes.patch | 28 | ||||
-rw-r--r-- | PKGBUILD | 55 | ||||
-rw-r--r-- | relayd.conf | 1 | ||||
-rw-r--r-- | relayd.service | 12 |
7 files changed, 1481 insertions, 0 deletions
diff --git a/.SRCINFO b/.SRCINFO new file mode 100644 index 000000000000..309a63fa80eb --- /dev/null +++ b/.SRCINFO @@ -0,0 +1,26 @@ +pkgbase = relayd + pkgdesc = Transparent routing / relay daemon (taken from OpenWrt) + pkgver = 20200425 + pkgrel = 1 + url = https://git.openwrt.org/project/relayd.git + arch = x86_64 + arch = armv7h + license = GPL + makedepends = git + depends = glibc + backup = etc/conf.d/relayd + source = relayd::git+https://git.openwrt.org/project/relayd.git#commit=f4d759be54ceb37714e9a6ca320d5b50c95e9ce9 + source = 0001-libubox-import-list-uloop-utils-.h-uloop-epoll-.c.patch + source = 0002-CMakeLists.txt-adjust-to-compile-with-inline-uloop.patch + source = 0003-relayd.h-fix-includes.patch + source = relayd.conf + source = relayd.service + sha256sums = SKIP + sha256sums = 3073ac119de2635eeb5affa6c8e46a6328179ffe568302a463f62d5e5b0ac4f5 + sha256sums = b002ab6bf4729984c630e3ef57caf2606e2a667cdd2fac1046d16475bd5cb98e + sha256sums = b4fcb393e3567e61999d31734d45314e2cced8620d52146696f982437a978c75 + sha256sums = 58c84f0f6c335e05c281d9f2eeb144839a5e0e2021bac9073872a4634739fd1f + sha256sums = 91a601ba5080851ecba276ad8ba11bcd1c4ed97715e631fc8e3c58fa86962b62 + +pkgname = relayd + diff --git a/0001-libubox-import-list-uloop-utils-.h-uloop-epoll-.c.patch b/0001-libubox-import-list-uloop-utils-.h-uloop-epoll-.c.patch new file mode 100644 index 000000000000..2a5c21f1bd9a --- /dev/null +++ b/0001-libubox-import-list-uloop-utils-.h-uloop-epoll-.c.patch @@ -0,0 +1,1332 @@ +From 93e640d3236f1937ddb0ab07b06397cd950b6fb0 Mon Sep 17 00:00:00 2001 +From: Dobroslaw Kijowski <dobo90@gmail.com> +Date: Thu, 25 Mar 2021 22:06:53 +0100 +Subject: [PATCH 1/3] libubox: import {list,uloop,utils}.h uloop{,-epoll}.c + +From HEAD: + +commit 551d75b5662cccd0466b990d58136bdf799a804d +Author: Peter Seiderer <ps.report@gmx.net> +Date: Sat Mar 6 11:54:50 2021 +0100 + + libubox: tests: add more blobmsg/json test cases + + * add mixed int/double tests + * add blobmsg_cast_u64/blobmsg_cast_s64 tests + + Signed-off-by: Peter Seiderer <ps.report@gmx.net> +--- + list.h | 208 ++++++++++++++++++ + uloop-epoll.c | 107 ++++++++++ + uloop.c | 581 ++++++++++++++++++++++++++++++++++++++++++++++++++ + uloop.h | 115 ++++++++++ + utils.h | 258 ++++++++++++++++++++++ + 5 files changed, 1269 insertions(+) + create mode 100644 list.h + create mode 100644 uloop-epoll.c + create mode 100644 uloop.c + create mode 100644 uloop.h + create mode 100644 utils.h + +diff --git a/list.h b/list.h +new file mode 100644 +index 0000000..8e61e47 +--- /dev/null ++++ b/list.h +@@ -0,0 +1,208 @@ ++/*- ++ * Copyright (c) 2011 Felix Fietkau <nbd@openwrt.org> ++ * Copyright (c) 2010 Isilon Systems, Inc. ++ * Copyright (c) 2010 iX Systems, Inc. ++ * Copyright (c) 2010 Panasas, Inc. ++ * All rights reserved. ++ * ++ * Redistribution and use in source and binary forms, with or without ++ * modification, are permitted provided that the following conditions ++ * are met: ++ * 1. Redistributions of source code must retain the above copyright ++ * notice unmodified, this list of conditions, and the following ++ * disclaimer. ++ * 2. Redistributions in binary form must reproduce the above copyright ++ * notice, this list of conditions and the following disclaimer in the ++ * documentation and/or other materials provided with the distribution. ++ * ++ * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR ++ * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES ++ * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. ++ * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, ++ * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT ++ * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, ++ * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY ++ * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT ++ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF ++ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. ++ */ ++#ifndef _LINUX_LIST_H_ ++#define _LINUX_LIST_H_ ++ ++#include <stddef.h> ++#include <stdbool.h> ++ ++#define prefetch(x) ++ ++#ifndef container_of ++#define container_of(ptr, type, member) \ ++ ({ \ ++ const __typeof__(((type *) NULL)->member) *__mptr = (ptr); \ ++ (type *) ((char *) __mptr - offsetof(type, member)); \ ++ }) ++#endif ++ ++struct list_head { ++ struct list_head *next; ++ struct list_head *prev; ++}; ++ ++#define LIST_HEAD_INIT(name) { &(name), &(name) } ++#undef LIST_HEAD ++#define LIST_HEAD(name) struct list_head name = LIST_HEAD_INIT(name) ++ ++static inline void ++INIT_LIST_HEAD(struct list_head *list) ++{ ++ list->next = list->prev = list; ++} ++ ++static inline bool ++list_empty(const struct list_head *head) ++{ ++ return (head->next == head); ++} ++ ++static inline bool ++list_is_first(const struct list_head *list, ++ const struct list_head *head) ++{ ++ return list->prev == head; ++} ++ ++static inline bool ++list_is_last(const struct list_head *list, ++ const struct list_head *head) ++{ ++ return list->next == head; ++} ++ ++static inline void ++_list_del(struct list_head *entry) ++{ ++ entry->next->prev = entry->prev; ++ entry->prev->next = entry->next; ++} ++ ++static inline void ++list_del(struct list_head *entry) ++{ ++ _list_del(entry); ++ entry->next = entry->prev = NULL; ++} ++ ++static inline void ++_list_add(struct list_head *_new, struct list_head *prev, ++ struct list_head *next) ++{ ++ ++ next->prev = _new; ++ _new->next = next; ++ _new->prev = prev; ++ prev->next = _new; ++} ++ ++static inline void ++list_del_init(struct list_head *entry) ++{ ++ _list_del(entry); ++ INIT_LIST_HEAD(entry); ++} ++ ++#define list_entry(ptr, type, field) container_of(ptr, type, field) ++#define list_first_entry(ptr, type, field) list_entry((ptr)->next, type, field) ++#define list_last_entry(ptr, type, field) list_entry((ptr)->prev, type, field) ++ ++#define list_for_each(p, head) \ ++ for (p = (head)->next; p != (head); p = p->next) ++ ++#define list_for_each_safe(p, n, head) \ ++ for (p = (head)->next, n = p->next; p != (head); p = n, n = p->next) ++ ++#define list_for_each_entry(p, h, field) \ ++ for (p = list_first_entry(h, __typeof__(*p), field); &p->field != (h); \ ++ p = list_entry(p->field.next, __typeof__(*p), field)) ++ ++#define list_for_each_entry_safe(p, n, h, field) \ ++ for (p = list_first_entry(h, __typeof__(*p), field), \ ++ n = list_entry(p->field.next, __typeof__(*p), field); &p->field != (h);\ ++ p = n, n = list_entry(n->field.next, __typeof__(*n), field)) ++ ++#define list_for_each_entry_reverse(p, h, field) \ ++ for (p = list_last_entry(h, __typeof__(*p), field); &p->field != (h); \ ++ p = list_entry(p->field.prev, __typeof__(*p), field)) ++ ++#define list_for_each_prev(p, h) for (p = (h)->prev; p != (h); p = p->prev) ++#define list_for_each_prev_safe(p, n, h) for (p = (h)->prev, n = p->prev; p != (h); p = n, n = p->prev) ++ ++static inline void ++list_add(struct list_head *_new, struct list_head *head) ++{ ++ _list_add(_new, head, head->next); ++} ++ ++static inline void ++list_add_tail(struct list_head *_new, struct list_head *head) ++{ ++ _list_add(_new, head->prev, head); ++} ++ ++static inline void ++list_move(struct list_head *list, struct list_head *head) ++{ ++ _list_del(list); ++ list_add(list, head); ++} ++ ++static inline void ++list_move_tail(struct list_head *entry, struct list_head *head) ++{ ++ _list_del(entry); ++ list_add_tail(entry, head); ++} ++ ++static inline void ++_list_splice(const struct list_head *list, struct list_head *prev, ++ struct list_head *next) ++{ ++ struct list_head *first; ++ struct list_head *last; ++ ++ if (list_empty(list)) ++ return; ++ ++ first = list->next; ++ last = list->prev; ++ first->prev = prev; ++ prev->next = first; ++ last->next = next; ++ next->prev = last; ++} ++ ++static inline void ++list_splice(const struct list_head *list, struct list_head *head) ++{ ++ _list_splice(list, head, head->next); ++} ++ ++static inline void ++list_splice_tail(struct list_head *list, struct list_head *head) ++{ ++ _list_splice(list, head->prev, head); ++} ++ ++static inline void ++list_splice_init(struct list_head *list, struct list_head *head) ++{ ++ _list_splice(list, head, head->next); ++ INIT_LIST_HEAD(list); ++} ++ ++static inline void ++list_splice_tail_init(struct list_head *list, struct list_head *head) ++{ ++ _list_splice(list, head->prev, head); ++ INIT_LIST_HEAD(list); ++} ++ ++#endif /* _LINUX_LIST_H_ */ +diff --git a/uloop-epoll.c b/uloop-epoll.c +new file mode 100644 +index 0000000..609ca6e +--- /dev/null ++++ b/uloop-epoll.c +@@ -0,0 +1,107 @@ ++/* ++ * uloop - event loop implementation ++ * ++ * Copyright (C) 2010-2016 Felix Fietkau <nbd@openwrt.org> ++ * ++ * Permission to use, copy, modify, and/or distribute this software for any ++ * purpose with or without fee is hereby granted, provided that the above ++ * copyright notice and this permission notice appear in all copies. ++ * ++ * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES ++ * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF ++ * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ++ * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES ++ * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ++ * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF ++ * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. ++ */ ++ ++/** ++ * FIXME: uClibc < 0.9.30.3 does not define EPOLLRDHUP for Linux >= 2.6.17 ++ */ ++#ifndef EPOLLRDHUP ++#define EPOLLRDHUP 0x2000 ++#endif ++ ++static int uloop_init_pollfd(void) ++{ ++ if (poll_fd >= 0) ++ return 0; ++ ++ poll_fd = epoll_create(32); ++ if (poll_fd < 0) ++ return -1; ++ ++ fcntl(poll_fd, F_SETFD, fcntl(poll_fd, F_GETFD) | FD_CLOEXEC); ++ return 0; ++} ++ ++static int register_poll(struct uloop_fd *fd, unsigned int flags) ++{ ++ struct epoll_event ev; ++ int op = fd->registered ? EPOLL_CTL_MOD : EPOLL_CTL_ADD; ++ ++ memset(&ev, 0, sizeof(struct epoll_event)); ++ ++ if (flags & ULOOP_READ) ++ ev.events |= EPOLLIN | EPOLLRDHUP; ++ ++ if (flags & ULOOP_WRITE) ++ ev.events |= EPOLLOUT; ++ ++ if (flags & ULOOP_EDGE_TRIGGER) ++ ev.events |= EPOLLET; ++ ++ ev.data.ptr = fd; ++ fd->flags = flags; ++ ++ return epoll_ctl(poll_fd, op, fd->fd, &ev); ++} ++ ++static struct epoll_event events[ULOOP_MAX_EVENTS]; ++ ++static int __uloop_fd_delete(struct uloop_fd *sock) ++{ ++ sock->flags = 0; ++ return epoll_ctl(poll_fd, EPOLL_CTL_DEL, sock->fd, 0); ++} ++ ++static int uloop_fetch_events(int timeout) ++{ ++ int n, nfds; ++ ++ nfds = epoll_wait(poll_fd, events, ARRAY_SIZE(events), timeout); ++ for (n = 0; n < nfds; ++n) { ++ struct uloop_fd_event *cur = &cur_fds[n]; ++ struct uloop_fd *u = events[n].data.ptr; ++ unsigned int ev = 0; ++ ++ cur->fd = u; ++ if (!u) ++ continue; ++ ++ if (events[n].events & (EPOLLERR|EPOLLHUP)) { ++ u->error = true; ++ if (!(u->flags & ULOOP_ERROR_CB)) ++ uloop_fd_delete(u); ++ } ++ ++ if(!(events[n].events & (EPOLLRDHUP|EPOLLIN|EPOLLOUT|EPOLLERR|EPOLLHUP))) { ++ cur->fd = NULL; ++ continue; ++ } ++ ++ if(events[n].events & EPOLLRDHUP) ++ u->eof = true; ++ ++ if(events[n].events & EPOLLIN) ++ ev |= ULOOP_READ; ++ ++ if(events[n].events & EPOLLOUT) ++ ev |= ULOOP_WRITE; ++ ++ cur->events = ev; ++ } ++ ++ return nfds; ++} +diff --git a/uloop.c b/uloop.c +new file mode 100644 +index 0000000..8517366 +--- /dev/null ++++ b/uloop.c +@@ -0,0 +1,581 @@ ++/* ++ * uloop - event loop implementation ++ * ++ * Copyright (C) 2010-2016 Felix Fietkau <nbd@openwrt.org> ++ * ++ * Permission to use, copy, modify, and/or distribute this software for any ++ * purpose with or without fee is hereby granted, provided that the above ++ * copyright notice and this permission notice appear in all copies. ++ * ++ * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES ++ * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF ++ * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ++ * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES ++ * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ++ * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF ++ * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. ++ */ ++#include <sys/time.h> ++#include <sys/types.h> ++ ++#include <unistd.h> ++#include <stdio.h> ++#include <stdlib.h> ++#include <errno.h> ++#include <poll.h> ++#include <string.h> ++#include <fcntl.h> ++#include <stdbool.h> ++ ++#include "uloop.h" ++#include "utils.h" ++ ++#ifdef USE_KQUEUE ++#include <sys/event.h> ++#endif ++#ifdef USE_EPOLL ++#include <sys/epoll.h> ++#endif ++#include <sys/wait.h> ++ ++struct uloop_fd_event { ++ struct uloop_fd *fd; ++ unsigned int events; ++}; ++ ++struct uloop_fd_stack { ++ struct uloop_fd_stack *next; ++ struct uloop_fd *fd; ++ unsigned int events; ++}; ++ ++static struct uloop_fd_stack *fd_stack = NULL; ++ ++#define ULOOP_MAX_EVENTS 10 ++ ++static struct list_head timeouts = LIST_HEAD_INIT(timeouts); ++static struct list_head processes = LIST_HEAD_INIT(processes); ++ ++static int poll_fd = -1; ++bool uloop_cancelled = false; ++bool uloop_handle_sigchld = true; ++static int uloop_status = 0; ++static bool do_sigchld = false; ++ ++static struct uloop_fd_event cur_fds[ULOOP_MAX_EVENTS]; ++static int cur_fd, cur_nfds; ++static int uloop_run_depth = 0; ++ ++int uloop_fd_add(struct uloop_fd *sock, unsigned int flags); ++ ++#ifdef USE_KQUEUE ++#include "uloop-kqueue.c" ++#endif ++ ++#ifdef USE_EPOLL ++#include "uloop-epoll.c" ++#endif ++ ++static void waker_consume(struct uloop_fd *fd, unsigned int events) ++{ ++ char buf[4]; ++ ++ while (read(fd->fd, buf, 4) > 0) ++ ; ++} ++ ++static int waker_pipe = -1; ++static struct uloop_fd waker_fd = { ++ .fd = -1, ++ .cb = waker_consume, ++}; ++ ++static void waker_init_fd(int fd) ++{ ++ fcntl(fd, F_SETFD, fcntl(fd, F_GETFD) | FD_CLOEXEC); ++ fcntl(fd, F_SETFL, fcntl(fd, F_GETFL) | O_NONBLOCK); ++} ++ ++static int waker_init(void) ++{ ++ int fds[2]; ++ ++ if (waker_pipe >= 0) ++ return 0; ++ ++ if (pipe(fds) < 0) ++ return -1; ++ ++ waker_init_fd(fds[0]); ++ waker_init_fd(fds[1]); ++ waker_pipe = fds[1]; ++ ++ waker_fd.fd = fds[0]; ++ waker_fd.cb = waker_consume; ++ uloop_fd_add(&waker_fd, ULOOP_READ); ++ ++ return 0; ++} ++ ++static void uloop_setup_signals(bool add); ++ ++int uloop_init(void) ++{ ++ if (uloop_init_pollfd() < 0) ++ return -1; ++ ++ if (waker_init() < 0) { ++ uloop_done(); ++ return -1; ++ } ++ ++ uloop_setup_signals(true); ++ ++ return 0; ++} ++ ++static bool uloop_fd_stack_event(struct uloop_fd *fd, int events) ++{ ++ struct uloop_fd_stack *cur; ++ ++ /* ++ * Do not buffer events for level-triggered fds, they will keep firing. ++ * Caller needs to take care of recursion issues. ++ */ ++ if (!(fd->flags & ULOOP_EDGE_TRIGGER)) ++ return false; ++ ++ for (cur = fd_stack; cur; cur = cur->next) { ++ if (cur->fd != fd) ++ continue; ++ ++ if (events < 0) ++ cur->fd = NULL; ++ else ++ cur->events |= events | ULOOP_EVENT_BUFFERED; ++ ++ return true; ++ } ++ ++ return false; ++} ++ ++static void uloop_run_events(int timeout) ++{ ++ struct uloop_fd_event *cur; ++ struct uloop_fd *fd; ++ ++ if (!cur_nfds) { ++ cur_fd = 0; ++ cur_nfds = uloop_fetch_events(timeout); ++ if (cur_nfds < 0) ++ cur_nfds = 0; ++ } ++ ++ while (cur_nfds > 0) { ++ struct uloop_fd_stack stack_cur; ++ unsigned int events; ++ ++ cur = &cur_fds[cur_fd++]; ++ cur_nfds--; ++ ++ fd = cur->fd; ++ events = cur->events; ++ if (!fd) ++ continue; ++ ++ if (!fd->cb) ++ continue; ++ ++ if (uloop_fd_stack_event(fd, cur->events)) ++ continue; ++ ++ stack_cur.next = fd_stack; ++ stack_cur.fd = fd; ++ fd_stack = &stack_cur; ++ do { ++ stack_cur.events = 0; ++ fd->cb(fd, events); ++ events = stack_cur.events & ULOOP_EVENT_MASK; ++ } while (stack_cur.fd && events); ++ fd_stack = stack_cur.next; ++ ++ return; ++ } ++} ++ ++int uloop_fd_add(struct uloop_fd *sock, unsigned int flags) ++{ ++ unsigned int fl; ++ int ret; ++ ++ if (!(flags & (ULOOP_READ | ULOOP_WRITE))) ++ return uloop_fd_delete(sock); ++ ++ if (!sock->registered && !(flags & ULOOP_BLOCKING)) { ++ fl = fcntl(sock->fd, F_GETFL, 0); ++ fl |= O_NONBLOCK; ++ fcntl(sock->fd, F_SETFL, fl); ++ } ++ ++ ret = register_poll(sock, flags); ++ if (ret < 0) ++ goto out; ++ ++ sock->registered = true; ++ sock->eof = false; ++ sock->error = false; ++ ++out: ++ return ret; ++} ++ ++int uloop_fd_delete(struct uloop_fd *fd) ++{ ++ int i; ++ ++ for (i = 0; i < cur_nfds; i++) { ++ if (cur_fds[cur_fd + i].fd != fd) ++ continue; ++ ++ cur_fds[cur_fd + i].fd = NULL; ++ } ++ ++ if (!fd->registered) ++ return 0; ++ ++ fd->registered = false; ++ uloop_fd_stack_event(fd, -1); ++ return __uloop_fd_delete(fd); ++} ++ ++static int tv_diff(struct timeval *t1, struct timeval *t2) ++{ ++ return ++ (t1->tv_sec - t2->tv_sec) * 1000 + ++ (t1->tv_usec - t2->tv_usec) / 1000; ++} ++ ++int uloop_timeout_add(struct uloop_timeout *timeout) ++{ ++ struct uloop_timeout *tmp; ++ struct list_head *h = &timeouts; ++ ++ if (timeout->pending) ++ return -1; ++ ++ list_for_each_entry(tmp, &timeouts, list) { ++ if (tv_diff(&tmp->time, &timeout->time) > 0) { ++ h = &tmp->list; ++ break; ++ } ++ } ++ ++ list_add_tail(&timeout->list, h); ++ timeout->pending = true; ++ ++ return 0; ++} ++ ++static void uloop_gettime(struct timeval *tv) ++{ ++ struct timespec ts; ++ ++ clock_gettime(CLOCK_MONOTONIC, &ts); ++ tv->tv_sec = ts.tv_sec; ++ tv->tv_usec = ts.tv_nsec / 1000; ++} ++ ++int uloop_timeout_set(struct uloop_timeout *timeout, int msecs) ++{ ++ struct timeval *time = &timeout->time; ++ ++ if (timeout->pending) ++ uloop_timeout_cancel(timeout); ++ ++ uloop_gettime(time); ++ ++ time->tv_sec += msecs / 1000; ++ time->tv_usec += (msecs % 1000) * 1000; ++ ++ if (time->tv_usec > 1000000) { ++ time->tv_sec++; ++ time->tv_usec -= 1000000; ++ } ++ ++ return uloop_timeout_add(timeout); ++} ++ ++int uloop_timeout_cancel(struct uloop_timeout *timeout) ++{ ++ if (!timeout->pending) ++ return -1; ++ ++ list_del(&timeout->list); ++ timeout->pending = false; ++ ++ return 0; ++} ++ ++int uloop_timeout_remaining(struct uloop_timeout *timeout) ++{ ++ struct timeval now; ++ ++ if (!timeout->pending) ++ return -1; ++ ++ uloop_gettime(&now); ++ ++ return tv_diff(&timeout->time, &now); ++} ++ ++int uloop_process_add(struct uloop_process *p) ++{ ++ struct uloop_process *tmp; ++ struct list_head *h = &processes; ++ ++ if (p->pending) ++ return -1; ++ ++ list_for_each_entry(tmp, &processes, list) { ++ if (tmp->pid > p->pid) { ++ h = &tmp->list; ++ break; ++ } ++ } ++ ++ list_add_tail(&p->list, h); ++ p->pending = true; ++ ++ return 0; ++} ++ ++int uloop_process_delete(struct uloop_process *p) ++{ ++ if (!p->pending) ++ return -1; ++ ++ list_del(&p->list); ++ p->pending = false; ++ ++ return 0; ++} ++ ++static void uloop_handle_processes(void) ++{ ++ struct uloop_process *p, *tmp; ++ pid_t pid; ++ int ret; ++ ++ do_sigchld = false; ++ ++ while (1) { ++ pid = waitpid(-1, &ret, WNOHANG); ++ if (pid < 0 && errno == EINTR) ++ continue; ++ ++ if (pid <= 0) ++ return; ++ ++ list_for_each_entry_safe(p, tmp, &processes, list) { ++ if (p->pid < pid) ++ continue; ++ ++ if (p->pid > pid) ++ break; ++ ++ uloop_process_delete(p); ++ p->cb(p, ret); ++ } ++ } ++ ++} ++ ++static void uloop_signal_wake(void) ++{ ++ do { ++ if (write(waker_pipe, "w", 1) < 0) { ++ if (errno == EINTR) ++ continue; ++ } ++ break; ++ } while (1); ++} ++ ++static void uloop_handle_sigint(int signo) ++{ ++ uloop_status = signo; ++ uloop_cancelled = true; ++ uloop_signal_wake(); ++} ++ ++static void uloop_sigchld(int signo) ++{ ++ do_sigchld = true; ++ uloop_signal_wake(); ++} ++ ++static void uloop_install_handler(int signum, void (*handler)(int), struct sigaction* old, bool add) ++{ ++ struct sigaction s; ++ struct sigaction *act; ++ ++ act = NULL; ++ sigaction(signum, NULL, &s); ++ ++ if (add) { ++ if (s.sa_handler == SIG_DFL) { /* Do not override existing custom signal handlers */ ++ memcpy(old, &s, sizeof(struct sigaction)); ++ s.sa_handler = handler; ++ s.sa_flags = 0; ++ act = &s; ++ } ++ } ++ else if (s.sa_handler == handler) { /* Do not restore if someone modified our handler */ ++ act = old; ++ } ++ ++ if (act != NULL) ++ sigaction(signum, act, NULL); ++} ++ ++static void uloop_ignore_signal(int signum, bool ignore) ++{ ++ struct sigaction s; ++ void *new_handler = NULL; ++ ++ sigaction(signum, NULL, &s); ++ ++ if (ignore) { ++ if (s.sa_handler == SIG_DFL) /* Ignore only if there isn't any custom handler */ ++ new_handler = SIG_IGN; ++ } else { ++ if (s.sa_handler == SIG_IGN) /* Restore only if noone modified our SIG_IGN */ ++ new_handler = SIG_DFL; ++ } ++ ++ if (new_handler) { ++ s.sa_handler = new_handler; ++ s.sa_flags = 0; ++ sigaction(signum, &s, NULL); ++ } ++} ++ ++static void uloop_setup_signals(bool add) ++{ ++ static struct sigaction old_sigint, old_sigchld, old_sigterm; ++ ++ uloop_install_handler(SIGINT, uloop_handle_sigint, &old_sigint, add); ++ uloop_install_handler(SIGTERM, uloop_handle_sigint, &old_sigterm, add); ++ ++ if (uloop_handle_sigchld) ++ uloop_install_handler(SIGCHLD, uloop_sigchld, &old_sigchld, add); ++ ++ uloop_ignore_signal(SIGPIPE, add); ++} ++ ++static int uloop_get_next_timeout(struct timeval *tv) ++{ ++ struct uloop_timeout *timeout; ++ int diff; ++ ++ if (list_empty(&timeouts)) ++ return -1; ++ ++ timeout = list_first_entry(&timeouts, struct uloop_timeout, list); ++ diff = tv_diff(&timeout->time, tv); ++ if (diff < 0) ++ return 0; ++ ++ return diff; ++} ++ ++static void uloop_process_timeouts(struct timeval *tv) ++{ ++ struct uloop_timeout *t; ++ ++ while (!list_empty(&timeouts)) { ++ t = list_first_entry(&timeouts, struct uloop_timeout, list); ++ ++ if (tv_diff(&t->time, tv) > 0) ++ break; ++ ++ uloop_timeout_cancel(t); ++ if (t->cb) ++ t->cb(t); ++ } ++} ++ ++static void uloop_clear_timeouts(void) ++{ ++ struct uloop_timeout *t, *tmp; ++ ++ list_for_each_entry_safe(t, tmp, &timeouts, list) ++ uloop_timeout_cancel(t); ++} ++ ++static void uloop_clear_processes(void) ++{ ++ struct uloop_process *p, *tmp; ++ ++ list_for_each_entry_safe(p, tmp, &processes, list) ++ uloop_process_delete(p); ++} ++ ++bool uloop_cancelling(void) ++{ ++ return uloop_run_depth > 0 && uloop_cancelled; ++} ++ ++int uloop_run_timeout(int timeout) ++{ ++ int next_time = 0; ++ struct timeval tv; ++ ++ uloop_run_depth++; ++ ++ uloop_status = 0; ++ uloop_cancelled = false; ++ while (!uloop_cancelled) ++ { ++ uloop_gettime(&tv); ++ uloop_process_timeouts(&tv); ++ ++ if (do_sigchld) ++ uloop_handle_processes(); ++ ++ if (uloop_cancelled) ++ break; ++ ++ uloop_gettime(&tv); ++ ++ next_time = uloop_get_next_timeout(&tv); ++ if (timeout >= 0 && timeout < next_time) ++ next_time = timeout; ++ uloop_run_events(next_time); ++ } ++ ++ --uloop_run_depth; ++ ++ return uloop_status; ++} ++ ++void uloop_done(void) ++{ ++ uloop_setup_signals(false); ++ ++ if (poll_fd >= 0) { ++ close(poll_fd); ++ poll_fd = -1; ++ } ++ ++ if (waker_pipe >= 0) { ++ uloop_fd_delete(&waker_fd); ++ close(waker_pipe); ++ close(waker_fd.fd); ++ waker_pipe = -1; ++ } ++ ++ uloop_clear_timeouts(); ++ uloop_clear_processes(); ++} +diff --git a/uloop.h b/uloop.h +new file mode 100644 +index 0000000..36084f5 +--- /dev/null ++++ b/uloop.h +@@ -0,0 +1,115 @@ ++/* ++ * uloop - event loop implementation ++ * ++ * Copyright (C) 2010-2013 Felix Fietkau <nbd@openwrt.org> ++ * ++ * Permission to use, copy, modify, and/or distribute this software for any ++ * purpose with or without fee is hereby granted, provided that the above ++ * copyright notice and this permission notice appear in all copies. ++ * ++ * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES ++ * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF ++ * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ++ * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES ++ * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ++ * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF ++ * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. ++ */ ++#ifndef _ULOOP_H__ ++#define _ULOOP_H__ ++ ++#include <sys/time.h> ++#include <sys/types.h> ++#include <stdbool.h> ++#include <stdint.h> ++#include <signal.h> ++ ++#if defined(__APPLE__) || defined(__FreeBSD__) ++#define USE_KQUEUE ++#else ++#define USE_EPOLL ++#endif ++ ++#include "list.h" ++ ++struct uloop_fd; ++struct uloop_timeout; ++struct uloop_process; ++ ++typedef void (*uloop_fd_handler)(struct uloop_fd *u, unsigned int events); ++typedef void (*uloop_timeout_handler)(struct uloop_timeout *t); ++typedef void (*uloop_process_handler)(struct uloop_process *c, int ret); ++ ++#define ULOOP_READ (1 << 0) ++#define ULOOP_WRITE (1 << 1) ++#define ULOOP_EDGE_TRIGGER (1 << 2) ++#define ULOOP_BLOCKING (1 << 3) ++ ++#define ULOOP_EVENT_MASK (ULOOP_READ | ULOOP_WRITE) ++ ++/* internal flags */ ++#define ULOOP_EVENT_BUFFERED (1 << 4) ++#ifdef USE_KQUEUE ++#define ULOOP_EDGE_DEFER (1 << 5) ++#endif ++ ++#define ULOOP_ERROR_CB (1 << 6) ++ ++struct uloop_fd ++{ ++ uloop_fd_handler cb; ++ int fd; ++ bool eof; ++ bool error; ++ bool registered; ++ uint8_t flags; ++}; ++ ++struct uloop_timeout ++{ ++ struct list_head list; ++ bool pending; ++ ++ uloop_timeout_handler cb; ++ struct timeval time; ++}; ++ ++struct uloop_process ++{ ++ struct list_head list; ++ bool pending; ++ ++ uloop_process_handler cb; ++ pid_t pid; ++}; ++ ++extern bool uloop_cancelled; ++extern bool uloop_handle_sigchld; ++ ++int uloop_fd_add(struct uloop_fd *sock, unsigned int flags); ++int uloop_fd_delete(struct uloop_fd *sock); ++ ++int uloop_timeout_add(struct uloop_timeout *timeout); ++int uloop_timeout_set(struct uloop_timeout *timeout, int msecs); ++int uloop_timeout_cancel(struct uloop_timeout *timeout); ++int uloop_timeout_remaining(struct uloop_timeout *timeout); ++ ++int uloop_process_add(struct uloop_process *p); ++int uloop_process_delete(struct uloop_process *p); ++ ++bool uloop_cancelling(void); ++ ++static inline void uloop_end(void) ++{ ++ uloop_cancelled = true; ++} ++ ++int uloop_init(void); ++int uloop_run_timeout(int timeout); ++static inline int uloop_run(void) ++{ ++ return uloop_run_timeout(-1); ++} ++void uloop_done(void); ++ ++#endif +diff --git a/utils.h b/utils.h +new file mode 100644 +index 0000000..5c53cc0 +--- /dev/null ++++ b/utils.h +@@ -0,0 +1,258 @@ ++/* ++ * utils - misc libubox utility functions ++ * ++ * Copyright (C) 2012 Felix Fietkau <nbd@openwrt.org> ++ * ++ * Permission to use, copy, modify, and/or distribute this software for any ++ * purpose with or without fee is hereby granted, provided that the above ++ * copyright notice and this permission notice appear in all copies. ++ * ++ * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES ++ * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF ++ * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ++ * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES ++ * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ++ * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF ++ * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. ++ */ ++ ++#ifndef __LIBUBOX_UTILS_H ++#define __LIBUBOX_UTILS_H ++ ++#include <sys/stat.h> ++#include <sys/types.h> ++#include <sys/time.h> ++#include <stdint.h> ++#include <stdbool.h> ++#include <unistd.h> ++#include <time.h> ++ ++/* ++ * calloc_a(size_t len, [void **addr, size_t len,...], NULL) ++ * ++ * allocate a block of memory big enough to hold multiple aligned objects. ++ * the pointer to the full object (starting with the first chunk) is returned, ++ * all other pointers are stored in the locations behind extra addr arguments. ++ * the last argument needs to be a NULL pointer ++ */ ++ ++#define calloc_a(len, ...) __calloc_a(len, ##__VA_ARGS__, NULL) ++ ++void *__calloc_a(size_t len, ...); ++ ++#ifndef ARRAY_SIZE ++#define ARRAY_SIZE(arr) (sizeof(arr) / sizeof((arr)[0])) ++#endif ++ ++#define __BUILD_BUG_ON(condition) ((void)sizeof(char[1 - 2*!!(condition)])) ++ ++#ifdef __OPTIMIZE__ ++extern int __BUILD_BUG_ON_CONDITION_FAILED; ++#define BUILD_BUG_ON(condition) \ ++ do { \ ++ __BUILD_BUG_ON(condition); \ ++ if (condition) \ ++ __BUILD_BUG_ON_CONDITION_FAILED = 1; \ ++ } while(0) ++#else ++#define BUILD_BUG_ON __BUILD_BUG_ON ++#endif ++ ++#if defined(__APPLE__) && !defined(CLOCK_MONOTONIC) ++#define LIBUBOX_COMPAT_CLOCK_GETTIME ++ ++#include <mach/clock_types.h> ++#define CLOCK_REALTIME CALENDAR_CLOCK ++#define CLOCK_MONOTONIC SYSTEM_CLOCK ++ ++int clock_gettime(int type, struct timespec *tv); ++ ++#endif ++ ++#ifdef __GNUC__ ++#define _GNUC_MIN_VER(maj, min) (((__GNUC__ << 8) + __GNUC_MINOR__) >= (((maj) << 8) + (min))) ++#else ++#define _GNUC_MIN_VER(maj, min) 0 ++#endif ++ ++#if defined(__linux__) || defined(__CYGWIN__) ++#include <byteswap.h> ++#include <endian.h> ++ ++#elif defined(__APPLE__) ++#include <machine/endian.h> ++#include <machine/byte_order.h> ++#elif defined(__FreeBSD__) ++#include <sys/endian.h> ++#else ++#include <machine/endian.h> ++#endif ++ ++#ifndef __BYTE_ORDER ++#define __BYTE_ORDER BYTE_ORDER ++#endif ++#ifndef __BIG_ENDIAN ++#define __BIG_ENDIAN BIG_ENDIAN ++#endif ++#ifndef __LITTLE_ENDIAN ++#define __LITTLE_ENDIAN LITTLE_ENDIAN ++#endif ++ ++#define __constant_swap16(x) ((uint16_t)( \ ++ (((uint16_t)(x) & (uint16_t)0x00ffU) << 8) | \ ++ (((uint16_t)(x) & (uint16_t)0xff00U) >> 8))) ++ ++#define __constant_swap32(x) ((uint32_t)( \ ++ (((uint32_t)(x) & (uint32_t)0x000000ffUL) << 24) | \ ++ (((uint32_t)(x) & (uint32_t)0x0000ff00UL) << 8) | \ ++ (((uint32_t)(x) & (uint32_t)0x00ff0000UL) >> 8) | \ ++ (((uint32_t)(x) & (uint32_t)0xff000000UL) >> 24))) ++ ++#define __constant_swap64(x) ((uint64_t)( \ ++ (((uint64_t)(x) & (uint64_t)0x00000000000000ffULL) << 56) | \ ++ (((uint64_t)(x) & (uint64_t)0x000000000000ff00ULL) << 40) | \ ++ (((uint64_t)(x) & (uint64_t)0x0000000000ff0000ULL) << 24) | \ ++ (((uint64_t)(x) & (uint64_t)0x00000000ff000000ULL) << 8) | \ ++ (((uint64_t)(x) & (uint64_t)0x000000ff00000000ULL) >> 8) | \ ++ (((uint64_t)(x) & (uint64_t)0x0000ff0000000000ULL) >> 24) | \ ++ (((uint64_t)(x) & (uint64_t)0x00ff000000000000ULL) >> 40) | \ ++ (((uint64_t)(x) & (uint64_t)0xff00000000000000ULL) >> 56))) ++ ++/* ++ * This returns a constant expression while determining if an argument is ++ * a constant expression, most importantly without evaluating the argument. ++ */ ++#define __is_constant(x) \ ++ (sizeof(int) == sizeof(*(1 ? ((void*)((long)(x) * 0l)) : (int*)1))) ++ ++#define __eval_once(func, x) \ ++ ({ __typeof__(x) __x = x; func(__x); }) ++ ++#ifdef __cplusplus ++/* ++ * g++ does not support __builtin_choose_expr, so always use __eval_once. ++ * Unfortunately this means that the byte order functions can't be used ++ * as a constant expression anymore ++ */ ++#define __eval_safe(func, x) __eval_once(func, x) ++#else ++#define __eval_safe(func, x) \ ++ __builtin_choose_expr(__is_constant(x), \ ++ func(x), __eval_once(func, x)) ++#endif ++ ++#if __BYTE_ORDER == __LITTLE_ENDIAN ++ ++#define const_cpu_to_be64(x) __constant_swap64(x) ++#define const_cpu_to_be32(x) __constant_swap32(x) ++#define const_cpu_to_be16(x) __constant_swap16(x) ++ ++#define const_be64_to_cpu(x) __constant_swap64(x) ++#define const_be32_to_cpu(x) __constant_swap32(x) ++#define const_be16_to_cpu(x) __constant_swap16(x) ++ ++#define const_cpu_to_le64(x) (x) ++#define const_cpu_to_le32(x) (x) ++#define const_cpu_to_le16(x) (x) ++ ++#define const_le64_to_cpu(x) (x) ++#define const_le32_to_cpu(x) (x) ++#define const_le16_to_cpu(x) (x) ++ ++#define cpu_to_be64(x) __eval_safe(__constant_swap64, x) ++#define cpu_to_be32(x) __eval_safe(__constant_swap32, x) ++#define cpu_to_be16(x) __eval_safe(__constant_swap16, x) ++ ++#define be64_to_cpu(x) __eval_safe(__constant_swap64, x) ++#define be32_to_cpu(x) __eval_safe(__constant_swap32, x) ++#define be16_to_cpu(x) __eval_safe(__constant_swap16, x) ++ ++#define cpu_to_le64(x) (x) ++#define cpu_to_le32(x) (x) ++#define cpu_to_le16(x) (x) ++ ++#define le64_to_cpu(x) (x) ++#define le32_to_cpu(x) (x) ++#define le16_to_cpu(x) (x) ++ ++#else /* __BYTE_ORDER == __LITTLE_ENDIAN */ ++ ++#define const_cpu_to_le64(x) __constant_swap64(x) ++#define const_cpu_to_le32(x) __constant_swap32(x) ++#define const_cpu_to_le16(x) __constant_swap16(x) ++ ++#define const_le64_to_cpu(x) __constant_swap64(x) ++#define const_le32_to_cpu(x) __constant_swap32(x) ++#define const_le16_to_cpu(x) __constant_swap16(x) ++ ++#define const_cpu_to_be64(x) (x) ++#define const_cpu_to_be32(x) (x) ++#define const_cpu_to_be16(x) (x) ++ ++#define const_be64_to_cpu(x) (x) ++#define const_be32_to_cpu(x) (x) ++#define const_be16_to_cpu(x) (x) ++ ++#define cpu_to_le64(x) __eval_safe(__constant_swap64, x) ++#define cpu_to_le32(x) __eval_safe(__constant_swap32, x) ++#define cpu_to_le16(x) __eval_safe(__constant_swap16, x) ++ ++#define le64_to_cpu(x) __eval_safe(__constant_swap64, x) ++#define le32_to_cpu(x) __eval_safe(__constant_swap32, x) ++#define le16_to_cpu(x) __eval_safe(__constant_swap16, x) ++ ++#define cpu_to_be64(x) (x) ++#define cpu_to_be32(x) (x) ++#define cpu_to_be16(x) (x) ++ ++#define be64_to_cpu(x) (x) ++#define be32_to_cpu(x) (x) ++#define be16_to_cpu(x) (x) ++ ++#endif ++ ++#ifndef __packed ++#define __packed __attribute__((packed)) ++#endif ++ ++#ifndef __constructor ++#define __constructor __attribute__((constructor)) ++#endif ++ ++#ifndef __destructor ++#define __destructor __attribute__((destructor)) ++#endif ++ ++#ifndef __hidden ++#define __hidden __attribute__((visibility("hidden"))) ++#endif ++ ++int b64_encode(const void *src, size_t src_len, ++ void *dest, size_t dest_len); ++ ++int b64_decode(const void *src, void *dest, size_t dest_len); ++ ++#define B64_ENCODE_LEN(_len) ((((_len) + 2) / 3) * 4 + 1) ++#define B64_DECODE_LEN(_len) (((_len) / 4) * 3 + 1) ++ ++static inline unsigned int cbuf_order(unsigned int x) ++{ ++ return 32 - __builtin_clz(x - 1); ++} ++ ++static inline unsigned long cbuf_size(int order) ++{ ++ unsigned long page_size = sysconf(_SC_PAGESIZE); ++ unsigned long ret = 1ULL << order; ++ ++ if (ret < page_size) ++ ret = page_size; ++ ++ return ret; ++} ++ ++void *cbuf_alloc(unsigned int order); ++void cbuf_free(void *ptr, unsigned int order); ++int mkdir_p(char *dir, mode_t mask); ++ ++#endif +-- +2.31.0 + diff --git a/0002-CMakeLists.txt-adjust-to-compile-with-inline-uloop.patch b/0002-CMakeLists.txt-adjust-to-compile-with-inline-uloop.patch new file mode 100644 index 000000000000..4ac084e88660 --- /dev/null +++ b/0002-CMakeLists.txt-adjust-to-compile-with-inline-uloop.patch @@ -0,0 +1,27 @@ +From 3f5dabdc0c5e83077c10aec1f1fa2de0dc93e6d5 Mon Sep 17 00:00:00 2001 +From: Dobroslaw Kijowski <dobo90@gmail.com> +Date: Thu, 25 Mar 2021 22:10:03 +0100 +Subject: [PATCH 2/3] CMakeLists.txt: adjust to compile with inline uloop + +--- + CMakeLists.txt | 4 ++-- + 1 file changed, 2 insertions(+), 2 deletions(-) + +diff --git a/CMakeLists.txt b/CMakeLists.txt +index 7e960ab..450ed01 100644 +--- a/CMakeLists.txt ++++ b/CMakeLists.txt +@@ -8,8 +8,8 @@ IF(APPLE) + LINK_DIRECTORIES(/opt/local/lib) + ENDIF() + +-ADD_EXECUTABLE(relayd main.c dhcp.c route.c) +-TARGET_LINK_LIBRARIES(relayd ubox) ++ADD_EXECUTABLE(relayd main.c dhcp.c route.c uloop.c) ++TARGET_LINK_LIBRARIES(relayd) + + SET(CMAKE_INSTALL_PREFIX /usr) + +-- +2.31.0 + diff --git a/0003-relayd.h-fix-includes.patch b/0003-relayd.h-fix-includes.patch new file mode 100644 index 000000000000..70cd5754a4d7 --- /dev/null +++ b/0003-relayd.h-fix-includes.patch @@ -0,0 +1,28 @@ +From 87702b57d615bc20d4af21f8a5fb183ab33de0e9 Mon Sep 17 00:00:00 2001 +From: Dobroslaw Kijowski <dobo90@gmail.com> +Date: Thu, 25 Mar 2021 22:13:34 +0100 +Subject: [PATCH 3/3] relayd.h: fix includes + +* Change system includes into relative ones. +--- + relayd.h | 4 ++-- + 1 file changed, 2 insertions(+), 2 deletions(-) + +diff --git a/relayd.h b/relayd.h +index d7ad212..c1e85a2 100644 +--- a/relayd.h ++++ b/relayd.h +@@ -31,8 +31,8 @@ + #include <stdint.h> + #include <stdbool.h> + +-#include <libubox/uloop.h> +-#include <libubox/list.h> ++#include "uloop.h" ++#include "list.h" + + #define DEBUG + #ifdef DEBUG +-- +2.31.0 + diff --git a/PKGBUILD b/PKGBUILD new file mode 100644 index 000000000000..bbc30ad63609 --- /dev/null +++ b/PKGBUILD @@ -0,0 +1,55 @@ +# Maintainer: Dobroslaw Kijowski <dobo90_at_gmail.com> + +pkgname=relayd +pkgver=20200425 +pkgrel=1 +pkgdesc="Transparent routing / relay daemon (taken from OpenWrt)" +arch=(x86_64 armv7h) +url="https://git.openwrt.org/project/relayd.git" +license=(GPL) +depends=(glibc) +makedepends=(git) +backup=("etc/conf.d/relayd") +_repo_commit="f4d759be54ceb37714e9a6ca320d5b50c95e9ce9" +source=("relayd::git+https://git.openwrt.org/project/relayd.git#commit=${_repo_commit}" + "0001-libubox-import-list-uloop-utils-.h-uloop-epoll-.c.patch" + "0002-CMakeLists.txt-adjust-to-compile-with-inline-uloop.patch" + "0003-relayd.h-fix-includes.patch" + "relayd.conf" + "relayd.service") +sha256sums=('SKIP' + '3073ac119de2635eeb5affa6c8e46a6328179ffe568302a463f62d5e5b0ac4f5' + 'b002ab6bf4729984c630e3ef57caf2606e2a667cdd2fac1046d16475bd5cb98e' + 'b4fcb393e3567e61999d31734d45314e2cced8620d52146696f982437a978c75' + '58c84f0f6c335e05c281d9f2eeb144839a5e0e2021bac9073872a4634739fd1f' + '91a601ba5080851ecba276ad8ba11bcd1c4ed97715e631fc8e3c58fa86962b62') + +prepare() { + cd "${pkgname}" + + patch -p1 -i "${srcdir}/0001-libubox-import-list-uloop-utils-.h-uloop-epoll-.c.patch" + patch -p1 -i "${srcdir}/0002-CMakeLists.txt-adjust-to-compile-with-inline-uloop.patch" + patch -p1 -i "${srcdir}/0003-relayd.h-fix-includes.patch" +} + +build() { + cd "${pkgname}" + + CFLAGS="${CFLAGS} -Wno-unused-result" + + cmake -B build \ + -DCMAKE_BUILD_TYPE=Release \ + -DCMAKE_INSTALL_PREFIX=/usr + + make -C build +} + +package() { + cd "${pkgname}" + + make -C build DESTDIR="${pkgdir}" install + mv "${pkgdir}/usr/sbin" "${pkgdir}/usr/bin" + + install -Dm644 "${srcdir}/relayd.conf" "${pkgdir}/etc/conf.d/relayd" + install -Dm644 "${srcdir}/relayd.service" "${pkgdir}/usr/lib/systemd/system/relayd.service" +} diff --git a/relayd.conf b/relayd.conf new file mode 100644 index 000000000000..ef684a846b34 --- /dev/null +++ b/relayd.conf @@ -0,0 +1 @@ +ARGS=-I eth0 -I wlan0 -B -D diff --git a/relayd.service b/relayd.service new file mode 100644 index 000000000000..c16e54511d3d --- /dev/null +++ b/relayd.service @@ -0,0 +1,12 @@ +[Unit] +Description=relayd +After=network-online.target +Wants=network-online.target + +[Service] +EnvironmentFile=/etc/conf.d/relayd +ExecStart=/usr/bin/relayd $ARGS +Restart=always + +[Install] +WantedBy=multi-user.target |