Skip to content
GitLab
Menu
Projects
Groups
Snippets
Help
Help
Support
Community forum
Keyboard shortcuts
?
Submit feedback
Contribute to GitLab
Sign in / Register
Toggle navigation
Menu
Open sidebar
CMake
CMake
Commits
669db35a
Commit
669db35a
authored
Jan 17, 2008
by
Brad King
Browse files
ENH: Changed signature of GET_PROPERTY command to be more powerful and extendible.
parent
83901b30
Changes
6
Hide whitespace changes
Inline
Side-by-side
Modules/CPackDeb.cmake
View file @
669db35a
...
...
@@ -39,8 +39,8 @@ IF(NOT CPACK_DEBIAN_PACKAGE_ARCHITECTURE)
SET
(
CPACK_DEBIAN_PACKAGE_ARCHITECTURE i386
)
ENDIF
(
NOT CPACK_DEBIAN_PACKAGE_ARCHITECTURE
)
# have a look at GET_PROPERTY(result GLOBAL ENABLED_FEATURES),
this returns
# the successful FIND_PACKAGE() calls, maybe this can help
# have a look at GET_PROPERTY(result GLOBAL
PROPERTY
ENABLED_FEATURES),
#
this returns
the successful FIND_PACKAGE() calls, maybe this can help
# Depends:
IF
(
NOT CPACK_DEBIAN_PACKAGE_DEPENDS
)
MESSAGE
(
STATUS
"CPACK_DEBIAN_PACKAGE_DEPENDS not set, the package will have no dependencies."
)
...
...
Modules/FeatureSummary.cmake
View file @
669db35a
...
...
@@ -33,18 +33,18 @@ ENDMACRO(SET_FEATURE_INFO)
MACRO
(
_PRINT_FEATURES _property _text
)
SET
(
_currentFeatureText
"
${
_text
}
"
)
GET_PROPERTY
(
_EnabledFeatures GLOBAL
${
_property
}
)
GET_PROPERTY
(
_EnabledFeatures GLOBAL
PROPERTY
${
_property
}
)
FOREACH
(
_currentFeature
${
_EnabledFeatures
}
)
SET
(
_currentFeatureText
"
${
_currentFeatureText
}
\n
${
_currentFeature
}
"
)
GET_PROPERTY
(
_info GLOBAL
${
_currentFeature
}
_DESCRIPTION
)
GET_PROPERTY
(
_info GLOBAL
PROPERTY
${
_currentFeature
}
_DESCRIPTION
)
IF
(
_info
)
SET
(
_currentFeatureText
"
${
_currentFeatureText
}
,
${
_info
}
"
)
ENDIF
(
_info
)
GET_PROPERTY
(
_info GLOBAL
${
_currentFeature
}
_URL
)
GET_PROPERTY
(
_info GLOBAL
PROPERTY
${
_currentFeature
}
_URL
)
IF
(
_info
)
SET
(
_currentFeatureText
"
${
_currentFeatureText
}
, <
${
_info
}
>"
)
ENDIF
(
_info
)
GET_PROPERTY
(
_info GLOBAL
${
_currentFeature
}
_COMMENT
)
GET_PROPERTY
(
_info GLOBAL
PROPERTY
${
_currentFeature
}
_COMMENT
)
IF
(
_info
)
SET
(
_currentFeatureText
"
${
_currentFeatureText
}
,
${
_info
}
"
)
ENDIF
(
_info
)
...
...
Modules/FindPythonLibs.cmake
View file @
669db35a
...
...
@@ -93,7 +93,8 @@ IF(NOT _FIND_PYTHONLIBS_ALREADY_INCLUDED)
SET
(
PY_MODULES_LIST
""
CACHE STRING
"Collect a list of all added python modules"
FORCE
)
ENDIF
(
NOT _FIND_PYTHONLIBS_ALREADY_INCLUDED
)
GET_PROPERTY
(
_TARGET_SUPPORTS_SHARED_LIBS GLOBAL TARGET_SUPPORTS_SHARED_LIBS
)
GET_PROPERTY
(
_TARGET_SUPPORTS_SHARED_LIBS
GLOBAL PROPERTY TARGET_SUPPORTS_SHARED_LIBS
)
MACRO
(
PYTHON_ADD_MODULE _NAME
)
OPTION
(
PYTHON_ENABLE_MODULE_
${
_NAME
}
"Add module
${
_NAME
}
"
TRUE
)
...
...
Source/cmGetPropertyCommand.cxx
View file @
669db35a
...
...
@@ -20,9 +20,14 @@
#include
"cmTest.h"
#include
"cmPropertyDefinition.h"
// cmGetPropertyCommand
bool
cmGetPropertyCommand
::
InitialPass
(
std
::
vector
<
std
::
string
>
const
&
args
)
//----------------------------------------------------------------------------
cmGetPropertyCommand
::
cmGetPropertyCommand
()
{
this
->
InfoType
=
OutValue
;
}
//----------------------------------------------------------------------------
bool
cmGetPropertyCommand
::
InitialPass
(
std
::
vector
<
std
::
string
>
const
&
args
)
{
if
(
args
.
size
()
<
3
)
{
...
...
@@ -30,182 +35,308 @@ bool cmGetPropertyCommand::InitialPass(
return
false
;
}
// the last argument in the property to get
const
char
*
property
=
args
[
args
.
size
()
-
1
].
c_str
();
bool
get_brief
=
false
;
if
(
!
strcmp
(
property
,
"BRIEF_DOCS"
))
{
get_brief
=
true
;
property
=
args
[
args
.
size
()
-
2
].
c_str
();
}
bool
get_full
=
false
;
if
(
!
strcmp
(
property
,
"FULL_DOCS"
))
{
get_full
=
true
;
property
=
args
[
args
.
size
()
-
2
].
c_str
();
}
std
::
string
output
=
"NOTFOUND"
;
// The cmake variable in which to store the result.
this
->
Variable
=
args
[
0
];
// Get the scope from which to get the property.
cmProperty
::
ScopeType
scope
;
const
char
*
scopeName
=
0
;
if
(
args
[
1
]
==
"GLOBAL"
)
if
(
args
[
1
]
==
"GLOBAL"
)
{
scope
=
cmProperty
::
GLOBAL
;
}
else
if
(
args
[
1
]
==
"VARIABLE"
)
{
scope
=
cmProperty
::
VARIABLE
;
}
else
if
(
args
[
1
]
==
"DIRECTORY"
&&
args
.
size
()
>=
3
)
else
if
(
args
[
1
]
==
"DIRECTORY"
)
{
scope
=
cmProperty
::
DIRECTORY
;
if
((
args
.
size
()
==
4
&&
!
get_brief
&&
!
get_full
)
||
(
args
.
size
()
==
5
&&
(
get_brief
||
get_full
)))
{
scopeName
=
args
[
2
].
c_str
();
}
}
else
if
(
args
[
1
]
==
"TARGET"
&&
args
.
size
()
>=
4
)
else
if
(
args
[
1
]
==
"TARGET"
)
{
scope
=
cmProperty
::
TARGET
;
scopeName
=
args
[
2
].
c_str
();
}
else
if
(
args
[
1
]
==
"TEST"
&&
args
.
size
()
>=
4
)
else
if
(
args
[
1
]
==
"SOURCE"
)
{
scope
=
cmProperty
::
SOURCE_FILE
;
}
else
if
(
args
[
1
]
==
"TEST"
)
{
scope
=
cmProperty
::
TEST
;
scopeName
=
args
[
2
].
c_str
();
}
else
if
(
args
[
1
]
==
"
SOURCE_FILE"
&&
args
.
size
()
>=
4
)
else
if
(
args
[
1
]
==
"
VARIABLE"
)
{
scope
=
cmProperty
::
SOURCE_FILE
;
scopeName
=
args
[
2
].
c_str
();
scope
=
cmProperty
::
VARIABLE
;
}
else
{
this
->
SetError
(
"called with illegal arguments."
);
cmOStringStream
e
;
e
<<
"given invalid scope "
<<
args
[
1
]
<<
". "
<<
"Valid scopes are "
<<
"GLOBAL, DIRECTORY, TARGET, SOURCE, TEST, VARIABLE."
;
this
->
SetError
(
e
.
str
().
c_str
());
return
false
;
}
if
(
get_brief
)
// Parse remaining arguments.
enum
Doing
{
DoingNone
,
DoingName
,
DoingProperty
,
DoingType
};
Doing
doing
=
DoingName
;
for
(
unsigned
int
i
=
2
;
i
<
args
.
size
();
++
i
)
{
cmPropertyDefinition
*
def
=
this
->
Makefile
->
GetCMakeInstance
()
->
GetPropertyDefinition
(
property
,
scope
);
if
(
def
)
if
(
args
[
i
]
==
"PROPERTY"
)
{
doing
=
DoingProperty
;
}
else
if
(
args
[
i
]
==
"BRIEF_DOCS"
)
{
doing
=
DoingNone
;
this
->
InfoType
=
OutBriefDoc
;
}
else
if
(
args
[
i
]
==
"FULL_DOCS"
)
{
doing
=
DoingNone
;
this
->
InfoType
=
OutFullDoc
;
}
else
if
(
args
[
i
]
==
"DEFINED"
)
{
doing
=
DoingNone
;
this
->
InfoType
=
OutDefined
;
}
else
if
(
doing
==
DoingName
)
{
doing
=
DoingNone
;
this
->
Name
=
args
[
i
];
}
else
if
(
doing
==
DoingProperty
)
{
doing
=
DoingNone
;
this
->
PropertyName
=
args
[
i
];
}
else
{
cmOStringStream
e
;
e
<<
"given invalid argument
\"
"
<<
args
[
i
]
<<
"
\"
."
;
this
->
SetError
(
e
.
str
().
c_str
());
return
false
;
}
}
// Make sure a property name was found.
if
(
this
->
PropertyName
.
empty
())
{
this
->
SetError
(
"not given a PROPERTY <name> argument."
);
return
false
;
}
// Compute requested output.
if
(
this
->
InfoType
==
OutBriefDoc
)
{
// Lookup brief documentation.
std
::
string
output
;
if
(
cmPropertyDefinition
*
def
=
this
->
Makefile
->
GetCMakeInstance
()
->
GetPropertyDefinition
(
this
->
PropertyName
.
c_str
(),
scope
))
{
output
=
def
->
GetShortDescription
();
}
else
{
output
=
"NOTFOUND"
;
}
this
->
Makefile
->
AddDefinition
(
this
->
Variable
.
c_str
(),
output
.
c_str
());
}
else
if
(
get_full
)
else
if
(
this
->
InfoType
==
OutFullDoc
)
{
cmPropertyDefinition
*
def
=
this
->
Makefile
->
GetCMakeInstance
()
->
GetPropertyDefinition
(
property
,
scope
);
if
(
def
)
// Lookup full documentation.
std
::
string
output
;
if
(
cmPropertyDefinition
*
def
=
this
->
Makefile
->
GetCMakeInstance
()
->
GetPropertyDefinition
(
this
->
PropertyName
.
c_str
(),
scope
))
{
output
=
def
->
GetFullDescription
();
}
else
{
output
=
"NOTFOUND"
;
}
this
->
Makefile
->
AddDefinition
(
this
->
Variable
.
c_str
(),
output
.
c_str
());
}
else
switch
(
scope
)
{
case
cmProperty
::
VARIABLE
:
{
if
(
this
->
Makefile
->
GetDefinition
(
property
))
{
output
=
this
->
Makefile
->
GetDefinition
(
property
);
}
}
break
;
case
cmProperty
::
TARGET
:
{
cmTarget
*
tgt
=
this
->
Makefile
->
GetLocalGenerator
()
->
GetGlobalGenerator
()
->
FindTarget
(
0
,
scopeName
,
true
);
if
(
tgt
)
{
cmTarget
&
target
=
*
tgt
;
const
char
*
prop
=
target
.
GetProperty
(
property
);
if
(
prop
)
{
output
=
prop
;
}
}
}
break
;
case
cmProperty
::
DIRECTORY
:
{
cmLocalGenerator
*
lg
=
this
->
Makefile
->
GetLocalGenerator
();
if
(
args
.
size
()
>=
4
)
{
std
::
string
sd
=
scopeName
;
// make sure the start dir is a full path
if
(
!
cmSystemTools
::
FileIsFullPath
(
sd
.
c_str
()))
{
sd
=
this
->
Makefile
->
GetStartDirectory
();
sd
+=
"/"
;
sd
+=
scopeName
;
}
// The local generators are associated with collapsed paths.
sd
=
cmSystemTools
::
CollapseFullPath
(
sd
.
c_str
());
// lookup the makefile from the directory name
lg
=
this
->
Makefile
->
GetLocalGenerator
()
->
GetGlobalGenerator
()
->
FindLocalGenerator
(
sd
.
c_str
());
}
if
(
!
lg
)
{
this
->
SetError
(
"DIRECTORY argument provided but requested directory not found. "
"This could be because the directory argument was invalid or, "
"it is valid but has not been processed yet."
);
return
false
;
}
const
char
*
prop
=
lg
->
GetMakefile
()
->
GetProperty
(
property
);
if
(
prop
)
{
output
=
prop
;
}
}
break
;
case
cmProperty
::
GLOBAL
:
{
const
char
*
prop
=
this
->
Makefile
->
GetCMakeInstance
()
->
GetProperty
(
property
);
if
(
prop
)
{
output
=
prop
;
}
}
break
;
case
cmProperty
::
TEST
:
{
cmTest
*
test
=
this
->
Makefile
->
GetTest
(
scopeName
);
const
char
*
prop
=
test
->
GetProperty
(
property
);
if
(
prop
)
{
output
=
prop
;
}
}
break
;
case
cmProperty
::
SOURCE_FILE
:
{
cmSourceFile
*
sf
=
this
->
Makefile
->
GetSource
(
scopeName
);
const
char
*
prop
=
sf
->
GetProperty
(
property
);
if
(
prop
)
{
output
=
prop
;
}
}
break
;
case
cmProperty
::
CACHED_VARIABLE
:
// not handled by GetProperty
break
;
}
this
->
Makefile
->
AddDefinition
(
args
[
0
].
c_str
(),
output
.
c_str
());
else
{
// Dispatch property getting.
switch
(
scope
)
{
case
cmProperty
::
GLOBAL
:
return
this
->
HandleGlobalMode
();
case
cmProperty
::
DIRECTORY
:
return
this
->
HandleDirectoryMode
();
case
cmProperty
::
TARGET
:
return
this
->
HandleTargetMode
();
case
cmProperty
::
SOURCE_FILE
:
return
this
->
HandleSourceMode
();
case
cmProperty
::
TEST
:
return
this
->
HandleTestMode
();
case
cmProperty
::
VARIABLE
:
return
this
->
HandleVariableMode
();
case
cmProperty
::
CACHED_VARIABLE
:
break
;
// should never happen
}
}
return
true
;
}
//----------------------------------------------------------------------------
bool
cmGetPropertyCommand
::
StoreResult
(
const
char
*
value
)
{
if
(
this
->
InfoType
==
OutDefined
)
{
this
->
Makefile
->
AddDefinition
(
this
->
Variable
.
c_str
(),
value
?
"1"
:
"0"
);
}
else
// if(this->InfoType == OutValue)
{
this
->
Makefile
->
AddDefinition
(
this
->
Variable
.
c_str
(),
value
);
}
return
true
;
}
//----------------------------------------------------------------------------
bool
cmGetPropertyCommand
::
HandleGlobalMode
()
{
if
(
!
this
->
Name
.
empty
())
{
this
->
SetError
(
"given name for GLOBAL scope."
);
return
false
;
}
// Get the property.
cmake
*
cm
=
this
->
Makefile
->
GetCMakeInstance
();
return
this
->
StoreResult
(
cm
->
GetProperty
(
this
->
PropertyName
.
c_str
()));
}
//----------------------------------------------------------------------------
bool
cmGetPropertyCommand
::
HandleDirectoryMode
()
{
// Default to the current directory.
cmMakefile
*
mf
=
this
->
Makefile
;
// Lookup the directory if given.
if
(
!
this
->
Name
.
empty
())
{
// Construct the directory name. Interpret relative paths with
// respect to the current directory.
std
::
string
dir
=
this
->
Name
;
if
(
!
cmSystemTools
::
FileIsFullPath
(
dir
.
c_str
()))
{
dir
=
this
->
Makefile
->
GetCurrentDirectory
();
dir
+=
"/"
;
dir
+=
this
->
Name
;
}
// The local generators are associated with collapsed paths.
dir
=
cmSystemTools
::
CollapseFullPath
(
dir
.
c_str
());
// Lookup the generator.
if
(
cmLocalGenerator
*
lg
=
(
this
->
Makefile
->
GetLocalGenerator
()
->
GetGlobalGenerator
()
->
FindLocalGenerator
(
dir
.
c_str
())))
{
// Use the makefile for the directory found.
mf
=
lg
->
GetMakefile
();
}
else
{
// Could not find the directory.
this
->
SetError
(
"DIRECTORY scope provided but requested directory was not found. "
"This could be because the directory argument was invalid or, "
"it is valid but has not been processed yet."
);
return
false
;
}
}
// Get the property.
return
this
->
StoreResult
(
mf
->
GetProperty
(
this
->
PropertyName
.
c_str
()));
}
//----------------------------------------------------------------------------
bool
cmGetPropertyCommand
::
HandleTargetMode
()
{
if
(
this
->
Name
.
empty
())
{
this
->
SetError
(
"not given name for TARGET scope."
);
return
false
;
}
if
(
cmTarget
*
target
=
this
->
Makefile
->
GetLocalGenerator
()
->
GetGlobalGenerator
()
->
FindTarget
(
0
,
this
->
Name
.
c_str
(),
true
))
{
return
this
->
StoreResult
(
target
->
GetProperty
(
this
->
PropertyName
.
c_str
()));
}
else
{
cmOStringStream
e
;
e
<<
"could not find TARGET "
<<
this
->
Name
<<
". Perhaps it has not yet been created."
;
this
->
SetError
(
e
.
str
().
c_str
());
return
false
;
}
}
//----------------------------------------------------------------------------
bool
cmGetPropertyCommand
::
HandleSourceMode
()
{
if
(
this
->
Name
.
empty
())
{
this
->
SetError
(
"not given name for SOURCE scope."
);
return
false
;
}
// Get the source file.
if
(
cmSourceFile
*
sf
=
this
->
Makefile
->
GetOrCreateSource
(
this
->
Name
.
c_str
()))
{
return
this
->
StoreResult
(
sf
->
GetProperty
(
this
->
PropertyName
.
c_str
()));
}
else
{
cmOStringStream
e
;
e
<<
"given SOURCE name that could not be found or created: "
<<
this
->
Name
;
this
->
SetError
(
e
.
str
().
c_str
());
return
false
;
}
}
//----------------------------------------------------------------------------
bool
cmGetPropertyCommand
::
HandleTestMode
()
{
if
(
this
->
Name
.
empty
())
{
this
->
SetError
(
"not given name for TEST scope."
);
return
false
;
}
// Loop over all tests looking for matching names.
std
::
vector
<
cmTest
*>
const
&
tests
=
*
this
->
Makefile
->
GetTests
();
for
(
std
::
vector
<
cmTest
*>::
const_iterator
ti
=
tests
.
begin
();
ti
!=
tests
.
end
();
++
ti
)
{
cmTest
*
test
=
*
ti
;
if
(
test
->
GetName
()
==
this
->
Name
)
{
return
this
->
StoreResult
(
test
->
GetProperty
(
this
->
PropertyName
.
c_str
()));
}
}
// If not found it is an error.
cmOStringStream
e
;
e
<<
"given TEST name that does not exist: "
<<
this
->
Name
;
this
->
SetError
(
e
.
str
().
c_str
());
return
false
;
}
//----------------------------------------------------------------------------
bool
cmGetPropertyCommand
::
HandleVariableMode
()
{
if
(
!
this
->
Name
.
empty
())
{
this
->
SetError
(
"given name for VARIABLE scope."
);
return
false
;
}
return
this
->
StoreResult
(
this
->
Makefile
->
GetDefinition
(
this
->
PropertyName
.
c_str
()));
}
Source/cmGetPropertyCommand.h
View file @
669db35a
...
...
@@ -22,6 +22,8 @@
class
cmGetPropertyCommand
:
public
cmCommand
{
public:
cmGetPropertyCommand
();
virtual
cmCommand
*
Clone
()
{
return
new
cmGetPropertyCommand
;
...
...
@@ -57,23 +59,57 @@ public:
virtual
const
char
*
GetFullDocumentation
()
{
return
" get_property(VAR scope_value property)
\n
"
" get_property(VAR scope_value property
\n
"
" BRIEF_DOCS)
\n
"
" get_property(VAR scope_value property
\n
"
" FULL_DOCS)
\n
"
"Get a property from cmake. The scope_value is either GLOBAL, "
"DIRECTORY dir_name, TARGET tgt_name, SOURCE_FILE src_name, "
"TEST test_name or VARIABLE var_name. The resulting value is "
"stored in the variable VAR. If the property is not found, "
"CMake will report an error. The second and third signatures "
"return the documentation for a property or variable instead of "
"its value."
;
" get_property(<variable>
\n
"
" <GLOBAL |
\n
"
" DIRECTORY [dir] |
\n
"
" TARGET <target> |
\n
"
" SOURCE <source> |
\n
"
" TEST <test> |
\n
"
" VARIABLE>
\n
"
" PROPERTY <name>
\n
"
" [DEFINED | BRIEF_DOCS | FULL_DOCS])
\n
"
"Get one property from one object in a scope. "
"The first argument specifies the variable in which to store the "
"result. "
"The second argument determines the scope from which to get the "
"property. It must be one of the following:
\n
"
"GLOBAL scope is unique and does not accept a name.
\n
"
"DIRECTORY scope defaults to the current directory but another "
"directory (already processed by CMake) may be named by full or "
"relative path.
\n
"
"TARGET scope must name one existing target.
\n
"
"SOURCE scope must name one source file.
\n
"
"TEST scope must name one existing test.
\n
"
"VARIABLE scope is unique and does not accept a name.
\n
"
"The required PROPERTY option is immediately followed by the name "
"of the property to get. "
"If the property is not set an empty value is returned. "
"If the DEFINED option is given the variable is set to a boolean "
"value indicating whether the property has been set. "
"If BRIEF_DOCS or FULL_DOCS is given then the variable is set to "
"a string containing documentation for the requested property. "
"If documentation is requested for a property that has not been "
"defined NOTFOUND is returned."
;
}
cmTypeMacro
(
cmGetPropertyCommand
,
cmCommand
);
};
private:
enum
OutType
{
OutValue
,
OutDefined
,
OutBriefDoc
,
OutFullDoc
};
std
::
string
Variable
;
std
::
string
Name
;
std
::
string
PropertyName
;
OutType
InfoType
;
// Implementation of result storage.
bool
StoreResult
(
const
char
*
value
);
// Implementation of each property type.
bool
HandleGlobalMode
();
bool
HandleDirectoryMode
();
bool
HandleTargetMode
();
bool
HandleSourceMode
();
bool
HandleTestMode
();
bool
HandleVariableMode
();
};
#endif
Tests/Properties/CMakeLists.txt
View file @
669db35a
...
...
@@ -27,32 +27,34 @@ define_property(GLOBALTEST GLOBAL "A test property"
set_property
(
GLOBAL PROPERTY GLOBALTEST 1
)
set_property
(
DIRECTORY PROPERTY DIRECTORYTEST 1
)
set_property
(
SOURCE SubDir/properties3.cxx PROPERTY SOURCETEST 1
)
get_property
(
GLOBALRESULT GLOBAL GLOBALTEST
)
get_property
(
DIRECTORYRESULT DIRECTORY
"
${
CMAKE_CURRENT_SOURCE_DIR
}
"
DIRECTORYTEST
)
get_property
(
SOURCE_FILERESULT SOURCE_FILE SubDir/properties3.cxx SOURCETEST
)
get_property
(
GLOBALRESULT GLOBAL PROPERTY GLOBALTEST
)
get_property
(
DIRECTORYRESULT DIRECTORY PROPERTY DIRECTORYTEST
)
get_property
(
SOURCERESULT
SOURCE SubDir/properties3.cxx
PROPERTY SOURCETEST
)
<