1/*
2 *  OpenVPN -- An application to securely tunnel IP networks
3 *             over a single TCP/UDP port, with support for SSL/TLS-based
4 *             session authentication and key exchange,
5 *             packet encryption, packet authentication, and
6 *             packet compression.
7 *
8 *  Copyright (C) 2002-2010 OpenVPN Technologies, Inc. <sales@openvpn.net>
9 *
10 *  This program is free software; you can redistribute it and/or modify
11 *  it under the terms of the GNU General Public License version 2
12 *  as published by the Free Software Foundation.
13 *
14 *  This program is distributed in the hope that it will be useful,
15 *  but WITHOUT ANY WARRANTY; without even the implied warranty of
16 *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
17 *  GNU General Public License for more details.
18 *
19 *  You should have received a copy of the GNU General Public License
20 *  along with this program (see the file COPYING included with this
21 *  distribution); if not, write to the Free Software Foundation, Inc.,
22 *  59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
23 */
24
25#ifdef HAVE_CONFIG_H
26#include "config.h"
27#elif defined(_MSC_VER)
28#include "config-msvc.h"
29#endif
30
31#include "syshead.h"
32
33#ifdef ENABLE_MANAGEMENT
34
35#include "error.h"
36#include "fdmisc.h"
37#include "options.h"
38#include "sig.h"
39#include "event.h"
40#include "otime.h"
41#include "integer.h"
42#include "misc.h"
43#include "ssl.h"
44#include "common.h"
45#include "manage.h"
46
47#include "memdbg.h"
48
49#ifdef ENABLE_PKCS11
50#include "pkcs11.h"
51#endif
52
53#define MANAGEMENT_ECHO_PULL_INFO 0
54
55#if MANAGEMENT_ECHO_PULL_INFO
56#define MANAGEMENT_ECHO_FLAGS LOG_PRINT_INTVAL
57#else
58#define MANAGEMENT_ECHO_FLAGS 0
59#endif
60
61/* tag for blank username/password */
62static const char blank_up[] = "[[BLANK]]";
63
64struct management *management; /* GLOBAL */
65
66/* static forward declarations */
67static void man_output_standalone (struct management *man, volatile int *signal_received);
68static void man_reset_client_socket (struct management *man, const bool exiting);
69
70static void
71man_help ()
72{
73  msg (M_CLIENT, "Management Interface for %s", title_string);
74  msg (M_CLIENT, "Commands:");
75  msg (M_CLIENT, "auth-retry t           : Auth failure retry mode (none,interact,nointeract).");
76  msg (M_CLIENT, "bytecount n            : Show bytes in/out, update every n secs (0=off).");
77  msg (M_CLIENT, "echo [on|off] [N|all]  : Like log, but only show messages in echo buffer.");
78  msg (M_CLIENT, "exit|quit              : Close management session.");
79  msg (M_CLIENT, "forget-passwords       : Forget passwords entered so far.");
80  msg (M_CLIENT, "help                   : Print this message.");
81  msg (M_CLIENT, "hold [on|off|release]  : Set/show hold flag to on/off state, or");
82  msg (M_CLIENT, "                         release current hold and start tunnel.");
83  msg (M_CLIENT, "kill cn                : Kill the client instance(s) having common name cn.");
84  msg (M_CLIENT, "kill IP:port           : Kill the client instance connecting from IP:port.");
85  msg (M_CLIENT, "load-stats             : Show global server load stats.");
86  msg (M_CLIENT, "log [on|off] [N|all]   : Turn on/off realtime log display");
87  msg (M_CLIENT, "                         + show last N lines or 'all' for entire history.");
88  msg (M_CLIENT, "mute [n]               : Set log mute level to n, or show level if n is absent.");
89  msg (M_CLIENT, "needok type action     : Enter confirmation for NEED-OK request of 'type',");
90  msg (M_CLIENT, "                         where action = 'ok' or 'cancel'.");
91  msg (M_CLIENT, "needstr type action    : Enter confirmation for NEED-STR request of 'type',");
92  msg (M_CLIENT, "                         where action is reply string.");
93  msg (M_CLIENT, "net                    : (Windows only) Show network info and routing table.");
94  msg (M_CLIENT, "password type p        : Enter password p for a queried OpenVPN password.");
95  msg (M_CLIENT, "remote type [host port] : Override remote directive, type=ACCEPT|MOD|SKIP.");
96  msg (M_CLIENT, "proxy type [host port flags] : Enter dynamic proxy server info.");
97  msg (M_CLIENT, "pid                    : Show process ID of the current OpenVPN process.");
98#ifdef ENABLE_PKCS11
99  msg (M_CLIENT, "pkcs11-id-count        : Get number of available PKCS#11 identities.");
100  msg (M_CLIENT, "pkcs11-id-get index    : Get PKCS#11 identity at index.");
101#endif
102#ifdef MANAGEMENT_DEF_AUTH
103  msg (M_CLIENT, "client-auth CID KID    : Authenticate client-id/key-id CID/KID (MULTILINE)");
104  msg (M_CLIENT, "client-auth-nt CID KID : Authenticate client-id/key-id CID/KID");
105  msg (M_CLIENT, "client-deny CID KID R [CR] : Deny auth client-id/key-id CID/KID with log reason");
106  msg (M_CLIENT, "                             text R and optional client reason text CR");
107  msg (M_CLIENT, "client-kill CID [M]    : Kill client instance CID with message M (def=RESTART)");
108  msg (M_CLIENT, "env-filter [level]     : Set env-var filter level");
109#ifdef MANAGEMENT_PF
110  msg (M_CLIENT, "client-pf CID          : Define packet filter for client CID (MULTILINE)");
111#endif
112#endif
113#ifdef MANAGMENT_EXTERNAL_KEY
114  msg (M_CLIENT, "rsa-sig                : Enter an RSA signature in response to >RSA_SIGN challenge");
115  msg (M_CLIENT, "                         Enter signature base64 on subsequent lines followed by END");
116#endif
117  msg (M_CLIENT, "signal s               : Send signal s to daemon,");
118  msg (M_CLIENT, "                         s = SIGHUP|SIGTERM|SIGUSR1|SIGUSR2.");
119  msg (M_CLIENT, "state [on|off] [N|all] : Like log, but show state history.");
120  msg (M_CLIENT, "status [n]             : Show current daemon status info using format #n.");
121  msg (M_CLIENT, "test n                 : Produce n lines of output for testing/debugging.");
122  msg (M_CLIENT, "username type u        : Enter username u for a queried OpenVPN username.");
123  msg (M_CLIENT, "verb [n]               : Set log verbosity level to n, or show if n is absent.");
124  msg (M_CLIENT, "version                : Show current version number.");
125  msg (M_CLIENT, "END");
126}
127
128static const char *
129man_state_name (const int state)
130{
131  switch (state)
132    {
133    case OPENVPN_STATE_INITIAL:
134      return "INITIAL";
135    case OPENVPN_STATE_CONNECTING:
136      return "CONNECTING";
137    case OPENVPN_STATE_WAIT:
138      return "WAIT";
139    case OPENVPN_STATE_AUTH:
140      return "AUTH";
141    case OPENVPN_STATE_GET_CONFIG:
142      return "GET_CONFIG";
143    case OPENVPN_STATE_ASSIGN_IP:
144      return "ASSIGN_IP";
145    case OPENVPN_STATE_ADD_ROUTES:
146      return "ADD_ROUTES";
147    case OPENVPN_STATE_CONNECTED:
148      return "CONNECTED";
149    case OPENVPN_STATE_RECONNECTING:
150      return "RECONNECTING";
151    case OPENVPN_STATE_EXITING:
152      return "EXITING";
153    case OPENVPN_STATE_RESOLVE:
154      return "RESOLVE";
155    case OPENVPN_STATE_TCP_CONNECT:
156      return "TCP_CONNECT";
157    default:
158      return "?";
159    }
160}
161
162static void
163man_welcome (struct management *man)
164{
165  msg (M_CLIENT, ">INFO:OpenVPN Management Interface Version %d -- type 'help' for more info",
166       MANAGEMENT_VERSION);
167  if (man->persist.special_state_msg)
168    msg (M_CLIENT, "%s", man->persist.special_state_msg);
169}
170
171static inline bool
172man_password_needed (struct management *man)
173{
174  return man->settings.up.defined && !man->connection.password_verified;
175}
176
177static void
178man_check_password (struct management *man, const char *line)
179{
180  if (man_password_needed (man))
181    {
182      if (streq (line, man->settings.up.password))
183	{
184	  man->connection.password_verified = true;
185	  msg (M_CLIENT, "SUCCESS: password is correct");
186	  man_welcome (man);
187	}
188      else
189	{
190	  man->connection.password_verified = false;
191	  msg (M_CLIENT, "ERROR: bad password");
192	  if (++man->connection.password_tries >= MANAGEMENT_N_PASSWORD_RETRIES)
193	    {
194	      msg (M_WARN, "MAN: client connection rejected after %d failed password attempts",
195		   MANAGEMENT_N_PASSWORD_RETRIES);
196	      man->connection.halt = true;
197	    }
198	}
199    }
200}
201
202static void
203man_update_io_state (struct management *man)
204{
205  if (socket_defined (man->connection.sd_cli))
206    {
207      if (buffer_list_defined (man->connection.out))
208	{
209	  man->connection.state = MS_CC_WAIT_WRITE;
210	}
211      else
212	{
213	  man->connection.state = MS_CC_WAIT_READ;
214	}
215    }
216}
217
218static void
219man_output_list_push_finalize (struct management *man)
220{
221  if (management_connected (man))
222    {
223      man_update_io_state (man);
224      if (!man->persist.standalone_disabled)
225	{
226	  volatile int signal_received = 0;
227	  man_output_standalone (man, &signal_received);
228	}
229    }
230}
231
232static void
233man_output_list_push_str (struct management *man, const char *str)
234{
235  if (management_connected (man) && str)
236    {
237      buffer_list_push (man->connection.out, (const unsigned char *) str);
238    }
239}
240
241static void
242man_output_list_push (struct management *man, const char *str)
243{
244  man_output_list_push_str (man, str);
245  man_output_list_push_finalize (man);
246}
247
248static void
249man_prompt (struct management *man)
250{
251  if (man_password_needed (man))
252    man_output_list_push (man, "ENTER PASSWORD:");
253#if 0 /* should we use prompt? */
254  else
255    man_output_list_push (man, ">");
256#endif
257}
258
259static void
260man_delete_unix_socket (struct management *man)
261{
262#if UNIX_SOCK_SUPPORT
263  if ((man->settings.flags & (MF_UNIX_SOCK|MF_CONNECT_AS_CLIENT)) == MF_UNIX_SOCK)
264    socket_delete_unix (&man->settings.local_unix);
265#endif
266}
267
268static void
269man_close_socket (struct management *man, const socket_descriptor_t sd)
270{
271#ifndef WIN32
272  /*
273   * Windows doesn't need this because the ne32 event is permanently
274   * enabled at struct management scope.
275   */
276  if (man->persist.callback.delete_event)
277    (*man->persist.callback.delete_event) (man->persist.callback.arg, sd);
278#endif
279  openvpn_close_socket (sd);
280}
281
282static void
283virtual_output_callback_func (void *arg, const unsigned int flags, const char *str)
284{
285  struct management *man = (struct management *) arg;
286  static int recursive_level = 0; /* GLOBAL */
287
288# define AF_DID_PUSH  (1<<0)
289# define AF_DID_RESET (1<<1)
290
291  if (!recursive_level) /* don't allow recursion */
292    {
293      struct gc_arena gc = gc_new ();
294      struct log_entry e;
295      const char *out = NULL;
296      unsigned int action_flags = 0;
297
298      ++recursive_level;
299
300      CLEAR (e);
301      update_time ();
302      e.timestamp = now;
303      e.u.msg_flags = flags;
304      e.string = str;
305
306      if (flags & M_FATAL)
307	man->persist.standalone_disabled = false;
308
309      if (flags != M_CLIENT)
310	log_history_add (man->persist.log, &e);
311
312      if (!man_password_needed (man))
313	{
314	  if (flags == M_CLIENT)
315	    out = log_entry_print (&e, LOG_PRINT_CRLF, &gc);
316	  else if (man->connection.log_realtime)
317	    out = log_entry_print (&e, LOG_PRINT_INT_DATE
318				   |   LOG_PRINT_MSG_FLAGS
319				   |   LOG_PRINT_LOG_PREFIX
320				   |   LOG_PRINT_CRLF, &gc);
321	  if (out)
322	    {
323	      man_output_list_push_str (man, out);
324	      action_flags |= AF_DID_PUSH;
325	    }
326	  if (flags & M_FATAL)
327	    {
328	      out = log_entry_print (&e, LOG_FATAL_NOTIFY|LOG_PRINT_CRLF, &gc);
329	      if (out)
330		{
331		  man_output_list_push_str (man, out);
332		  action_flags |= (AF_DID_PUSH|AF_DID_RESET);
333		}
334	    }
335	}
336
337      gc_free (&gc);
338
339      if (action_flags & AF_DID_PUSH)
340        man_output_list_push_finalize (man);
341      if (action_flags & AF_DID_RESET)
342        man_reset_client_socket (man, true);
343
344      --recursive_level;
345    }
346}
347
348/*
349 * Given a signal, return the signal with possible remapping applied,
350 * or -1 if the signal should be ignored.
351 */
352static int
353man_mod_signal (const struct management *man, const int signum)
354{
355  const unsigned int flags = man->settings.mansig;
356  int s = signum;
357  if (s == SIGUSR1)
358    {
359      if (flags & MANSIG_MAP_USR1_TO_HUP)
360	s = SIGHUP;
361      if (flags & MANSIG_MAP_USR1_TO_TERM)
362	s = SIGTERM;
363    }
364  if (flags & MANSIG_IGNORE_USR1_HUP)
365    {
366      if (s == SIGHUP || s == SIGUSR1)
367	s = -1;
368    }
369  return s;
370}
371
372static void
373man_signal (struct management *man, const char *name)
374{
375  const int sig = parse_signal (name);
376  if (sig >= 0)
377    {
378      const int sig_mod = man_mod_signal (man, sig);
379      if (sig_mod >= 0)
380	{
381	  throw_signal (sig_mod);
382	  msg (M_CLIENT, "SUCCESS: signal %s thrown", signal_name (sig_mod, true));
383	}
384      else
385	{
386	  if (man->persist.special_state_msg)
387	    msg (M_CLIENT, "%s", man->persist.special_state_msg);
388	  else
389	    msg (M_CLIENT, "ERROR: signal '%s' is currently ignored", name);
390	}
391    }
392  else
393    {
394      msg (M_CLIENT, "ERROR: signal '%s' is not a known signal type", name);
395    }
396}
397
398static void
399man_status (struct management *man, const int version, struct status_output *so)
400{
401  if (man->persist.callback.status)
402    {
403      (*man->persist.callback.status) (man->persist.callback.arg, version, so);
404    }
405  else
406    {
407      msg (M_CLIENT, "ERROR: The 'status' command is not supported by the current daemon mode");
408    }
409}
410
411static void
412man_bytecount (struct management *man, const int update_seconds)
413{
414  if (update_seconds >= 0)
415    man->connection.bytecount_update_seconds = update_seconds;
416  else
417    man->connection.bytecount_update_seconds = 0;
418  msg (M_CLIENT, "SUCCESS: bytecount interval changed");
419}
420
421void
422man_bytecount_output_client (struct management *man)
423{
424  char in[32];
425  char out[32];
426  /* do in a roundabout way to work around possible mingw or mingw-glibc bug */
427  openvpn_snprintf (in, sizeof (in), counter_format, man->persist.bytes_in);
428  openvpn_snprintf (out, sizeof (out), counter_format, man->persist.bytes_out);
429  msg (M_CLIENT, ">BYTECOUNT:%s,%s", in, out);
430  man->connection.bytecount_last_update = now;
431}
432
433#ifdef MANAGEMENT_DEF_AUTH
434
435void
436man_bytecount_output_server (struct management *man,
437			     const counter_type *bytes_in_total,
438			     const counter_type *bytes_out_total,
439			     struct man_def_auth_context *mdac)
440{
441  char in[32];
442  char out[32];
443  /* do in a roundabout way to work around possible mingw or mingw-glibc bug */
444  openvpn_snprintf (in, sizeof (in), counter_format, *bytes_in_total);
445  openvpn_snprintf (out, sizeof (out), counter_format, *bytes_out_total);
446  msg (M_CLIENT, ">BYTECOUNT_CLI:%lu,%s,%s", mdac->cid, in, out);
447  mdac->bytecount_last_update = now;
448}
449
450#endif
451
452static void
453man_kill (struct management *man, const char *victim)
454{
455  struct gc_arena gc = gc_new ();
456
457  if (man->persist.callback.kill_by_cn && man->persist.callback.kill_by_addr)
458    {
459      struct buffer buf;
460      char p1[128];
461      char p2[128];
462      int n_killed;
463
464      buf_set_read (&buf, (uint8_t*) victim, strlen (victim) + 1);
465      buf_parse (&buf, ':', p1, sizeof (p1));
466      buf_parse (&buf, ':', p2, sizeof (p2));
467
468      if (strlen (p1) && strlen (p2))
469	{
470	  /* IP:port specified */
471	  bool status;
472	  const in_addr_t addr = getaddr (GETADDR_HOST_ORDER|GETADDR_MSG_VIRT_OUT, p1, 0, &status, NULL);
473	  if (status)
474	    {
475	      const int port = atoi (p2);
476	      if (port > 0 && port < 65536)
477		{
478		  n_killed = (*man->persist.callback.kill_by_addr) (man->persist.callback.arg, addr, port);
479		  if (n_killed > 0)
480		    {
481		      msg (M_CLIENT, "SUCCESS: %d client(s) at address %s:%d killed",
482			   n_killed,
483			   print_in_addr_t (addr, 0, &gc),
484			   port);
485		    }
486		  else
487		    {
488		      msg (M_CLIENT, "ERROR: client at address %s:%d not found",
489			   print_in_addr_t (addr, 0, &gc),
490			   port);
491		    }
492		}
493	      else
494		{
495		  msg (M_CLIENT, "ERROR: port number is out of range: %s", p2);
496		}
497	    }
498	  else
499	    {
500	      msg (M_CLIENT, "ERROR: error parsing IP address: %s", p1);
501	    }
502	}
503      else if (strlen (p1))
504	{
505	  /* common name specified */
506	  n_killed = (*man->persist.callback.kill_by_cn) (man->persist.callback.arg, p1);
507	  if (n_killed > 0)
508	    {
509	      msg (M_CLIENT, "SUCCESS: common name '%s' found, %d client(s) killed", p1, n_killed);
510	    }
511	  else
512	    {
513	      msg (M_CLIENT, "ERROR: common name '%s' not found", p1);
514	    }
515	}
516      else
517	{
518	  msg (M_CLIENT, "ERROR: kill parse");
519	}
520    }
521  else
522    {
523      msg (M_CLIENT, "ERROR: The 'kill' command is not supported by the current daemon mode");
524    }
525
526  gc_free (&gc);
527}
528
529/*
530 * General-purpose history command handler
531 * for the log and echo commands.
532 */
533static void
534man_history (struct management *man,
535	     const char *parm,
536	     const char *type,
537	     struct log_history *log,
538	     bool *realtime,
539	     const unsigned int lep_flags)
540{
541  struct gc_arena gc = gc_new ();
542  int n = 0;
543
544  if (streq (parm, "on"))
545    {
546      *realtime = true;
547      msg (M_CLIENT, "SUCCESS: real-time %s notification set to ON", type);
548    }
549  else if (streq (parm, "off"))
550    {
551      *realtime = false;
552      msg (M_CLIENT, "SUCCESS: real-time %s notification set to OFF", type);
553    }
554  else if (streq (parm, "all") || (n = atoi (parm)) > 0)
555    {
556      const int size = log_history_size (log);
557      const int start = (n ? n : size) - 1;
558      int i;
559
560      for (i = start; i >= 0; --i)
561	{
562	  const struct log_entry *e = log_history_ref (log, i);
563	  if (e)
564	    {
565	      const char *out = log_entry_print (e, lep_flags, &gc);
566	      virtual_output_callback_func (man, M_CLIENT, out);
567	    }
568	}
569      msg (M_CLIENT, "END");
570    }
571  else
572    {
573      msg (M_CLIENT, "ERROR: %s parameter must be 'on' or 'off' or some number n or 'all'", type);
574    }
575
576  gc_free (&gc);
577}
578
579static void
580man_log (struct management *man, const char *parm)
581{
582  man_history (man,
583	       parm,
584	       "log",
585	       man->persist.log,
586	       &man->connection.log_realtime,
587	       LOG_PRINT_INT_DATE|LOG_PRINT_MSG_FLAGS);
588}
589
590static void
591man_echo (struct management *man, const char *parm)
592{
593  man_history (man,
594	       parm,
595	       "echo",
596	       man->persist.echo,
597	       &man->connection.echo_realtime,
598	       LOG_PRINT_INT_DATE|MANAGEMENT_ECHO_FLAGS);
599}
600
601static void
602man_state (struct management *man, const char *parm)
603{
604  man_history (man,
605	       parm,
606	       "state",
607	       man->persist.state,
608	       &man->connection.state_realtime,
609	       LOG_PRINT_INT_DATE|LOG_PRINT_STATE|
610	       LOG_PRINT_LOCAL_IP|LOG_PRINT_REMOTE_IP);
611}
612
613static void
614man_up_finalize (struct management *man)
615{
616  switch (man->connection.up_query_mode)
617    {
618    case UP_QUERY_USER_PASS:
619      if (!strlen (man->connection.up_query.username))
620	break;
621      /* fall through */
622    case UP_QUERY_PASS:
623    case UP_QUERY_NEED_OK:
624    case UP_QUERY_NEED_STR:
625      if (strlen (man->connection.up_query.password))
626	man->connection.up_query.defined = true;
627      break;
628    case UP_QUERY_DISABLED:
629      man->connection.up_query.defined = false;
630      break;
631    default:
632      ASSERT (0);
633    }
634}
635
636static void
637man_query_user_pass (struct management *man,
638		     const char *type,
639		     const char *string,
640		     const bool needed,
641		     const char *prompt,
642		     char *dest,
643		     int len)
644{
645  if (needed)
646    {
647      ASSERT (man->connection.up_query_type);
648      if (streq (man->connection.up_query_type, type))
649	{
650	  strncpynt (dest, string, len);
651	  man_up_finalize (man);
652	  msg (M_CLIENT, "SUCCESS: '%s' %s entered, but not yet verified",
653	       type,
654	       prompt);
655	}
656      else
657	msg (M_CLIENT, "ERROR: %s of type '%s' entered, but we need one of type '%s'",
658	     prompt,
659	     type,
660	     man->connection.up_query_type);
661    }
662  else
663    {
664      msg (M_CLIENT, "ERROR: no %s is currently needed at this time", prompt);
665    }
666}
667
668static void
669man_query_username (struct management *man, const char *type, const char *string)
670{
671  const bool needed = ((man->connection.up_query_mode == UP_QUERY_USER_PASS
672			) && man->connection.up_query_type);
673  man_query_user_pass (man, type, string, needed, "username", man->connection.up_query.username, USER_PASS_LEN);
674}
675
676static void
677man_query_password (struct management *man, const char *type, const char *string)
678{
679  const bool needed = ((man->connection.up_query_mode == UP_QUERY_PASS
680			|| man->connection.up_query_mode == UP_QUERY_USER_PASS
681			) && man->connection.up_query_type);
682  if (!string[0]) /* allow blank passwords to be passed through using the blank_up tag */
683    string = blank_up;
684  man_query_user_pass (man, type, string, needed, "password", man->connection.up_query.password, USER_PASS_LEN);
685}
686
687static void
688man_query_need_ok (struct management *man, const char *type, const char *action)
689{
690  const bool needed = ((man->connection.up_query_mode == UP_QUERY_NEED_OK) && man->connection.up_query_type);
691  man_query_user_pass (man, type, action, needed, "needok-confirmation", man->connection.up_query.password, USER_PASS_LEN);
692}
693
694static void
695man_query_need_str (struct management *man, const char *type, const char *action)
696{
697  const bool needed = ((man->connection.up_query_mode == UP_QUERY_NEED_STR) && man->connection.up_query_type);
698  man_query_user_pass (man, type, action, needed, "needstr-string", man->connection.up_query.password, USER_PASS_LEN);
699}
700
701static void
702man_forget_passwords (struct management *man)
703{
704#if defined(ENABLE_CRYPTO) && defined(ENABLE_SSL)
705  ssl_purge_auth (false);
706  msg (M_CLIENT, "SUCCESS: Passwords were forgotten");
707#endif
708}
709
710static void
711man_net (struct management *man)
712{
713  if (man->persist.callback.show_net)
714    {
715      (*man->persist.callback.show_net) (man->persist.callback.arg, M_CLIENT);
716    }
717  else
718    {
719      msg (M_CLIENT, "ERROR: The 'net' command is not supported by the current daemon mode");
720    }
721}
722
723#ifdef ENABLE_PKCS11
724
725static void
726man_pkcs11_id_count (struct management *man)
727{
728  msg (M_CLIENT, ">PKCS11ID-COUNT:%d", pkcs11_management_id_count ());
729}
730
731static void
732man_pkcs11_id_get (struct management *man, const int index)
733{
734  char *id = NULL;
735  char *base64 = NULL;
736
737  if (pkcs11_management_id_get (index, &id, &base64))
738    msg (M_CLIENT, ">PKCS11ID-ENTRY:'%d', ID:'%s', BLOB:'%s'", index, id, base64);
739  else
740    msg (M_CLIENT, ">PKCS11ID-ENTRY:'%d'", index);
741
742  if (id != NULL)
743    free (id);
744  if (base64 != NULL)
745    free (base64);
746}
747
748#endif
749
750static void
751man_hold (struct management *man, const char *cmd)
752{
753  if (cmd)
754    {
755      if (streq (cmd, "on"))
756	{
757	  man->settings.flags |= MF_HOLD;
758	  msg (M_CLIENT, "SUCCESS: hold flag set to ON");
759	}
760      else if (streq (cmd, "off"))
761	{
762	  man->settings.flags &= ~MF_HOLD;
763	  msg (M_CLIENT, "SUCCESS: hold flag set to OFF");
764	}
765      else if (streq (cmd, "release"))
766	{
767	  man->persist.hold_release = true;
768	  msg (M_CLIENT, "SUCCESS: hold release succeeded");
769	}
770      else
771	{
772	  msg (M_CLIENT, "ERROR: bad hold command parameter");
773	}
774    }
775  else
776    msg (M_CLIENT, "SUCCESS: hold=%d", BOOL_CAST(man->settings.flags & MF_HOLD));
777}
778
779#ifdef MANAGEMENT_IN_EXTRA
780
781#define IER_RESET      0
782#define IER_NEW        1
783
784static void
785in_extra_reset (struct man_connection *mc, const int mode)
786{
787  if (mc)
788    {
789      if (mode != IER_NEW)
790	{
791	  mc->in_extra_cmd = IEC_UNDEF;
792#ifdef MANAGEMENT_DEF_AUTH
793	  mc->in_extra_cid = 0;
794	  mc->in_extra_kid = 0;
795#endif
796	}
797      if (mc->in_extra)
798	{
799	  buffer_list_free (mc->in_extra);
800	  mc->in_extra = NULL;
801	}
802      if (mode == IER_NEW)
803	mc->in_extra = buffer_list_new (0);
804    }
805}
806
807static void
808in_extra_dispatch (struct management *man)
809{
810   switch (man->connection.in_extra_cmd)
811    {
812#ifdef MANAGEMENT_DEF_AUTH
813    case IEC_CLIENT_AUTH:
814       if (man->persist.callback.client_auth)
815	{
816	  const bool status = (*man->persist.callback.client_auth)
817	    (man->persist.callback.arg,
818	     man->connection.in_extra_cid,
819	     man->connection.in_extra_kid,
820	     true,
821	     NULL,
822	     NULL,
823	     man->connection.in_extra);
824	  man->connection.in_extra = NULL;
825	  if (status)
826	    {
827	      msg (M_CLIENT, "SUCCESS: client-auth command succeeded");
828	    }
829	  else
830	    {
831	      msg (M_CLIENT, "ERROR: client-auth command failed");
832	    }
833	}
834      else
835	{
836	  msg (M_CLIENT, "ERROR: The client-auth command is not supported by the current daemon mode");
837	}
838      break;
839#endif
840#ifdef MANAGEMENT_PF
841    case IEC_CLIENT_PF:
842      if (man->persist.callback.client_pf)
843	{
844	  const bool status = (*man->persist.callback.client_pf)
845	    (man->persist.callback.arg,
846	     man->connection.in_extra_cid,
847	     man->connection.in_extra);
848	  man->connection.in_extra = NULL;
849	  if (status)
850	    {
851	      msg (M_CLIENT, "SUCCESS: client-pf command succeeded");
852	    }
853	  else
854	    {
855	      msg (M_CLIENT, "ERROR: client-pf command failed");
856	    }
857	}
858      else
859	{
860	  msg (M_CLIENT, "ERROR: The client-pf command is not supported by the current daemon mode");
861	}
862      break;
863#endif
864#ifdef MANAGMENT_EXTERNAL_KEY
865    case IEC_RSA_SIGN:
866      man->connection.ext_key_state = EKS_READY;
867      buffer_list_free (man->connection.ext_key_input);
868      man->connection.ext_key_input = man->connection.in_extra;
869      man->connection.in_extra = NULL;
870      return;
871#endif
872    }
873   in_extra_reset (&man->connection, IER_RESET);
874}
875
876#endif /* MANAGEMENT_IN_EXTRA */
877
878#ifdef MANAGEMENT_DEF_AUTH
879
880static bool
881parse_cid (const char *str, unsigned long *cid)
882{
883  if (sscanf (str, "%lu", cid) == 1)
884    return true;
885  else
886    {
887      msg (M_CLIENT, "ERROR: cannot parse CID");
888      return false;
889    }
890}
891
892static bool
893parse_kid (const char *str, unsigned int *kid)
894{
895  if (sscanf (str, "%u", kid) == 1)
896    return true;
897  else
898    {
899      msg (M_CLIENT, "ERROR: cannot parse KID");
900      return false;
901    }
902}
903
904static void
905man_client_auth (struct management *man, const char *cid_str, const char *kid_str, const bool extra)
906{
907  struct man_connection *mc = &man->connection;
908  mc->in_extra_cid = 0;
909  mc->in_extra_kid = 0;
910  if (parse_cid (cid_str, &mc->in_extra_cid)
911      && parse_kid (kid_str, &mc->in_extra_kid))
912    {
913      mc->in_extra_cmd = IEC_CLIENT_AUTH;
914      in_extra_reset (mc, IER_NEW);
915      if (!extra)
916	in_extra_dispatch (man);
917    }
918}
919
920static void
921man_client_deny (struct management *man, const char *cid_str, const char *kid_str, const char *reason, const char *client_reason)
922{
923  unsigned long cid = 0;
924  unsigned int kid = 0;
925  if (parse_cid (cid_str, &cid) && parse_kid (kid_str, &kid))
926    {
927      if (man->persist.callback.client_auth)
928	{
929	  const bool status = (*man->persist.callback.client_auth)
930	    (man->persist.callback.arg,
931	     cid,
932	     kid,
933	     false,
934	     reason,
935	     client_reason,
936	     NULL);
937	  if (status)
938	    {
939	      msg (M_CLIENT, "SUCCESS: client-deny command succeeded");
940	    }
941	  else
942	    {
943	      msg (M_CLIENT, "ERROR: client-deny command failed");
944	    }
945	}
946      else
947	{
948	  msg (M_CLIENT, "ERROR: The client-deny command is not supported by the current daemon mode");
949	}
950    }
951}
952
953static void
954man_client_kill (struct management *man, const char *cid_str, const char *kill_msg)
955{
956  unsigned long cid = 0;
957  if (parse_cid (cid_str, &cid))
958    {
959      if (man->persist.callback.kill_by_cid)
960	{
961	  const bool status = (*man->persist.callback.kill_by_cid) (man->persist.callback.arg, cid, kill_msg);
962	  if (status)
963	    {
964	      msg (M_CLIENT, "SUCCESS: client-kill command succeeded");
965	    }
966	  else
967	    {
968	      msg (M_CLIENT, "ERROR: client-kill command failed");
969	    }
970	}
971      else
972	{
973	  msg (M_CLIENT, "ERROR: The client-kill command is not supported by the current daemon mode");
974	}
975    }
976}
977
978static void
979man_client_n_clients (struct management *man)
980{
981  if (man->persist.callback.n_clients)
982    {
983      const int nclients = (*man->persist.callback.n_clients) (man->persist.callback.arg);
984      msg (M_CLIENT, "SUCCESS: nclients=%d", nclients);
985    }
986  else
987    {
988      msg (M_CLIENT, "ERROR: The nclients command is not supported by the current daemon mode");
989    }
990}
991
992static void
993man_env_filter (struct management *man, const int level)
994{
995  man->connection.env_filter_level = level;
996  msg (M_CLIENT, "SUCCESS: env_filter_level=%d", level);
997}
998
999#ifdef MANAGEMENT_PF
1000
1001static void
1002man_client_pf (struct management *man, const char *cid_str)
1003{
1004  struct man_connection *mc = &man->connection;
1005  mc->in_extra_cid = 0;
1006  mc->in_extra_kid = 0;
1007  if (parse_cid (cid_str, &mc->in_extra_cid))
1008    {
1009      mc->in_extra_cmd = IEC_CLIENT_PF;
1010      in_extra_reset (mc, IER_NEW);
1011    }
1012}
1013
1014#endif /* MANAGEMENT_PF */
1015#endif /* MANAGEMENT_DEF_AUTH */
1016
1017#ifdef MANAGMENT_EXTERNAL_KEY
1018
1019static void
1020man_rsa_sig (struct management *man)
1021{
1022  struct man_connection *mc = &man->connection;
1023  if (mc->ext_key_state == EKS_SOLICIT)
1024    {
1025      mc->ext_key_state = EKS_INPUT;
1026      mc->in_extra_cmd = IEC_RSA_SIGN;
1027      in_extra_reset (mc, IER_NEW);
1028    }
1029  else
1030    msg (M_CLIENT, "ERROR: The rsa-sig command is not currently available");
1031}
1032
1033#endif
1034
1035static void
1036man_load_stats (struct management *man)
1037{
1038  extern counter_type link_read_bytes_global;
1039  extern counter_type link_write_bytes_global;
1040  int nclients = 0;
1041
1042  if (man->persist.callback.n_clients)
1043    nclients = (*man->persist.callback.n_clients) (man->persist.callback.arg);
1044  msg (M_CLIENT, "SUCCESS: nclients=%d,bytesin=" counter_format ",bytesout=" counter_format,
1045       nclients,
1046       link_read_bytes_global,
1047       link_write_bytes_global);
1048}
1049
1050#define MN_AT_LEAST (1<<0)
1051
1052static bool
1053man_need (struct management *man, const char **p, const int n, unsigned int flags)
1054{
1055  int i;
1056  ASSERT (p[0]);
1057  for (i = 1; i <= n; ++i)
1058    {
1059      if (!p[i])
1060	{
1061	  msg (M_CLIENT, "ERROR: the '%s' command requires %s%d parameter%s",
1062	       p[0],
1063	       (flags & MN_AT_LEAST) ? "at least " : "",
1064	       n,
1065	       n > 1 ? "s" : "");
1066	  return false;
1067	}
1068    }
1069  return true;
1070}
1071
1072static void
1073man_proxy (struct management *man, const char **p)
1074{
1075  if (man->persist.callback.proxy_cmd)
1076    {
1077      const bool status = (*man->persist.callback.proxy_cmd)(man->persist.callback.arg, p);
1078      if (status)
1079        msg (M_CLIENT, "SUCCESS: proxy command succeeded");
1080      else
1081        msg (M_CLIENT, "ERROR: proxy command failed");
1082    }
1083  else
1084    msg (M_CLIENT, "ERROR: The proxy command is not supported by the current daemon mode");
1085}
1086
1087static void
1088man_remote (struct management *man, const char **p)
1089{
1090  if (man->persist.callback.remote_cmd)
1091    {
1092      const bool status = (*man->persist.callback.remote_cmd)(man->persist.callback.arg, p);
1093      if (status)
1094	{
1095	  msg (M_CLIENT, "SUCCESS: remote command succeeded");
1096	}
1097      else
1098	{
1099	  msg (M_CLIENT, "ERROR: remote command failed");
1100	}
1101    }
1102  else
1103    {
1104      msg (M_CLIENT, "ERROR: The remote command is not supported by the current daemon mode");
1105    }
1106}
1107
1108static void
1109man_dispatch_command (struct management *man, struct status_output *so, const char **p, const int nparms)
1110{
1111  struct gc_arena gc = gc_new ();
1112
1113  ASSERT (p[0]);
1114  if (streq (p[0], "exit") || streq (p[0], "quit"))
1115    {
1116      man->connection.halt = true;
1117      goto done;
1118    }
1119  else if (streq (p[0], "help"))
1120    {
1121      man_help ();
1122    }
1123  else if (streq (p[0], "version"))
1124    {
1125      msg (M_CLIENT, "OpenVPN Version: %s", title_string);
1126      msg (M_CLIENT, "Management Version: %d", MANAGEMENT_VERSION);
1127      msg (M_CLIENT, "END");
1128    }
1129  else if (streq (p[0], "pid"))
1130    {
1131      msg (M_CLIENT, "SUCCESS: pid=%d", platform_getpid ());
1132    }
1133#ifdef MANAGEMENT_DEF_AUTH
1134  else if (streq (p[0], "nclients"))
1135    {
1136      man_client_n_clients (man);
1137    }
1138  else if (streq (p[0], "env-filter"))
1139    {
1140      int level = 0;
1141      if (p[1])
1142	level = atoi (p[1]);
1143      man_env_filter (man, level);
1144    }
1145#endif
1146  else if (streq (p[0], "signal"))
1147    {
1148      if (man_need (man, p, 1, 0))
1149	man_signal (man, p[1]);
1150    }
1151  else if (streq (p[0], "load-stats"))
1152    {
1153      man_load_stats (man);
1154    }
1155  else if (streq (p[0], "status"))
1156    {
1157      int version = 0;
1158      if (p[1])
1159	version = atoi (p[1]);
1160      man_status (man, version, so);
1161    }
1162  else if (streq (p[0], "kill"))
1163    {
1164      if (man_need (man, p, 1, 0))
1165	man_kill (man, p[1]);
1166    }
1167  else if (streq (p[0], "verb"))
1168    {
1169      if (p[1])
1170	{
1171	  const int level = atoi(p[1]);
1172	  if (set_debug_level (level, 0))
1173	    msg (M_CLIENT, "SUCCESS: verb level changed");
1174	  else
1175	    msg (M_CLIENT, "ERROR: verb level is out of range");
1176	}
1177      else
1178	msg (M_CLIENT, "SUCCESS: verb=%d", get_debug_level ());
1179    }
1180  else if (streq (p[0], "mute"))
1181    {
1182      if (p[1])
1183	{
1184	  const int level = atoi(p[1]);
1185	  if (set_mute_cutoff (level))
1186	    msg (M_CLIENT, "SUCCESS: mute level changed");
1187	  else
1188	    msg (M_CLIENT, "ERROR: mute level is out of range");
1189	}
1190      else
1191	msg (M_CLIENT, "SUCCESS: mute=%d", get_mute_cutoff ());
1192    }
1193  else if (streq (p[0], "auth-retry"))
1194    {
1195#if P2MP
1196      if (p[1])
1197	{
1198	  if (auth_retry_set (M_CLIENT, p[1]))
1199	    msg (M_CLIENT, "SUCCESS: auth-retry parameter changed");
1200	  else
1201	    msg (M_CLIENT, "ERROR: bad auth-retry parameter");
1202	}
1203      else
1204	msg (M_CLIENT, "SUCCESS: auth-retry=%s", auth_retry_print ());
1205#else
1206      msg (M_CLIENT, "ERROR: auth-retry feature is unavailable");
1207#endif
1208    }
1209  else if (streq (p[0], "state"))
1210    {
1211      if (!p[1])
1212	{
1213	  man_state (man, "1");
1214	}
1215      else
1216	{
1217	  if (p[1])
1218	    man_state (man, p[1]);
1219	  if (p[2])
1220	    man_state (man, p[2]);
1221	}
1222    }
1223  else if (streq (p[0], "log"))
1224    {
1225      if (man_need (man, p, 1, MN_AT_LEAST))
1226	{
1227	  if (p[1])
1228	    man_log (man, p[1]);
1229	  if (p[2])
1230	    man_log (man, p[2]);
1231	}
1232    }
1233  else if (streq (p[0], "echo"))
1234    {
1235      if (man_need (man, p, 1, MN_AT_LEAST))
1236	{
1237	  if (p[1])
1238	    man_echo (man, p[1]);
1239	  if (p[2])
1240	    man_echo (man, p[2]);
1241	}
1242    }
1243  else if (streq (p[0], "username"))
1244    {
1245      if (man_need (man, p, 2, 0))
1246	man_query_username (man, p[1], p[2]);
1247    }
1248  else if (streq (p[0], "password"))
1249    {
1250      if (man_need (man, p, 2, 0))
1251	man_query_password (man, p[1], p[2]);
1252    }
1253  else if (streq (p[0], "forget-passwords"))
1254    {
1255      man_forget_passwords (man);
1256    }
1257  else if (streq (p[0], "needok"))
1258    {
1259      if (man_need (man, p, 2, 0))
1260	man_query_need_ok (man, p[1], p[2]);
1261    }
1262  else if (streq (p[0], "needstr"))
1263    {
1264      if (man_need (man, p, 2, 0))
1265	man_query_need_str (man, p[1], p[2]);
1266    }
1267  else if (streq (p[0], "net"))
1268    {
1269      man_net (man);
1270    }
1271  else if (streq (p[0], "hold"))
1272    {
1273      man_hold (man, p[1]);
1274    }
1275  else if (streq (p[0], "bytecount"))
1276    {
1277      if (man_need (man, p, 1, 0))
1278	man_bytecount (man, atoi(p[1]));
1279    }
1280#ifdef MANAGEMENT_DEF_AUTH
1281  else if (streq (p[0], "client-kill"))
1282    {
1283      if (man_need (man, p, 1, MN_AT_LEAST))
1284	man_client_kill (man, p[1], p[2]);
1285    }
1286  else if (streq (p[0], "client-deny"))
1287    {
1288      if (man_need (man, p, 3, MN_AT_LEAST))
1289	man_client_deny (man, p[1], p[2], p[3], p[4]);
1290    }
1291  else if (streq (p[0], "client-auth-nt"))
1292    {
1293      if (man_need (man, p, 2, 0))
1294	man_client_auth (man, p[1], p[2], false);
1295    }
1296  else if (streq (p[0], "client-auth"))
1297    {
1298      if (man_need (man, p, 2, 0))
1299	man_client_auth (man, p[1], p[2], true);
1300    }
1301#ifdef MANAGEMENT_PF
1302  else if (streq (p[0], "client-pf"))
1303    {
1304      if (man_need (man, p, 1, 0))
1305	man_client_pf (man, p[1]);
1306    }
1307#endif
1308#endif
1309#ifdef MANAGMENT_EXTERNAL_KEY
1310  else if (streq (p[0], "rsa-sig"))
1311    {
1312      man_rsa_sig (man);
1313    }
1314#endif
1315#ifdef ENABLE_PKCS11
1316  else if (streq (p[0], "pkcs11-id-count"))
1317    {
1318      man_pkcs11_id_count (man);
1319    }
1320  else if (streq (p[0], "pkcs11-id-get"))
1321    {
1322      if (man_need (man, p, 1, 0))
1323	man_pkcs11_id_get (man, atoi(p[1]));
1324    }
1325#endif
1326  else if (streq (p[0], "proxy"))
1327    {
1328      if (man_need (man, p, 1, MN_AT_LEAST))
1329        man_proxy (man, p);
1330    }
1331  else if (streq (p[0], "remote"))
1332    {
1333      if (man_need (man, p, 1, MN_AT_LEAST))
1334	man_remote (man, p);
1335    }
1336#if 1
1337  else if (streq (p[0], "test"))
1338    {
1339      if (man_need (man, p, 1, 0))
1340	{
1341	  int i;
1342	  const int n = atoi (p[1]);
1343	  for (i = 0; i < n; ++i)
1344	    {
1345	      msg (M_CLIENT, "[%d] The purpose of this command is to generate large amounts of output.", i);
1346	    }
1347	}
1348    }
1349#endif
1350  else
1351    {
1352      msg (M_CLIENT, "ERROR: unknown command, enter 'help' for more options");
1353    }
1354
1355 done:
1356  gc_free (&gc);
1357}
1358
1359#ifdef WIN32
1360
1361static void
1362man_start_ne32 (struct management *man)
1363{
1364  switch (man->connection.state)
1365    {
1366    case MS_LISTEN:
1367      net_event_win32_start (&man->connection.ne32, FD_ACCEPT, man->connection.sd_top);
1368      break;
1369    case MS_CC_WAIT_READ:
1370    case MS_CC_WAIT_WRITE:
1371      net_event_win32_start (&man->connection.ne32, FD_READ|FD_WRITE|FD_CLOSE, man->connection.sd_cli);
1372      break;
1373    default:
1374      ASSERT (0);
1375    }
1376}
1377
1378static void
1379man_stop_ne32 (struct management *man)
1380{
1381  net_event_win32_stop (&man->connection.ne32);
1382}
1383
1384#endif
1385
1386static void
1387man_record_peer_info (struct management *man)
1388{
1389  struct gc_arena gc = gc_new ();
1390  if (man->settings.write_peer_info_file)
1391    {
1392      bool success = false;
1393#ifdef HAVE_GETSOCKNAME
1394      if (socket_defined (man->connection.sd_cli))
1395	{
1396	  struct sockaddr_in addr;
1397	  socklen_t addrlen = sizeof (addr);
1398	  int status;
1399
1400	  CLEAR (addr);
1401	  status = getsockname (man->connection.sd_cli, (struct sockaddr *)&addr, &addrlen);
1402	  if (!status && addrlen == sizeof (addr))
1403	    {
1404	      const in_addr_t a = ntohl (addr.sin_addr.s_addr);
1405	      const int p = ntohs (addr.sin_port);
1406	      FILE *fp = platform_fopen (man->settings.write_peer_info_file, "w");
1407	      if (fp)
1408		{
1409		  fprintf (fp, "%s\n%d\n", print_in_addr_t (a, 0, &gc), p);
1410		  if (!fclose (fp))
1411		    success = true;
1412		}
1413	    }
1414	}
1415#endif
1416      if (!success)
1417	{
1418	  msg (D_MANAGEMENT, "MANAGEMENT: failed to write peer info to file %s",
1419	       man->settings.write_peer_info_file);
1420	  throw_signal_soft (SIGTERM, "management-connect-failed");
1421	}
1422    }
1423  gc_free (&gc);
1424}
1425
1426static void
1427man_connection_settings_reset (struct management *man)
1428{
1429  man->connection.state_realtime = false;
1430  man->connection.log_realtime = false;
1431  man->connection.echo_realtime = false;
1432  man->connection.bytecount_update_seconds = 0;
1433  man->connection.password_verified = false;
1434  man->connection.password_tries = 0;
1435  man->connection.halt = false;
1436  man->connection.state = MS_CC_WAIT_WRITE;
1437}
1438
1439static void
1440man_new_connection_post (struct management *man, const char *description)
1441{
1442  struct gc_arena gc = gc_new ();
1443
1444  set_nonblock (man->connection.sd_cli);
1445  set_cloexec (man->connection.sd_cli);
1446
1447  man_connection_settings_reset (man);
1448
1449#ifdef WIN32
1450  man_start_ne32 (man);
1451#endif
1452
1453#if UNIX_SOCK_SUPPORT
1454  if (man->settings.flags & MF_UNIX_SOCK)
1455    {
1456      msg (D_MANAGEMENT, "MANAGEMENT: %s %s",
1457	   description,
1458	   sockaddr_unix_name (&man->settings.local_unix, "NULL"));
1459    }
1460  else
1461#endif
1462    msg (D_MANAGEMENT, "MANAGEMENT: %s %s",
1463	 description,
1464	 print_sockaddr (&man->settings.local, &gc));
1465
1466  buffer_list_reset (man->connection.out);
1467
1468  if (!man_password_needed (man))
1469    man_welcome (man);
1470  man_prompt (man);
1471  man_update_io_state (man);
1472
1473  gc_free (&gc);
1474}
1475
1476#if UNIX_SOCK_SUPPORT
1477static bool
1478man_verify_unix_peer_uid_gid (struct management *man, const socket_descriptor_t sd)
1479{
1480  if (socket_defined (sd) && (man->settings.client_uid != -1 || man->settings.client_gid != -1))
1481    {
1482      static const char err_prefix[] = "MANAGEMENT: unix domain socket client connection rejected --";
1483      int uid, gid;
1484      if (unix_socket_get_peer_uid_gid (man->connection.sd_cli, &uid, &gid))
1485	{
1486	  if (man->settings.client_uid != -1 && man->settings.client_uid != uid)
1487	    {
1488	      msg (D_MANAGEMENT, "%s UID of socket peer (%d) doesn't match required value (%d) as given by --management-client-user",
1489		   err_prefix, uid, man->settings.client_uid);
1490	      return false;
1491	    }
1492	  if (man->settings.client_gid != -1 && man->settings.client_gid != gid)
1493	    {
1494	      msg (D_MANAGEMENT, "%s GID of socket peer (%d) doesn't match required value (%d) as given by --management-client-group",
1495		   err_prefix, gid, man->settings.client_gid);
1496	      return false;
1497	    }
1498	}
1499      else
1500	{
1501	  msg (D_MANAGEMENT, "%s cannot get UID/GID of socket peer", err_prefix);
1502	  return false;
1503	}
1504    }
1505  return true;
1506}
1507#endif
1508
1509static void
1510man_accept (struct management *man)
1511{
1512  struct link_socket_actual act;
1513  CLEAR (act);
1514
1515  /*
1516   * Accept the TCP or Unix domain socket client.
1517   */
1518#if UNIX_SOCK_SUPPORT
1519  if (man->settings.flags & MF_UNIX_SOCK)
1520    {
1521      struct sockaddr_un remote;
1522      man->connection.sd_cli = socket_accept_unix (man->connection.sd_top, &remote);
1523      if (!man_verify_unix_peer_uid_gid (man, man->connection.sd_cli))
1524	sd_close (&man->connection.sd_cli);
1525    }
1526  else
1527#endif
1528    man->connection.sd_cli = socket_do_accept (man->connection.sd_top, &act, false);
1529
1530  if (socket_defined (man->connection.sd_cli))
1531    {
1532      man->connection.remote = act.dest;
1533
1534      if (socket_defined (man->connection.sd_top))
1535	{
1536#ifdef WIN32
1537	  man_stop_ne32 (man);
1538#endif
1539	}
1540
1541      man_new_connection_post (man, "Client connected from");
1542    }
1543}
1544
1545static void
1546man_listen (struct management *man)
1547{
1548  struct gc_arena gc = gc_new ();
1549
1550  /*
1551   * Initialize state
1552   */
1553  man->connection.state = MS_LISTEN;
1554  man->connection.sd_cli = SOCKET_UNDEFINED;
1555
1556  /*
1557   * Initialize listening socket
1558   */
1559  if (man->connection.sd_top == SOCKET_UNDEFINED)
1560    {
1561#if UNIX_SOCK_SUPPORT
1562      if (man->settings.flags & MF_UNIX_SOCK)
1563	{
1564	  man_delete_unix_socket (man);
1565	  man->connection.sd_top = create_socket_unix ();
1566	  socket_bind_unix (man->connection.sd_top, &man->settings.local_unix, "MANAGEMENT");
1567	}
1568      else
1569#endif
1570	{
1571	  man->connection.sd_top = create_socket_tcp (AF_INET);
1572	  socket_bind (man->connection.sd_top, &man->settings.local, "MANAGEMENT");
1573	}
1574
1575      /*
1576       * Listen for connection
1577       */
1578      if (listen (man->connection.sd_top, 1))
1579	msg (M_ERR, "MANAGEMENT: listen() failed");
1580
1581      /*
1582       * Set misc socket properties
1583       */
1584      set_nonblock (man->connection.sd_top);
1585      set_cloexec (man->connection.sd_top);
1586
1587#if UNIX_SOCK_SUPPORT
1588      if (man->settings.flags & MF_UNIX_SOCK)
1589	{
1590	  msg (D_MANAGEMENT, "MANAGEMENT: unix domain socket listening on %s",
1591	       sockaddr_unix_name (&man->settings.local_unix, "NULL"));
1592	}
1593      else
1594#endif
1595	msg (D_MANAGEMENT, "MANAGEMENT: TCP Socket listening on %s",
1596	     print_sockaddr (&man->settings.local, &gc));
1597    }
1598
1599#ifdef WIN32
1600  man_start_ne32 (man);
1601#endif
1602
1603  gc_free (&gc);
1604}
1605
1606static void
1607man_connect (struct management *man)
1608{
1609  struct gc_arena gc = gc_new ();
1610  int status;
1611  int signal_received = 0;
1612
1613  /*
1614   * Initialize state
1615   */
1616  man->connection.state = MS_INITIAL;
1617  man->connection.sd_top = SOCKET_UNDEFINED;
1618
1619#if UNIX_SOCK_SUPPORT
1620  if (man->settings.flags & MF_UNIX_SOCK)
1621    {
1622      man->connection.sd_cli = create_socket_unix ();
1623      status = socket_connect_unix (man->connection.sd_cli, &man->settings.local_unix);
1624      if (!status && !man_verify_unix_peer_uid_gid (man, man->connection.sd_cli))
1625	  {
1626#ifdef EPERM
1627	    status = EPERM;
1628#else
1629	    status = 1;
1630#endif
1631	    sd_close (&man->connection.sd_cli);
1632	  }
1633    }
1634  else
1635#endif
1636    {
1637      man->connection.sd_cli = create_socket_tcp (AF_INET);
1638      status = openvpn_connect (man->connection.sd_cli,
1639				&man->settings.local,
1640				5,
1641				&signal_received);
1642    }
1643
1644  if (signal_received)
1645    {
1646      throw_signal (signal_received);
1647      goto done;
1648    }
1649
1650  if (status)
1651    {
1652#if UNIX_SOCK_SUPPORT
1653      if (man->settings.flags & MF_UNIX_SOCK)
1654	{
1655	  msg (D_LINK_ERRORS,
1656	       "MANAGEMENT: connect to unix socket %s failed: %s",
1657	       sockaddr_unix_name (&man->settings.local_unix, "NULL"),
1658	       strerror_ts (status, &gc));
1659	}
1660      else
1661#endif
1662      msg (D_LINK_ERRORS,
1663	   "MANAGEMENT: connect to %s failed: %s",
1664	   print_sockaddr (&man->settings.local, &gc),
1665	   strerror_ts (status, &gc));
1666      throw_signal_soft (SIGTERM, "management-connect-failed");
1667      goto done;
1668    }
1669
1670  man_record_peer_info (man);
1671  man_new_connection_post (man, "Connected to management server at");
1672
1673 done:
1674  gc_free (&gc);
1675}
1676
1677static void
1678man_reset_client_socket (struct management *man, const bool exiting)
1679{
1680  if (socket_defined (man->connection.sd_cli))
1681    {
1682#ifdef WIN32
1683      man_stop_ne32 (man);
1684#endif
1685      man_close_socket (man, man->connection.sd_cli);
1686      man->connection.sd_cli = SOCKET_UNDEFINED;
1687      man->connection.state = MS_INITIAL;
1688      command_line_reset (man->connection.in);
1689      buffer_list_reset (man->connection.out);
1690#ifdef MANAGEMENT_IN_EXTRA
1691      in_extra_reset (&man->connection, IER_RESET);
1692#endif
1693      msg (D_MANAGEMENT, "MANAGEMENT: Client disconnected");
1694    }
1695  if (!exiting)
1696    {
1697#if defined(ENABLE_CRYPTO) && defined(ENABLE_SSL)
1698      if (man->settings.flags & MF_FORGET_DISCONNECT)
1699	ssl_purge_auth (false);
1700#endif
1701      if (man->settings.flags & MF_SIGNAL) {
1702      	  int mysig = man_mod_signal (man, SIGUSR1);
1703	  if (mysig >= 0)
1704	    {
1705	      msg (D_MANAGEMENT, "MANAGEMENT: Triggering management signal");
1706	      throw_signal_soft (mysig, "management-disconnect");
1707	    }
1708      }
1709
1710      if (man->settings.flags & MF_CONNECT_AS_CLIENT)
1711	{
1712	  msg (D_MANAGEMENT, "MANAGEMENT: Triggering management exit");
1713	  throw_signal_soft (SIGTERM, "management-exit");
1714	}
1715      else
1716	man_listen (man);
1717    }
1718}
1719
1720static void
1721man_process_command (struct management *man, const char *line)
1722{
1723  struct gc_arena gc = gc_new ();
1724  struct status_output *so;
1725  int nparms;
1726  char *parms[MAX_PARMS+1];
1727
1728  CLEAR (parms);
1729  so = status_open (NULL, 0, -1, &man->persist.vout, 0);
1730#ifdef MANAGEMENT_IN_EXTRA
1731  in_extra_reset (&man->connection, IER_RESET);
1732#endif
1733
1734  if (man_password_needed (man))
1735    {
1736      man_check_password (man, line);
1737    }
1738  else
1739    {
1740      nparms = parse_line (line, parms, MAX_PARMS, "TCP", 0, M_CLIENT, &gc);
1741      if (parms[0] && streq (parms[0], "password"))
1742	msg (D_MANAGEMENT_DEBUG, "MANAGEMENT: CMD 'password [...]'");
1743      else if (!streq (line, "load-stats"))
1744	msg (D_MANAGEMENT_DEBUG, "MANAGEMENT: CMD '%s'", line);
1745
1746#if 0
1747      /* DEBUGGING -- print args */
1748      {
1749	int i;
1750	for (i = 0; i < nparms; ++i)
1751	  msg (M_INFO, "[%d] '%s'", i, parms[i]);
1752      }
1753#endif
1754
1755      if (nparms > 0)
1756	man_dispatch_command (man, so, (const char **)parms, nparms);
1757    }
1758
1759  CLEAR (parms);
1760  status_close (so);
1761  gc_free (&gc);
1762}
1763
1764static bool
1765man_io_error (struct management *man, const char *prefix)
1766{
1767  const int err = openvpn_errno ();
1768
1769  if (!ignore_sys_error (err))
1770    {
1771      struct gc_arena gc = gc_new ();
1772      msg (D_MANAGEMENT, "MANAGEMENT: TCP %s error: %s",
1773	   prefix,
1774	   strerror_ts (err, &gc));
1775      gc_free (&gc);
1776      return true;
1777    }
1778  else
1779    return false;
1780}
1781
1782static int
1783man_read (struct management *man)
1784{
1785  /*
1786   * read command line from socket
1787   */
1788  unsigned char buf[256];
1789  int len = 0;
1790
1791  len = recv (man->connection.sd_cli, buf, sizeof (buf), MSG_NOSIGNAL);
1792  if (len == 0)
1793    {
1794      man_reset_client_socket (man, false);
1795    }
1796  else if (len > 0)
1797    {
1798      bool processed_command = false;
1799
1800      ASSERT (len <= (int) sizeof (buf));
1801      command_line_add (man->connection.in, buf, len);
1802
1803      /*
1804       * Reset output object
1805       */
1806      buffer_list_reset (man->connection.out);
1807
1808      /*
1809       * process command line if complete
1810       */
1811      {
1812	const unsigned char *line;
1813	while ((line = command_line_get (man->connection.in)))
1814	  {
1815#ifdef MANAGEMENT_IN_EXTRA
1816	    if (man->connection.in_extra)
1817	      {
1818		if (!strcmp ((char *)line, "END"))
1819		  in_extra_dispatch (man);
1820		else
1821		  buffer_list_push (man->connection.in_extra, line);
1822	      }
1823	    else
1824#endif
1825	      man_process_command (man, (char *) line);
1826	    if (man->connection.halt)
1827	      break;
1828	    command_line_next (man->connection.in);
1829	    processed_command = true;
1830	  }
1831      }
1832
1833      /*
1834       * Reset output state to MS_CC_WAIT_(READ|WRITE)
1835       */
1836      if (man->connection.halt)
1837	{
1838	  man_reset_client_socket (man, false);
1839	  len = 0;
1840	}
1841      else
1842	{
1843	  if (processed_command)
1844	    man_prompt (man);
1845	  man_update_io_state (man);
1846	}
1847    }
1848  else /* len < 0 */
1849    {
1850      if (man_io_error (man, "recv"))
1851	man_reset_client_socket (man, false);
1852    }
1853  return len;
1854}
1855
1856static int
1857man_write (struct management *man)
1858{
1859  const int size_hint = 1024;
1860  int sent = 0;
1861  const struct buffer *buf;
1862
1863  buffer_list_aggregate(man->connection.out, size_hint);
1864  buf = buffer_list_peek (man->connection.out);
1865  if (buf && BLEN (buf))
1866    {
1867      const int len = min_int (size_hint, BLEN (buf));
1868      sent = send (man->connection.sd_cli, BPTR (buf), len, MSG_NOSIGNAL);
1869      if (sent >= 0)
1870	{
1871	  buffer_list_advance (man->connection.out, sent);
1872	}
1873      else if (sent < 0)
1874	{
1875	  if (man_io_error (man, "send"))
1876	    man_reset_client_socket (man, false);
1877	}
1878    }
1879
1880  /*
1881   * Reset output state to MS_CC_WAIT_(READ|WRITE)
1882   */
1883  man_update_io_state (man);
1884
1885  return sent;
1886}
1887
1888static void
1889man_connection_clear (struct man_connection *mc)
1890{
1891  CLEAR (*mc);
1892
1893  /* set initial state */
1894  mc->state = MS_INITIAL;
1895
1896  /* clear socket descriptors */
1897  mc->sd_top = SOCKET_UNDEFINED;
1898  mc->sd_cli = SOCKET_UNDEFINED;
1899}
1900
1901static void
1902man_persist_init (struct management *man,
1903		  const int log_history_cache,
1904		  const int echo_buffer_size,
1905		  const int state_buffer_size)
1906{
1907  struct man_persist *mp = &man->persist;
1908  if (!mp->defined)
1909    {
1910      CLEAR (*mp);
1911
1912      /* initialize log history store */
1913      mp->log = log_history_init (log_history_cache);
1914
1915      /*
1916       * Initialize virtual output object, so that functions
1917       * which write to a virtual_output object can be redirected
1918       * here to the management object.
1919       */
1920      mp->vout.func = virtual_output_callback_func;
1921      mp->vout.arg = man;
1922      mp->vout.flags_default = M_CLIENT;
1923      msg_set_virtual_output (&mp->vout);
1924
1925      /*
1926       * Initialize --echo list
1927       */
1928      man->persist.echo = log_history_init (echo_buffer_size);
1929
1930      /*
1931       * Initialize --state list
1932       */
1933      man->persist.state = log_history_init (state_buffer_size);
1934
1935      mp->defined = true;
1936    }
1937}
1938
1939static void
1940man_persist_close (struct man_persist *mp)
1941{
1942  if (mp->log)
1943    {
1944      msg_set_virtual_output (NULL);
1945      log_history_close (mp->log);
1946    }
1947
1948  if (mp->echo)
1949    log_history_close (mp->echo);
1950
1951  if (mp->state)
1952    log_history_close (mp->state);
1953
1954  CLEAR (*mp);
1955}
1956
1957static void
1958man_settings_init (struct man_settings *ms,
1959		   const char *addr,
1960		   const int port,
1961		   const char *pass_file,
1962		   const char *client_user,
1963		   const char *client_group,
1964		   const int log_history_cache,
1965		   const int echo_buffer_size,
1966		   const int state_buffer_size,
1967		   const char *write_peer_info_file,
1968		   const int remap_sigusr1,
1969		   const unsigned int flags)
1970{
1971  if (!ms->defined)
1972    {
1973      CLEAR (*ms);
1974
1975      ms->flags = flags;
1976      ms->client_uid = -1;
1977      ms->client_gid = -1;
1978
1979      /*
1980       * Get username/password
1981       */
1982      if (pass_file)
1983	get_user_pass (&ms->up, pass_file, "Management", GET_USER_PASS_PASSWORD_ONLY);
1984
1985      /*
1986       * lookup client UID/GID if specified
1987       */
1988      if (client_user)
1989	{
1990	  struct platform_state_user s;
1991	  platform_user_get (client_user, &s);
1992	  ms->client_uid = platform_state_user_uid (&s);
1993	  msg (D_MANAGEMENT, "MANAGEMENT: client_uid=%d", ms->client_uid);
1994	  ASSERT (ms->client_uid >= 0);
1995	}
1996      if (client_group)
1997	{
1998	  struct platform_state_group s;
1999	  platform_group_get (client_group, &s);
2000	  ms->client_gid = platform_state_group_gid (&s);
2001	  msg (D_MANAGEMENT, "MANAGEMENT: client_gid=%d", ms->client_gid);
2002	  ASSERT (ms->client_gid >= 0);
2003	}
2004
2005      ms->write_peer_info_file = string_alloc (write_peer_info_file, NULL);
2006
2007#if UNIX_SOCK_SUPPORT
2008      if (ms->flags & MF_UNIX_SOCK)
2009	sockaddr_unix_init (&ms->local_unix, addr);
2010      else
2011#endif
2012	{
2013	  /*
2014	   * Initialize socket address
2015	   */
2016	  ms->local.addr.in4.sin_family = AF_INET;
2017	  ms->local.addr.in4.sin_addr.s_addr = 0;
2018	  ms->local.addr.in4.sin_port = htons (port);
2019
2020	  /*
2021	   * Run management over tunnel, or
2022	   * separate channel?
2023	   */
2024	  if (streq (addr, "tunnel") && !(flags & MF_CONNECT_AS_CLIENT))
2025	    {
2026	      ms->management_over_tunnel = true;
2027	    }
2028	  else
2029	    {
2030	      ms->local.addr.in4.sin_addr.s_addr = getaddr
2031		(GETADDR_RESOLVE|GETADDR_WARN_ON_SIGNAL|GETADDR_FATAL, addr, 0, NULL, NULL);
2032	    }
2033	}
2034
2035      /*
2036       * Log history and echo buffer may need to be resized
2037       */
2038      ms->log_history_cache = log_history_cache;
2039      ms->echo_buffer_size = echo_buffer_size;
2040      ms->state_buffer_size = state_buffer_size;
2041
2042      /*
2043       * Set remap sigusr1 flags
2044       */
2045      if (remap_sigusr1 == SIGHUP)
2046	ms->mansig |= MANSIG_MAP_USR1_TO_HUP;
2047      else if (remap_sigusr1 == SIGTERM)
2048	ms->mansig |= MANSIG_MAP_USR1_TO_TERM;
2049
2050      ms->defined = true;
2051    }
2052}
2053
2054static void
2055man_settings_close (struct man_settings *ms)
2056{
2057  free (ms->write_peer_info_file);
2058  CLEAR (*ms);
2059}
2060
2061
2062static void
2063man_connection_init (struct management *man)
2064{
2065  if (man->connection.state == MS_INITIAL)
2066    {
2067#ifdef WIN32
2068      /*
2069       * This object is a sort of TCP/IP helper
2070       * for Windows.
2071       */
2072      net_event_win32_init (&man->connection.ne32);
2073#endif
2074
2075      /*
2076       * Allocate helper objects for command line input and
2077       * command output from/to the socket.
2078       */
2079      man->connection.in = command_line_new (1024);
2080      man->connection.out = buffer_list_new (0);
2081
2082      /*
2083       * Initialize event set for standalone usage, when we are
2084       * running outside of the primary event loop.
2085       */
2086      {
2087	int maxevents = 1;
2088	man->connection.es = event_set_init (&maxevents, EVENT_METHOD_FAST);
2089      }
2090
2091      /*
2092       * Listen/connect socket
2093       */
2094      if (man->settings.flags & MF_CONNECT_AS_CLIENT)
2095	man_connect (man);
2096      else
2097	man_listen (man);
2098    }
2099}
2100
2101static void
2102man_connection_close (struct management *man)
2103{
2104  struct man_connection *mc = &man->connection;
2105
2106  if (mc->es)
2107    event_free (mc->es);
2108#ifdef WIN32
2109  net_event_win32_close (&mc->ne32);
2110#endif
2111  if (socket_defined (mc->sd_top))
2112    {
2113      man_close_socket (man, mc->sd_top);
2114      man_delete_unix_socket (man);
2115    }
2116  if (socket_defined (mc->sd_cli))
2117    man_close_socket (man, mc->sd_cli);
2118  if (mc->in)
2119    command_line_free (mc->in);
2120  if (mc->out)
2121    buffer_list_free (mc->out);
2122#ifdef MANAGEMENT_IN_EXTRA
2123  in_extra_reset (&man->connection, IER_RESET);
2124#endif
2125#ifdef MANAGMENT_EXTERNAL_KEY
2126  buffer_list_free (mc->ext_key_input);
2127#endif
2128  man_connection_clear (mc);
2129}
2130
2131struct management *
2132management_init (void)
2133{
2134  struct management *man;
2135  ALLOC_OBJ_CLEAR (man, struct management);
2136
2137  man_persist_init (man,
2138		    MANAGEMENT_LOG_HISTORY_INITIAL_SIZE,
2139		    MANAGEMENT_ECHO_BUFFER_SIZE,
2140		    MANAGEMENT_STATE_BUFFER_SIZE);
2141
2142  man_connection_clear (&man->connection);
2143
2144  return man;
2145}
2146
2147bool
2148management_open (struct management *man,
2149		 const char *addr,
2150		 const int port,
2151		 const char *pass_file,
2152		 const char *client_user,
2153		 const char *client_group,
2154		 const int log_history_cache,
2155		 const int echo_buffer_size,
2156		 const int state_buffer_size,
2157		 const char *write_peer_info_file,
2158		 const int remap_sigusr1,
2159		 const unsigned int flags)
2160{
2161  bool ret = false;
2162
2163  /*
2164   * Save the settings only if they have not
2165   * been saved before.
2166   */
2167  man_settings_init (&man->settings,
2168		     addr,
2169		     port,
2170		     pass_file,
2171		     client_user,
2172		     client_group,
2173		     log_history_cache,
2174		     echo_buffer_size,
2175		     state_buffer_size,
2176		     write_peer_info_file,
2177		     remap_sigusr1,
2178		     flags);
2179
2180  /*
2181   * The log is initially sized to MANAGEMENT_LOG_HISTORY_INITIAL_SIZE,
2182   * but may be changed here.  Ditto for echo and state buffers.
2183   */
2184  log_history_resize (man->persist.log, man->settings.log_history_cache);
2185  log_history_resize (man->persist.echo, man->settings.echo_buffer_size);
2186  log_history_resize (man->persist.state, man->settings.state_buffer_size);
2187
2188  /*
2189   * If connection object is uninitialized and we are not doing
2190   * over-the-tunnel management, then open (listening) connection.
2191   */
2192  if (man->connection.state == MS_INITIAL)
2193    {
2194      if (!man->settings.management_over_tunnel)
2195	{
2196	  man_connection_init (man);
2197	  ret = true;
2198	}
2199    }
2200
2201  return ret;
2202}
2203
2204void
2205management_close (struct management *man)
2206{
2207  man_output_list_push_finalize (man);  /* flush output queue */
2208  man_connection_close (man);
2209  man_settings_close (&man->settings);
2210  man_persist_close (&man->persist);
2211  free (man);
2212}
2213
2214void
2215management_set_callback (struct management *man,
2216			 const struct management_callback *cb)
2217{
2218  man->persist.standalone_disabled = true;
2219  man->persist.callback = *cb;
2220}
2221
2222void
2223management_clear_callback (struct management *man)
2224{
2225  man->persist.standalone_disabled = false;
2226  man->persist.hold_release = false;
2227  CLEAR (man->persist.callback);
2228  man_output_list_push_finalize (man); /* flush output queue */
2229}
2230
2231void
2232management_set_state (struct management *man,
2233		      const int state,
2234		      const char *detail,
2235		      const in_addr_t tun_local_ip,
2236		      const in_addr_t tun_remote_ip)
2237{
2238  if (man->persist.state && (!(man->settings.flags & MF_SERVER) || state < OPENVPN_STATE_CLIENT_BASE))
2239    {
2240      struct gc_arena gc = gc_new ();
2241      struct log_entry e;
2242      const char *out = NULL;
2243
2244      update_time ();
2245      CLEAR (e);
2246      e.timestamp = now;
2247      e.u.state = state;
2248      e.string = detail;
2249      e.local_ip = tun_local_ip;
2250      e.remote_ip = tun_remote_ip;
2251
2252      log_history_add (man->persist.state, &e);
2253
2254      if (man->connection.state_realtime)
2255	out = log_entry_print (&e, LOG_PRINT_STATE_PREFIX
2256			       |   LOG_PRINT_INT_DATE
2257                               |   LOG_PRINT_STATE
2258			       |   LOG_PRINT_LOCAL_IP
2259			       |   LOG_PRINT_REMOTE_IP
2260                               |   LOG_PRINT_CRLF
2261			       |   LOG_ECHO_TO_LOG, &gc);
2262
2263      if (out)
2264	man_output_list_push (man, out);
2265
2266      gc_free (&gc);
2267    }
2268}
2269
2270static bool
2271env_filter_match (const char *env_str, const int env_filter_level)
2272{
2273  static const char *env_names[] = {
2274    "username=",
2275    "password=",
2276    "X509_0_CN=",
2277    "tls_serial_",
2278    "untrusted_ip=",
2279    "ifconfig_local=",
2280    "ifconfig_netmask=",
2281    "daemon_start_time=",
2282    "daemon_pid=",
2283    "dev=",
2284    "ifconfig_pool_remote_ip=",
2285    "ifconfig_pool_netmask=",
2286    "time_duration=",
2287    "bytes_sent=",
2288    "bytes_received="
2289  };
2290
2291  if (env_filter_level == 0)
2292    return true;
2293  else if (env_filter_level <= 1 && !strncmp(env_str, "X509_", 5))
2294    return true;
2295  else if (env_filter_level <= 2)
2296    {
2297      size_t i;
2298      for (i = 0; i < SIZE(env_names); ++i)
2299	{
2300	  const char *en = env_names[i];
2301	  const size_t len = strlen(en);
2302	  if (!strncmp(env_str, en, len))
2303	    return true;
2304	}
2305      return false;
2306    }
2307  return false;
2308}
2309
2310static void
2311man_output_env (const struct env_set *es, const bool tail, const int env_filter_level, const char *prefix)
2312{
2313  if (es)
2314    {
2315      struct env_item *e;
2316      for (e = es->list; e != NULL; e = e->next)
2317	{
2318	  if (e->string && (!env_filter_level || env_filter_match(e->string, env_filter_level)))
2319	    msg (M_CLIENT, ">%s:ENV,%s", prefix, e->string);
2320	}
2321    }
2322  if (tail)
2323    msg (M_CLIENT, ">%s:ENV,END", prefix);
2324}
2325
2326static void
2327man_output_extra_env (struct management *man, const char *prefix)
2328{
2329  struct gc_arena gc = gc_new ();
2330  struct env_set *es = env_set_create (&gc);
2331  if (man->persist.callback.n_clients)
2332    {
2333      const int nclients = (*man->persist.callback.n_clients) (man->persist.callback.arg);
2334      setenv_int (es, "n_clients", nclients);
2335    }
2336  man_output_env (es, false, man->connection.env_filter_level, prefix);
2337  gc_free (&gc);
2338}
2339
2340void
2341management_up_down(struct management *man, const char *updown, const struct env_set *es)
2342{
2343  if (man->settings.flags & MF_UP_DOWN)
2344    {
2345      msg (M_CLIENT, ">UPDOWN:%s", updown);
2346      man_output_env (es, true, 0, "UPDOWN");
2347    }
2348}
2349
2350void
2351management_notify(struct management *man, const char *severity, const char *type, const char *text)
2352{
2353  msg (M_CLIENT, ">NOTIFY:%s,%s,%s", severity, type, text);
2354}
2355
2356void
2357management_notify_generic (struct management *man, const char *str)
2358{
2359  msg (M_CLIENT, "%s", str);
2360}
2361
2362#ifdef MANAGEMENT_DEF_AUTH
2363
2364static bool
2365validate_peer_info_line(const char *line)
2366{
2367  uint8_t c;
2368  int state = 0;
2369  while ((c=*line++))
2370    {
2371      switch (state)
2372	{
2373	case 0:
2374	case 1:
2375	  if (c == '=' && state == 1)
2376	    state = 2;
2377	  else if (isalnum(c) || c == '_')
2378	    state = 1;
2379	  else
2380	    return false;
2381	case 2:
2382	  if (isprint(c))
2383	    ;
2384	  else
2385	    return false;
2386	}
2387    }
2388  return (state == 2);
2389}
2390
2391static void
2392man_output_peer_info_env (struct management *man, struct man_def_auth_context *mdac)
2393{
2394  char line[256];
2395  if (man->persist.callback.get_peer_info)
2396    {
2397      const char *peer_info = (*man->persist.callback.get_peer_info) (man->persist.callback.arg, mdac->cid);
2398      if (peer_info)
2399	{
2400	  struct buffer buf;
2401	  buf_set_read (&buf, (const uint8_t *) peer_info, strlen(peer_info));
2402	  while (buf_parse (&buf, '\n', line, sizeof (line)))
2403	    {
2404	      chomp (line);
2405	      if (validate_peer_info_line(line))
2406		{
2407		  msg (M_CLIENT, ">CLIENT:ENV,%s", line);
2408		}
2409	      else
2410		msg (D_MANAGEMENT, "validation failed on peer_info line received from client");
2411	    }
2412	}
2413    }
2414}
2415
2416void
2417management_notify_client_needing_auth (struct management *management,
2418				       const unsigned int mda_key_id,
2419				       struct man_def_auth_context *mdac,
2420				       const struct env_set *es)
2421{
2422  if (!(mdac->flags & DAF_CONNECTION_CLOSED))
2423    {
2424      const char *mode = "CONNECT";
2425      if (mdac->flags & DAF_CONNECTION_ESTABLISHED)
2426	mode = "REAUTH";
2427      msg (M_CLIENT, ">CLIENT:%s,%lu,%u", mode, mdac->cid, mda_key_id);
2428      man_output_extra_env (management, "CLIENT");
2429      man_output_peer_info_env(management, mdac);
2430      man_output_env (es, true, management->connection.env_filter_level, "CLIENT");
2431      mdac->flags |= DAF_INITIAL_AUTH;
2432    }
2433}
2434
2435void
2436management_connection_established (struct management *management,
2437				   struct man_def_auth_context *mdac,
2438				   const struct env_set *es)
2439{
2440  mdac->flags |= DAF_CONNECTION_ESTABLISHED;
2441  msg (M_CLIENT, ">CLIENT:ESTABLISHED,%lu", mdac->cid);
2442  man_output_extra_env (management, "CLIENT");
2443  man_output_env (es, true, management->connection.env_filter_level, "CLIENT");
2444}
2445
2446void
2447management_notify_client_close (struct management *management,
2448				struct man_def_auth_context *mdac,
2449				const struct env_set *es)
2450{
2451  if ((mdac->flags & DAF_INITIAL_AUTH) && !(mdac->flags & DAF_CONNECTION_CLOSED))
2452    {
2453      msg (M_CLIENT, ">CLIENT:DISCONNECT,%lu", mdac->cid);
2454      man_output_env (es, true, management->connection.env_filter_level, "CLIENT");
2455      mdac->flags |= DAF_CONNECTION_CLOSED;
2456    }
2457}
2458
2459void
2460management_learn_addr (struct management *management,
2461		       struct man_def_auth_context *mdac,
2462		       const struct mroute_addr *addr,
2463		       const bool primary)
2464{
2465  struct gc_arena gc = gc_new ();
2466  if ((mdac->flags & DAF_INITIAL_AUTH) && !(mdac->flags & DAF_CONNECTION_CLOSED))
2467    {
2468      msg (M_CLIENT, ">CLIENT:ADDRESS,%lu,%s,%d",
2469	   mdac->cid,
2470	   mroute_addr_print_ex (addr, MAPF_SUBNET, &gc),
2471	   BOOL_CAST (primary));
2472    }
2473  gc_free (&gc);
2474}
2475
2476#endif /* MANAGEMENT_DEF_AUTH */
2477
2478void
2479management_echo (struct management *man, const char *string, const bool pull)
2480{
2481  if (man->persist.echo)
2482    {
2483      struct gc_arena gc = gc_new ();
2484      struct log_entry e;
2485      const char *out = NULL;
2486
2487      update_time ();
2488      CLEAR (e);
2489      e.timestamp = now;
2490      e.string = string;
2491      e.u.intval = BOOL_CAST (pull);
2492
2493      log_history_add (man->persist.echo, &e);
2494
2495      if (man->connection.echo_realtime)
2496	out = log_entry_print (&e, LOG_PRINT_INT_DATE|LOG_PRINT_ECHO_PREFIX|LOG_PRINT_CRLF|MANAGEMENT_ECHO_FLAGS, &gc);
2497
2498      if (out)
2499	man_output_list_push (man, out);
2500
2501      gc_free (&gc);
2502    }
2503}
2504
2505void
2506management_post_tunnel_open (struct management *man, const in_addr_t tun_local_ip)
2507{
2508  /*
2509   * If we are running management over the tunnel,
2510   * this is the place to initialize the connection.
2511   */
2512  if (man->settings.management_over_tunnel
2513      && man->connection.state == MS_INITIAL)
2514    {
2515      /* listen on our local TUN/TAP IP address */
2516      man->settings.local.addr.in4.sin_addr.s_addr = htonl (tun_local_ip);
2517      man_connection_init (man);
2518    }
2519
2520}
2521
2522void
2523management_pre_tunnel_close (struct management *man)
2524{
2525  if (man->settings.management_over_tunnel)
2526    man_connection_close (man);
2527}
2528
2529void
2530management_auth_failure (struct management *man, const char *type, const char *reason)
2531{
2532  if (reason)
2533    msg (M_CLIENT, ">PASSWORD:Verification Failed: '%s' ['%s']", type, reason);
2534  else
2535    msg (M_CLIENT, ">PASSWORD:Verification Failed: '%s'", type);
2536}
2537
2538void
2539management_auth_token (struct management *man, const char *token)
2540{
2541  msg (M_CLIENT, ">PASSWORD:Auth-Token:%s", token);
2542}
2543
2544static inline bool
2545man_persist_state (unsigned int *persistent, const int n)
2546{
2547  if (persistent)
2548    {
2549      if (*persistent == (unsigned int)n)
2550	return false;
2551      *persistent = n;
2552    }
2553  return true;
2554}
2555
2556#ifdef WIN32
2557
2558void
2559management_socket_set (struct management *man,
2560		       struct event_set *es,
2561		       void *arg,
2562		       unsigned int *persistent)
2563{
2564  if (man->connection.state != MS_INITIAL)
2565    {
2566      event_t ev = net_event_win32_get_event (&man->connection.ne32);
2567      net_event_win32_reset_write (&man->connection.ne32);
2568
2569      switch (man->connection.state)
2570	{
2571	case MS_LISTEN:
2572	  if (man_persist_state (persistent, 1))
2573	    event_ctl (es, ev, EVENT_READ, arg);
2574	  break;
2575	case MS_CC_WAIT_READ:
2576	  if (man_persist_state (persistent, 2))
2577	    event_ctl (es, ev, EVENT_READ, arg);
2578	  break;
2579	case MS_CC_WAIT_WRITE:
2580	  if (man_persist_state (persistent, 3))
2581	    event_ctl (es, ev, EVENT_READ|EVENT_WRITE, arg);
2582	  break;
2583	default:
2584	  ASSERT (0);
2585	}
2586    }
2587}
2588
2589void
2590management_io (struct management *man)
2591{
2592  if (man->connection.state != MS_INITIAL)
2593    {
2594      long net_events;
2595      net_event_win32_reset (&man->connection.ne32);
2596      net_events = net_event_win32_get_event_mask (&man->connection.ne32);
2597
2598      if (net_events & FD_CLOSE)
2599	{
2600	  man_reset_client_socket (man, false);
2601	}
2602      else
2603	{
2604	  if (man->connection.state == MS_LISTEN)
2605	    {
2606	      if (net_events & FD_ACCEPT)
2607		{
2608		  man_accept (man);
2609		  net_event_win32_clear_selected_events (&man->connection.ne32, FD_ACCEPT);
2610		}
2611	    }
2612	  else if (man->connection.state == MS_CC_WAIT_READ || man->connection.state == MS_CC_WAIT_WRITE)
2613	    {
2614	      if (net_events & FD_READ)
2615		{
2616		  while (man_read (man) > 0)
2617		    ;
2618		  net_event_win32_clear_selected_events (&man->connection.ne32, FD_READ);
2619		}
2620
2621	      if (net_events & FD_WRITE)
2622		{
2623		  int status;
2624		  status = man_write (man);
2625		  if (status < 0 && WSAGetLastError() == WSAEWOULDBLOCK)
2626		    {
2627		      net_event_win32_clear_selected_events (&man->connection.ne32, FD_WRITE);
2628		    }
2629		}
2630	    }
2631	}
2632    }
2633}
2634
2635#else
2636
2637void
2638management_socket_set (struct management *man,
2639		       struct event_set *es,
2640		       void *arg,
2641		       unsigned int *persistent)
2642{
2643  switch (man->connection.state)
2644    {
2645    case MS_LISTEN:
2646      if (man_persist_state (persistent, 1))
2647	event_ctl (es, man->connection.sd_top, EVENT_READ, arg);
2648      break;
2649    case MS_CC_WAIT_READ:
2650      if (man_persist_state (persistent, 2))
2651	event_ctl (es, man->connection.sd_cli, EVENT_READ, arg);
2652      break;
2653    case MS_CC_WAIT_WRITE:
2654      if (man_persist_state (persistent, 3))
2655	event_ctl (es, man->connection.sd_cli, EVENT_WRITE, arg);
2656      break;
2657    case MS_INITIAL:
2658      break;
2659    default:
2660      ASSERT (0);
2661    }
2662}
2663
2664void
2665management_io (struct management *man)
2666{
2667  switch (man->connection.state)
2668    {
2669    case MS_LISTEN:
2670      man_accept (man);
2671      break;
2672    case MS_CC_WAIT_READ:
2673      man_read (man);
2674      break;
2675    case MS_CC_WAIT_WRITE:
2676      man_write (man);
2677      break;
2678    case MS_INITIAL:
2679      break;
2680    default:
2681      ASSERT (0);
2682    }
2683}
2684
2685#endif
2686
2687static inline bool
2688man_standalone_ok (const struct management *man)
2689{
2690  return !man->settings.management_over_tunnel && man->connection.state != MS_INITIAL;
2691}
2692
2693static bool
2694man_check_for_signals (volatile int *signal_received)
2695{
2696  if (signal_received)
2697    {
2698      get_signal (signal_received);
2699      if (*signal_received)
2700	return true;
2701    }
2702  return false;
2703}
2704
2705/*
2706 * Wait for socket I/O when outside primary event loop
2707 */
2708static int
2709man_block (struct management *man, volatile int *signal_received, const time_t expire)
2710{
2711  struct timeval tv;
2712  struct event_set_return esr;
2713  int status = -1;
2714
2715  if (man_standalone_ok (man))
2716    {
2717      while (true)
2718	{
2719	  event_reset (man->connection.es);
2720	  management_socket_set (man, man->connection.es, NULL, NULL);
2721	  tv.tv_usec = 0;
2722	  tv.tv_sec = 1;
2723	  if (man_check_for_signals (signal_received))
2724	    {
2725	      status = -1;
2726	      break;
2727	    }
2728	  status = event_wait (man->connection.es, &tv, &esr, 1);
2729	  update_time ();
2730	  if (man_check_for_signals (signal_received))
2731	    {
2732	      status = -1;
2733	      break;
2734	    }
2735
2736	  if (status > 0)
2737	    break;
2738	  else if (expire && now >= expire)
2739	    {
2740	      /* set SIGINT signal if expiration time exceeded */
2741	      status = 0;
2742	      if (signal_received)
2743		*signal_received = SIGINT;
2744	      break;
2745	    }
2746	}
2747    }
2748  return status;
2749}
2750
2751/*
2752 * Perform management socket output outside primary event loop
2753 */
2754static void
2755man_output_standalone (struct management *man, volatile int *signal_received)
2756{
2757  if (man_standalone_ok (man))
2758    {
2759      while (man->connection.state == MS_CC_WAIT_WRITE)
2760	{
2761	  management_io (man);
2762	  if (man->connection.state == MS_CC_WAIT_WRITE)
2763	    man_block (man, signal_received, 0);
2764	  if (signal_received && *signal_received)
2765	    break;
2766	}
2767    }
2768}
2769
2770/*
2771 * Process management event loop outside primary event loop
2772 */
2773static int
2774man_standalone_event_loop (struct management *man, volatile int *signal_received, const time_t expire)
2775{
2776  int status = -1;
2777  if (man_standalone_ok (man))
2778    {
2779      status = man_block (man, signal_received, expire);
2780      if (status > 0)
2781	management_io (man);
2782    }
2783  return status;
2784}
2785
2786#define MWCC_PASSWORD_WAIT (1<<0)
2787#define MWCC_HOLD_WAIT     (1<<1)
2788#define MWCC_OTHER_WAIT    (1<<2)
2789
2790/*
2791 * Block until client connects
2792 */
2793static void
2794man_wait_for_client_connection (struct management *man,
2795				volatile int *signal_received,
2796				const time_t expire,
2797				unsigned int flags)
2798{
2799  ASSERT (man_standalone_ok (man));
2800  if (man->connection.state == MS_LISTEN)
2801    {
2802      if (flags & MWCC_PASSWORD_WAIT)
2803	msg (D_MANAGEMENT, "Need password(s) from management interface, waiting...");
2804      if (flags & MWCC_HOLD_WAIT)
2805	msg (D_MANAGEMENT, "Need hold release from management interface, waiting...");
2806      if (flags & MWCC_OTHER_WAIT)
2807	msg (D_MANAGEMENT, "Need information from management interface, waiting...");
2808      do {
2809	man_standalone_event_loop (man, signal_received, expire);
2810	if (signal_received && *signal_received)
2811	  break;
2812      } while (man->connection.state == MS_LISTEN || man_password_needed (man));
2813    }
2814}
2815
2816/*
2817 * Process the management event loop for sec seconds
2818 */
2819void
2820management_event_loop_n_seconds (struct management *man, int sec)
2821{
2822  if (man_standalone_ok (man))
2823    {
2824      volatile int signal_received = 0;
2825      const bool standalone_disabled_save = man->persist.standalone_disabled;
2826      time_t expire = 0;
2827
2828      man->persist.standalone_disabled = false; /* This is so M_CLIENT messages will be correctly passed through msg() */
2829
2830      /* set expire time */
2831      update_time ();
2832      if (sec)
2833	expire = now + sec;
2834
2835      /* if no client connection, wait for one */
2836      man_wait_for_client_connection (man, &signal_received, expire, 0);
2837      if (signal_received)
2838	return;
2839
2840      /* run command processing event loop */
2841      do
2842	{
2843	  man_standalone_event_loop (man, &signal_received, expire);
2844	  if (!signal_received)
2845	    man_check_for_signals (&signal_received);
2846	  if (signal_received)
2847	    return;
2848	} while (expire);
2849
2850      /* revert state */
2851      man->persist.standalone_disabled = standalone_disabled_save;
2852    }
2853  else
2854    {
2855      sleep (sec);
2856    }
2857}
2858
2859/*
2860 * Get a username/password from management channel in standalone mode.
2861 */
2862bool
2863management_query_user_pass (struct management *man,
2864			    struct user_pass *up,
2865			    const char *type,
2866			    const unsigned int flags,
2867			    const char *static_challenge)
2868{
2869  struct gc_arena gc = gc_new ();
2870  bool ret = false;
2871
2872  if (man_standalone_ok (man))
2873    {
2874      volatile int signal_received = 0;
2875      const bool standalone_disabled_save = man->persist.standalone_disabled;
2876      struct buffer alert_msg = alloc_buf_gc (128, &gc);
2877      const char *alert_type = NULL;
2878      const char *prefix = NULL;
2879      unsigned int up_query_mode = 0;
2880#ifdef ENABLE_CLIENT_CR
2881      const char *sc = NULL;
2882#endif
2883      ret = true;
2884      man->persist.standalone_disabled = false; /* This is so M_CLIENT messages will be correctly passed through msg() */
2885      man->persist.special_state_msg = NULL;
2886
2887      CLEAR (man->connection.up_query);
2888
2889      if (flags & GET_USER_PASS_NEED_OK)
2890	{
2891	  up_query_mode = UP_QUERY_NEED_OK;
2892	  prefix= "NEED-OK";
2893	  alert_type = "confirmation";
2894	}
2895      else if (flags & GET_USER_PASS_NEED_STR)
2896        {
2897	  up_query_mode = UP_QUERY_NEED_STR;
2898	  prefix= "NEED-STR";
2899	  alert_type = "string";
2900	}
2901      else if (flags & GET_USER_PASS_PASSWORD_ONLY)
2902	{
2903	  up_query_mode = UP_QUERY_PASS;
2904	  prefix = "PASSWORD";
2905	  alert_type = "password";
2906	}
2907      else
2908	{
2909	  up_query_mode = UP_QUERY_USER_PASS;
2910	  prefix = "PASSWORD";
2911	  alert_type = "username/password";
2912#ifdef ENABLE_CLIENT_CR
2913	  if (static_challenge)
2914	    sc = static_challenge;
2915#endif
2916	}
2917      buf_printf (&alert_msg, ">%s:Need '%s' %s",
2918		  prefix,
2919		  type,
2920		  alert_type);
2921
2922      if (flags & (GET_USER_PASS_NEED_OK | GET_USER_PASS_NEED_STR))
2923	buf_printf (&alert_msg, " MSG:%s", up->username);
2924
2925#ifdef ENABLE_CLIENT_CR
2926      if (sc)
2927	buf_printf (&alert_msg, " SC:%d,%s",
2928		    BOOL_CAST(flags & GET_USER_PASS_STATIC_CHALLENGE_ECHO),
2929		    sc);
2930#endif
2931
2932      man_wait_for_client_connection (man, &signal_received, 0, MWCC_PASSWORD_WAIT);
2933      if (signal_received)
2934	ret = false;
2935
2936      if (ret)
2937	{
2938	  man->persist.special_state_msg = BSTR (&alert_msg);
2939	  msg (M_CLIENT, "%s", man->persist.special_state_msg);
2940
2941	  /* tell command line parser which info we need */
2942	  man->connection.up_query_mode = up_query_mode;
2943	  man->connection.up_query_type = type;
2944
2945	  /* run command processing event loop until we get our username/password/response */
2946	  do
2947	    {
2948	      man_standalone_event_loop (man, &signal_received, 0);
2949	      if (!signal_received)
2950		man_check_for_signals (&signal_received);
2951	      if (signal_received)
2952		{
2953		  ret = false;
2954		  break;
2955		}
2956	    } while (!man->connection.up_query.defined);
2957	}
2958
2959      /* revert state */
2960      man->connection.up_query_mode = UP_QUERY_DISABLED;
2961      man->connection.up_query_type = NULL;
2962      man->persist.standalone_disabled = standalone_disabled_save;
2963      man->persist.special_state_msg = NULL;
2964
2965      /* pass through blank passwords */
2966      if (!strcmp (man->connection.up_query.password, blank_up))
2967	CLEAR (man->connection.up_query.password);
2968
2969      /*
2970       * Transfer u/p to return object, zero any record
2971       * we hold in the management object.
2972       */
2973      if (ret)
2974	{
2975	  man->connection.up_query.nocache = up->nocache; /* preserve caller's nocache setting */
2976	  *up = man->connection.up_query;
2977	}
2978      CLEAR (man->connection.up_query);
2979    }
2980
2981  gc_free (&gc);
2982  return ret;
2983}
2984
2985#ifdef MANAGMENT_EXTERNAL_KEY
2986
2987char * /* returns allocated base64 signature */
2988management_query_rsa_sig (struct management *man,
2989			  const char *b64_data)
2990{
2991  struct gc_arena gc = gc_new ();
2992  char *ret = NULL;
2993  volatile int signal_received = 0;
2994  struct buffer alert_msg = clear_buf();
2995  struct buffer *buf;
2996  const bool standalone_disabled_save = man->persist.standalone_disabled;
2997  struct man_connection *mc = &man->connection;
2998
2999  if (man_standalone_ok (man))
3000    {
3001      man->persist.standalone_disabled = false; /* This is so M_CLIENT messages will be correctly passed through msg() */
3002      man->persist.special_state_msg = NULL;
3003
3004      mc->ext_key_state = EKS_SOLICIT;
3005
3006      alert_msg = alloc_buf_gc (strlen(b64_data)+64, &gc);
3007      buf_printf (&alert_msg, ">RSA_SIGN:%s", b64_data);
3008
3009      man_wait_for_client_connection (man, &signal_received, 0, MWCC_OTHER_WAIT);
3010
3011      if (signal_received)
3012	goto done;
3013
3014      man->persist.special_state_msg = BSTR (&alert_msg);
3015      msg (M_CLIENT, "%s", man->persist.special_state_msg);
3016
3017      /* run command processing event loop until we get our signature */
3018      do
3019	{
3020	  man_standalone_event_loop (man, &signal_received, 0);
3021	  if (!signal_received)
3022	    man_check_for_signals (&signal_received);
3023	  if (signal_received)
3024	    goto done;
3025	} while (mc->ext_key_state != EKS_READY);
3026
3027      if (buffer_list_defined(mc->ext_key_input))
3028	{
3029	  buffer_list_aggregate (mc->ext_key_input, 2048);
3030	  buf = buffer_list_peek (mc->ext_key_input);
3031	  if (buf && BLEN(buf) > 0)
3032	    {
3033	      ret = (char *) malloc(BLEN(buf)+1);
3034	      check_malloc_return(ret);
3035	      memcpy(ret, buf->data, BLEN(buf));
3036	      ret[BLEN(buf)] = '\0';
3037	    }
3038	}
3039    }
3040
3041 done:
3042  if (mc->ext_key_state == EKS_READY && ret)
3043    msg (M_CLIENT, "SUCCESS: rsa-sig command succeeded");
3044  else if (mc->ext_key_state == EKS_INPUT || mc->ext_key_state == EKS_READY)
3045    msg (M_CLIENT, "ERROR: rsa-sig command failed");
3046
3047  /* revert state */
3048  man->persist.standalone_disabled = standalone_disabled_save;
3049  man->persist.special_state_msg = NULL;
3050  in_extra_reset (mc, IER_RESET);
3051  mc->ext_key_state = EKS_UNDEF;
3052  buffer_list_free (mc->ext_key_input);
3053  mc->ext_key_input = NULL;
3054
3055  gc_free (&gc);
3056  return ret;
3057}
3058
3059#endif
3060
3061/*
3062 * Return true if management_hold() would block
3063 */
3064bool
3065management_would_hold (struct management *man)
3066{
3067  return (man->settings.flags & MF_HOLD) && !man->persist.hold_release && man_standalone_ok (man);
3068}
3069
3070/*
3071 * Return true if (from the management interface's perspective) OpenVPN should
3072 * daemonize.
3073 */
3074bool
3075management_should_daemonize (struct management *man)
3076{
3077  return management_would_hold (man) || (man->settings.flags & MF_QUERY_PASSWORDS);
3078}
3079
3080/*
3081 * If the hold flag is enabled, hibernate until a management client releases the hold.
3082 * Return true if the caller should not sleep for an additional time interval.
3083 */
3084bool
3085management_hold (struct management *man)
3086{
3087  if (management_would_hold (man))
3088    {
3089      volatile int signal_received = 0;
3090      const bool standalone_disabled_save = man->persist.standalone_disabled;
3091
3092      man->persist.standalone_disabled = false; /* This is so M_CLIENT messages will be correctly passed through msg() */
3093      man->persist.special_state_msg = NULL;
3094      man->settings.mansig |= MANSIG_IGNORE_USR1_HUP;
3095
3096      man_wait_for_client_connection (man, &signal_received, 0, MWCC_HOLD_WAIT);
3097
3098      if (!signal_received)
3099	{
3100	  man->persist.special_state_msg = ">HOLD:Waiting for hold release";
3101	  msg (M_CLIENT, "%s", man->persist.special_state_msg);
3102
3103	  /* run command processing event loop until we get our username/password */
3104	  do
3105	    {
3106	      man_standalone_event_loop (man, &signal_received, 0);
3107	      if (!signal_received)
3108		man_check_for_signals (&signal_received);
3109	      if (signal_received)
3110		break;
3111	    } while (!man->persist.hold_release);
3112	}
3113
3114      /* revert state */
3115      man->persist.standalone_disabled = standalone_disabled_save;
3116      man->persist.special_state_msg = NULL;
3117      man->settings.mansig &= ~MANSIG_IGNORE_USR1_HUP;
3118
3119      return true;
3120    }
3121  return false;
3122}
3123
3124/*
3125 * struct command_line
3126 */
3127
3128struct command_line *
3129command_line_new (const int buf_len)
3130{
3131  struct command_line *cl;
3132  ALLOC_OBJ_CLEAR (cl, struct command_line);
3133  cl->buf = alloc_buf (buf_len);
3134  cl->residual = alloc_buf (buf_len);
3135  return cl;
3136}
3137
3138void
3139command_line_reset (struct command_line *cl)
3140{
3141  buf_clear (&cl->buf);
3142  buf_clear (&cl->residual);
3143}
3144
3145void
3146command_line_free (struct command_line *cl)
3147{
3148  command_line_reset (cl);
3149  free_buf (&cl->buf);
3150  free_buf (&cl->residual);
3151  free (cl);
3152}
3153
3154void
3155command_line_add (struct command_line *cl, const unsigned char *buf, const int len)
3156{
3157  int i;
3158  for (i = 0; i < len; ++i)
3159    {
3160      if (buf[i] && char_class(buf[i], (CC_PRINT|CC_NEWLINE)))
3161	{
3162	  if (!buf_write_u8 (&cl->buf, buf[i]))
3163	    buf_clear (&cl->buf);
3164	}
3165    }
3166}
3167
3168const unsigned char *
3169command_line_get (struct command_line *cl)
3170{
3171  int i;
3172  const unsigned char *ret = NULL;
3173
3174  i = buf_substring_len (&cl->buf, '\n');
3175  if (i >= 0)
3176    {
3177      buf_copy_excess (&cl->residual, &cl->buf, i);
3178      buf_chomp (&cl->buf);
3179      ret = (const unsigned char *) BSTR (&cl->buf);
3180    }
3181  return ret;
3182}
3183
3184void
3185command_line_next (struct command_line *cl)
3186{
3187  buf_clear (&cl->buf);
3188  buf_copy (&cl->buf, &cl->residual);
3189  buf_clear (&cl->residual);
3190}
3191
3192/*
3193 * struct log_entry
3194 */
3195
3196const char *
3197log_entry_print (const struct log_entry *e, unsigned int flags, struct gc_arena *gc)
3198{
3199  struct buffer out = alloc_buf_gc (ERR_BUF_SIZE, gc);
3200  if (flags & LOG_FATAL_NOTIFY)
3201    buf_printf (&out, ">FATAL:");
3202  if (flags & LOG_PRINT_LOG_PREFIX)
3203    buf_printf (&out, ">LOG:");
3204  if (flags & LOG_PRINT_ECHO_PREFIX)
3205    buf_printf (&out, ">ECHO:");
3206  if (flags & LOG_PRINT_STATE_PREFIX)
3207    buf_printf (&out, ">STATE:");
3208  if (flags & LOG_PRINT_INT_DATE)
3209    buf_printf (&out, "%u,", (unsigned int)e->timestamp);
3210  if (flags & LOG_PRINT_MSG_FLAGS)
3211    buf_printf (&out, "%s,", msg_flags_string (e->u.msg_flags, gc));
3212  if (flags & LOG_PRINT_STATE)
3213    buf_printf (&out, "%s,", man_state_name (e->u.state));
3214  if (flags & LOG_PRINT_INTVAL)
3215    buf_printf (&out, "%d,", e->u.intval);
3216  if (e->string)
3217    buf_printf (&out, "%s", e->string);
3218  if (flags & LOG_PRINT_LOCAL_IP)
3219    buf_printf (&out, ",%s", print_in_addr_t (e->local_ip, IA_EMPTY_IF_UNDEF, gc));
3220  if (flags & LOG_PRINT_REMOTE_IP)
3221    buf_printf (&out, ",%s", print_in_addr_t (e->remote_ip, IA_EMPTY_IF_UNDEF, gc));
3222  if (flags & LOG_ECHO_TO_LOG)
3223    msg (D_MANAGEMENT, "MANAGEMENT: %s", BSTR (&out));
3224  if (flags & LOG_PRINT_CRLF)
3225    buf_printf (&out, "\r\n");
3226  return BSTR (&out);
3227}
3228
3229static void
3230log_entry_free_contents (struct log_entry *e)
3231{
3232  if (e->string)
3233    free ((char *)e->string);
3234  CLEAR (*e);
3235}
3236
3237/*
3238 * struct log_history
3239 */
3240
3241static inline int
3242log_index (const struct log_history *h, int i)
3243{
3244  return modulo_add (h->base, i, h->capacity);
3245}
3246
3247static void
3248log_history_obj_init (struct log_history *h, int capacity)
3249{
3250  CLEAR (*h);
3251  h->capacity = capacity;
3252  ALLOC_ARRAY_CLEAR (h->array, struct log_entry, capacity);
3253}
3254
3255struct log_history *
3256log_history_init (const int capacity)
3257{
3258  struct log_history *h;
3259  ASSERT (capacity > 0);
3260  ALLOC_OBJ (h, struct log_history);
3261  log_history_obj_init (h, capacity);
3262  return h;
3263}
3264
3265static void
3266log_history_free_contents (struct log_history *h)
3267{
3268  int i;
3269  for (i = 0; i < h->size; ++i)
3270    log_entry_free_contents (&h->array[log_index(h, i)]);
3271  free (h->array);
3272}
3273
3274void
3275log_history_close (struct log_history *h)
3276{
3277  log_history_free_contents (h);
3278  free (h);
3279}
3280
3281void
3282log_history_add (struct log_history *h, const struct log_entry *le)
3283{
3284  struct log_entry *e;
3285  ASSERT (h->size >= 0 && h->size <= h->capacity);
3286  if (h->size == h->capacity)
3287    {
3288      e = &h->array[h->base];
3289      log_entry_free_contents (e);
3290      h->base = log_index (h, 1);
3291    }
3292  else
3293    {
3294      e = &h->array[log_index(h, h->size)];
3295      ++h->size;
3296    }
3297
3298  *e = *le;
3299  e->string = string_alloc (le->string, NULL);
3300}
3301
3302void
3303log_history_resize (struct log_history *h, const int capacity)
3304{
3305  if (capacity != h->capacity)
3306    {
3307      struct log_history newlog;
3308      int i;
3309
3310      ASSERT (capacity > 0);
3311      log_history_obj_init (&newlog, capacity);
3312
3313      for (i = 0; i < h->size; ++i)
3314	log_history_add (&newlog, &h->array[log_index(h, i)]);
3315
3316      log_history_free_contents (h);
3317      *h = newlog;
3318    }
3319}
3320
3321const struct log_entry *
3322log_history_ref (const struct log_history *h, const int index)
3323{
3324  if (index >= 0 && index < h->size)
3325    return &h->array[log_index(h, (h->size - 1) - index)];
3326  else
3327    return NULL;
3328}
3329
3330#else
3331static void dummy(void) {}
3332#endif /* ENABLE_MANAGEMENT */
3333