44 const char *protocol,
int flags)
47#ifdef ENABLE_MANAGEMENT
49 const char *payload_msg = NULL;
62 payload_msg =
CBSTR(buf);
75 mda->
cid, mda_key_id, protocol,
fragment, payload_msg);
85 msg(
D_PUSH,
"Received custom app control message (protocol '%s'%s)",
86 protocol,
fragment ?
", fragment" :
"");
95 for (
const char *flag =
flags; *flag !=
'\0'; flag++)
101 else if (*flag ==
'6')
105 else if (*flag ==
'F')
111 *err_reason =
"Unknown flag in flags";
120 if (base64enc + asciienc != 1)
123 snprintf(tmp, 512,
"number of encodings must be exactly one "
124 "(B64=%d, ASCII=%d)",
125 base64enc, asciienc);
145 *err_reason =
"could not extract flags field";
155 const char *err_reason =
"";
163 err_reason =
"ACC not enabled or no negotiated protocols";
169 err_reason =
"missing , after ACC";
177 err_reason =
"could not extract protocol field";
184 buf_printf(&msg_buf,
"protocol '%s' not in list of negotiated protocols '%s'",
203 err_reason =
"could not extract payload length field";
216 if (
buf_len(&buf) != payload_len + 1)
219 snprintf(tmp, 512,
"field length %d, payload length %d mismatch",
220 payload_len,
buf_len(&buf) - 1);
231 msg(
D_PUSH_ERRORS,
"WARNING: Received malformed custom app control channel "
243 const char *protocol,
bool fragment,
244 const char *acc_msg_payload,
bool base64)
251 const size_t max_header_size = strlen(
"ACC,") + strlen(protocol) + 1 + 4 + 1 + 2 + 1;
252 size_t len = max_header_size + strlen(acc_msg_payload);
262 msg(
M_CLIENT,
"header (%zu) + message size (%zu) length (%zu) exceeds "
263 "maximum allowed length negotiated with peer (%d)",
264 max_header_size, strlen(acc_msg_payload),
len,
274 buf_printf(&buf,
"ACC,%s,%zu,%s%s,%s", protocol,
275 strlen(acc_msg_payload),
294 char *tmp_message_orig = tmp_message;
297 const char *token =
strtok_r(tmp_message, delim, &lasts);
301 const char *protocols = NULL;
317 msg(
D_PUSH_ERRORS,
"App custom control encoding must include base64 and ascii");
321 if (p == 1 && !server && strcmp(token,
"A:6") && strcmp(token,
"6:A"))
323 msg(
D_PUSH_ERRORS,
"App custom control encoding must be exactly base64 and ascii");
338 token =
strtok_r(NULL, delim, &lasts);
346 free(tmp_message_orig);
355 const char *token =
strtok_r(tmp,
":", &lasts);
358 size_t max_len =
min_size(strlen(list1), strlen(list2));
369 if (
buf_len(&common_protocols) > 0)
375 token =
strtok_r(NULL,
":", &lasts);
378 return common_protocols;
399 const char *peer_info = multi->
peer_info;
413 msg(
D_PUSH_ERRORS,
"WARNING: IV_ACC peer info variable of peer is malformed");
419 if (
buf_len(&common_protocols) == 0)
438#ifdef ENABLE_MANAGEMENT
441 msg(
M_CLIENT,
">ACC_PROTOCOLS:protocols=%s,message_len=%d",
bool send_acc_message(struct context *c, struct tls_multi *multi, struct tls_session *session, const char *protocol, bool fragment, const char *acc_msg_payload, bool base64)
void receive_acc_message(struct context *c, const struct buffer *buffer)
This method parses an app custom control message and delivers it to the management interface.
char * parse_acc_parameters(const char *capabilities, const char *delim, int *max_acc_len, bool server, struct gc_arena *gc)
Parses an info message from the server that contains app custom control info information prior to the...
static int parse_acc_message_flags_buf(struct buffer *buf, const char **err_reason, struct gc_arena *gc)
Wrapper around parse_acc_message_flags to also include the step of extracting the flags from the buff...
void determine_common_acc_protocols(struct tls_multi *multi, struct tls_session *session)
Parses the IV_ACC of the peer and sets multi.acc_negotiated_protocols to the common protocols of serv...
struct buffer get_list_intersection(struct gc_arena *gc, const char *list1, const char *list2)
Calculates the intersection of two list that are both separated by : Items in the result will have th...
int parse_acc_message_flags(const char *flags, const char **err_reason, struct gc_arena *gc)
Parses the flags field of an app control message If there is an error parsing the flags field the met...
static void log_acc_message(struct context *c, const struct buffer *buf, int payload_len, const char *protocol, int flags)
void notify_client_acc_protocols(struct tls_multi *multi)
Notifies a client via management interface of the negotiated app custom protocols.
@ ACC_MESSAGE_FLAGS_FRAGMENT
@ ACC_MESSAGE_FLAGS_BASE64
@ ACC_MESSAGE_FLAGS_ASCII
bool buf_printf(struct buffer *buf, const char *format,...)
printf-style append to a buffer with overflow check.
char * buf_extract_field(struct buffer *buf, char sep, struct gc_arena *gc)
Extract a field from buf that ends with the sep character.
void * gc_malloc(size_t size, bool clear, struct gc_arena *a)
Allocate memory and, optionally, zero it.
struct buffer alloc_buf_gc(size_t size, struct gc_arena *gc)
Allocate a buffer of the given size under garbage collection.
void gc_addspecial(void *addr, void(*free_function)(void *), struct gc_arena *a)
Register an address with a custom free function in a garbage collection arena.
char * string_alloc(const char *str, struct gc_arena *gc)
Duplicate a string, allocating memory under garbage collection.
Buffer management functions and garbage collection.
#define BSTR(buf)
Return the buffer content pointer cast to char *.
static const char * buf_cstr(const struct buffer *buf)
Return the buffer content pointer cast to const char *.
static int buf_len(const struct buffer *buf)
Return the length of the buffer content.
#define CBPTR(buf)
Return a const pointer to the start of the buffer content.
static bool buf_advance(struct buffer *buf, ssize_t size)
Advance the content start of a buffer, consuming bytes from the front.
static bool buf_write_u8(struct buffer *dest, uint8_t data)
Append a uint8_t to a buffer.
static int buf_read_u8(struct buffer *buf)
Read and consume a uint8_t from the front of a buffer.
#define BLEN(buf)
Return the length of the buffer content in bytes.
static char * format_hex(const uint8_t *data, size_t size, size_t maxoutput, struct gc_arena *gc)
Format a binary buffer as a hex string with spaces every 4 bytes.
static void gc_free(struct gc_arena *a)
Free all allocations in a garbage collection arena.
#define CBSTR(buf)
Return the buffer content pointer cast to const char *.
static struct gc_arena gc_new(void)
Allocate and return a new, empty garbage collection arena.
static char * buf_str(struct buffer *buf)
Return the buffer content pointer cast to char *.
#define TLS_CHANNEL_BUF_SIZE
char * strtok_r(char *s, const char *delim, char **last)
void setenv_int(struct env_set *es, const char *name, int value)
void setenv_str(struct env_set *es, const char *name, const char *value)
void reschedule_multi_process(struct context *c)
Reschedule tls_multi_process.
bool send_control_channel_string_dowork(struct tls_session *session, const char *str, msglvl_t msglevel)
Interface functions to the internal and external multiplexers.
#define TM_ACTIVE
Active tls_session.
static size_t min_size(size_t x, size_t y)
static int min_int(int x, int y)
Header file for server-mode related structures and functions.
bool atoi_constrained(const char *str, int *value, const char *name, int min, int max, msglvl_t msglevel)
Converts a str to an integer if the string can be represented as an integer number and is between min...
int openvpn_base64_encode(const void *data, int size, char **str)
static const struct key_state * get_primary_key(const struct tls_multi *multi)
gets an item of key_state objects in the order they should be scanned by data channel modules.
bool tls_item_in_cipher_list(const char *item, const char *list)
Return true iff item is present in the colon-separated zero-terminated cipher list.
Control Channel SSL/Data dynamic negotiation Module This file is split from ssl.h to be able to unit ...
char * extract_var_peer_info(const char *peer_info, const char *var, struct gc_arena *gc)
Extracts a variable from peer info, the returned string will be allocated using the supplied gc_arena...
Wrapper structure for dynamically allocated memory.
int len
Length in bytes of the actual content within the allocated memory.
struct tls_multi * tls_multi
TLS state structure for this VPN tunnel.
Contains all state information for one tunnel.
struct context_2 c2
Level 2 context.
struct options options
Options loaded from command line or configuration file.
Structure for reassembling one incoming fragmented packet.
Garbage collection arena used to keep track of dynamically allocated memory.
Security parameter state for a single VPN tunnel.
char * peer_info
A multi-line string of general-purpose info received from peer over control channel.
int acc_max_message_length
the maximum length of an ACC control channel message
struct tls_session session[TM_SIZE]
Array of tls_session objects representing control channel sessions with the remote peer.
char * acc_negotiated_protocols
the protocols that are negotiated with the peer.
const char * acc_protocols
The app custom control protocols we should announce as supported.
Security parameter state of a single session within a VPN tunnel.