View Issue Details Jump to Notes ] Print ]
IDProjectCategoryView StatusDate SubmittedLast Update
0011701CMakeDocumentationpublic2011-01-14 14:512011-01-31 16:01
ReporterMarkus Elfring 
Assigned ToBrad King 
PrioritynormalSeveritymajorReproducibilityalways
StatusclosedResolutionfixed 
PlatformOSOS Version
Product VersionCMake 2.8.3 
Target VersionCMake 2.8.4Fixed in VersionCMake 2.8.4 
Summary0011701: Check condition evaluation for a passed variable
DescriptionThe current documentation contains the following description.

"...
The convenience feature that sometimes throws new authors is how CMake handles values that do not match the true or false list. Those values are treated as variables and are dereferenced even though they do not have the required ${} syntax. This means that if you write

  if (boobah)

CMake will treat it as if you wrote

  if (${boobah})
..."


I have written a small script to test the corresponding expectations.

cmake_minimum_required(VERSION 2.6)
project(my_condition_test1)
set(MY_TEXT "condition-test1.cxx")
if(MY_TEXT)
   message(STATUS "Good day.")
else()
   message(FATAL_ERROR "Bad day!")
endif()
if(${MY_TEXT})
   message(STATUS "This result was expected.")
else()
   message(FATAL_ERROR "Which result should be expected here?")
endif()


I get the following log for my configuration try.
"...
Good day.
CMake Error at CMakeLists.txt:12 (message):
  Which result should be expected here?


Configuring incomplete, errors occurred!"


I have got the impression that the mentioned "convenience feature" includes the (undocumented?) condition application "if(DEFINED variable)" so far.

Which behaviour is correct in the demonstrated situation?
Are you going to update any information sources for this issue?
TagsNo tags attached.
Attached Files

 Relationships
duplicate of 0010773closedBrad King IF() command behaviour contradicts examples in documentation 

  Notes
(0024694)
Markus Elfring (reporter)
2011-01-14 15:08

My story seems to be related to the bug report "IF() command behaviour contradicts examples in documentation".
http://public.kitware.com/Bug/view.php?id=10773 [^]
(0024696)
Brad King (manager)
2011-01-14 17:21

Closing as duplicate of 0010773. Please visit that bug and click the "Monitor" button to track its progress.
(0024704)
Markus Elfring (reporter)
2011-01-15 02:30

I find that your documentation adjustment is still not enough.
http://cmake.org/gitweb?p=cmake.git;a=commitdiff;h=e4e14e85 [^]

Would you like to mention the "magic evaluation" like the condition application "if(DEFINED variable)" in any clearer way?
Where is this behaviour completely described at the moment?

Are any further clarifications needed for handling of variables without "${}" in conditions?
(0024709)
Brad King (manager)
2011-01-15 08:07

The full behavior is documented well above the example that was replaced:

       Possible expressions are:

         if(<constant>)

       True if the constant is 1, ON, YES, TRUE, Y, or a non-zero number.
       False if the constant is 0, OFF, NO, FALSE, N, IGNORE, "", or ends in
       the suffix '-NOTFOUND'. Named boolean constants are case-insensitive.
       If the argument is not one of these constants, it is treated as a
       variable:

         if(<variable>)

       True if the variable is defined to a value that is not a false
       constant. False otherwise.

       ...

         if(DEFINED variable)

       True if the given variable is defined. It does not matter if the
       variable is true or false just if it has been set.

I don't see how that can be any clearer.
(0024712)
Markus Elfring (reporter)
2011-01-15 09:49

I agree that the functionality "if(<variable>)" is documented by itself. But I find that the explanation for the combination with "old style" variable evaluation is still an open issue.
Does the "magic" result in any differences in comparison with the current ${} syntax?

Modestas Vainius and I have got different expectations about the usable behaviour ...
(0024715)
Brad King (manager)
2011-01-15 10:26

> Does the "magic" result in any differences in comparison with the current ${} syntax?

The ${} syntax is evaluated before if() sees the arguments. Then the arguments that if() does see are evaluated as specified in the documentation I quoted. Please ignore the old "behave as if you wrote ${}" example that was just plain wrong. Read the documentation from scratch as it appears now. What is missing?
(0024719)
Markus Elfring (reporter)
2011-01-15 13:00

Please look at my script example for this issue (again):
A variable was set to a value that I would not interpret as the boolean status "true" according to the updated documentation.

Why was the message "Good day." displayed?
(0024746)
Brad King (manager)
2011-01-17 09:28

In the line

  if(MY_TEXT)

"MY_TEXT" is not one of the named boolean constants. Therefore the command moves on to the "if(<variable>)" form, which is documented as

  True if the variable is defined to a value that is not a false constant. False otherwise.

