Revision: 77288
          http://sourceforge.net/p/brlcad/code/77288
Author:   starseeker
Date:     2020-09-30 19:13:07 +0000 (Wed, 30 Sep 2020)
Log Message:
-----------
Redo the tclcad auto_path setup, be more agressive in init about setting 
tcl_library.  Gets closer to building and running, but vanilla Tcl/Tk 8.6 
installs Itcl 4, and most of our Tcl code doesn't explicitly call out version 3 
when doing a package require.

Modified Paths:
--------------
    brlcad/branches/thirdparty_rework/CMakeLists.txt
    brlcad/branches/thirdparty_rework/include/bu/app.h
    brlcad/branches/thirdparty_rework/src/libbu/dir.c
    brlcad/branches/thirdparty_rework/src/libtclcad/auto_path.c
    brlcad/branches/thirdparty_rework/src/libtclcad/bu.c
    brlcad/branches/thirdparty_rework/src/libtclcad/init.c
    brlcad/branches/thirdparty_rework/src/superbuild/CMakeLists.txt
    brlcad/branches/thirdparty_rework/src/tclscripts/CMakeLists.txt

Modified: brlcad/branches/thirdparty_rework/CMakeLists.txt
===================================================================
--- brlcad/branches/thirdparty_rework/CMakeLists.txt    2020-09-30 15:50:47 UTC 
(rev 77287)
+++ brlcad/branches/thirdparty_rework/CMakeLists.txt    2020-09-30 19:13:07 UTC 
(rev 77288)
@@ -2102,6 +2102,8 @@
 # Now put back the BRL-CAD flags
 RESTORE_CACHED_BUILD_FLAGS(_BRLCAD)
 
+set(TCL_VERSION "8.6")
+CONFIG_H_APPEND(BRLCAD "#define TCL_VERSION \"${TCL_VERSION}\"\n")
 
 set(ITCL_VERSION "3.4")
 CONFIG_H_APPEND(BRLCAD "#cmakedefine ITCL_VERSION \"${ITCL_VERSION}\"\n")

Modified: brlcad/branches/thirdparty_rework/include/bu/app.h
===================================================================
--- brlcad/branches/thirdparty_rework/include/bu/app.h  2020-09-30 15:50:47 UTC 
(rev 77287)
+++ brlcad/branches/thirdparty_rework/include/bu/app.h  2020-09-30 19:13:07 UTC 
(rev 77288)
@@ -237,6 +237,7 @@
     BU_DIR_DATA,    /**< (read-only) data files (share) */
     BU_DIR_DOC,     /**< (read-only) documentation, (DATA/doc) */
     BU_DIR_MAN,     /**< (read-only) manual pages, (DATA/man) */
+    BU_DIR_INSTALL, /**< (read-only) root dir of install target */
     BU_DIR_TEMP,    /**< (read/write) temporary files (TEMP) */
     BU_DIR_HOME,    /**< (read/write) user home directory (HOME) */
     BU_DIR_CACHE,   /**< (read/write) user cache directory (BU_CACHE_DIR) */

Modified: brlcad/branches/thirdparty_rework/src/libbu/dir.c
===================================================================
--- brlcad/branches/thirdparty_rework/src/libbu/dir.c   2020-09-30 15:50:47 UTC 
(rev 77287)
+++ brlcad/branches/thirdparty_rework/src/libbu/dir.c   2020-09-30 19:13:07 UTC 
(rev 77288)
@@ -561,6 +561,9 @@
                cpath = _bu_dir_brlcad_root(BRLCAD_MAN_DIR, 1);
                path_append(&vls, cpath);
                break;
+           case BU_DIR_INSTALL:
+               bu_vls_strcat(&vls, BRLCAD_ROOT);
+               break;
            case BU_DIR_TEMP:
                cpath = dir_temp(buf, MAXPATHLEN);
                path_append(&vls, cpath);

Modified: brlcad/branches/thirdparty_rework/src/libtclcad/auto_path.c
===================================================================
--- brlcad/branches/thirdparty_rework/src/libtclcad/auto_path.c 2020-09-30 
15:50:47 UTC (rev 77287)
+++ brlcad/branches/thirdparty_rework/src/libtclcad/auto_path.c 2020-09-30 
19:13:07 UTC (rev 77288)
@@ -48,40 +48,12 @@
 #endif
 
 #include "bu/app.h"
+#include "bu/path.h"
+#include "bu/ptbl.h"
 #include "tclcad.h"
 
 #define MAX_BUF 2048
 
