aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorChristian Grothoff <christian@grothoff.org>2016-03-31 18:52:13 +0000
committerChristian Grothoff <christian@grothoff.org>2016-03-31 18:52:13 +0000
commit669d5032383c22014233fe0732a5485494b1b469 (patch)
treea97f92769defed730ad0458f4e754edfe045dde3
parent2f89dd84130dbeeb6166ebf9500f3be8201b3023 (diff)
downloadgnunet-669d5032383c22014233fe0732a5485494b1b469.tar.gz
gnunet-669d5032383c22014233fe0732a5485494b1b469.zip
extend GNUNET_OS-API to allow re-use of os_installation logic for programs with different libs, paths, binaries and environment variables
-rw-r--r--src/include/gnunet_os_lib.h60
-rw-r--r--src/util/os_installation.c188
2 files changed, 193 insertions, 55 deletions
diff --git a/src/include/gnunet_os_lib.h b/src/include/gnunet_os_lib.h
index eca64b7f1..8cd4a4578 100644
--- a/src/include/gnunet_os_lib.h
+++ b/src/include/gnunet_os_lib.h
@@ -200,6 +200,66 @@ enum GNUNET_OS_ProcessStatusType
200 200
201 201
202/** 202/**
203 * Project-specific data used to help the OS subsystem
204 * find installation paths.
205 */
206struct GNUNET_OS_ProjectData
207{
208 /**
209 * Name of a library that is installed in the "lib/" directory of
210 * the project, such as "libgnunetutil". Used to locate the
211 * installation by scanning dependencies of the current process.
212 */
213 const char *libname;
214
215 /**
216 * Name of the project that is used in the "libexec" prefix, For
217 * example, "gnunet". Certain helper binaries are then expected to
218 * be installed in "$PREFIX/libexec/gnunet/" and resources in
219 * "$PREFIX/share/gnunet/".
220 */
221 const char *project_dirname;
222
223 /**
224 * Name of a project-specific binary that should be in "$PREFIX/bin/".
225 * Used to determine installation path from $PATH variable.
226 * For example "gnunet-arm". On W32, ".exe" should be omitted.
227 */
228 const char *binary_name;
229
230 /**
231 * Name of an environment variable that can be used to override
232 * installation path detection, for example "GNUNET_PREFIX".
233 */
234 const char *env_varname;
235
236 /**
237 * Alternative name of an environment variable that can be used to
238 * override installation path detection, if "env_varname" is not
239 * set. Again, for example, "GNUNET_PREFIX".
240 */
241 const char *env_varname_alt;
242
243};
244
245
246/**
247 * Return default project data used by 'libgnunetutil' for GNUnet.
248 */
249const struct GNUNET_OS_ProjectData *
250GNUNET_OS_project_data_default (void);
251
252
253/**
254 * Setup OS subsystem with project data.
255 *
256 * @param pd project data used to determine paths.
257 */
258void
259GNUNET_OS_init (const struct GNUNET_OS_ProjectData *pd);
260
261
262/**
203 * Get the path to a specific GNUnet installation directory or, with 263 * Get the path to a specific GNUnet installation directory or, with
204 * #GNUNET_OS_IPK_SELF_PREFIX, the current running apps installation 264 * #GNUNET_OS_IPK_SELF_PREFIX, the current running apps installation
205 * directory. 265 * directory.
diff --git a/src/util/os_installation.c b/src/util/os_installation.c
index 31a2647c2..38cf7b539 100644
--- a/src/util/os_installation.c
+++ b/src/util/os_installation.c
@@ -1,6 +1,6 @@
1/* 1/*
2 This file is part of GNUnet. 2 This file is part of GNUnet.
3 Copyright (C) 2006-2014 GNUnet e.V. 3 Copyright (C) 2006-2016 GNUnet e.V.
4 4
5 GNUnet is free software; you can redistribute it and/or modify 5 GNUnet is free software; you can redistribute it and/or modify
6 it under the terms of the GNU General Public License as published 6 it under the terms of the GNU General Public License as published
@@ -22,6 +22,11 @@
22 * @file src/util/os_installation.c 22 * @file src/util/os_installation.c
23 * @brief get paths used by the program 23 * @brief get paths used by the program
24 * @author Milan 24 * @author Milan
25 * @author Christian Fuchs
26 * @author Christian Grothoff
27 * @author Matthias Wachs
28 * @author Heikki Lindholm
29 * @author LRN
25 */ 30 */
26#include <sys/stat.h> 31#include <sys/stat.h>
27#include <stdlib.h> 32#include <stdlib.h>
@@ -44,6 +49,47 @@
44#define LOG_STRERROR_FILE(kind,syscall,filename) GNUNET_log_from_strerror_file (kind, "util", syscall, filename) 49#define LOG_STRERROR_FILE(kind,syscall,filename) GNUNET_log_from_strerror_file (kind, "util", syscall, filename)
45 50
46 51
52/**
53 * Default project data used for installation path detection
54 * for GNUnet (core).
55 */
56static const struct GNUNET_OS_ProjectData default_pd = {
57 .libname = "libgnunetutil",
58 .project_dirname = "gnunet",
59 .binary_name = "gnunet-arm",
60 .env_varname = "GNUNET_PREFIX",
61};
62
63/**
64 * Which project data do we currently use for installation
65 * path detection? Never NULL.
66 */
67static const struct GNUNET_OS_ProjectData *current_pd = &default_pd;
68
69/**
70 * Return default project data used by 'libgnunetutil' for GNUnet.
71 */
72const struct GNUNET_OS_ProjectData *
73GNUNET_OS_project_data_default (void)
74{
75 return &default_pd;
76}
77
78
79/**
80 * Setup OS subsystem with project data.
81 *
82 * @param pd project data used to determine paths
83 */
84void
85GNUNET_OS_init (const struct GNUNET_OS_ProjectData *pd)
86{
87 GNUNET_assert (NULL != pd);
88 current_pd = pd;
89}
90
91
92
47#if LINUX 93#if LINUX
48/** 94/**
49 * Try to determine path by reading /proc/PID/exe 95 * Try to determine path by reading /proc/PID/exe
@@ -66,7 +112,8 @@ get_path_from_proc_maps ()
66 { 112 {
67 if ((1 == 113 if ((1 ==
68 SSCANF (line, "%*x-%*x %*c%*c%*c%*c %*x %*2x:%*2x %*u%*[ ]%1023s", dir)) && 114 SSCANF (line, "%*x-%*x %*c%*c%*c%*c %*x %*2x:%*2x %*u%*[ ]%1023s", dir)) &&
69 (NULL != (lgu = strstr (dir, "libgnunetutil")))) 115 (NULL != (lgu = strstr (dir,
116 current_pd->libname))))
70 { 117 {
71 lgu[0] = '\0'; 118 lgu[0] = '\0';
72 FCLOSE (f); 119 FCLOSE (f);
@@ -89,6 +136,7 @@ get_path_from_proc_exe ()
89 char fn[64]; 136 char fn[64];
90 char lnk[1024]; 137 char lnk[1024];
91 ssize_t size; 138 ssize_t size;
139 char *lep;
92 140
93 GNUNET_snprintf (fn, sizeof (fn), "/proc/%u/exe", getpid ()); 141 GNUNET_snprintf (fn, sizeof (fn), "/proc/%u/exe", getpid ());
94 size = readlink (fn, lnk, sizeof (lnk) - 1); 142 size = readlink (fn, lnk, sizeof (lnk) - 1);
@@ -101,11 +149,15 @@ get_path_from_proc_exe ()
101 lnk[size] = '\0'; 149 lnk[size] = '\0';
102 while ((lnk[size] != '/') && (size > 0)) 150 while ((lnk[size] != '/') && (size > 0))
103 size--; 151 size--;
152 GNUNET_asprintf (&lep,
153 "/%s/libexec/",
154 current_pd->project_dirname);
104 /* test for being in lib/gnunet/libexec/ or lib/MULTIARCH/gnunet/libexec */ 155 /* test for being in lib/gnunet/libexec/ or lib/MULTIARCH/gnunet/libexec */
105 if ( (size > strlen ("/gnunet/libexec/")) && 156 if ( (size > strlen (lep)) &&
106 (0 == strcmp ("/gnunet/libexec/", 157 (0 == strcmp (lep,
107 &lnk[size - strlen ("/gnunet/libexec/")])) ) 158 &lnk[size - strlen (lep)])) )
108 size -= strlen ("gnunet/libexec/"); 159 size -= strlen (lep) - 1;
160 GNUNET_free (lep);
109 if ((size < 4) || (lnk[size - 4] != '/')) 161 if ((size < 4) || (lnk[size - 4] != '/'))
110 { 162 {
111 /* not installed in "/bin/" -- binary path probably useless */ 163 /* not installed in "/bin/" -- binary path probably useless */
@@ -127,7 +179,9 @@ static HINSTANCE dll_instance;
127 * and hInstance saving. 179 * and hInstance saving.
128 */ 180 */
129BOOL WINAPI 181BOOL WINAPI
130DllMain (HINSTANCE hinstDLL, DWORD fdwReason, LPVOID lpvReserved) 182DllMain (HINSTANCE hinstDLL,
183 DWORD fdwReason,
184 LPVOID lpvReserved)
131{ 185{
132 switch (fdwReason) 186 switch (fdwReason)
133 { 187 {
@@ -168,9 +222,12 @@ get_path_from_module_filename ()
168 do 222 do
169 { 223 {
170 pathlen = pathlen * 2; 224 pathlen = pathlen * 2;
171 modulepath = GNUNET_realloc (modulepath, pathlen * sizeof (wchar_t)); 225 modulepath = GNUNET_realloc (modulepath,
226 pathlen * sizeof (wchar_t));
172 SetLastError (0); 227 SetLastError (0);
173 real_pathlen = GetModuleFileNameW (dll_instance, modulepath, pathlen * sizeof (wchar_t)); 228 real_pathlen = GetModuleFileNameW (dll_instance,
229 modulepath,
230 pathlen * sizeof (wchar_t));
174 } while (real_pathlen >= pathlen && pathlen < 16*1024); 231 } while (real_pathlen >= pathlen && pathlen < 16*1024);
175 if (real_pathlen >= pathlen) 232 if (real_pathlen >= pathlen)
176 GNUNET_assert (0); 233 GNUNET_assert (0);
@@ -234,10 +291,12 @@ get_path_from_module_filename ()
234 * Signature of the '_NSGetExecutablePath" function. 291 * Signature of the '_NSGetExecutablePath" function.
235 * 292 *
236 * @param buf where to write the path 293 * @param buf where to write the path
237 * @param number of bytes available in 'buf' 294 * @param number of bytes available in @a buf
238 * @return 0 on success, otherwise desired number of bytes is stored in 'bufsize' 295 * @return 0 on success, otherwise desired number of bytes is stored in 'bufsize'
239 */ 296 */
240typedef int (*MyNSGetExecutablePathProto) (char *buf, size_t * bufsize); 297typedef int
298(*MyNSGetExecutablePathProto) (char *buf,
299 size_t *bufsize);
241 300
242 301
243/** 302/**
@@ -294,7 +353,8 @@ get_path_from_dyld_image ()
294 c = _dyld_image_count (); 353 c = _dyld_image_count ();
295 for (i = 0; i < c; i++) 354 for (i = 0; i < c; i++)
296 { 355 {
297 if (((const void *) _dyld_get_image_header (i)) != (const void *)&_mh_dylib_header) 356 if (((const void *) _dyld_get_image_header (i)) !=
357 ((const void *) &_mh_dylib_header) )
298 continue; 358 continue;
299 path = _dyld_get_image_name (i); 359 path = _dyld_get_image_name (i);
300 if ( (NULL == path) || (0 == strlen (path)) ) 360 if ( (NULL == path) || (0 == strlen (path)) )
@@ -376,7 +436,11 @@ get_path_from_GNUNET_PREFIX ()
376{ 436{
377 const char *p; 437 const char *p;
378 438
379 if (NULL != (p = getenv ("GNUNET_PREFIX"))) 439 if ( (NULL != current_pd->env_varname) &&
440 (NULL != (p = getenv (current_pd->env_varname))) )
441 return GNUNET_strdup (p);
442 if ( (NULL != current_pd->env_varname_alt) &&
443 (NULL != (p = getenv (current_pd->env_varname_alt))) )
380 return GNUNET_strdup (p); 444 return GNUNET_strdup (p);
381 return NULL; 445 return NULL;
382} 446}
@@ -399,7 +463,8 @@ os_get_gnunet_path ()
399 if (NULL != (ret = get_path_from_proc_maps ())) 463 if (NULL != (ret = get_path_from_proc_maps ()))
400 return ret; 464 return ret;
401 /* try path *first*, before /proc/exe, as /proc/exe can be wrong */ 465 /* try path *first*, before /proc/exe, as /proc/exe can be wrong */
402 if (NULL != (ret = get_path_from_PATH ("gnunet-arm"))) 466 if ( (NULL != current_pd->binary_name) &&
467 (NULL != (ret = get_path_from_PATH (current_pd->binary_name))) )
403 return ret; 468 return ret;
404 if (NULL != (ret = get_path_from_proc_exe ())) 469 if (NULL != (ret = get_path_from_proc_exe ()))
405 return ret; 470 return ret;
@@ -414,20 +479,20 @@ os_get_gnunet_path ()
414 if (NULL != (ret = get_path_from_NSGetExecutablePath ())) 479 if (NULL != (ret = get_path_from_NSGetExecutablePath ()))
415 return ret; 480 return ret;
416#endif 481#endif
417 if (NULL != (ret = get_path_from_PATH ("gnunet-arm"))) 482 if ( (NULL != current_pd->binary_name) &&
483 (NULL != (ret = get_path_from_PATH (current_pd->binary_name))) )
418 return ret; 484 return ret;
419 /* other attempts here */ 485 /* other attempts here */
420 LOG (GNUNET_ERROR_TYPE_ERROR, 486 LOG (GNUNET_ERROR_TYPE_ERROR,
421 _("Could not determine installation path for %s. Set `%s' environment variable.\n"), 487 _("Could not determine installation path for %s. Set `%s' environment variable.\n"),
422 "GNUnet", "GNUNET_PREFIX"); 488 current_pd->project_dirname,
489 current_pd->env_varname);
423 return NULL; 490 return NULL;
424} 491}
425 492
426 493
427/** 494/**
428 * @brief get the path to current app's bin/ 495 * @brief get the path to current app's bin/
429 * @author Milan
430 *
431 * @return a pointer to the executable path, or NULL on error 496 * @return a pointer to the executable path, or NULL on error
432 */ 497 */
433static char * 498static char *
@@ -455,14 +520,13 @@ os_get_exec_path ()
455/** 520/**
456 * @brief get the path to a specific GNUnet installation directory or, 521 * @brief get the path to a specific GNUnet installation directory or,
457 * with #GNUNET_OS_IPK_SELF_PREFIX, the current running apps installation directory 522 * with #GNUNET_OS_IPK_SELF_PREFIX, the current running apps installation directory
458 * @author Milan
459 * @return a pointer to the dir path (to be freed by the caller) 523 * @return a pointer to the dir path (to be freed by the caller)
460 */ 524 */
461char * 525char *
462GNUNET_OS_installation_get_path (enum GNUNET_OS_InstallationPathKind dirkind) 526GNUNET_OS_installation_get_path (enum GNUNET_OS_InstallationPathKind dirkind)
463{ 527{
464 size_t n; 528 size_t n;
465 const char *dirname; 529 char *dirname;
466 char *execpath = NULL; 530 char *execpath = NULL;
467 char *tmp; 531 char *tmp;
468 char *multiarch; 532 char *multiarch;
@@ -533,21 +597,23 @@ GNUNET_OS_installation_get_path (enum GNUNET_OS_InstallationPathKind dirkind)
533 { 597 {
534 case GNUNET_OS_IPK_PREFIX: 598 case GNUNET_OS_IPK_PREFIX:
535 case GNUNET_OS_IPK_SELF_PREFIX: 599 case GNUNET_OS_IPK_SELF_PREFIX:
536 dirname = DIR_SEPARATOR_STR; 600 dirname = GNUNET_strdup (DIR_SEPARATOR_STR);
537 break; 601 break;
538 case GNUNET_OS_IPK_BINDIR: 602 case GNUNET_OS_IPK_BINDIR:
539 dirname = DIR_SEPARATOR_STR "bin" DIR_SEPARATOR_STR; 603 dirname = GNUNET_strdup (DIR_SEPARATOR_STR "bin" DIR_SEPARATOR_STR);
540 break; 604 break;
541 case GNUNET_OS_IPK_LIBDIR: 605 case GNUNET_OS_IPK_LIBDIR:
542 if (isbasedir) 606 if (isbasedir)
543 { 607 {
544 GNUNET_asprintf (&tmp, 608 GNUNET_asprintf (&tmp,
545 "%s%s%s%s%s", 609 "%s%s%s%s%s%s%s",
546 execpath, 610 execpath,
547 DIR_SEPARATOR_STR "lib", 611 DIR_SEPARATOR_STR "lib",
548 (NULL != multiarch) ? DIR_SEPARATOR_STR : "", 612 (NULL != multiarch) ? DIR_SEPARATOR_STR : "",
549 (NULL != multiarch) ? multiarch : "", 613 (NULL != multiarch) ? multiarch : "",
550 DIR_SEPARATOR_STR "gnunet" DIR_SEPARATOR_STR); 614 DIR_SEPARATOR_STR,
615 current_pd->project_dirname,
616 DIR_SEPARATOR_STR);
551 if (GNUNET_YES == 617 if (GNUNET_YES ==
552 GNUNET_DISK_directory_test (tmp, GNUNET_YES)) 618 GNUNET_DISK_directory_test (tmp, GNUNET_YES))
553 { 619 {
@@ -556,10 +622,12 @@ GNUNET_OS_installation_get_path (enum GNUNET_OS_InstallationPathKind dirkind)
556 } 622 }
557 GNUNET_free (tmp); 623 GNUNET_free (tmp);
558 tmp = NULL; 624 tmp = NULL;
625 dirname = NULL;
559 if (4 == sizeof (void *)) 626 if (4 == sizeof (void *))
560 { 627 {
561 dirname = 628 GNUNET_asprintf (&dirname,
562 DIR_SEPARATOR_STR "lib32" DIR_SEPARATOR_STR "gnunet" DIR_SEPARATOR_STR; 629 DIR_SEPARATOR_STR "lib32" DIR_SEPARATOR_STR "%s" DIR_SEPARATOR_STR,
630 current_pd->project_dirname);
563 GNUNET_asprintf (&tmp, 631 GNUNET_asprintf (&tmp,
564 "%s%s", 632 "%s%s",
565 execpath, 633 execpath,
@@ -567,8 +635,9 @@ GNUNET_OS_installation_get_path (enum GNUNET_OS_InstallationPathKind dirkind)
567 } 635 }
568 if (8 == sizeof (void *)) 636 if (8 == sizeof (void *))
569 { 637 {
570 dirname = 638 GNUNET_asprintf (&dirname,
571 DIR_SEPARATOR_STR "lib64" DIR_SEPARATOR_STR "gnunet" DIR_SEPARATOR_STR; 639 DIR_SEPARATOR_STR "lib64" DIR_SEPARATOR_STR "%s" DIR_SEPARATOR_STR,
640 current_pd->project_dirname);
572 GNUNET_asprintf (&tmp, 641 GNUNET_asprintf (&tmp,
573 "%s%s", 642 "%s%s",
574 execpath, 643 execpath,
@@ -580,34 +649,38 @@ GNUNET_OS_installation_get_path (enum GNUNET_OS_InstallationPathKind dirkind)
580 GNUNET_DISK_directory_test (tmp, GNUNET_YES)) ) 649 GNUNET_DISK_directory_test (tmp, GNUNET_YES)) )
581 { 650 {
582 GNUNET_free (execpath); 651 GNUNET_free (execpath);
652 GNUNET_free_non_null (dirname);
583 return tmp; 653 return tmp;
584 } 654 }
585 GNUNET_free (tmp); 655 GNUNET_free (tmp);
656 GNUNET_free_non_null (dirname);
586 } 657 }
587 dirname = DIR_SEPARATOR_STR "gnunet" DIR_SEPARATOR_STR; 658 GNUNET_asprintf (&dirname,
659 DIR_SEPARATOR_STR "%s" DIR_SEPARATOR_STR,
660 current_pd->project_dirname);
588 break; 661 break;
589 case GNUNET_OS_IPK_DATADIR: 662 case GNUNET_OS_IPK_DATADIR:
590 dirname = 663 GNUNET_asprintf (&dirname,
591 DIR_SEPARATOR_STR "share" DIR_SEPARATOR_STR "gnunet" DIR_SEPARATOR_STR; 664 DIR_SEPARATOR_STR "share" DIR_SEPARATOR_STR "%s" DIR_SEPARATOR_STR,
665 current_pd->project_dirname);
592 break; 666 break;
593 case GNUNET_OS_IPK_LOCALEDIR: 667 case GNUNET_OS_IPK_LOCALEDIR:
594 dirname = 668 dirname = GNUNET_strdup (DIR_SEPARATOR_STR "share" DIR_SEPARATOR_STR "locale" DIR_SEPARATOR_STR);
595 DIR_SEPARATOR_STR "share" DIR_SEPARATOR_STR "locale" DIR_SEPARATOR_STR;
596 break; 669 break;
597 case GNUNET_OS_IPK_ICONDIR: 670 case GNUNET_OS_IPK_ICONDIR:
598 dirname = 671 dirname = GNUNET_strdup (DIR_SEPARATOR_STR "share" DIR_SEPARATOR_STR "icons" DIR_SEPARATOR_STR);
599 DIR_SEPARATOR_STR "share" DIR_SEPARATOR_STR "icons" DIR_SEPARATOR_STR;
600 break; 672 break;
601 case GNUNET_OS_IPK_DOCDIR: 673 case GNUNET_OS_IPK_DOCDIR:
602 dirname = 674 GNUNET_asprintf (&dirname,
603 DIR_SEPARATOR_STR "share" DIR_SEPARATOR_STR "doc" DIR_SEPARATOR_STR \ 675 DIR_SEPARATOR_STR "share" DIR_SEPARATOR_STR "doc" DIR_SEPARATOR_STR "%s" DIR_SEPARATOR_STR,
604 "gnunet" DIR_SEPARATOR_STR; 676 current_pd->project_dirname);
605 break; 677 break;
606 case GNUNET_OS_IPK_LIBEXECDIR: 678 case GNUNET_OS_IPK_LIBEXECDIR:
607 if (isbasedir) 679 if (isbasedir)
608 { 680 {
609 dirname = 681 GNUNET_asprintf (&dirname,
610 DIR_SEPARATOR_STR "gnunet" DIR_SEPARATOR_STR "libexec" DIR_SEPARATOR_STR; 682 DIR_SEPARATOR_STR "%s" DIR_SEPARATOR_STR "libexec" DIR_SEPARATOR_STR,
683 current_pd->project_dirname);
611 GNUNET_asprintf (&tmp, 684 GNUNET_asprintf (&tmp,
612 "%s%s%s%s", 685 "%s%s%s%s",
613 execpath, 686 execpath,
@@ -618,15 +691,17 @@ GNUNET_OS_installation_get_path (enum GNUNET_OS_InstallationPathKind dirkind)
618 GNUNET_DISK_directory_test (tmp, GNUNET_YES)) 691 GNUNET_DISK_directory_test (tmp, GNUNET_YES))
619 { 692 {
620 GNUNET_free (execpath); 693 GNUNET_free (execpath);
694 GNUNET_free (dirname);
621 return tmp; 695 return tmp;
622 } 696 }
623 GNUNET_free (tmp); 697 GNUNET_free (tmp);
624 tmp = NULL; 698 tmp = NULL;
699 dirname = NULL;
625 if (4 == sizeof (void *)) 700 if (4 == sizeof (void *))
626 { 701 {
627 dirname = 702 GNUNET_asprintf (&dirname,
628 DIR_SEPARATOR_STR "lib32" DIR_SEPARATOR_STR "gnunet" DIR_SEPARATOR_STR \ 703 DIR_SEPARATOR_STR "lib32" DIR_SEPARATOR_STR "%s" DIR_SEPARATOR_STR "libexec" DIR_SEPARATOR_STR,
629 "libexec" DIR_SEPARATOR_STR; 704 current_pd->project_dirname);
630 GNUNET_asprintf (&tmp, 705 GNUNET_asprintf (&tmp,
631 "%s%s", 706 "%s%s",
632 execpath, 707 execpath,
@@ -634,9 +709,9 @@ GNUNET_OS_installation_get_path (enum GNUNET_OS_InstallationPathKind dirkind)
634 } 709 }
635 if (8 == sizeof (void *)) 710 if (8 == sizeof (void *))
636 { 711 {
637 dirname = 712 GNUNET_asprintf (&dirname,
638 DIR_SEPARATOR_STR "lib64" DIR_SEPARATOR_STR "gnunet" DIR_SEPARATOR_STR \ 713 DIR_SEPARATOR_STR "lib64" DIR_SEPARATOR_STR "%s" DIR_SEPARATOR_STR "libexec" DIR_SEPARATOR_STR,
639 "libexec" DIR_SEPARATOR_STR; 714 current_pd->project_dirname);
640 GNUNET_asprintf (&tmp, 715 GNUNET_asprintf (&tmp,
641 "%s%s", 716 "%s%s",
642 execpath, 717 execpath,
@@ -647,14 +722,15 @@ GNUNET_OS_installation_get_path (enum GNUNET_OS_InstallationPathKind dirkind)
647 GNUNET_DISK_directory_test (tmp, GNUNET_YES)) ) 722 GNUNET_DISK_directory_test (tmp, GNUNET_YES)) )
648 { 723 {
649 GNUNET_free (execpath); 724 GNUNET_free (execpath);
725 GNUNET_free_non_null (dirname);
650 return tmp; 726 return tmp;
651 } 727 }
652
653 GNUNET_free (tmp); 728 GNUNET_free (tmp);
729 GNUNET_free_non_null (dirname);
654 } 730 }
655 dirname = 731 GNUNET_asprintf (&dirname,
656 DIR_SEPARATOR_STR "gnunet" DIR_SEPARATOR_STR \ 732 DIR_SEPARATOR_STR "%s" DIR_SEPARATOR_STR "libexec" DIR_SEPARATOR_STR,
657 "libexec" DIR_SEPARATOR_STR; 733 current_pd->project_dirname);
658 break; 734 break;
659 default: 735 default:
660 GNUNET_free (execpath); 736 GNUNET_free (execpath);
@@ -685,7 +761,10 @@ GNUNET_OS_get_libexec_binary_path (const char *progname)
685 char *binary; 761 char *binary;
686 762
687 if ( (DIR_SEPARATOR == progname[0]) || 763 if ( (DIR_SEPARATOR == progname[0]) ||
688 (GNUNET_YES == GNUNET_STRINGS_path_is_absolute (progname, GNUNET_NO, NULL, NULL)) ) 764 (GNUNET_YES ==
765 GNUNET_STRINGS_path_is_absolute (progname,
766 GNUNET_NO,
767 NULL, NULL)) )
689 return GNUNET_strdup (progname); 768 return GNUNET_strdup (progname);
690 if (NULL != cache) 769 if (NULL != cache)
691 libexecdir = cache; 770 libexecdir = cache;
@@ -703,10 +782,9 @@ GNUNET_OS_get_libexec_binary_path (const char *progname)
703 782
704 783
705/** 784/**
706 * Check whether an executable exists and possibly 785 * Check whether an executable exists and possibly if the suid bit is
707 * if the suid bit is set on the file. 786 * set on the file. Attempts to find the file using the current PATH
708 * Attempts to find the file using the current 787 * environment variable as a search path.
709 * PATH environment variable as a search path.
710 * 788 *
711 * @param binary the name of the file to check. 789 * @param binary the name of the file to check.
712 * W32: must not have an .exe suffix. 790 * W32: must not have an .exe suffix.