Commit | Line | Data |
---|---|---|
c215a4bc IJ |
1 | /* |
2 | * This file is part of secnet. | |
3 | * See README for full list of copyright holders. | |
4 | * | |
5 | * secnet is free software; you can redistribute it and/or modify it | |
6 | * under the terms of the GNU General Public License as published by | |
7 | * the Free Software Foundation; either version d of the License, or | |
8 | * (at your option) any later version. | |
9 | * | |
10 | * secnet is distributed in the hope that it will be useful, but | |
11 | * WITHOUT ANY WARRANTY; without even the implied warranty of | |
12 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU | |
13 | * General Public License for more details. | |
14 | * | |
15 | * You should have received a copy of the GNU General Public License | |
16 | * version 3 along with secnet; if not, see | |
17 | * https://www.gnu.org/licenses/gpl.html. | |
18 | */ | |
54d5ef00 IJ |
19 | |
20 | #ifndef COMM_COMMON_H | |
21 | #define COMM_COMMON_H | |
22 | ||
23 | #include "secnet.h" | |
2d7478f7 | 24 | #include "util.h" |
54d5ef00 | 25 | |
763e458f IJ |
26 | /*----- for all comms -----*/ |
27 | ||
54d5ef00 IJ |
28 | struct comm_notify_entry { |
29 | comm_notify_fn *fn; | |
30 | void *state; | |
31 | LIST_ENTRY(comm_notify_entry) entry; | |
32 | }; | |
33 | LIST_HEAD(comm_notify_list, comm_notify_entry) notify; | |
34 | ||
35 | struct commcommon { /* must be first so that void* is comm_common* */ | |
36 | closure_t cl; | |
37 | struct comm_if ops; | |
38 | struct cloc loc; | |
39 | struct comm_notify_list notify; | |
40 | struct buffer_if *rbuf; | |
41 | }; | |
42 | ||
43 | void comm_request_notify(void *commst, void *nst, comm_notify_fn *fn); | |
44 | void comm_release_notify(void *commst, void *nst, comm_notify_fn *fn); | |
45 | ||
46 | bool_t comm_notify(struct comm_notify_list *notify, struct buffer_if *buf, | |
47 | const struct comm_addr *ca); | |
48 | /* Either: returns True, with message delivered and buffer freed. | |
49 | * Or: False, if no-one wanted it - buffer still allocd'd. | |
50 | * Ie, like comm_notify_fn. */ | |
51 | ||
52 | void comm_apply(struct commcommon *cc, void *st); | |
53 | ||
54 | #define COMM_APPLY(st,cc,prefix,desc,loc) \ | |
952f601f | 55 | NEW(st); \ |
54d5ef00 IJ |
56 | (cc)->loc=loc; \ |
57 | (cc)->cl.description=desc; \ | |
58 | (cc)->ops.sendmsg=prefix##sendmsg; \ | |
59 | (cc)->ops.addr_to_string=prefix##addr_to_string; \ | |
60 | comm_apply((cc),(st)) | |
61 | /* void COMM_APPLY(SOMETHING *st, struct commcommon *FUNCTIONOF(st), | |
62 | * prefix, "DESC", struct cloc loc); | |
63 | * // Expects in scope: prefix##sendmsg, prefix##addr_to_string. | |
64 | */ | |
65 | ||
66 | #define COMM_APPLY_STANDARD(st,cc,desc,args) \ | |
67 | item_t *item=list_elem(args,0); \ | |
68 | if (!item || item->type!=t_dict) { \ | |
69 | cfgfatal((cc)->loc,desc,"first argument must be a dictionary\n"); \ | |
70 | } \ | |
71 | dict_t *d=item->data.dict; \ | |
72 | (cc)->rbuf=find_cl_if(d,"buffer",CL_BUFFER,True,desc,(cc)->loc) | |
73 | /* void COMM_APPLY_STANDARD(SOMETHING *st, struct commcommon *cc, | |
74 | * const char *desc, list_t *args); | |
75 | * // Declares: | |
76 | * // item_t *item = <undefined>; | |
77 | * // dict_t *dict = <construction dictionary argument>; | |
78 | */ | |
79 | ||
763e458f IJ |
80 | /*----- for udp-based comms -----*/ |
81 | ||
82 | #define UDP_MAX_SOCKETS 3 /* 2 ought to do really */ | |
83 | ||
2d7478f7 IJ |
84 | #define MAX_AF MAX_RAW(AF_INET6,AF_INET) |
85 | ||
763e458f IJ |
86 | struct udpsock { |
87 | union iaddr addr; | |
88 | int fd; | |
2d7478f7 | 89 | bool_t experienced[/*0=recv,1=send*/2][MAX_AF+1][/*success?*/2]; |
763e458f IJ |
90 | }; |
91 | ||
92 | struct udpsocks { | |
93 | int n_socks; | |
94 | struct udpsock socks[UDP_MAX_SOCKETS]; | |
f7af3192 IJ |
95 | /* private for udp_socks_* */ |
96 | struct udpcommon *uc; /* link to parent, for cfg, notify list, etc. */ | |
5c679ae0 | 97 | struct poll_interest *interest; |
c72d679d | 98 | const char *desc; |
763e458f IJ |
99 | }; |
100 | ||
101 | struct udpcommon { | |
102 | struct commcommon cc; | |
103 | int port; | |
104 | string_t authbind; | |
105 | bool_t use_proxy; | |
106 | union iaddr proxy; | |
107 | }; | |
108 | ||
53f4e666 IJ |
109 | bool_t udp_make_socket(struct udpcommon *uc, struct udpsock *us, |
110 | int failmsgclass); | |
9c44ef13 IJ |
111 | /* Caller should have filled in ->addr. Fills in us->fd, |
112 | ->experienced; updates ->addr. Logs any errors with lg_[v]perror. */ | |
113 | bool_t udp_import_socket(struct udpcommon *uc, struct udpsock *us, | |
114 | int failmsgclass, int fd); | |
115 | /* Like udp_make_socket, but caller provides fd. fd is not closed | |
116 | on error */ | |
53f4e666 | 117 | |
5f8b7a8e IJ |
118 | void udp_destroy_socket(struct udpcommon *uc, struct udpsock *us); |
119 | /* Idempotent. No errors are possible. */ | |
120 | ||
2d7478f7 IJ |
121 | const char *af_name(int af); |
122 | void udp_sock_experienced(struct log_if *lg, struct udpcommon *uc, | |
c72d679d | 123 | struct udpsocks *socks, struct udpsock *us, |
6c5889e6 | 124 | const union iaddr *dest, int af /* 0 means any */, |
2d7478f7 IJ |
125 | int r, int errnoval); |
126 | ||
c72d679d IJ |
127 | void udp_socks_register(struct udpcommon *uc, struct udpsocks *socks, |
128 | const char *desc); | |
5c679ae0 | 129 | void udp_socks_deregister(struct udpcommon *uc, struct udpsocks *socks); |
32654a31 | 130 | void udp_socks_childpersist(struct udpcommon *uc, struct udpsocks *socks); |
763e458f IJ |
131 | |
132 | #define UDP_APPLY_STANDARD(st,uc,desc) \ | |
133 | (uc)->use_proxy=False; \ | |
134 | (uc)->authbind=dict_read_string(d,"authbind",False,"udp",(uc)->cc.loc); \ | |
9c44ef13 | 135 | (uc)->port=dict_read_number(d,"port",False,"udp",(uc)->cc.loc,0) |
763e458f IJ |
136 | /* void UDP_APPLY_STANDARD(SOMETHING *st, struct udpcommon *uc, |
137 | * const char *desc); | |
138 | * // Expects in scope: dict_t *d=...; as from COMM_APPLY_STANDARD | |
139 | */ | |
140 | ||
54d5ef00 | 141 | #endif /*COMM_COMMON_H*/ |