The value of the variable is "condition-test1.cxx", which is not a false constant. Therefore it is TRUE.
(0024747)
Brad King (manager)
2011-01-17 09:47

This makes the signatures where auto-dereferencing occurs more explicit:

  http://cmake.org/gitweb?p=cmake.git;a=commitdiff;h=7d9b9037 [^]
(0024848)
Brad King (manager)
2011-01-18 07:26

Closing as "fixed" since the commit mentioned in 0011701:0024747 clarifies the documentation further.
(0024850)
Markus Elfring (reporter)
2011-01-18 07:31

Thanks for your explanation and the fine-tuning of the documentation.

I have got the impression that a syntax diagram (or decision tree) might be needed to understand the dependencies of parameter evaluation a bit easier here.
http://en.wikipedia.org/wiki/File:Syntax_Diagrams.png [^]

Are the displays the same from the execution of the following script example by a couple of CMake versions?

cmake_minimum_required(VERSION 2.6)
project(my_condition_test2)
set(my_text "condition-test2")
if(my_text)
   set(result1 one)
else()
   set(result1 two)
endif()
if(${my_text})
   set(result2 one)
else()
   set(result2 two)
endif()
if("Bluff")
   set(result3 one)
else()
   set(result3 two)
endif()
if( (${result1} STREQUAL ${result2})
   AND (${result1} STREQUAL ${result3}))
   message(STATUS "This result was expected.")
else()
   message(FATAL_ERROR "Results:
1. ${result1}
2. ${result2}
3. ${result3}
Check your expectations again!")
endif()


I get the following log display from CMake-GUI 2.8.3.
"CMake Error at CMakeLists.txt:23 (message):
  Results:

  1. one

  2. two

  3. two

  Check your expectations again!


Configuring incomplete, errors occurred!"


How do you think about this situation now?


By the way:
Does it also show an open issue that blank lines are added to the original output text?
(0024851)
Brad King (manager)
2011-01-18 07:54

The results *exactly* match the documentation!

Part 1: "my_text" is a variable defined to a value that is not a false constant -> true

Part 2: "${my_text}" becomes "condition-test2" before if() even sees it. The latter is not a defined variable -> false

Part 3: "Bluff" is not a defined variable -> false

Please, this issue tracker is not a place to ask for tutorials. Go to the mailing list and ask for help there. I don't mean to be dismissive but I've already spent way too much time on this. Only a few people read the issue tracker and we don't have time to give everyone detailed tutorial sessions. There are may people on the mailing list that answer questions. It distributes the load.

The documentation is correct and consistent with the implementation and the behavior that we intend. The examples are correct. This issue is resolved. If you open it again without a link to discussion on the mailing list that involves posts other than yours, I will close it without answering again.

 Issue History
Date Modified Username Field Change
2011-01-14 14:51 Markus Elfring New Issue
2011-01-14 15:08 Markus Elfring Note Added: 0024694
2011-01-14 17:20 Brad King Relationship added duplicate of 0010773
2011-01-14 17:21 Brad King Note Added: 0024696
2011-01-14 17:21 Brad King Status new => closed
2011-01-14 17:21 Brad King Assigned To => Brad King
2011-01-14 17:21 Brad King Resolution open => duplicate
2011-01-15 02:30 Markus Elfring Note Added: 0024704
2011-01-15 02:30 Markus Elfring Status closed => feedback
2011-01-15 02:30 Markus Elfring Resolution duplicate => reopened
2011-01-15 08:07 Brad King Note Added: 0024709
2011-01-15 09:49 Markus Elfring Note Added: 0024712
2011-01-15 09:49 Markus Elfring Status feedback => assigned
2011-01-15 10:26 Brad King Note Added: 0024715
2011-01-15 13:00 Markus Elfring Note Added: 0024719
2011-01-17 09:28 Brad King Note Added: 0024746
2011-01-17 09:47 Brad King Note Added: 0024747
2011-01-18 07:26 Brad King Note Added: 0024848
2011-01-18 07:26 Brad King Status assigned => closed
2011-01-18 07:26 Brad King Resolution reopened => fixed
2011-01-18 07:31 Markus Elfring Note Added: 0024850
2011-01-18 07:31 Markus Elfring Status closed => feedback
2011-01-18 07:31 Markus Elfring Resolution fixed => reopened
2011-01-18 07:54 Brad King Note Added: 0024851
2011-01-18 07:54 Brad King Status feedback => closed
2011-01-18 07:54 Brad King Resolution reopened => fixed
2011-01-31 16:01 David Cole Fixed in Version => CMake 2.8.4
2011-01-31 16:01 David Cole Target Version => CMake 2.8.4


Copyright © 2000 - 2018 MantisBT Team