-/* Appends a new path to the path list, preceded by BU_PATH_SEPARATOR.
- *
- * The path is specified as a sequence of string arguments, one per
- * directory, terminated by a (const char *)NULL argument.
- *
- * BU_DIR_SEPARATOR is inserted between the string arguments (but not
- * before or after the path).
- */
-static void
-join_path(struct bu_vls *path_list, ...)
-{
-    va_list ap;
-    const char *dir;
-
-    bu_vls_putc(path_list, BU_PATH_SEPARATOR);
-
-    va_start(ap, path_list);
-
-    dir = va_arg(ap, const char *);
-    while (dir != NULL) {
-       bu_vls_printf(path_list, "%s", dir);
-
-       dir = va_arg(ap, const char *);
-       if (dir != NULL) {
-           bu_vls_putc(path_list, BU_DIR_SEPARATOR);
-       }
-    }
-    va_end(ap);
-}
-
 /**
  * Set up the Tcl auto_path for locating various necessary BRL-CAD
  * scripting resources. Detect whether the current invocation is from
@@ -96,8 +68,7 @@
  * BRLCAD_ROOT/lib/iwidgetsIWIDGETS_VERSION/iwidgets.tcl
  * BRLCAD_ROOT/share/tclscripts/pkgIndex.tcl and subdirs
  *
- * if TCLCAD_LIBRARY_PATH is set
- *   append to search path
+ * if TCLCAD_LIBRARY_PATH is set append to search path.
  * get installation directory and invocation path
  * if being run from installation directory
  *   add installation paths to search path
@@ -108,189 +79,303 @@
 void
 tclcad_auto_path(Tcl_Interp *interp)
 {
-    struct bu_vls auto_path = BU_VLS_INIT_ZERO;
-    struct bu_vls lappend = BU_VLS_INIT_ZERO;
-    const char *library_path = NULL;
 
-    struct bu_vls root_buf = BU_VLS_INIT_ZERO;
-    const char *root = NULL;
-    const char *data = NULL;
-    struct bu_vls buffer = BU_VLS_INIT_ZERO;
-
-    const char *which_argv = NULL;
-    const char *srcpath = NULL;
-    int from_installed = 0;
-
-    int found_init_tcl = 0;
-    int found_tk_tcl = 0;
-    int found_itcl_tcl = 0;
-    int found_itk_tcl = 0;
-
-    char pathsep[2] = { BU_PATH_SEPARATOR, '\0' };
-
-    struct bu_vls initpath = BU_VLS_INIT_ZERO;
-    struct bu_vls tcl = BU_VLS_INIT_ZERO;
-    struct bu_vls itcl = BU_VLS_INIT_ZERO;
-#ifdef HAVE_TK
-    struct bu_vls tk = BU_VLS_INIT_ZERO;
-    struct bu_vls itk = BU_VLS_INIT_ZERO;
-    struct bu_vls iwidgets = BU_VLS_INIT_ZERO;
-#endif
-
     if (!interp) {
        /* nothing to do */
        return;
     }
 
+    /* Used for getenv calls */
+    const char *env = NULL;
+
+
     /* If we are using an external Tcl, we need the
      * location of its init file */
-    bu_vls_trunc(&initpath, 0);
+    int tcl_set = 0;
 #ifdef TCL_SYSTEM_INITTCL_PATH
