Adolfo Rodríguez wrote:
On Fri, May 29, 2009 at 5:48 AM, Clinton Stimpson <[email protected] <mailto:[email protected]>> wrote:

    Jed Brown wrote:

        Alexander Neundorf wrote:
            On Monday 25 May 2009, Jed Brown wrote:
                Bill Hoffman wrote:
                    You can also set QMake on the cmake command line
                    as well:

                    cmake -DQT_QMAKE_EXECUTABLE=/path/to/qmake ../source
                Yeah, I'm much less concerned with this particular
                case as with the
                philosophy that the correct way to select
                installations is by modifying
                PATH.  Frustratingly, a new user will fire up cmake
                and get the wrong
                version (they're not even aware of exactly what the
                dependencies are,
                let alone the naming convention for the cache variable
                that will get the
                correct version).  So they interactively change a
                couple paths and
                reconfigure.  Lo and behold, they now have an
                inconsistent state because
                the cache wasn't flushed when they changed
                QT_QMAKE_EXECUTABLE (I don't
                know if this is the case with Qt, but is is with most
                packages).
            ...
                Using PATH and falling back on peculiarly named
                variables (hopefully
                only one non-advanced variable per package, so that
                it's unambiguous)
            With the new cmake-gui this is now much easier :-)

        CMake gui is nice and it's easier to edit variables.  For this
        case, I
        think the only way it makes a difference is that you can go to
        advanced
        grouped mode and wipe out a whole group easily.  Some packages
        have
        dependencies, so this isn't a complete solution, but it does
        make a big
        difference.  I wrote the following before noticing that it was
        easy to
        clear groups, but I think it's still somewhat relevant.


        The user doesn't know the name of special variables (like
        QT_QMAKE_EXECUTABLE) until they press Configure.  If the wrong
        version
        is found on the first pass, it's typically too late to change
        the path.
        (There isn't a concept of dependent cache variables so very
        few Find*
        modules can clean up after an incorrect version is found.
         There is an
        implicit assumpition that if *any* installation is found, it
        is the one
        the user wanted.  FindQt4 might be a very rare exception to
        this.  I
        haven't tested its robustness since I don't use it, but I see
        a lot of
        QT_QMAKE_CHANGED logic so the author is at least trying to
        handle this.)

        So they have to flush the cache and define the special
        variable *before*
        CMake shows them that the variable exists.  Until packages can
        robustly
        support changing their path *after* the first pass finds an
        undesired
        version, I think that recognizing semi-standard environment
        variables
        like QTDIR would be good policy (e.g. the user is much more
        likely to
        guess QTDIR than QT_QMAKE_EXECUTABLE if they are unfamiliar
        with CMake
        and only know that the your package needs Qt).
    I don't think of QTDIR as anything of a standard anymore.  It was
    necessary in Qt3 to make the qmake build system work.
    Anyway...  read below.

            Also, instead of setting PATH to /opt/qt-a.b.c/bin/ you
            can also set CMAKE_PREFIX_PATH to /opt/qt-a.b.c/, also to
            a list of directories, which cmake will search in the
            order you specified.

        I know about these, but they have global scope and are thus not a
        solution to the problem I stated.  You need to be able to specify
        install paths *independently*.  As a concrete example, suppose
        different
        versions of MPI are installed at /usr and /usr/local.  Similarly,
        suppose different versions of Qt are installed at /usr and
        /usr/local.
        I'm not claiming this is the best organization, but it's not
        terribly
        uncommon or pathological, so some users will have this
        situation and
        it's none of our business to tell them to reinstall just to
        build our
        package.

        Qt and MPI are independent packages so their selection cannot be
        dependent.  Modifying variables like PATH or CMAKE_PREFIX_PATH
        will
        choose versions for both of these packages.  FindMPI.cmake
        cannot be set
        independently, so if I wanted to get MPI from /usr, I have to
        put /usr
        first in PATH/CMAKE_PREFIX_PATH.  A new user will not know this in
        advance.  To get Qt from /usr/local, I can set
        QT_QMAKE_EXECUTABLE, but
        a new user won't know this before running CMake (gui) and
        looking at the
        options.  If they are lucky, they will get the correct MPI on
        the first
        pass, and although the incorrect Qt is found, they can change
        QT_QMAKE_EXECUTABLE and the QT_QMAKE_CHANGED logic will work
        correctly
        to give them a consistent build.  If the wrong MPI is found,
        they have
        no choice but to delete the cache, modify some global state
        (PATH or
        similar) and try again.  Note that very few Find* modules can
        recover
        from finding an incorrect package (it takes a lot of work, you
        basically
        have to work around the cache).  In addition, not many have a
        single
        variable to control which installation is found, thus
        necessitating
        global control which creates the locking problem.

    I think what is being asked here is a good idea.
    There is already the CMAKE_PREFIX_PATH which gives
    find_package(Qt4) a prefix to work from.
    If I set it to one of my other Qt4, directories, it finds that Qt
    installation fine.
    But maybe adding something like a
    QT4_PREFIX_PATH to have find_package(Qt4) prefer another directory
    first
    and
    MPI_PREFIX_PATH to have find_package(MPI) prefer yet a different
    directory
    would be nice.

    Maybe even extend that so if one did
    find_program(MYVAR_EXECUTABLE ...)
    find_library(MYVAR_LIBRARY ...)
    a user of a CMakeLists.txt file containing that could set
    MYVAR_PREFIX_PATH.

    Or maybe use MYVAR_DIR so the same variable works when cmake
    config files are found by find_package().

    Maybe another step would be to detect if MYVAR_DIR changed, and
    remove all dependent variables and do a re-find.

    I see that FindBoost.cmake has a BOOST_ROOT that tries to do the
    above, but a standard mechanism for all find_* would be better.
    Or does cmake already have a standard way of doing this?


