OpenVPN: Update to version 2.3.2. Solves TLS security bug.
[tomato.git] / release / src / router / openvpn / src / openvpn / misc.c
blobfa327f8c7315216308b6d93f55e4103444f7f82d
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.
8 * Copyright (C) 2002-2010 OpenVPN Technologies, Inc. <sales@openvpn.net>
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.
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.
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
25 #ifdef HAVE_CONFIG_H
26 #include "config.h"
27 #elif defined(_MSC_VER)
28 #include "config-msvc.h"
29 #endif
31 #include "syshead.h"
33 #include "buffer.h"
34 #include "misc.h"
35 #include "base64.h"
36 #include "tun.h"
37 #include "error.h"
38 #include "otime.h"
39 #include "plugin.h"
40 #include "options.h"
41 #include "manage.h"
42 #include "crypto.h"
43 #include "route.h"
44 #include "console.h"
45 #include "win32.h"
47 #include "memdbg.h"
49 #ifdef ENABLE_IPROUTE
50 const char *iproute_path = IPROUTE_PATH; /* GLOBAL */
51 #endif
53 /* contains an SSEC_x value defined in misc.h */
54 int script_security = SSEC_BUILT_IN; /* GLOBAL */
57 * Pass tunnel endpoint and MTU parms to a user-supplied script.
58 * Used to execute the up/down script/plugins.
60 void
61 run_up_down (const char *command,
62 const struct plugin_list *plugins,
63 int plugin_type,
64 const char *arg,
65 const char *dev_type,
66 int tun_mtu,
67 int link_mtu,
68 const char *ifconfig_local,
69 const char* ifconfig_remote,
70 const char *context,
71 const char *signal_text,
72 const char *script_type,
73 struct env_set *es)
75 struct gc_arena gc = gc_new ();
77 if (signal_text)
78 setenv_str (es, "signal", signal_text);
79 setenv_str (es, "script_context", context);
80 setenv_int (es, "tun_mtu", tun_mtu);
81 setenv_int (es, "link_mtu", link_mtu);
82 setenv_str (es, "dev", arg);
83 if (dev_type)
84 setenv_str (es, "dev_type", dev_type);
86 if (!ifconfig_local)
87 ifconfig_local = "";
88 if (!ifconfig_remote)
89 ifconfig_remote = "";
90 if (!context)
91 context = "";
93 if (plugin_defined (plugins, plugin_type))
95 struct argv argv = argv_new ();
96 ASSERT (arg);
97 argv_printf (&argv,
98 "%s %d %d %s %s %s",
99 arg,
100 tun_mtu, link_mtu,
101 ifconfig_local, ifconfig_remote,
102 context);
104 if (plugin_call (plugins, plugin_type, &argv, NULL, es) != OPENVPN_PLUGIN_FUNC_SUCCESS)
105 msg (M_FATAL, "ERROR: up/down plugin call failed");
107 argv_reset (&argv);
110 if (command)
112 struct argv argv = argv_new ();
113 ASSERT (arg);
114 setenv_str (es, "script_type", script_type);
115 argv_printf (&argv,
116 "%sc %s %d %d %s %s %s",
117 command,
118 arg,
119 tun_mtu, link_mtu,
120 ifconfig_local, ifconfig_remote,
121 context);
122 argv_msg (M_INFO, &argv);
123 openvpn_run_script (&argv, es, S_FATAL, "--up/--down");
124 argv_reset (&argv);
127 gc_free (&gc);
130 /* Get the file we will later write our process ID to */
131 void
132 get_pid_file (const char* filename, struct pid_state *state)
134 CLEAR (*state);
135 if (filename)
137 state->fp = platform_fopen (filename, "w");
138 if (!state->fp)
139 msg (M_ERR, "Open error on pid file %s", filename);
140 state->filename = filename;
144 /* Write our PID to a file */
145 void
146 write_pid (const struct pid_state *state)
148 if (state->filename && state->fp)
150 unsigned int pid = platform_getpid ();
151 fprintf(state->fp, "%u\n", pid);
152 if (fclose (state->fp))
153 msg (M_ERR, "Close error on pid file %s", state->filename);
158 * Set standard file descriptors to /dev/null
160 void
161 set_std_files_to_null (bool stdin_only)
163 #if defined(HAVE_DUP) && defined(HAVE_DUP2)
164 int fd;
165 if ((fd = open ("/dev/null", O_RDWR, 0)) != -1)
167 dup2 (fd, 0);
168 if (!stdin_only)
170 dup2 (fd, 1);
171 dup2 (fd, 2);
173 if (fd > 2)
174 close (fd);
176 #endif
180 * dup inetd/xinetd socket descriptor and save
183 int inetd_socket_descriptor = SOCKET_UNDEFINED; /* GLOBAL */
185 void
186 save_inetd_socket_descriptor (void)
188 inetd_socket_descriptor = INETD_SOCKET_DESCRIPTOR;
189 #if defined(HAVE_DUP) && defined(HAVE_DUP2)
190 /* use handle passed by inetd/xinetd */
191 if ((inetd_socket_descriptor = dup (INETD_SOCKET_DESCRIPTOR)) < 0)
192 msg (M_ERR, "INETD_SOCKET_DESCRIPTOR dup(%d) failed", INETD_SOCKET_DESCRIPTOR);
193 set_std_files_to_null (true);
194 #endif
198 * Warn if a given file is group/others accessible.
200 void
201 warn_if_group_others_accessible (const char* filename)
203 #ifndef WIN32
204 #ifdef HAVE_STAT
205 if (strcmp (filename, INLINE_FILE_TAG))
207 struct stat st;
208 if (stat (filename, &st))
210 msg (M_WARN | M_ERRNO, "WARNING: cannot stat file '%s'", filename);
212 else
214 if (st.st_mode & (S_IRWXG|S_IRWXO))
215 msg (M_WARN, "WARNING: file '%s' is group or others accessible", filename);
218 #endif
219 #endif
223 * Print an error message based on the status code returned by system().
225 const char *
226 system_error_message (int stat, struct gc_arena *gc)
228 struct buffer out = alloc_buf_gc (256, gc);
229 #ifdef WIN32
230 if (stat == -1)
231 buf_printf (&out, "external program did not execute -- ");
232 buf_printf (&out, "returned error code %d", stat);
233 #else
234 if (stat == -1)
235 buf_printf (&out, "external program fork failed");
236 else if (!WIFEXITED (stat))
237 buf_printf (&out, "external program did not exit normally");
238 else
240 const int cmd_ret = WEXITSTATUS (stat);
241 if (!cmd_ret)
242 buf_printf (&out, "external program exited normally");
243 else if (cmd_ret == 127)
244 buf_printf (&out, "could not execute external program");
245 else
246 buf_printf (&out, "external program exited with error status: %d", cmd_ret);
248 #endif
249 return (const char *)out.data;
253 * Wrapper around openvpn_execve
255 bool
256 openvpn_execve_check (const struct argv *a, const struct env_set *es, const unsigned int flags, const char *error_message)
258 struct gc_arena gc = gc_new ();
259 const int stat = openvpn_execve (a, es, flags);
260 int ret = false;
262 if (platform_system_ok (stat))
263 ret = true;
264 else
266 if (error_message)
267 msg (((flags & S_FATAL) ? M_FATAL : M_WARN), "%s: %s",
268 error_message,
269 system_error_message (stat, &gc));
271 gc_free (&gc);
272 return ret;
275 bool
276 openvpn_execve_allowed (const unsigned int flags)
278 if (flags & S_SCRIPT)
279 return script_security >= SSEC_SCRIPTS;
280 else
281 return script_security >= SSEC_BUILT_IN;
285 #ifndef WIN32
287 * Run execve() inside a fork(). Designed to replicate the semantics of system() but
288 * in a safer way that doesn't require the invocation of a shell or the risks
289 * assocated with formatting and parsing a command line.
292 openvpn_execve (const struct argv *a, const struct env_set *es, const unsigned int flags)
294 struct gc_arena gc = gc_new ();
295 int ret = -1;
296 static bool warn_shown = false;
298 if (a && a->argv[0])
300 #if defined(ENABLE_FEATURE_EXECVE)
301 if (openvpn_execve_allowed (flags))
303 const char *cmd = a->argv[0];
304 char *const *argv = a->argv;
305 char *const *envp = (char *const *)make_env_array (es, true, &gc);
306 pid_t pid;
308 pid = fork ();
309 if (pid == (pid_t)0) /* child side */
311 execve (cmd, argv, envp);
312 exit (127);
314 else if (pid < (pid_t)0) /* fork failed */
315 msg (M_ERR, "openvpn_execve: unable to fork");
316 else /* parent side */
318 if (waitpid (pid, &ret, 0) != pid)
319 ret = -1;
322 else if (!warn_shown && (script_security < SSEC_SCRIPTS))
324 msg (M_WARN, SCRIPT_SECURITY_WARNING);
325 warn_shown = true;
327 #else
328 msg (M_WARN, "openvpn_execve: execve function not available");
329 #endif
331 else
333 msg (M_FATAL, "openvpn_execve: called with empty argv");
336 gc_free (&gc);
337 return ret;
339 #endif
342 * Run execve() inside a fork(), duping stdout. Designed to replicate the semantics of popen() but
343 * in a safer way that doesn't require the invocation of a shell or the risks
344 * assocated with formatting and parsing a command line.
347 openvpn_popen (const struct argv *a, const struct env_set *es)
349 struct gc_arena gc = gc_new ();
350 int ret = -1;
351 static bool warn_shown = false;
353 if (a && a->argv[0])
355 #if defined(ENABLE_FEATURE_EXECVE)
356 if (script_security >= SSEC_BUILT_IN)
358 const char *cmd = a->argv[0];
359 char *const *argv = a->argv;
360 char *const *envp = (char *const *)make_env_array (es, true, &gc);
361 pid_t pid;
362 int pipe_stdout[2];
364 if (pipe (pipe_stdout) == 0) {
365 pid = fork ();
366 if (pid == (pid_t)0) /* child side */
368 close (pipe_stdout[0]);
369 dup2 (pipe_stdout[1],1);
370 execve (cmd, argv, envp);
371 exit (127);
373 else if (pid < (pid_t)0) /* fork failed */
375 msg (M_ERR, "openvpn_popen: unable to fork");
377 else /* parent side */
379 ret=pipe_stdout[0];
380 close (pipe_stdout[1]);
383 else {
384 msg (M_WARN, "openvpn_popen: unable to create stdout pipe");
385 ret = -1;
388 else if (!warn_shown && (script_security < SSEC_SCRIPTS))
390 msg (M_WARN, SCRIPT_SECURITY_WARNING);
391 warn_shown = true;
393 #else
394 msg (M_WARN, "openvpn_popen: execve function not available");
395 #endif
397 else
399 msg (M_FATAL, "openvpn_popen: called with empty argv");
402 gc_free (&gc);
403 return ret;
409 * Initialize random number seed. random() is only used
410 * when "weak" random numbers are acceptable.
411 * OpenSSL routines are always used when cryptographically
412 * strong random numbers are required.
415 void
416 init_random_seed(void)
418 struct timeval tv;
420 if (!gettimeofday (&tv, NULL))
422 const unsigned int seed = (unsigned int) tv.tv_sec ^ tv.tv_usec;
423 srandom (seed);
427 /* thread-safe strerror */
429 const char *
430 strerror_ts (int errnum, struct gc_arena *gc)
432 #ifdef HAVE_STRERROR
433 struct buffer out = alloc_buf_gc (256, gc);
435 buf_printf (&out, "%s", openvpn_strerror (errnum, gc));
436 return BSTR (&out);
437 #else
438 return "[error string unavailable]";
439 #endif
443 * Set environmental variable (int or string).
445 * On Posix, we use putenv for portability,
446 * and put up with its painful semantics
447 * that require all the support code below.
450 /* General-purpose environmental variable set functions */
452 static char *
453 construct_name_value (const char *name, const char *value, struct gc_arena *gc)
455 struct buffer out;
457 ASSERT (name);
458 if (!value)
459 value = "";
460 out = alloc_buf_gc (strlen (name) + strlen (value) + 2, gc);
461 buf_printf (&out, "%s=%s", name, value);
462 return BSTR (&out);
465 bool
466 deconstruct_name_value (const char *str, const char **name, const char **value, struct gc_arena *gc)
468 char *cp;
470 ASSERT (str);
471 ASSERT (name && value);
473 *name = cp = string_alloc (str, gc);
474 *value = NULL;
476 while ((*cp))
478 if (*cp == '=' && !*value)
480 *cp = 0;
481 *value = cp + 1;
483 ++cp;
485 return *name && *value;
488 static bool
489 env_string_equal (const char *s1, const char *s2)
491 int c1, c2;
492 ASSERT (s1);
493 ASSERT (s2);
495 while (true)
497 c1 = *s1++;
498 c2 = *s2++;
499 if (c1 == '=')
500 c1 = 0;
501 if (c2 == '=')
502 c2 = 0;
503 if (!c1 && !c2)
504 return true;
505 if (c1 != c2)
506 break;
508 return false;
511 static bool
512 remove_env_item (const char *str, const bool do_free, struct env_item **list)
514 struct env_item *current, *prev;
516 ASSERT (str);
517 ASSERT (list);
519 for (current = *list, prev = NULL; current != NULL; current = current->next)
521 if (env_string_equal (current->string, str))
523 if (prev)
524 prev->next = current->next;
525 else
526 *list = current->next;
527 if (do_free)
529 memset (current->string, 0, strlen (current->string));
530 free (current->string);
531 free (current);
533 return true;
535 prev = current;
537 return false;
540 static void
541 add_env_item (char *str, const bool do_alloc, struct env_item **list, struct gc_arena *gc)
543 struct env_item *item;
545 ASSERT (str);
546 ASSERT (list);
548 ALLOC_OBJ_GC (item, struct env_item, gc);
549 item->string = do_alloc ? string_alloc (str, gc): str;
550 item->next = *list;
551 *list = item;
554 /* struct env_set functions */
556 static bool
557 env_set_del_nolock (struct env_set *es, const char *str)
559 return remove_env_item (str, es->gc == NULL, &es->list);
562 static void
563 env_set_add_nolock (struct env_set *es, const char *str)
565 remove_env_item (str, es->gc == NULL, &es->list);
566 add_env_item ((char *)str, true, &es->list, es->gc);
569 struct env_set *
570 env_set_create (struct gc_arena *gc)
572 struct env_set *es;
573 ALLOC_OBJ_CLEAR_GC (es, struct env_set, gc);
574 es->list = NULL;
575 es->gc = gc;
576 return es;
579 void
580 env_set_destroy (struct env_set *es)
582 if (es && es->gc == NULL)
584 struct env_item *e = es->list;
585 while (e)
587 struct env_item *next = e->next;
588 free (e->string);
589 free (e);
590 e = next;
592 free (es);
596 bool
597 env_set_del (struct env_set *es, const char *str)
599 bool ret;
600 ASSERT (es);
601 ASSERT (str);
602 ret = env_set_del_nolock (es, str);
603 return ret;
606 void
607 env_set_add (struct env_set *es, const char *str)
609 ASSERT (es);
610 ASSERT (str);
611 env_set_add_nolock (es, str);
614 void
615 env_set_print (int msglevel, const struct env_set *es)
617 if (check_debug_level (msglevel))
619 const struct env_item *e;
620 int i;
622 if (es)
624 e = es->list;
625 i = 0;
627 while (e)
629 if (env_safe_to_print (e->string))
630 msg (msglevel, "ENV [%d] '%s'", i, e->string);
631 ++i;
632 e = e->next;
638 void
639 env_set_inherit (struct env_set *es, const struct env_set *src)
641 const struct env_item *e;
643 ASSERT (es);
645 if (src)
647 e = src->list;
648 while (e)
650 env_set_add_nolock (es, e->string);
651 e = e->next;
656 void
657 env_set_add_to_environment (const struct env_set *es)
659 if (es)
661 struct gc_arena gc = gc_new ();
662 const struct env_item *e;
664 e = es->list;
666 while (e)
668 const char *name;
669 const char *value;
671 if (deconstruct_name_value (e->string, &name, &value, &gc))
672 setenv_str (NULL, name, value);
674 e = e->next;
676 gc_free (&gc);
680 void
681 env_set_remove_from_environment (const struct env_set *es)
683 if (es)
685 struct gc_arena gc = gc_new ();
686 const struct env_item *e;
688 e = es->list;
690 while (e)
692 const char *name;
693 const char *value;
695 if (deconstruct_name_value (e->string, &name, &value, &gc))
696 setenv_del (NULL, name);
698 e = e->next;
700 gc_free (&gc);
704 #ifdef HAVE_PUTENV
706 /* companion functions to putenv */
708 static struct env_item *global_env = NULL; /* GLOBAL */
710 #endif
712 /* add/modify/delete environmental strings */
714 void
715 setenv_counter (struct env_set *es, const char *name, counter_type value)
717 char buf[64];
718 openvpn_snprintf (buf, sizeof(buf), counter_format, value);
719 setenv_str (es, name, buf);
722 void
723 setenv_int (struct env_set *es, const char *name, int value)
725 char buf[64];
726 openvpn_snprintf (buf, sizeof(buf), "%d", value);
727 setenv_str (es, name, buf);
730 void
731 setenv_unsigned (struct env_set *es, const char *name, unsigned int value)
733 char buf[64];
734 openvpn_snprintf (buf, sizeof(buf), "%u", value);
735 setenv_str (es, name, buf);
738 void
739 setenv_str (struct env_set *es, const char *name, const char *value)
741 setenv_str_ex (es, name, value, CC_NAME, 0, 0, CC_PRINT, 0, 0);
744 void
745 setenv_str_safe (struct env_set *es, const char *name, const char *value)
747 uint8_t b[64];
748 struct buffer buf;
749 buf_set_write (&buf, b, sizeof (b));
750 if (buf_printf (&buf, "OPENVPN_%s", name))
751 setenv_str (es, BSTR(&buf), value);
752 else
753 msg (M_WARN, "setenv_str_safe: name overflow");
756 void
757 setenv_del (struct env_set *es, const char *name)
759 ASSERT (name);
760 setenv_str (es, name, NULL);
763 void
764 setenv_str_ex (struct env_set *es,
765 const char *name,
766 const char *value,
767 const unsigned int name_include,
768 const unsigned int name_exclude,
769 const char name_replace,
770 const unsigned int value_include,
771 const unsigned int value_exclude,
772 const char value_replace)
774 struct gc_arena gc = gc_new ();
775 const char *name_tmp;
776 const char *val_tmp = NULL;
778 ASSERT (name && strlen (name) > 1);
780 name_tmp = string_mod_const (name, name_include, name_exclude, name_replace, &gc);
782 if (value)
783 val_tmp = string_mod_const (value, value_include, value_exclude, value_replace, &gc);
785 ASSERT (es);
787 if (val_tmp)
789 const char *str = construct_name_value (name_tmp, val_tmp, &gc);
790 env_set_add (es, str);
791 #if DEBUG_VERBOSE_SETENV
792 msg (M_INFO, "SETENV_ES '%s'", str);
793 #endif
795 else
796 env_set_del (es, name_tmp);
798 gc_free (&gc);
802 * Setenv functions that append an integer index to the name
804 static const char *
805 setenv_format_indexed_name (const char *name, const int i, struct gc_arena *gc)
807 struct buffer out = alloc_buf_gc (strlen (name) + 16, gc);
808 if (i >= 0)
809 buf_printf (&out, "%s_%d", name, i);
810 else
811 buf_printf (&out, "%s", name);
812 return BSTR (&out);
815 void
816 setenv_int_i (struct env_set *es, const char *name, const int value, const int i)
818 struct gc_arena gc = gc_new ();
819 const char *name_str = setenv_format_indexed_name (name, i, &gc);
820 setenv_int (es, name_str, value);
821 gc_free (&gc);
824 void
825 setenv_str_i (struct env_set *es, const char *name, const char *value, const int i)
827 struct gc_arena gc = gc_new ();
828 const char *name_str = setenv_format_indexed_name (name, i, &gc);
829 setenv_str (es, name_str, value);
830 gc_free (&gc);
834 * taken from busybox networking/ifupdown.c
836 unsigned int
837 count_bits(unsigned int a)
839 unsigned int result;
840 result = (a & 0x55) + ((a >> 1) & 0x55);
841 result = (result & 0x33) + ((result >> 2) & 0x33);
842 return((result & 0x0F) + ((result >> 4) & 0x0F));
846 count_netmask_bits(const char *dotted_quad)
848 unsigned int result, a, b, c, d;
849 /* Found a netmask... Check if it is dotted quad */
850 if (sscanf(dotted_quad, "%u.%u.%u.%u", &a, &b, &c, &d) != 4)
851 return -1;
852 result = count_bits(a);
853 result += count_bits(b);
854 result += count_bits(c);
855 result += count_bits(d);
856 return ((int)result);
859 /* return true if filename can be opened for read */
860 bool
861 test_file (const char *filename)
863 bool ret = false;
864 if (filename)
866 FILE *fp = platform_fopen (filename, "r");
867 if (fp)
869 fclose (fp);
870 ret = true;
874 dmsg (D_TEST_FILE, "TEST FILE '%s' [%d]",
875 filename ? filename : "UNDEF",
876 ret);
878 return ret;
881 #ifdef ENABLE_CRYPTO
883 /* create a temporary filename in directory */
884 const char *
885 create_temp_file (const char *directory, const char *prefix, struct gc_arena *gc)
887 static unsigned int counter;
888 struct buffer fname = alloc_buf_gc (256, gc);
889 int fd;
890 const char *retfname = NULL;
891 unsigned int attempts = 0;
895 uint8_t rndbytes[16];
896 const char *rndstr;
898 ++attempts;
899 ++counter;
901 prng_bytes (rndbytes, sizeof rndbytes);
902 rndstr = format_hex_ex (rndbytes, sizeof rndbytes, 40, 0, NULL, gc);
903 buf_printf (&fname, PACKAGE "_%s_%s.tmp", prefix, rndstr);
905 retfname = gen_path (directory, BSTR (&fname), gc);
906 if (!retfname)
908 msg (M_FATAL, "Failed to create temporary filename and path");
909 return NULL;
912 /* Atomically create the file. Errors out if the file already
913 exists. */
914 fd = platform_open (retfname, O_CREAT | O_EXCL | O_WRONLY, S_IRUSR | S_IWUSR);
915 if (fd != -1)
917 close (fd);
918 return retfname;
920 else if (fd == -1 && errno != EEXIST)
922 /* Something else went wrong, no need to retry. */
923 struct gc_arena gcerr = gc_new ();
924 msg (M_FATAL, "Could not create temporary file '%s': %s",
925 retfname, strerror_ts (errno, &gcerr));
926 gc_free (&gcerr);
927 return NULL;
930 while (attempts < 6);
932 msg (M_FATAL, "Failed to create temporary file after %i attempts", attempts);
933 return NULL;
937 * Add a random string to first DNS label of hostname to prevent DNS caching.
938 * For example, foo.bar.gov would be modified to <random-chars>.foo.bar.gov.
939 * Of course, this requires explicit support in the DNS server.
941 const char *
942 hostname_randomize(const char *hostname, struct gc_arena *gc)
944 # define n_rnd_bytes 6
946 char *hst = string_alloc(hostname, gc);
947 char *dot = strchr(hst, '.');
949 if (dot)
951 uint8_t rnd_bytes[n_rnd_bytes];
952 const char *rnd_str;
953 struct buffer hname = alloc_buf_gc (strlen(hostname)+sizeof(rnd_bytes)*2+4, gc);
955 *dot++ = '\0';
956 prng_bytes (rnd_bytes, sizeof (rnd_bytes));
957 rnd_str = format_hex_ex (rnd_bytes, sizeof (rnd_bytes), 40, 0, NULL, gc);
958 buf_printf(&hname, "%s-0x%s.%s", hst, rnd_str, dot);
959 return BSTR(&hname);
961 else
962 return hostname;
963 # undef n_rnd_bytes
966 #else
968 const char *
969 hostname_randomize(const char *hostname, struct gc_arena *gc)
971 msg (M_WARN, "WARNING: hostname randomization disabled when crypto support is not compiled");
972 return hostname;
975 #endif
978 * Put a directory and filename together.
980 const char *
981 gen_path (const char *directory, const char *filename, struct gc_arena *gc)
983 #if WIN32
984 const int CC_PATH_RESERVED = CC_LESS_THAN|CC_GREATER_THAN|CC_COLON|
985 CC_DOUBLE_QUOTE|CC_SLASH|CC_BACKSLASH|CC_PIPE|CC_QUESTION_MARK|CC_ASTERISK;
986 #else
987 const int CC_PATH_RESERVED = CC_SLASH;
988 #endif
989 const char *safe_filename = string_mod_const (filename, CC_PRINT, CC_PATH_RESERVED, '_', gc);
991 if (safe_filename
992 && strcmp (safe_filename, ".")
993 && strcmp (safe_filename, "..")
994 #ifdef WIN32
995 && win_safe_filename (safe_filename)
996 #endif
999 const size_t outsize = strlen(safe_filename) + (directory ? strlen (directory) : 0) + 16;
1000 struct buffer out = alloc_buf_gc (outsize, gc);
1001 char dirsep[2];
1003 dirsep[0] = OS_SPECIFIC_DIRSEP;
1004 dirsep[1] = '\0';
1006 if (directory)
1007 buf_printf (&out, "%s%s", directory, dirsep);
1008 buf_printf (&out, "%s", safe_filename);
1010 return BSTR (&out);
1012 else
1013 return NULL;
1016 bool
1017 absolute_pathname (const char *pathname)
1019 if (pathname)
1021 const int c = pathname[0];
1022 #ifdef WIN32
1023 return c == '\\' || (isalpha(c) && pathname[1] == ':' && pathname[2] == '\\');
1024 #else
1025 return c == '/';
1026 #endif
1028 else
1029 return false;
1033 * Get and store a username/password
1036 bool
1037 get_user_pass_cr (struct user_pass *up,
1038 const char *auth_file,
1039 const char *prefix,
1040 const unsigned int flags,
1041 const char *auth_challenge)
1043 struct gc_arena gc = gc_new ();
1045 if (!up->defined)
1047 const bool from_stdin = (!auth_file || !strcmp (auth_file, "stdin"));
1049 if (flags & GET_USER_PASS_PREVIOUS_CREDS_FAILED)
1050 msg (M_WARN, "Note: previous '%s' credentials failed", prefix);
1052 #ifdef ENABLE_MANAGEMENT
1054 * Get username/password from management interface?
1056 if (management
1057 && ((auth_file && streq (auth_file, "management")) || (from_stdin && (flags & GET_USER_PASS_MANAGEMENT)))
1058 && management_query_user_pass_enabled (management))
1060 const char *sc = NULL;
1062 if (flags & GET_USER_PASS_PREVIOUS_CREDS_FAILED)
1063 management_auth_failure (management, prefix, "previous auth credentials failed");
1065 #ifdef ENABLE_CLIENT_CR
1066 if (auth_challenge && (flags & GET_USER_PASS_STATIC_CHALLENGE))
1067 sc = auth_challenge;
1068 #endif
1069 if (!management_query_user_pass (management, up, prefix, flags, sc))
1071 if ((flags & GET_USER_PASS_NOFATAL) != 0)
1072 return false;
1073 else
1074 msg (M_FATAL, "ERROR: could not read %s username/password/ok/string from management interface", prefix);
1077 else
1078 #endif
1080 * Get NEED_OK confirmation from the console
1082 if (flags & GET_USER_PASS_NEED_OK)
1084 struct buffer user_prompt = alloc_buf_gc (128, &gc);
1086 buf_printf (&user_prompt, "NEED-OK|%s|%s:", prefix, up->username);
1088 if (!get_console_input (BSTR (&user_prompt), true, up->password, USER_PASS_LEN))
1089 msg (M_FATAL, "ERROR: could not read %s ok-confirmation from stdin", prefix);
1091 if (!strlen (up->password))
1092 strcpy (up->password, "ok");
1096 * Get username/password from standard input?
1098 else if (from_stdin)
1100 #ifdef ENABLE_CLIENT_CR
1101 if (auth_challenge && (flags & GET_USER_PASS_DYNAMIC_CHALLENGE))
1103 struct auth_challenge_info *ac = get_auth_challenge (auth_challenge, &gc);
1104 if (ac)
1106 char *response = (char *) gc_malloc (USER_PASS_LEN, false, &gc);
1107 struct buffer packed_resp;
1109 buf_set_write (&packed_resp, (uint8_t*)up->password, USER_PASS_LEN);
1110 msg (M_INFO|M_NOPREFIX, "CHALLENGE: %s", ac->challenge_text);
1111 if (!get_console_input ("Response:", BOOL_CAST(ac->flags&CR_ECHO), response, USER_PASS_LEN))
1112 msg (M_FATAL, "ERROR: could not read challenge response from stdin");
1113 strncpynt (up->username, ac->user, USER_PASS_LEN);
1114 buf_printf (&packed_resp, "CRV1::%s::%s", ac->state_id, response);
1116 else
1118 msg (M_FATAL, "ERROR: received malformed challenge request from server");
1121 else
1122 #endif
1124 struct buffer user_prompt = alloc_buf_gc (128, &gc);
1125 struct buffer pass_prompt = alloc_buf_gc (128, &gc);
1127 buf_printf (&user_prompt, "Enter %s Username:", prefix);
1128 buf_printf (&pass_prompt, "Enter %s Password:", prefix);
1130 if (!(flags & GET_USER_PASS_PASSWORD_ONLY))
1132 if (!get_console_input (BSTR (&user_prompt), true, up->username, USER_PASS_LEN))
1133 msg (M_FATAL, "ERROR: could not read %s username from stdin", prefix);
1134 if (strlen (up->username) == 0)
1135 msg (M_FATAL, "ERROR: %s username is empty", prefix);
1138 if (!get_console_input (BSTR (&pass_prompt), false, up->password, USER_PASS_LEN))
1139 msg (M_FATAL, "ERROR: could not not read %s password from stdin", prefix);
1141 #ifdef ENABLE_CLIENT_CR
1142 if (auth_challenge && (flags & GET_USER_PASS_STATIC_CHALLENGE))
1144 char *response = (char *) gc_malloc (USER_PASS_LEN, false, &gc);
1145 struct buffer packed_resp;
1146 char *pw64=NULL, *resp64=NULL;
1148 msg (M_INFO|M_NOPREFIX, "CHALLENGE: %s", auth_challenge);
1149 if (!get_console_input ("Response:", BOOL_CAST(flags & GET_USER_PASS_STATIC_CHALLENGE_ECHO), response, USER_PASS_LEN))
1150 msg (M_FATAL, "ERROR: could not read static challenge response from stdin");
1151 if (openvpn_base64_encode(up->password, strlen(up->password), &pw64) == -1
1152 || openvpn_base64_encode(response, strlen(response), &resp64) == -1)
1153 msg (M_FATAL, "ERROR: could not base64-encode password/static_response");
1154 buf_set_write (&packed_resp, (uint8_t*)up->password, USER_PASS_LEN);
1155 buf_printf (&packed_resp, "SCRV1:%s:%s", pw64, resp64);
1156 string_clear(pw64);
1157 free(pw64);
1158 string_clear(resp64);
1159 free(resp64);
1161 #endif
1164 else
1167 * Get username/password from a file.
1169 FILE *fp;
1171 #ifndef ENABLE_PASSWORD_SAVE
1173 * Unless ENABLE_PASSWORD_SAVE is defined, don't allow sensitive passwords
1174 * to be read from a file.
1176 if (flags & GET_USER_PASS_SENSITIVE)
1177 msg (M_FATAL, "Sorry, '%s' password cannot be read from a file", prefix);
1178 #endif
1180 warn_if_group_others_accessible (auth_file);
1182 fp = platform_fopen (auth_file, "r");
1183 if (!fp)
1184 msg (M_ERR, "Error opening '%s' auth file: %s", prefix, auth_file);
1186 if (flags & GET_USER_PASS_PASSWORD_ONLY)
1188 if (fgets (up->password, USER_PASS_LEN, fp) == NULL)
1189 msg (M_FATAL, "Error reading password from %s authfile: %s",
1190 prefix,
1191 auth_file);
1193 else
1195 if (fgets (up->username, USER_PASS_LEN, fp) == NULL
1196 || fgets (up->password, USER_PASS_LEN, fp) == NULL)
1197 msg (M_FATAL, "Error reading username and password (must be on two consecutive lines) from %s authfile: %s",
1198 prefix,
1199 auth_file);
1202 fclose (fp);
1204 chomp (up->username);
1205 chomp (up->password);
1207 if (!(flags & GET_USER_PASS_PASSWORD_ONLY) && strlen (up->username) == 0)
1208 msg (M_FATAL, "ERROR: username from %s authfile '%s' is empty", prefix, auth_file);
1211 string_mod (up->username, CC_PRINT, CC_CRLF, 0);
1212 string_mod (up->password, CC_PRINT, CC_CRLF, 0);
1214 up->defined = true;
1217 #if 0
1218 msg (M_INFO, "GET_USER_PASS %s u='%s' p='%s'", prefix, up->username, up->password);
1219 #endif
1221 gc_free (&gc);
1223 return true;
1226 #ifdef ENABLE_CLIENT_CR
1229 * See management/management-notes.txt for more info on the
1230 * the dynamic challenge/response protocol implemented here.
1232 struct auth_challenge_info *
1233 get_auth_challenge (const char *auth_challenge, struct gc_arena *gc)
1235 if (auth_challenge)
1237 struct auth_challenge_info *ac;
1238 const int len = strlen (auth_challenge);
1239 char *work = (char *) gc_malloc (len+1, false, gc);
1240 char *cp;
1242 struct buffer b;
1243 buf_set_read (&b, (const uint8_t *)auth_challenge, len);
1245 ALLOC_OBJ_CLEAR_GC (ac, struct auth_challenge_info, gc);
1247 /* parse prefix */
1248 if (!buf_parse(&b, ':', work, len))
1249 return NULL;
1250 if (strcmp(work, "CRV1"))
1251 return NULL;
1253 /* parse flags */
1254 if (!buf_parse(&b, ':', work, len))
1255 return NULL;
1256 for (cp = work; *cp != '\0'; ++cp)
1258 const char c = *cp;
1259 if (c == 'E')
1260 ac->flags |= CR_ECHO;
1261 else if (c == 'R')
1262 ac->flags |= CR_RESPONSE;
1265 /* parse state ID */
1266 if (!buf_parse(&b, ':', work, len))
1267 return NULL;
1268 ac->state_id = string_alloc(work, gc);
1270 /* parse user name */
1271 if (!buf_parse(&b, ':', work, len))
1272 return NULL;
1273 ac->user = (char *) gc_malloc (strlen(work)+1, true, gc);
1274 openvpn_base64_decode(work, (void*)ac->user, -1);
1276 /* parse challenge text */
1277 ac->challenge_text = string_alloc(BSTR(&b), gc);
1279 return ac;
1281 else
1282 return NULL;
1285 #endif
1287 #if AUTO_USERID
1289 void
1290 get_user_pass_auto_userid (struct user_pass *up, const char *tag)
1292 struct gc_arena gc = gc_new ();
1293 struct buffer buf;
1294 uint8_t macaddr[6];
1295 static uint8_t digest [MD5_DIGEST_LENGTH];
1296 static const uint8_t hashprefix[] = "AUTO_USERID_DIGEST";
1298 const md_kt_t *md5_kt = md_kt_get("MD5");
1299 md_ctx_t ctx;
1301 CLEAR (*up);
1302 buf_set_write (&buf, (uint8_t*)up->username, USER_PASS_LEN);
1303 buf_printf (&buf, "%s", TARGET_PREFIX);
1304 if (get_default_gateway_mac_addr (macaddr))
1306 dmsg (D_AUTO_USERID, "GUPAU: macaddr=%s", format_hex_ex (macaddr, sizeof (macaddr), 0, 1, ":", &gc));
1307 md_ctx_init(&ctx, md5_kt);
1308 md_ctx_update(&ctx, hashprefix, sizeof (hashprefix) - 1);
1309 md_ctx_update(&ctx, macaddr, sizeof (macaddr));
1310 md_ctx_final(&ctx, digest);
1311 md_ctx_cleanup(&ctx)
1312 buf_printf(&buf, "%s", format_hex_ex (digest, sizeof (digest), 0, 256, " ", &gc));
1314 else
1316 buf_printf (&buf, "UNKNOWN");
1318 if (tag && strcmp (tag, "stdin"))
1319 buf_printf (&buf, "-%s", tag);
1320 up->defined = true;
1321 gc_free (&gc);
1323 dmsg (D_AUTO_USERID, "GUPAU: AUTO_USERID: '%s'", up->username);
1326 #endif
1328 void
1329 purge_user_pass (struct user_pass *up, const bool force)
1331 const bool nocache = up->nocache;
1332 static bool warn_shown = false;
1333 if (nocache || force)
1335 CLEAR (*up);
1336 up->nocache = nocache;
1338 else if (!warn_shown)
1340 msg (M_WARN, "WARNING: this configuration may cache passwords in memory -- use the auth-nocache option to prevent this");
1341 warn_shown = true;
1345 void
1346 set_auth_token (struct user_pass *up, const char *token)
1348 if (token && strlen(token) && up && up->defined && !up->nocache)
1350 CLEAR (up->password);
1351 strncpynt (up->password, token, USER_PASS_LEN);
1356 * Process string received by untrusted peer before
1357 * printing to console or log file.
1359 * Assumes that string has been null terminated.
1361 const char *
1362 safe_print (const char *str, struct gc_arena *gc)
1364 return string_mod_const (str, CC_PRINT, CC_CRLF, '.', gc);
1367 static bool
1368 is_password_env_var (const char *str)
1370 return (strncmp (str, "password", 8) == 0);
1373 bool
1374 env_allowed (const char *str)
1376 return (script_security >= SSEC_PW_ENV || !is_password_env_var (str));
1379 bool
1380 env_safe_to_print (const char *str)
1382 #ifndef UNSAFE_DEBUG
1383 if (is_password_env_var (str))
1384 return false;
1385 #endif
1386 return true;
1389 /* Make arrays of strings */
1391 const char **
1392 make_env_array (const struct env_set *es,
1393 const bool check_allowed,
1394 struct gc_arena *gc)
1396 char **ret = NULL;
1397 struct env_item *e = NULL;
1398 int i = 0, n = 0;
1400 /* figure length of es */
1401 if (es)
1403 for (e = es->list; e != NULL; e = e->next)
1404 ++n;
1407 /* alloc return array */
1408 ALLOC_ARRAY_CLEAR_GC (ret, char *, n+1, gc);
1410 /* fill return array */
1411 if (es)
1413 i = 0;
1414 for (e = es->list; e != NULL; e = e->next)
1416 if (!check_allowed || env_allowed (e->string))
1418 ASSERT (i < n);
1419 ret[i++] = e->string;
1424 ret[i] = NULL;
1425 return (const char **)ret;
1428 const char **
1429 make_arg_array (const char *first, const char *parms, struct gc_arena *gc)
1431 char **ret = NULL;
1432 int base = 0;
1433 const int max_parms = MAX_PARMS + 2;
1434 int n = 0;
1436 /* alloc return array */
1437 ALLOC_ARRAY_CLEAR_GC (ret, char *, max_parms, gc);
1439 /* process first parameter, if provided */
1440 if (first)
1442 ret[base++] = string_alloc (first, gc);
1445 if (parms)
1447 n = parse_line (parms, &ret[base], max_parms - base - 1, "make_arg_array", 0, M_WARN, gc);
1448 ASSERT (n >= 0 && n + base + 1 <= max_parms);
1450 ret[base + n] = NULL;
1452 return (const char **)ret;
1455 static const char **
1456 make_inline_array (const char *str, struct gc_arena *gc)
1458 char line[OPTION_LINE_SIZE];
1459 struct buffer buf;
1460 int len = 0;
1461 char **ret = NULL;
1462 int i = 0;
1464 buf_set_read (&buf, (const uint8_t *) str, strlen (str));
1465 while (buf_parse (&buf, '\n', line, sizeof (line)))
1466 ++len;
1468 /* alloc return array */
1469 ALLOC_ARRAY_CLEAR_GC (ret, char *, len + 1, gc);
1471 buf_set_read (&buf, (const uint8_t *) str, strlen(str));
1472 while (buf_parse (&buf, '\n', line, sizeof (line)))
1474 chomp (line);
1475 ASSERT (i < len);
1476 ret[i] = string_alloc (skip_leading_whitespace (line), gc);
1477 ++i;
1479 ASSERT (i <= len);
1480 ret[i] = NULL;
1481 return (const char **)ret;
1484 static const char **
1485 make_arg_copy (char **p, struct gc_arena *gc)
1487 char **ret = NULL;
1488 const int len = string_array_len ((const char **)p);
1489 const int max_parms = len + 1;
1490 int i;
1492 /* alloc return array */
1493 ALLOC_ARRAY_CLEAR_GC (ret, char *, max_parms, gc);
1495 for (i = 0; i < len; ++i)
1496 ret[i] = p[i];
1498 return (const char **)ret;
1501 const char **
1502 make_extended_arg_array (char **p, struct gc_arena *gc)
1504 const int argc = string_array_len ((const char **)p);
1505 if (!strcmp (p[0], INLINE_FILE_TAG) && argc == 2)
1506 return make_inline_array (p[1], gc);
1507 else
1508 if (argc == 0)
1509 return make_arg_array (NULL, NULL, gc);
1510 else if (argc == 1)
1511 return make_arg_array (p[0], NULL, gc);
1512 else if (argc == 2)
1513 return make_arg_array (p[0], p[1], gc);
1514 else
1515 return make_arg_copy (p, gc);
1518 void
1519 openvpn_sleep (const int n)
1521 #ifdef ENABLE_MANAGEMENT
1522 if (management)
1524 management_event_loop_n_seconds (management, n);
1525 return;
1527 #endif
1528 sleep (n);
1532 * Return the next largest power of 2
1533 * or u if u is a power of 2.
1535 size_t
1536 adjust_power_of_2 (size_t u)
1538 size_t ret = 1;
1540 while (ret < u)
1542 ret <<= 1;
1543 ASSERT (ret > 0);
1546 return ret;
1550 * A printf-like function (that only recognizes a subset of standard printf
1551 * format operators) that prints arguments to an argv list instead
1552 * of a standard string. This is used to build up argv arrays for passing
1553 * to execve.
1556 void
1557 argv_init (struct argv *a)
1559 a->capacity = 0;
1560 a->argc = 0;
1561 a->argv = NULL;
1562 a->system_str = NULL;
1565 struct argv
1566 argv_new (void)
1568 struct argv ret;
1569 argv_init (&ret);
1570 return ret;
1573 void
1574 argv_reset (struct argv *a)
1576 size_t i;
1577 for (i = 0; i < a->argc; ++i)
1578 free (a->argv[i]);
1579 free (a->argv);
1580 free (a->system_str);
1581 argv_init (a);
1584 static void
1585 argv_extend (struct argv *a, const size_t newcap)
1587 if (newcap > a->capacity)
1589 char **newargv;
1590 size_t i;
1591 ALLOC_ARRAY_CLEAR (newargv, char *, newcap);
1592 for (i = 0; i < a->argc; ++i)
1593 newargv[i] = a->argv[i];
1594 free (a->argv);
1595 a->argv = newargv;
1596 a->capacity = newcap;
1600 static void
1601 argv_grow (struct argv *a, const size_t add)
1603 const size_t newargc = a->argc + add + 1;
1604 ASSERT (newargc > a->argc);
1605 argv_extend (a, adjust_power_of_2 (newargc));
1608 static void
1609 argv_append (struct argv *a, char *str) /* str must have been malloced or be NULL */
1611 argv_grow (a, 1);
1612 a->argv[a->argc++] = str;
1615 static void
1616 argv_system_str_append (struct argv *a, const char *str, const bool enquote)
1618 if (str)
1620 char *newstr;
1622 /* compute length of new system_str */
1623 size_t l = strlen (str) + 1; /* space for new string plus trailing '\0' */
1624 if (a->system_str)
1625 l += strlen (a->system_str) + 1; /* space for existing string + space (" ") separator */
1626 if (enquote)
1627 l += 2; /* space for two quotes */
1629 /* build new system_str */
1630 newstr = (char *) malloc (l);
1631 newstr[0] = '\0';
1632 check_malloc_return (newstr);
1633 if (a->system_str)
1635 strcpy (newstr, a->system_str);
1636 strcat (newstr, " ");
1638 if (enquote)
1639 strcat (newstr, "\"");
1640 strcat (newstr, str);
1641 if (enquote)
1642 strcat (newstr, "\"");
1643 free (a->system_str);
1644 a->system_str = newstr;
1648 static char *
1649 argv_extract_cmd_name (const char *path)
1651 if (path)
1653 char *path_cp = strdup(path); /* POSIX basename() implementaions may modify its arguments */
1654 const char *bn = basename (path_cp);
1655 if (bn)
1657 char *ret = string_alloc (bn, NULL);
1658 char *dot = strrchr (ret, '.');
1659 if (dot)
1660 *dot = '\0';
1661 free(path_cp);
1662 if (ret[0] != '\0')
1663 return ret;
1666 return NULL;
1669 const char *
1670 argv_system_str (const struct argv *a)
1672 return a->system_str;
1675 struct argv
1676 argv_clone (const struct argv *a, const size_t headroom)
1678 struct argv r;
1679 size_t i;
1681 argv_init (&r);
1682 for (i = 0; i < headroom; ++i)
1683 argv_append (&r, NULL);
1684 if (a)
1686 for (i = 0; i < a->argc; ++i)
1687 argv_append (&r, string_alloc (a->argv[i], NULL));
1688 r.system_str = string_alloc (a->system_str, NULL);
1690 return r;
1693 struct argv
1694 argv_insert_head (const struct argv *a, const char *head)
1696 struct argv r;
1697 char *s;
1699 r = argv_clone (a, 1);
1700 r.argv[0] = string_alloc (head, NULL);
1701 s = r.system_str;
1702 r.system_str = string_alloc (head, NULL);
1703 if (s)
1705 argv_system_str_append (&r, s, false);
1706 free (s);
1708 return r;
1711 char *
1712 argv_term (const char **f)
1714 const char *p = *f;
1715 const char *term = NULL;
1716 size_t termlen = 0;
1718 if (*p == '\0')
1719 return NULL;
1721 while (true)
1723 const int c = *p;
1724 if (c == '\0')
1725 break;
1726 if (term)
1728 if (!isspace (c))
1729 ++termlen;
1730 else
1731 break;
1733 else
1735 if (!isspace (c))
1737 term = p;
1738 termlen = 1;
1741 ++p;
1743 *f = p;
1745 if (term)
1747 char *ret;
1748 ASSERT (termlen > 0);
1749 ret = malloc (termlen + 1);
1750 check_malloc_return (ret);
1751 memcpy (ret, term, termlen);
1752 ret[termlen] = '\0';
1753 return ret;
1755 else
1756 return NULL;
1759 const char *
1760 argv_str (const struct argv *a, struct gc_arena *gc, const unsigned int flags)
1762 if (a->argv)
1763 return print_argv ((const char **)a->argv, gc, flags);
1764 else
1765 return "";
1768 void
1769 argv_msg (const int msglev, const struct argv *a)
1771 struct gc_arena gc = gc_new ();
1772 msg (msglev, "%s", argv_str (a, &gc, 0));
1773 gc_free (&gc);
1776 void
1777 argv_msg_prefix (const int msglev, const struct argv *a, const char *prefix)
1779 struct gc_arena gc = gc_new ();
1780 msg (msglev, "%s: %s", prefix, argv_str (a, &gc, 0));
1781 gc_free (&gc);
1784 void
1785 argv_printf (struct argv *a, const char *format, ...)
1787 va_list arglist;
1788 va_start (arglist, format);
1789 argv_printf_arglist (a, format, 0, arglist);
1790 va_end (arglist);
1793 void
1794 argv_printf_cat (struct argv *a, const char *format, ...)
1796 va_list arglist;
1797 va_start (arglist, format);
1798 argv_printf_arglist (a, format, APA_CAT, arglist);
1799 va_end (arglist);
1802 void
1803 argv_printf_arglist (struct argv *a, const char *format, const unsigned int flags, va_list arglist)
1805 struct gc_arena gc = gc_new ();
1806 char *term;
1807 const char *f = format;
1809 if (!(flags & APA_CAT))
1810 argv_reset (a);
1811 argv_extend (a, 1); /* ensure trailing NULL */
1813 while ((term = argv_term (&f)) != NULL)
1815 if (term[0] == '%')
1817 if (!strcmp (term, "%s"))
1819 char *s = va_arg (arglist, char *);
1820 if (!s)
1821 s = "";
1822 argv_append (a, string_alloc (s, NULL));
1823 argv_system_str_append (a, s, true);
1825 else if (!strcmp (term, "%sc"))
1827 char *s = va_arg (arglist, char *);
1828 if (s)
1830 int nparms;
1831 char *parms[MAX_PARMS+1];
1832 int i;
1834 nparms = parse_line (s, parms, MAX_PARMS, "SCRIPT-ARGV", 0, D_ARGV_PARSE_CMD, &gc);
1835 if (nparms)
1837 for (i = 0; i < nparms; ++i)
1838 argv_append (a, string_alloc (parms[i], NULL));
1840 else
1841 argv_append (a, string_alloc (s, NULL));
1843 argv_system_str_append (a, s, false);
1845 else
1847 argv_append (a, string_alloc ("", NULL));
1848 argv_system_str_append (a, "echo", false);
1851 else if (!strcmp (term, "%d"))
1853 char numstr[64];
1854 openvpn_snprintf (numstr, sizeof (numstr), "%d", va_arg (arglist, int));
1855 argv_append (a, string_alloc (numstr, NULL));
1856 argv_system_str_append (a, numstr, false);
1858 else if (!strcmp (term, "%u"))
1860 char numstr[64];
1861 openvpn_snprintf (numstr, sizeof (numstr), "%u", va_arg (arglist, unsigned int));
1862 argv_append (a, string_alloc (numstr, NULL));
1863 argv_system_str_append (a, numstr, false);
1865 else if (!strcmp (term, "%s/%d"))
1867 char numstr[64];
1868 char *s = va_arg (arglist, char *);
1870 if (!s)
1871 s = "";
1873 openvpn_snprintf (numstr, sizeof (numstr), "%d", va_arg (arglist, int));
1876 const size_t len = strlen(s) + strlen(numstr) + 2;
1877 char *combined = (char *) malloc (len);
1878 check_malloc_return (combined);
1880 strcpy (combined, s);
1881 strcat (combined, "/");
1882 strcat (combined, numstr);
1883 argv_append (a, combined);
1884 argv_system_str_append (a, combined, false);
1887 else if (!strcmp (term, "%s%sc"))
1889 char *s1 = va_arg (arglist, char *);
1890 char *s2 = va_arg (arglist, char *);
1891 char *combined;
1892 char *cmd_name;
1894 if (!s1) s1 = "";
1895 if (!s2) s2 = "";
1896 combined = (char *) malloc (strlen(s1) + strlen(s2) + 1);
1897 check_malloc_return (combined);
1898 strcpy (combined, s1);
1899 strcat (combined, s2);
1900 argv_append (a, combined);
1902 cmd_name = argv_extract_cmd_name (combined);
1903 if (cmd_name)
1905 argv_system_str_append (a, cmd_name, false);
1906 free (cmd_name);
1909 else
1910 ASSERT (0);
1911 free (term);
1913 else
1915 argv_append (a, term);
1916 argv_system_str_append (a, term, false);
1919 gc_free (&gc);
1922 #ifdef ARGV_TEST
1923 void
1924 argv_test (void)
1926 struct gc_arena gc = gc_new ();
1927 const char *s;
1929 struct argv a;
1931 argv_init (&a);
1932 argv_printf (&a, "%sc foo bar %s", "c:\\\\src\\\\test\\\\jyargs.exe", "foo bar");
1933 argv_msg_prefix (M_INFO, &a, "ARGV");
1934 msg (M_INFO, "ARGV-S: %s", argv_system_str(&a));
1935 /*openvpn_execve_check (&a, NULL, 0, "command failed");*/
1937 argv_printf (&a, "%sc %s %s", "c:\\\\src\\\\test files\\\\batargs.bat", "foo", "bar");
1938 argv_msg_prefix (M_INFO, &a, "ARGV");
1939 msg (M_INFO, "ARGV-S: %s", argv_system_str(&a));
1940 /*openvpn_execve_check (&a, NULL, 0, "command failed");*/
1942 argv_printf (&a, "%s%sc foo bar %s %s/%d %d %u", "/foo", "/bar.exe", "one two", "1.2.3.4", 24, -69, 96);
1943 argv_msg_prefix (M_INFO, &a, "ARGV");
1944 msg (M_INFO, "ARGV-S: %s", argv_system_str(&a));
1945 /*openvpn_execve_check (&a, NULL, 0, "command failed");*/
1947 argv_printf (&a, "this is a %s test of int %d unsigned %u", "FOO", -69, 42);
1948 s = argv_str (&a, &gc, PA_BRACKET);
1949 printf ("PF: %s\n", s);
1950 printf ("PF-S: %s\n", argv_system_str(&a));
1953 struct argv b = argv_insert_head (&a, "MARK");
1954 s = argv_str (&b, &gc, PA_BRACKET);
1955 printf ("PF: %s\n", s);
1956 printf ("PF-S: %s\n", argv_system_str(&b));
1957 argv_reset (&b);
1960 argv_printf (&a, "%sc foo bar %d", "\"multi term\" command following \\\"spaces", 99);
1961 s = argv_str (&a, &gc, PA_BRACKET);
1962 printf ("PF: %s\n", s);
1963 printf ("PF-S: %s\n", argv_system_str(&a));
1964 argv_reset (&a);
1966 s = argv_str (&a, &gc, PA_BRACKET);
1967 printf ("PF: %s\n", s);
1968 printf ("PF-S: %s\n", argv_system_str(&a));
1969 argv_reset (&a);
1971 argv_printf (&a, "foo bar %d", 99);
1972 argv_printf_cat (&a, "bar %d foo %sc", 42, "nonesuch");
1973 argv_printf_cat (&a, "cool %s %d u %s/%d end", "frood", 4, "hello", 7);
1974 s = argv_str (&a, &gc, PA_BRACKET);
1975 printf ("PF: %s\n", s);
1976 printf ("PF-S: %s\n", argv_system_str(&a));
1977 argv_reset (&a);
1979 #if 0
1981 char line[512];
1982 while (fgets (line, sizeof(line), stdin) != NULL)
1984 char *term;
1985 const char *f = line;
1986 int i = 0;
1988 while ((term = argv_term (&f)) != NULL)
1990 printf ("[%d] '%s'\n", i, term);
1991 ++i;
1992 free (term);
1996 #endif
1998 argv_reset (&a);
1999 gc_free (&gc);
2001 #endif
2004 * Remove security-sensitive strings from control message
2005 * so that they will not be output to log file.
2007 const char *
2008 sanitize_control_message(const char *src, struct gc_arena *gc)
2010 char *ret = gc_malloc (strlen(src)+1, false, gc);
2011 char *dest = ret;
2012 bool redact = false;
2013 int skip = 0;
2015 for (;;)
2017 const char c = *src;
2018 if (c == '\0')
2019 break;
2020 if (c == 'S' && !strncmp(src, "SESS_ID_", 8))
2022 skip = 7;
2023 redact = true;
2025 else if (c == 'e' && !strncmp(src, "echo ", 5))
2027 skip = 4;
2028 redact = true;
2031 if (c == ',') /* end of redacted item? */
2033 skip = 0;
2034 redact = false;
2037 if (redact)
2039 if (skip > 0)
2041 --skip;
2042 *dest++ = c;
2045 else
2046 *dest++ = c;
2048 ++src;
2050 *dest = '\0';
2051 return ret;
2055 * Will set or query for a global compat flag. To modify the compat flags
2056 * the COMPAT_FLAG_SET must be bitwise ORed together with the flag to set.
2057 * If no "operator" flag is given it defaults to COMPAT_FLAG_QUERY,
2058 * which returns the flag state.
2060 * @param flag Flag to be set/queried for bitwise ORed with the operator flag
2061 * @return Returns 0 if the flag is not set, otherwise the 'flag' value is returned
2063 bool
2064 compat_flag (unsigned int flag)
2066 static unsigned int compat_flags = 0;
2068 if (flag & COMPAT_FLAG_SET)
2069 compat_flags |= (flag >> 1);
2071 return (compat_flags & (flag >> 1));