+    struct bu_vls initpath = BU_VLS_INIT_ZERO;
     bu_vls_printf(&initpath, "set tcl_library {%s}", TCL_SYSTEM_INITTCL_PATH);
     if (Tcl_Eval(interp, bu_vls_addr(&initpath))) {
-       bu_log("Problem initializaing tcl_library to system init.tcl path: 
Tcl_Eval ERROR:\n%s\n", Tcl_GetStringResult(interp));
+       bu_log("Problem initializing tcl_library to system init.tcl path: 
Tcl_Eval ERROR:\n%s\n", Tcl_GetStringResult(interp));
+    } else {
+       tcl_set = 1;
     }
+    bu_vls_free(&initpath);
 #endif
 
-    bu_vls_printf(&tcl, "tcl%s", TCL_VERSION);
-    bu_vls_printf(&itcl, "itcl%s", ITCL_VERSION);
-#ifdef HAVE_TK
-    bu_vls_printf(&tk, "tk%s", TK_VERSION);
-    bu_vls_printf(&itk, "itk%s", ITCL_VERSION);
-    bu_vls_printf(&iwidgets, "iwidgets%s", IWIDGETS_VERSION);
-#endif
+    struct bu_ptbl paths = BU_PTBL_INIT_ZERO;
 
-    root = bu_brlcad_root("", 1);
-    bu_vls_printf(&root_buf, "%s", root);
-    root = bu_vls_addr(&root_buf);
-    data = bu_brlcad_root("share", 1);
+    /* If TCLCAD_LIBRARY_PATH is set, add to active paths. */
+    env = getenv("TCLCAD_LIBRARY_PATH");
+    if (env) {
+       struct bu_vls buffer = BU_VLS_INIT_ZERO;
+       /* limit path length from env var for sanity */
+       bu_vls_strncat(&buffer, env, MAX_BUF);
+       const char *p = bu_strdup(bu_vls_cstr(&buffer));
+       bu_ptbl_ins(&paths, (long *)p);
+       bu_vls_free(&buffer);
+    }
 
-    /* determine if TCLCAD_LIBRARY_PATH is set */
-    library_path = getenv("TCLCAD_LIBRARY_PATH");
-    if (library_path) {
-       /* it is set, set auto_path. limit buf just because. */
-       bu_vls_strncat(&auto_path, library_path, MAX_BUF);
+    /* See if user set ITCL_LIBRARY override */
+    int itcl_set = 0;
+    env = getenv("ITCL_LIBRARY");
+    if (env) {
+       struct bu_vls buffer = BU_VLS_INIT_ZERO;
+       bu_vls_strncat(&buffer, env, MAX_BUF);
+       bu_vls_printf(&buffer, "%citcl.tcl", BU_DIR_SEPARATOR);
+       if (bu_file_exists(bu_vls_cstr(&buffer), NULL)) {
+           const char *p = bu_strdup(bu_vls_cstr(&buffer));
+           bu_ptbl_ins(&paths, (long *)p);
+           itcl_set = 1;
+       } else {
+           bu_log("Warning: ITCL_LIBRARY environment variable is set to %s, 
but file itcl.tcl is not found in that directory, skipping.\n", env);
+       }
+       bu_vls_free(&buffer);
     }
 
-    /* make sure tcl_library path is in the auto_path */
-    bu_vls_sprintf(&buffer, "set tcl_library");
-    Tcl_Eval(interp, bu_vls_cstr(&buffer));
-    bu_vls_strncat(&auto_path, Tcl_GetStringResult(interp), MAX_BUF);
+    /* See if user set ITK_LIBRARY override */
+    int itk_set = 0;
+    env = getenv("ITK_LIBRARY");
+    if (env) {
+       struct bu_vls buffer = BU_VLS_INIT_ZERO;
+       bu_vls_strncat(&buffer, env, MAX_BUF);
+       bu_vls_printf(&buffer, "%citk.tcl", BU_DIR_SEPARATOR);
+       if (bu_file_exists(bu_vls_cstr(&buffer), NULL)) {
+           const char *p = bu_strdup(bu_vls_cstr(&buffer));
+           bu_ptbl_ins(&paths, (long *)p);
+       } else {
+           bu_log("Warning: ITK_LIBRARY environment variable is set to %s, but 
file itk.tcl is not found in that directory, skipping.\n", env);
+       }
+       bu_vls_free(&buffer);
+    }
 
-    /* get string of invocation binary */
-    which_argv = bu_which(bu_argv0_full_path());
-    if (!which_argv) {
-       which_argv = bu_argv0_full_path();
+    /* If tcl_library is defined in the interp, capture it for addition */
+    {
+       struct bu_vls buffer = BU_VLS_INIT_ZERO;
+       /* limit path length from env var for sanity */
+       bu_vls_sprintf(&buffer, "set tcl_library");
+       Tcl_Eval(interp, bu_vls_cstr(&buffer));
+       bu_vls_sprintf(&buffer, "%s", Tcl_GetStringResult(interp));
+       if (bu_vls_strlen(&buffer)) {
+           const char *p = bu_strdup(bu_vls_cstr(&buffer));
+           bu_ptbl_ins(&paths, (long *)p);
+       }
+       bu_vls_free(&buffer);
     }
 
-    /* get name of installation binary */
-    bu_vls_sprintf(&buffer, "%s%cbin%c%s", root, BU_DIR_SEPARATOR, 
BU_DIR_SEPARATOR, bu_getprogname());
+    /* Set up the subdirectories of interest.  Some are static, but some are
+     * version specific - we construct a table of all of them for easier
+     * use in subsequent testing. */
+    struct bu_ptbl lib_subpaths = BU_PTBL_INIT_ZERO;
+    struct bu_ptbl data_subpaths = BU_PTBL_INIT_ZERO;
+    {
+       const char *p = NULL;
+       struct bu_vls buffer = BU_VLS_INIT_ZERO;
 
-    /* are we running from an installed binary? if so add to path */
-    if (bu_file_exists(bu_vls_cstr(&buffer), NULL) && 
bu_file_same(bu_vls_cstr(&buffer), which_argv)) {
-       from_installed = 1;
-       join_path(&auto_path, root, "lib", NULL);
-       join_path(&auto_path, root, "lib", bu_vls_addr(&tcl), NULL);
+       bu_vls_sprintf(&buffer, "tcl%s", TCL_VERSION);
+       p = bu_strdup(bu_vls_cstr(&buffer));
+       bu_ptbl_ins(&lib_subpaths, (long *)p);
+
+       bu_vls_sprintf(&buffer, "itcl%s", ITCL_VERSION);
+       p = bu_strdup(bu_vls_cstr(&buffer));
+       bu_ptbl_ins(&lib_subpaths, (long *)p);
+
 #ifdef HAVE_TK
-       join_path(&auto_path, root, "lib", bu_vls_addr(&tk), NULL);
+       bu_vls_sprintf(&buffer, "tk%s", TK_VERSION);
+       p = bu_strdup(bu_vls_cstr(&buffer));
+       bu_ptbl_ins(&lib_subpaths, (long *)p);
+
+       bu_vls_sprintf(&buffer, "itk%s", ITCL_VERSION);
+       p = bu_strdup(bu_vls_cstr(&buffer));
+       bu_ptbl_ins(&lib_subpaths, (long *)p);
+
+       bu_vls_sprintf(&buffer, "iwidgets%s", IWIDGETS_VERSION);
+       p = bu_strdup(bu_vls_cstr(&buffer));
+       bu_ptbl_ins(&lib_subpaths, (long *)p);
 #endif
-       join_path(&auto_path, root, "lib", bu_vls_addr(&itcl), NULL);
-#ifdef HAVE_TK
-       join_path(&auto_path, root, "lib", bu_vls_addr(&itk), NULL);
-       join_path(&auto_path, root, "lib", bu_vls_addr(&iwidgets), NULL);
-#endif
-       join_path(&auto_path, data, "tclscripts", NULL);
-       join_path(&auto_path, data, "tclscripts", "lib", NULL);
-       join_path(&auto_path, data, "tclscripts", "util", NULL);
-       join_path(&auto_path, data, "tclscripts", "mged", NULL);
-       join_path(&auto_path, data, "tclscripts", "geometree", NULL);
-       join_path(&auto_path, data, "tclscripts", "graph", NULL);
-       join_path(&auto_path, data, "tclscripts", "rtwizard", NULL);
-       join_path(&auto_path, data, "tclscripts", "archer", NULL);
-       join_path(&auto_path, data, "tclscripts", "boteditor", NULL);
-       join_path(&auto_path, data, "tclscripts", "checker", NULL);
-       join_path(&auto_path, data, "tclscripts", "lod", NULL);
+
+       bu_vls_sprintf(&buffer, "tclscripts");
+       p = bu_strdup(bu_vls_cstr(&buffer));
+       bu_ptbl_ins(&data_subpaths, (long *)p);
+
+       bu_vls_sprintf(&buffer, "tclscripts%clib", BU_DIR_SEPARATOR);
+       p = bu_strdup(bu_vls_cstr(&buffer));
+       bu_ptbl_ins(&data_subpaths, (long *)p);
+
+       bu_vls_sprintf(&buffer, "tclscripts%cutil", BU_DIR_SEPARATOR);
+       p = bu_strdup(bu_vls_cstr(&buffer));
+       bu_ptbl_ins(&data_subpaths, (long *)p);
+
+       bu_vls_sprintf(&buffer, "tclscripts%cmged", BU_DIR_SEPARATOR);
+       p = bu_strdup(bu_vls_cstr(&buffer));
+       bu_ptbl_ins(&data_subpaths, (long *)p);
+
+       bu_vls_sprintf(&buffer, "tclscripts%cgeometree", BU_DIR_SEPARATOR);
+       p = bu_strdup(bu_vls_cstr(&buffer));
+       bu_ptbl_ins(&data_subpaths, (long *)p);
+
+       bu_vls_sprintf(&buffer, "tclscripts%crtwizard", BU_DIR_SEPARATOR);
+       p = bu_strdup(bu_vls_cstr(&buffer));
+       bu_ptbl_ins(&data_subpaths, (long *)p);
+
+       bu_vls_sprintf(&buffer, "tclscripts%carcher", BU_DIR_SEPARATOR);
+       p = bu_strdup(bu_vls_cstr(&buffer));
+       bu_ptbl_ins(&data_subpaths, (long *)p);
+
+       bu_vls_sprintf(&buffer, "tclscripts%cboteditor", BU_DIR_SEPARATOR);
+       p = bu_strdup(bu_vls_cstr(&buffer));
+       bu_ptbl_ins(&data_subpaths, (long *)p);
+
+       bu_vls_sprintf(&buffer, "tclscripts%cchecker", BU_DIR_SEPARATOR);
+       p = bu_strdup(bu_vls_cstr(&buffer));
+       bu_ptbl_ins(&data_subpaths, (long *)p);
+
+       bu_vls_sprintf(&buffer, "tclscripts%clod", BU_DIR_SEPARATOR);
+       p = bu_strdup(bu_vls_cstr(&buffer));
+       bu_ptbl_ins(&data_subpaths, (long *)p);
     }
 
-    /* be sure to check installation paths even if we aren't running from 
there */
-    if (!from_installed) {
-       join_path(&auto_path, root, "lib", NULL);
-       join_path(&auto_path, root, "lib", bu_vls_addr(&tcl), NULL);
-#ifdef HAVE_TK
-       join_path(&auto_path, root, "lib", bu_vls_addr(&tk), NULL);
-#endif
-       join_path(&auto_path, root, "lib", bu_vls_addr(&itcl), NULL);
-#ifdef HAVE_TK
-       join_path(&auto_path, root, "lib", bu_vls_addr(&itk), NULL);
-       join_path(&auto_path, root, "lib", bu_vls_addr(&iwidgets), NULL);
-#endif
-       join_path(&auto_path, data, "tclscripts", NULL);
-       join_path(&auto_path, data, "tclscripts", "lib", NULL);
-       join_path(&auto_path, data, "tclscripts", "util", NULL);
-       join_path(&auto_path, data, "tclscripts", "mged", NULL);
-       join_path(&auto_path, data, "tclscripts", "geometree", NULL);
-       join_path(&auto_path, data, "tclscripts", "graph", NULL);
-       join_path(&auto_path, data, "tclscripts", "rtwizard", NULL);
-       join_path(&auto_path, data, "tclscripts", "archer", NULL);
-       join_path(&auto_path, data, "tclscripts", "boteditor", NULL);
-       join_path(&auto_path, data, "tclscripts", "checker", NULL);
-       join_path(&auto_path, data, "tclscripts", "lod", NULL);
+    // The lib paths present some potential challenges.  Depending on where
+    // packages are at runtime, there are a variety of potential locations
+    // where they may be found.  To further complicate life, some of them
+    // may be in system locations and some in local locations.
+
+    // First off, see what's in BU_DIR_LIB.
+    char libdir[MAXPATHLEN] = {0};
+    struct bu_vls lib_path = BU_VLS_INIT_ZERO;
+    bu_dir(libdir, MAXPATHLEN, BU_DIR_LIB, NULL);
+    {
+       struct bu_ptbl found_subpaths = BU_PTBL_INIT_ZERO;
+       if (strlen(libdir)) {
+           // Have a library directory, see what's in it
+           for (size_t i = 0; i < BU_PTBL_LEN(&lib_subpaths); i++) {
+               const char *fname = (const char *)BU_PTBL_GET(&lib_subpaths, i);
+               bu_vls_sprintf(&lib_path, "%s%c%s", libdir, BU_DIR_SEPARATOR, 
fname);
+               if (bu_file_exists(bu_vls_cstr(&lib_path), NULL)) {
+                   // Have a path
+                   const char *p = bu_strdup(bu_vls_cstr(&lib_path));
+                   bu_ptbl_ins(&paths, (long *)p);
+                   bu_ptbl_ins(&found_subpaths, (long *)fname);
+               }
+           }
+           // Clear anything we found out of lib_subpaths - we don't need or
+           // want to find it again.  The more local to the install, the
+           // better...
+           for (size_t i = 0; i < BU_PTBL_LEN(&found_subpaths); i++) {
+               bu_ptbl_rm(&lib_subpaths, BU_PTBL_GET(&found_subpaths, i));
+           }
+       }
+       bu_ptbl_free(&found_subpaths);
     }
 
-    /*    printf("AUTO_PATH IS %s\n", bu_vls_addr(&auto_path)); */
+    // Determine if we're running from the final install location or from
+    // somewhere else, and whether the final install location has relevant
+    // files.  If we're in the non-final location, there is some
+    // extra work to do.
+    int installed = 0;
+    struct bu_vls w_root = BU_VLS_INIT_ZERO;
+    bu_path_component(&w_root, libdir, BU_PATH_DIRNAME);
+    {
+       char inst[MAXPATHLEN] = {0};
+       bu_dir(inst, MAXPATHLEN, BU_DIR_INSTALL, NULL);
+       if (BU_STR_EQUAL(bu_vls_cstr(&w_root), inst)) {
+           installed = 1;
+       }
+    }
 
-    /* see if user already set ITCL_LIBRARY override */
-    library_path = getenv("ITCL_LIBRARY");
-    if (!found_itcl_tcl && library_path) {
-       bu_vls_sprintf(&buffer, "%s%citcl.tcl", library_path, BU_DIR_SEPARATOR);
-       if (bu_file_exists(bu_vls_cstr(&buffer), NULL)) {
-           found_itcl_tcl=1;
+    // If we're not installed, we may be in a subbuild, in which case we
+    // need to go up the tree to find any not-yet-installed dependencies.
+    // The way the BRL-CAD subbuild is set up we should only need to go up
+    // one level, so that's all we implement right now.
+    if (!installed) {
+       // Get the actual lib directory name - that's what we'll be checking
+       // for in the parent dir.
+       struct bu_ptbl found_subpaths = BU_PTBL_INIT_ZERO;
+       struct bu_vls pdir = BU_VLS_INIT_ZERO;
+       struct bu_vls tdir = BU_VLS_INIT_ZERO;
+       struct bu_vls libstr = BU_VLS_INIT_ZERO;
+       bu_path_component(&libstr, libdir, BU_PATH_BASENAME);
+       bu_path_component(&pdir, bu_vls_cstr(&w_root), BU_PATH_DIRNAME);
+       bu_vls_sprintf(&tdir, "%s%c%s", bu_vls_cstr(&pdir), BU_DIR_SEPARATOR, 
bu_vls_cstr(&libstr));
+       // Have a library directory, see what's in it
+       if (bu_file_exists(bu_vls_cstr(&lib_path), NULL)) {
+           for (size_t i = 0; i < BU_PTBL_LEN(&lib_subpaths); i++) {
+               const char *fname = (const char *)BU_PTBL_GET(&lib_subpaths, i);
+               bu_vls_sprintf(&lib_path, "%s%c%s", libdir, BU_DIR_SEPARATOR, 
fname);
+               if (bu_file_exists(bu_vls_cstr(&lib_path), NULL)) {
+                   // Have a path
+                   const char *p = bu_strdup(bu_vls_cstr(&lib_path));
+                   bu_ptbl_ins(&paths, (long *)p);
+                   bu_ptbl_ins(&found_subpaths, (long *)fname);
+               }
+           }
+           // Clear anything we found out of lib_subpaths - we don't need or
+           // want to find it again.  The more local to the install, the
+           // better...
+           for (size_t i = 0; i < BU_PTBL_LEN(&found_subpaths); i++) {
+               bu_ptbl_rm(&lib_subpaths, BU_PTBL_GET(&found_subpaths, i));
+           }
        }
+       bu_ptbl_free(&found_subpaths);
     }
 
-    /* see if user already set ITK_LIBRARY override */
-    library_path = getenv("ITK_LIBRARY");
-    if (!found_itk_tcl && library_path) {
-       bu_vls_sprintf(&buffer, "%s%citk.tcl", library_path, BU_DIR_SEPARATOR);
-       if (bu_file_exists(bu_vls_cstr(&buffer), NULL)) {
-           found_itk_tcl=1;
+    // Now that we've looked for the libs, handle the data dirs.  These are
+    // simpler as they should be guaranteed to be in BU_DIR_DATA.
+    struct bu_vls data_path = BU_VLS_INIT_ZERO;
+    char datadir[MAXPATHLEN] = {0};
+    bu_dir(datadir, MAXPATHLEN, BU_DIR_DATA, NULL);
+    if (strlen(datadir)) {
+       // Have a directory, see what's in it
+       for (size_t i = 0; i < BU_PTBL_LEN(&data_subpaths); i++) {
+           const char *fname = (const char *)BU_PTBL_GET(&data_subpaths, i);
+           bu_vls_sprintf(&data_path, "%s%c%s", datadir, BU_DIR_SEPARATOR, 
fname);
+           if (bu_file_exists(bu_vls_cstr(&data_path), NULL)) {
+               // Have a path
+               const char *p = bu_strdup(bu_vls_cstr(&data_path));
+               bu_ptbl_ins(&paths, (long *)p);
+           } else {
+               bu_log("Warning: data path %s is not present in directory 
%s\n", fname, datadir);
+           }
        }
     }
 
-    /* iterate over the auto_path list and modify the real Tcl auto_path */
-    for (srcpath = strtok(bu_vls_addr(&auto_path), pathsep);
-        srcpath;
-        srcpath = strtok(NULL, pathsep)) {
-
+    /* iterate over the paths set and modify the real Tcl auto_path */
+    int tk_set = 0;
+    for (size_t i = 0; i < BU_PTBL_LEN(&paths); i++) {
+       const char *path = (const char *)BU_PTBL_GET(&paths, i);
        /* make sure it exists before appending */
-       if (bu_file_exists(srcpath, NULL)) {
-           /*          printf("APPENDING: %s\n", srcpath); */
-           bu_vls_sprintf(&lappend, "lappend auto_path {%s}", srcpath);
+       if (bu_file_exists(path, NULL)) {
+           printf("APPENDING: %s\n", path);
+           struct bu_vls lappend = BU_VLS_INIT_ZERO;
+           bu_vls_sprintf(&lappend, "lappend auto_path {%s}", path);
            (void)Tcl_Eval(interp, bu_vls_addr(&lappend));
+           bu_vls_free(&lappend);
        } else {
-           /*          printf("NOT APPENDING: %s\n", srcpath); */
+           printf("NOT APPENDING: %s\n", path);
            continue;
        }
 
+       /* Look for a number of special case initializations */
+
+       struct bu_vls buffer = BU_VLS_INIT_ZERO;
        /* specifically look for init.tcl so we can set tcl_library */
-       if (!found_init_tcl) {
-           bu_vls_sprintf(&buffer, "%s%cinit.tcl", srcpath, BU_DIR_SEPARATOR);
+       if (!tcl_set) {
+           bu_vls_sprintf(&buffer, "%s%cinit.tcl", path, BU_DIR_SEPARATOR);
            if (bu_file_exists(bu_vls_cstr(&buffer), NULL)) {
                /* this really sets it */
-               bu_vls_sprintf(&buffer, "set tcl_library {%s}", srcpath);
+               bu_vls_sprintf(&buffer, "set tcl_library {%s}", path);
                if (Tcl_Eval(interp, bu_vls_cstr(&buffer))) {
                    bu_log("Tcl_Eval ERROR:\n%s\n", 
Tcl_GetStringResult(interp));
                } else {
-                   found_init_tcl=1;
+                   tcl_set=1;
                }
 
-               /* extra measures necessary for "create interp":
-                * determine if TCL_LIBRARY is set, and set it if not.
-                */
-               library_path = getenv("TCL_LIBRARY");
-               if (!library_path) {
+               /* extra measures necessary for "create interp": determine if
+                * TCL_LIBRARY is set, and set it if not. */
+               env = getenv("TCL_LIBRARY");
+               if (!env) {
                    /* this REALLY sets it */
-                   bu_vls_sprintf(&buffer, "set env(TCL_LIBRARY) {%s}", 
srcpath);
+                   bu_vls_sprintf(&buffer, "set env(TCL_LIBRARY) {%s}", path);
                    if (Tcl_Eval(interp, bu_vls_cstr(&buffer))) {
                        bu_log("Tcl_Eval ERROR:\n%s\n", 
Tcl_GetStringResult(interp));
                    }
@@ -299,60 +384,65 @@
        }
 
        /* specifically look for tk.tcl so we can set tk_library */
-       if (!found_tk_tcl) {
-           bu_vls_sprintf(&buffer, "%s%ctk.tcl", srcpath, BU_DIR_SEPARATOR);
+       if (!tk_set) {
+           bu_vls_sprintf(&buffer, "%s%ctk.tcl", path, BU_DIR_SEPARATOR);
            if (bu_file_exists(bu_vls_cstr(&buffer), NULL)) {
                /* this really sets it */
-               bu_vls_sprintf(&buffer, "set tk_library {%s}", srcpath);
+               bu_vls_sprintf(&buffer, "set tk_library {%s}", path);
                if (Tcl_Eval(interp, bu_vls_cstr(&buffer))) {
                    bu_log("Tcl_Eval ERROR:\n%s\n", 
Tcl_GetStringResult(interp));
                } else {
-                   found_tk_tcl=1;
+                   tk_set=1;
                }
            }
        }
 
        /* specifically look for itcl.tcl so we can set ITCL_LIBRARY */
-       if (!found_itcl_tcl) {
-           bu_vls_sprintf(&buffer, "%s%citcl.tcl", srcpath, BU_DIR_SEPARATOR);
+       if (!itcl_set) {
+           bu_vls_sprintf(&buffer, "%s%citcl.tcl", path, BU_DIR_SEPARATOR);
            if (bu_file_exists(bu_vls_cstr(&buffer), NULL)) {
                /* this really sets it */
-               bu_vls_sprintf(&buffer, "set env(ITCL_LIBRARY) {%s}", srcpath);
+               bu_vls_sprintf(&buffer, "set env(ITCL_LIBRARY) {%s}", path);
                if (Tcl_Eval(interp, bu_vls_cstr(&buffer))) {
                    bu_log("Tcl_Eval ERROR:\n%s\n", 
Tcl_GetStringResult(interp));
                } else {
-                   found_itcl_tcl=1;
+                   itcl_set=1;
                }
            }
        }
 
        /* specifically look for itk.tcl so we can set ITK_LIBRARY */
-       if (!found_itk_tcl) {
-           bu_vls_sprintf(&buffer, "%s%citk.tcl", srcpath, BU_DIR_SEPARATOR);
+       if (!itk_set) {
+           bu_vls_sprintf(&buffer, "%s%citk.tcl", path, BU_DIR_SEPARATOR);
            if (bu_file_exists(bu_vls_cstr(&buffer), NULL)) {
                /* this really sets it */
-               bu_vls_sprintf(&buffer, "set env(ITK_LIBRARY) {%s}", srcpath);
+               bu_vls_sprintf(&buffer, "set env(ITK_LIBRARY) {%s}", path);
                if (Tcl_Eval(interp, bu_vls_cstr(&buffer))) {
                    bu_log("Tcl_Eval ERROR:\n%s\n", 
Tcl_GetStringResult(interp));
                } else {
-                   found_itk_tcl=1;
+                   itk_set=1;
                }
            }
        }
+
+       bu_vls_free(&buffer);
     }
 
-    which_argv = NULL;
-    bu_vls_free(&buffer);
-    bu_vls_free(&tcl);
-    bu_vls_free(&itcl);
-#ifdef HAVE_TK
-    bu_vls_free(&tk);
-    bu_vls_free(&itk);
-    bu_vls_free(&iwidgets);
-#endif
-    bu_vls_free(&auto_path);
-    bu_vls_free(&lappend);
-    bu_vls_free(&root_buf);
+    for (size_t i = 0; i < BU_PTBL_LEN(&lib_subpaths); i++) {
+       char *str = (char *)BU_PTBL_GET(&lib_subpaths, i);
+       bu_free(str, "subpath string");
+    }
+    bu_ptbl_free(&lib_subpaths);
+    for (size_t i = 0; i < BU_PTBL_LEN(&data_subpaths); i++) {
+       char *str = (char *)BU_PTBL_GET(&data_subpaths, i);
+       bu_free(str, "subpath string");
+    }
+    bu_ptbl_free(&data_subpaths);
+    for (size_t i = 0; i < BU_PTBL_LEN(&paths); i++) {
+       char *str = (char *)BU_PTBL_GET(&paths, i);
+       bu_free(str, "subpath string");
+    }
+    bu_ptbl_free(&paths);
 
     return;
 }

Modified: brlcad/branches/thirdparty_rework/src/libtclcad/bu.c
===================================================================
--- brlcad/branches/thirdparty_rework/src/libtclcad/bu.c        2020-09-30 
15:50:47 UTC (rev 77287)
+++ brlcad/branches/thirdparty_rework/src/libtclcad/bu.c        2020-09-30 
19:13:07 UTC (rev 77288)
@@ -318,6 +318,10 @@
        snprintf(result, MAXPATHLEN, "%s", bu_dir(NULL, 0, BU_DIR_MAN, NULL));
        return result;
     }
+    if (BU_STR_EQUIV(dirkey, "install") || BU_STR_EQUAL(dirkey, 
"BU_DIR_INSTALL")) {
+       snprintf(result, MAXPATHLEN, "%s", bu_dir(NULL, 0, BU_DIR_INSTALL, 
NULL));
+       return result;
+    }
     if (BU_STR_EQUIV(dirkey, "temp") || BU_STR_EQUAL(dirkey, "BU_DIR_TEMP")) {
        snprintf(result, MAXPATHLEN, "%s", bu_dir(NULL, 0, BU_DIR_TEMP, NULL));
        return result;
@@ -365,7 +369,7 @@
 {
     Tcl_Interp *interp = (Tcl_Interp *)clientData;
     if (argc != 2) {
-       bu_log("Usage: bu_dir 
[curr|init|bin|lib|libexec|include|data|doc|man|temp|home|cache|config|ext|libext]\n");
+       bu_log("Usage: bu_dir 
[curr|init|bin|lib|libexec|include|data|doc|man|install|temp|home|cache|config|ext|libext]\n");
        return BRLCAD_ERROR;
     }
     Tcl_AppendResult(interp, _tclcad_bu_dir_print(argv[1],1), NULL);

Modified: brlcad/branches/thirdparty_rework/src/libtclcad/init.c
===================================================================
--- brlcad/branches/thirdparty_rework/src/libtclcad/init.c      2020-09-30 
15:50:47 UTC (rev 77287)
+++ brlcad/branches/thirdparty_rework/src/libtclcad/init.c      2020-09-30 
19:13:07 UTC (rev 77288)
@@ -34,6 +34,9 @@
 #endif
 
 #include "vmath.h"
+#include "bu/app.h"
+#include "bu/path.h"
+#include "bu/vls.h"
 #include "bn.h"
 #include "dm.h"
 #include "raytrace.h"
@@ -87,6 +90,56 @@
     if (library_initialized(0))
        return TCL_OK;
 
+    /* Tcl_Init needs init.tcl.  It can be tricky to find init.tcl - help out,
+     * if we can.  Per the Tcl_Init() definition in generic/tclInterp.c in the
+     * Tcl source code, setting tcl_library is the recommended way for 
embedding
+     * applications to assist Tcl_Init in finding this file... */
+    char libdir[MAXPATHLEN] = {0};
+    bu_dir(libdir, MAXPATHLEN, BU_DIR_LIB, NULL);
+    if (strlen(libdir)) {
+       struct bu_vls initpath = BU_VLS_INIT_ZERO;
+       struct bu_vls lib_path = BU_VLS_INIT_ZERO;
+       bu_vls_sprintf(&lib_path, "%s%ctcl%s/init.tcl", libdir, 
BU_DIR_SEPARATOR, TCL_VERSION);
+       if (bu_file_exists(bu_vls_cstr(&lib_path), NULL)) {
+           bu_vls_sprintf(&lib_path, "%s%ctcl%s", libdir, BU_DIR_SEPARATOR, 
TCL_VERSION);
+           bu_vls_printf(&initpath, "set tcl_library {%s}", 
bu_vls_cstr(&lib_path));
+           if (Tcl_Eval(interp, bu_vls_addr(&initpath))) {
+               bu_log("Problem initializing tcl_library to system init.tcl 
path: Tcl_Eval ERROR:\n%s\n", Tcl_GetStringResult(interp));
+           }
+       } else {
+           /* For superbuilds, we may need to look one directory up.  Only do 
this when we're not installed. */
+           int installed = 0;
+           struct bu_vls ppath = BU_VLS_INIT_ZERO;
+           bu_path_component(&ppath, libdir, BU_PATH_DIRNAME);
+           {
+               char inst[MAXPATHLEN] = {0};
+               bu_dir(inst, MAXPATHLEN, BU_DIR_INSTALL, NULL);
+               if (BU_STR_EQUAL(bu_vls_cstr(&ppath), inst)) {
+                   installed = 1;
+               }
+           }
+           if (!installed) {
+               struct bu_vls ptail = BU_VLS_INIT_ZERO;
+               struct bu_vls tpath = BU_VLS_INIT_ZERO;
+               bu_path_component(&ptail, libdir, BU_PATH_BASENAME);
+               bu_path_component(&tpath, bu_vls_cstr(&ppath), BU_PATH_DIRNAME);
+               bu_vls_sprintf(&lib_path, "%s%c%s%ctcl%s/init.tcl", 
bu_vls_cstr(&tpath), BU_DIR_SEPARATOR, bu_vls_cstr(&ptail), BU_DIR_SEPARATOR, 
TCL_VERSION);
+               if (bu_file_exists(bu_vls_cstr(&lib_path), NULL)) {
+                   bu_vls_sprintf(&lib_path, "%s%c%s%ctcl%s", 
bu_vls_cstr(&tpath), BU_DIR_SEPARATOR, bu_vls_cstr(&ptail), BU_DIR_SEPARATOR, 
TCL_VERSION);
+                   bu_vls_printf(&initpath, "set tcl_library {%s}", 
bu_vls_cstr(&lib_path));
+                   if (Tcl_Eval(interp, bu_vls_addr(&initpath))) {
+                       bu_log("Problem initializing tcl_library to system 
init.tcl path: Tcl_Eval ERROR:\n%s\n", Tcl_GetStringResult(interp));
+                   }
+               }
+               bu_vls_free(&tpath);
+               bu_vls_free(&ptail);
+           }
+           bu_vls_free(&ppath);
+       }
+       bu_vls_free(&lib_path);
+       bu_vls_free(&initpath);
+    }
+
     if (Tcl_Init(interp) == TCL_ERROR) {
        if (tlog)
            bu_vls_printf(tlog, "Tcl init ERROR:\n%s\n", 
Tcl_GetStringResult(interp));

Modified: brlcad/branches/thirdparty_rework/src/superbuild/CMakeLists.txt
===================================================================
--- brlcad/branches/thirdparty_rework/src/superbuild/CMakeLists.txt     
2020-09-30 15:50:47 UTC (rev 77287)
+++ brlcad/branches/thirdparty_rework/src/superbuild/CMakeLists.txt     
2020-09-30 19:13:07 UTC (rev 77288)
@@ -227,7 +227,7 @@
   BINARY_DIR ${BRLCAD_BINARY_DIR}/brlcad-build
   CMAKE_ARGS -DCMAKE_INSTALL_PREFIX=${CMAKE_BINARY_DIR} -DLIB_DIR=${LIB_DIR} 
-DBIN_DIR=${BIN_DIR}
   -DCMAKE_INSTALL_RPATH=${CMAKE_BUILD_RPATH} 
-DBUILD_STATIC_LIBS=${BUILD_STATIC_LIBS}
-  -DSUBBUILD=ON
+  -DSUBBUILD=ON -DBRLCAD_INSTALL_PREFIX=${CMAKE_INSTALL_PREFIX}
   -DLEMON_ROOT=$<$<BOOL:${LEMON_TARGET}>:${CMAKE_BINARY_DIR}> 
-DLEMON_TEMPLATE=$<$<BOOL:${LEMON_TARGET}>:${LEMON_TEMPLATE}>
   -DRE2C_ROOT=$<$<BOOL:${RE2C_TARGET}>:${CMAKE_BINARY_DIR}>
   -DPERPLEX_ROOT=$<$<BOOL:${PERPLEX_TARGET}>:${CMAKE_BINARY_DIR}> 
-DPERPLEX_TEMPLATE=${CMAKE_SOURCE_DIR}/misc/tools/perplex/perplex_template.c

Modified: brlcad/branches/thirdparty_rework/src/tclscripts/CMakeLists.txt
===================================================================
--- brlcad/branches/thirdparty_rework/src/tclscripts/CMakeLists.txt     
2020-09-30 15:50:47 UTC (rev 77287)
+++ brlcad/branches/thirdparty_rework/src/tclscripts/CMakeLists.txt     
2020-09-30 19:13:07 UTC (rev 77288)
@@ -44,7 +44,8 @@
     # command that builds the index when the dependency is resolved
     add_custom_command(
       OUTPUT ${tclindex_outdir}/${outfile}
-      COMMAND btclsh ${CMAKE_BINARY_DIR}/CMakeTmp/${cmd}.tcl 
${tclindex_outdir} >> ${CMAKE_CURRENT_BINARY_DIR}/${cmd}_index_gen.log 2>&1
+      #COMMAND btclsh ${CMAKE_BINARY_DIR}/CMakeTmp/${cmd}.tcl 
${tclindex_outdir} >> ${CMAKE_CURRENT_BINARY_DIR}/${cmd}_index_gen.log 2>&1
+      COMMAND btclsh ${CMAKE_BINARY_DIR}/CMakeTmp/${cmd}.tcl ${tclindex_outdir}
       DEPENDS btclsh ${data_target_list} ${tcl_files}
       )
 

This was sent by the SourceForge.net collaborative development platform, the 
world's largest Open Source development site.



_______________________________________________
BRL-CAD Source Commits mailing list
[email protected]
https://lists.sourceforge.net/lists/listinfo/brlcad-commits

Reply via email to