This link [1] suggests that the correct name for the variable should be QT$_ROOT_DIR (instead of QT4_PREFIX_PATH or QT4_ROOT)

[1] http://public.kitware.com/cgi-bin/viewcvs.cgi/Modules/readme.txt?root=CMake&view=markup <http://public.kitware.com/cgi-bin/viewcvs.cgi/Modules/readme.txt?root=CMake&view=markup>

I do something like this when looking for simple packages (thanks to Greg Peele for a cool tip on this):

# Get hint from environment variable (if any)
if(DEFINED ENV{FOO_ROOT_DIR})
set(FOO_ROOT_DIR "$ENV{FOO_ROOT_DIR}" CACHE PATH "FOO base directory location (optional, used for nonstandard installation paths)" FORCE)
  mark_as_advanced(FOO_ROOT_DIR)
endif()

# Search path for nonstandard locations
if(FOO_ROOT_DIR)
  set(FOO_INCLUDE_PATH PATHS ${FOO_ROOT_DIR}/include NO_DEFAULT_PATH)
  set(FOO_LIBRARY_PATH PATHS ${FOO_ROOT_DIR}/lib NO_DEFAULT_PATH)
endif()

# Find headers and libraries
find_path(FOO_INCLUDE_DIR NAMES foo/FOO.h ${FOO_INCLUDE_PATH})
find_library(FOO_LIBRARY NAMES FOO ${FOO_LIBRARY_PATH})

... then you can use FindPackageHandleStandardArgs or whatever you like the most.

I know that FindQT4 is a _lot_ more complicated than this, but anyway, I find the FOO_ROOT_DIR (env. or cmake) variable very useful.


Yes, that's doable right now.
But, I was actually hoping for something that worked automatic like CMAKE_PREFIX_PATH. Not something extra people have to code into their Find*.cmake files or extra things they have to do with their find_* calls.
Also, I was thinking of a cmake variable, not an environment variable.

Clint


_______________________________________________
Powered by www.kitware.com

Visit other Kitware open-source projects at 
http://www.kitware.com/opensource/opensource.html

Please keep messages on-topic and check the CMake FAQ at: 
http://www.cmake.org/Wiki/CMake_FAQ

Follow this link to subscribe/unsubscribe:
http://www.cmake.org/mailman/listinfo/cmake

Reply via email to