diff --git a/.github/workflows/cmakelint.yml b/.github/workflows/cmakelint.yml new file mode 100644 index 00000000..103f6ed2 --- /dev/null +++ b/.github/workflows/cmakelint.yml @@ -0,0 +1,30 @@ +name: CMake Linter + +on: [push, pull_request] + +jobs: + run_cmakelint: + runs-on: ubuntu-latest + steps: + - name: Checkout + uses: actions/checkout@master + + - name: Set up Python + uses: actions/setup-python@v2 + with: + python-version: 3.8 + + - name: Install cmakelint + run: | + python -m pip install --upgrade pip + # cmake-lint does not find real problems with CMAke syntax + python -m pip install cmakelang + + - name: run cmake-lint + working-directory: ${{github.workspace}} + run: | + cmake-lint --version + for f in cmake/*.cmake; do + echo "Processing ${f}" + cmake-lint -c tools/cmakelang-config.py -- $f + done diff --git a/cmake/FindAVFORMAT.cmake b/cmake/FindAVFORMAT.cmake index 5f253873..1ef7f695 100644 --- a/cmake/FindAVFORMAT.cmake +++ b/cmake/FindAVFORMAT.cmake @@ -28,4 +28,4 @@ endif() include(FindPackageHandleStandardArgs) find_package_handle_standard_args( AVFORMAT - REQUIRED_VARS AVFORMAT_FOUND) \ No newline at end of file + REQUIRED_VARS AVFORMAT_FOUND) diff --git a/cmake/FindFreeImage.cmake b/cmake/FindFreeImage.cmake index 891e7552..0f3c43dd 100644 --- a/cmake/FindFreeImage.cmake +++ b/cmake/FindFreeImage.cmake @@ -44,7 +44,14 @@ if (NOT WIN32) set(FreeImage_test_output "") set(FreeImage_compile_output "") file(WRITE ${testFreeImageSource} - "#include \nint main () { if (FREEIMAGE_MAJOR_VERSION >= ${major_version} && FREEIMAGE_MINOR_VERSION >= ${minor_version}) return 1; else return 0;} \n") + "#include + int main () { + if (FREEIMAGE_MAJOR_VERSION >= ${major_version} && + FREEIMAGE_MINOR_VERSION >= ${minor_version}) + return 1; + else + return 0; + }") try_run(FREEIMAGE_RUNS FREEIMAGE_COMPILES diff --git a/cmake/FindIgnCURL.cmake b/cmake/FindIgnCURL.cmake index a2cf0337..1e8f26f7 100644 --- a/cmake/FindIgnCURL.cmake +++ b/cmake/FindIgnCURL.cmake @@ -51,7 +51,7 @@ if(${IgnCURL_FOUND}) set_target_properties(curl::curl PROPERTIES INTERFACE_LINK_LIBRARIES CURL::libcurl) endif() - + include(IgnImportTarget) if(NOT TARGET curl::curl) diff --git a/cmake/FindIgnOGRE.cmake b/cmake/FindIgnOGRE.cmake index 6825eb2f..6943a709 100644 --- a/cmake/FindIgnOGRE.cmake +++ b/cmake/FindIgnOGRE.cmake @@ -53,10 +53,10 @@ set(minor_version ${IgnOGRE_FIND_VERSION_MINOR}) set(full_version ${major_version}.${minor_version}) # Copied from OGREConfig.cmake -macro(ign_ogre_declare_plugin TYPE COMPONENT) - set(OGRE_${TYPE}_${COMPONENT}_FOUND TRUE) - set(OGRE_${TYPE}_${COMPONENT}_LIBRARIES ${TYPE}_${COMPONENT}) - list(APPEND OGRE_LIBRARIES ${TYPE}_${COMPONENT}) +macro(ign_ogre_declare_plugin type component) + set(OGRE_${type}_${component}_FOUND TRUE) + set(OGRE_${type}_${component}_LIBRARIES ${type}_${component}) + list(APPEND OGRE_LIBRARIES ${type}_${component}) endmacro() if (NOT WIN32) @@ -102,7 +102,9 @@ if (NOT WIN32) if (NOT OGRE_LIBRARY_DIRS) pkg_get_variable(OGRE_LIBRARY_DIRS OGRE libdir) if(NOT OGRE_LIBRARY_DIRS) - IGN_BUILD_WARNING ("Failed to find OGRE's library directory. The build will succeed, but there will likely be run-time errors.") + IGN_BUILD_WARNING ("\ + Failed to find OGRE's library directory. \ + The build will succeed, but there will likely be run-time errors.") else() # strip line break string(REGEX REPLACE "\n$" "" OGRE_LIBRARY_DIRS "${OGRE_LIBRARY_DIRS}") @@ -111,8 +113,8 @@ if (NOT WIN32) # in some cases the value of OGRE_LIBRARIES is "OgreMain;pthread" # Convert this to full path to library if (substr_found EQUAL -1) - foreach(OGRE_LIBRARY_NAME ${OGRE_LIBRARIES}) - find_library(OGRE_LIBRARY NAMES ${OGRE_LIBRARY_NAME} + foreach(ogre_library_name ${OGRE_LIBRARIES}) + find_library(OGRE_LIBRARY NAMES ${ogre_library_name} HINTS ${OGRE_LIBRARY_DIRS} NO_DEFAULT_PATH) list (APPEND TMP_OGRE_LIBRARIES "${OGRE_LIBRARY}") endforeach() @@ -146,7 +148,8 @@ if (NOT WIN32) pkg_get_variable(OGRE_PLUGINDIR OGRE plugindir) if(NOT OGRE_PLUGINDIR) - IGN_BUILD_WARNING ("Failed to find OGRE's plugin directory. The build will succeed, but there will likely be run-time errors.") + IGN_BUILD_WARNING ("Failed to find OGRE's plugin directory. \ + The build will succeed, but there will likely be run-time errors.") else() # Seems that OGRE_PLUGINDIR can end in a newline, which will cause problems # when we pass it to the compiler later. @@ -201,11 +204,11 @@ else() string(REGEX REPLACE "\\$.*>" "" ogre_lib ${ogre_lib}) # Be sure that all Ogre* libraries are using absolute paths set(prefix "") - # vcpkg uses special directory (lib/manual-link/) to place libraries - # with main sysmbol like OgreMain. - if(ogre_lib MATCHES "OgreMain" AND NOT IS_ABSOLUTE "${ogre_lib}" AND EXISTS "${OGRE_LIBRARY_DIRS}/manual-link/") + # vcpkg uses special directory (lib/manual-link/) to place libraries + # with main sysmbol like OgreMain. + if(ogre_lib MATCHES "OgreMain" AND NOT IS_ABSOLUTE "${ogre_lib}" AND EXISTS "${OGRE_LIBRARY_DIRS}/manual-link/") set(prefix "${OGRE_LIBRARY_DIRS}/manual-link/") - elseif(ogre_lib MATCHES "Ogre" AND NOT IS_ABSOLUTE "${ogre_lib}") + elseif(ogre_lib MATCHES "Ogre" AND NOT IS_ABSOLUTE "${ogre_lib}") set(prefix "${OGRE_LIBRARY_DIRS}/") endif() if(ogre_lib MATCHES "Plugin_" OR ogre_lib MATCHES "RenderSystem_") diff --git a/cmake/FindOptiX.cmake b/cmake/FindOptiX.cmake index a0ca83db..2218aadb 100644 --- a/cmake/FindOptiX.cmake +++ b/cmake/FindOptiX.cmake @@ -68,7 +68,8 @@ # Locate the OptiX distribution. Search in env path first, then look in the system. -set(OptiX_INSTALL_DIR "$ENV{OPTIX_INSTALL_DIR}" CACHE PATH "Path to OptiX installed location.") +set(OptiX_INSTALL_DIR "$ENV{OPTIX_INSTALL_DIR}" + CACHE PATH "Path to OptiX installed location.") # The distribution contains both 32 and 64 bit libraries. Adjust the library # search path based on the bit-ness of the build. (i.e. 64: bin64, lib64; 32: @@ -85,20 +86,16 @@ macro(ign_OPTIX_find_api_library name version) find_library(${name}_LIBRARY NAMES ${name}.${version} ${name} PATHS "${OptiX_INSTALL_DIR}/lib${bit_dest}" - NO_DEFAULT_PATH - ) + NO_DEFAULT_PATH) find_library(${name}_LIBRARY - NAMES ${name}.${version} ${name} - ) + NAMES ${name}.${version} ${name}) if(WIN32) find_file(${name}_DLL NAMES ${name}.${version}.dll PATHS "${OptiX_INSTALL_DIR}/bin${bit_dest}" - NO_DEFAULT_PATH - ) + NO_DEFAULT_PATH) find_file(${name}_DLL - NAMES ${name}.${version}.dll - ) + NAMES ${name}.${version}.dll) endif() endmacro() @@ -110,11 +107,9 @@ ign_OPTIX_find_api_library(optix_prime 1) find_path(OptiX_INCLUDE NAMES optix.h PATHS "${OptiX_INSTALL_DIR}/include" - NO_DEFAULT_PATH - ) + NO_DEFAULT_PATH) find_path(OptiX_INCLUDE - NAMES optix.h - ) + NAMES optix.h) # Check to make sure we found what we were looking for function(OptiX_report_error error_message required) @@ -139,7 +134,7 @@ endif() # Macro for setting up dummy targets function(OptiX_add_imported_library name lib_location dll_lib dependent_libs) - set(CMAKE_IMPORT_FILE_VERSION 1) + set(CMAKE_IMPORT_FILE_VERSION 1) # cmake-lint: disable=C0103 # Create imported target # ign-cmake modification: changed to use ${target_name} instead of ${name} @@ -152,27 +147,24 @@ function(OptiX_add_imported_library name lib_location dll_lib dependent_libs) IMPORTED_IMPLIB "${lib_location}" #IMPORTED_LINK_INTERFACE_LIBRARIES "glu32;opengl32" IMPORTED_LOCATION "${dll_lib}" - IMPORTED_LINK_INTERFACE_LIBRARIES "${dependent_libs}" - ) + IMPORTED_LINK_INTERFACE_LIBRARIES "${dependent_libs}") elseif(UNIX) set_target_properties(${target_name} PROPERTIES #IMPORTED_LINK_INTERFACE_LIBRARIES "glu32;opengl32" IMPORTED_LOCATION "${lib_location}" # We don't have versioned filenames for now, and it may not even matter. #IMPORTED_SONAME "${optix_soname}" - IMPORTED_LINK_INTERFACE_LIBRARIES "${dependent_libs}" - ) + IMPORTED_LINK_INTERFACE_LIBRARIES "${dependent_libs}") else() # Unknown system, but at least try and provide the minimum required # information. set_target_properties(${target_name} PROPERTIES IMPORTED_LOCATION "${lib_location}" - IMPORTED_LINK_INTERFACE_LIBRARIES "${dependent_libs}" - ) + IMPORTED_LINK_INTERFACE_LIBRARIES "${dependent_libs}") endif() # Commands beyond this point should not need to know the version. - set(CMAKE_IMPORT_FILE_VERSION) + set(CMAKE_IMPORT_FILE_VERSION) # cmake-lint: disable=C0103 endfunction() # Sets up a dummy target @@ -188,7 +180,12 @@ macro(ign_OptiX_check_same_path libA libB) # to the ${libB}. get_filename_component(_optix_name_of_${libA} "${${libA}_LIBRARY}" NAME) if(EXISTS "${_optix_path_to_${libB}}/${_optix_name_of_${libA}}") - message(WARNING " ${libA} library found next to ${libB} library that is not being used. Due to the way we are using rpath, the copy of ${libA} next to ${libB} will be used during loading instead of the one you intended. Consider putting the libraries in the same directory or moving ${_optix_path_to_${libB}}/${_optix_name_of_${libA} out of the way.") + message(WARNING "\ + ${libA} library found next to ${libB} library that is not being used. \ + Due to the way we are using rpath, the copy of ${libA} next to \ + ${libB} will be used during loading instead of the one you intended. \ + Consider putting the libraries in the same directory or moving \ + ${_optix_path_to_${libB}}/${_optix_name_of_${libA} out of the way.") endif() endif() set( _${libA}_rpath "-Wl,-rpath,${_optix_path_to_${libA}}" ) diff --git a/cmake/FindYAML.cmake b/cmake/FindYAML.cmake index f081d1af..ccc35a7d 100644 --- a/cmake/FindYAML.cmake +++ b/cmake/FindYAML.cmake @@ -88,7 +88,7 @@ else() ) endif() endif() - + include(FindPackageHandleStandardArgs) find_package_handle_standard_args( YAML diff --git a/cmake/FindZIP.cmake b/cmake/FindZIP.cmake index 2c2cd76a..a29b83a3 100644 --- a/cmake/FindZIP.cmake +++ b/cmake/FindZIP.cmake @@ -63,4 +63,4 @@ endif() include(FindPackageHandleStandardArgs) find_package_handle_standard_args( ZIP - REQUIRED_VARS ZIP_FOUND) \ No newline at end of file + REQUIRED_VARS ZIP_FOUND) diff --git a/cmake/FindZeroMQ.cmake b/cmake/FindZeroMQ.cmake index 46389486..9c5c542e 100644 --- a/cmake/FindZeroMQ.cmake +++ b/cmake/FindZeroMQ.cmake @@ -1,85 +1,85 @@ -##============================================================================= -# -# CMake - Cross Platform Makefile Generator -# Copyright 2000-2011 Kitware, Inc., Insight Software Consortium -# All rights reserved. -# -# Redistribution and use in source and binary forms, with or without -# modification, are permitted provided that the following conditions -# are met: -# -# * Redistributions of source code must retain the above copyright -# notice, this list of conditions and the following disclaimer. -# -# * Redistributions in binary form must reproduce the above copyright -# notice, this list of conditions and the following disclaimer in the -# documentation and/or other materials provided with the distribution. -# -# * Neither the names of Kitware, Inc., the Insight Software Consortium, -# nor the names of their contributors may be used to endorse or promote -# products derived from this software without specific prior written -# permission. -# -# THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS -# "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT -# LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR -# A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT -# HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, -# SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT -# LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, -# DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY -# THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT -# (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE -# OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. -# -# Modified by Jose Luis Rivero -# -##============================================================================= -# - Try to find ZeroMQ headers and libraries -# -# Usage of this module as follows: -# -# find_package(ZeroMQ) -# -# Variables used by this module, they can change the default behaviour and need -# to be set before calling find_package: -# -# ZeroMQ_ROOT_DIR Set this variable to the root installation of -# ZeroMQ if the module has problems finding -# the proper installation path. -# -# Variables defined by this module: -# -# ZEROMQ_FOUND System has ZeroMQ libs/headers -# ZeroMQ_LIBRARIES The ZeroMQ libraries -# ZeroMQ_INCLUDE_DIRS The location of ZeroMQ headers - -include(IgnPkgConfig) - -# We initialize this variable to the default target name -set(ZeroMQ_TARGET ZeroMQ::ZeroMQ) - -find_package(ZeroMQ ${ZeroMQ_FIND_VERSION} QUIET CONFIG) -if (ZeroMQ_FOUND) - - # ZeroMQ's cmake script imports its own target, so we'll - # overwrite the default with the name of theirs. In the - # future, we should be able to use a target alias instead. - set(ZeroMQ_TARGET libzmq) - - # Make sure to fill out the pkg-config information before quitting - ign_pkg_config_entry(ZeroMQ "libzmq >= ${ZeroMQ_FIND_VERSION}") - - return() - -endif() - -if (UNIX) - - if(NOT ZeroMQ_FIND_QUIETLY) - message(STATUS "Config-file not installed for ZeroMQ -- checking for pkg-config") - endif() - - ign_pkg_check_modules(ZeroMQ "libzmq >= ${ZeroMQ_FIND_VERSION}") - -endif() +##============================================================================= +# +# CMake - Cross Platform Makefile Generator +# Copyright 2000-2011 Kitware, Inc., Insight Software Consortium +# All rights reserved. +# +# Redistribution and use in source and binary forms, with or without +# modification, are permitted provided that the following conditions +# are met: +# +# * Redistributions of source code must retain the above copyright +# notice, this list of conditions and the following disclaimer. +# +# * Redistributions in binary form must reproduce the above copyright +# notice, this list of conditions and the following disclaimer in the +# documentation and/or other materials provided with the distribution. +# +# * Neither the names of Kitware, Inc., the Insight Software Consortium, +# nor the names of their contributors may be used to endorse or promote +# products derived from this software without specific prior written +# permission. +# +# THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS +# "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT +# LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR +# A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT +# HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, +# SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT +# LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, +# DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY +# THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT +# (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE +# OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. +# +# Modified by Jose Luis Rivero +# +##============================================================================= +# - Try to find ZeroMQ headers and libraries +# +# Usage of this module as follows: +# +# find_package(ZeroMQ) +# +# Variables used by this module, they can change the default behaviour and need +# to be set before calling find_package: +# +# ZeroMQ_ROOT_DIR Set this variable to the root installation of +# ZeroMQ if the module has problems finding +# the proper installation path. +# +# Variables defined by this module: +# +# ZEROMQ_FOUND System has ZeroMQ libs/headers +# ZeroMQ_LIBRARIES The ZeroMQ libraries +# ZeroMQ_INCLUDE_DIRS The location of ZeroMQ headers + +include(IgnPkgConfig) + +# We initialize this variable to the default target name +set(ZeroMQ_TARGET ZeroMQ::ZeroMQ) + +find_package(ZeroMQ ${ZeroMQ_FIND_VERSION} QUIET CONFIG) +if (ZeroMQ_FOUND) + + # ZeroMQ's cmake script imports its own target, so we'll + # overwrite the default with the name of theirs. In the + # future, we should be able to use a target alias instead. + set(ZeroMQ_TARGET libzmq) + + # Make sure to fill out the pkg-config information before quitting + ign_pkg_config_entry(ZeroMQ "libzmq >= ${ZeroMQ_FIND_VERSION}") + + return() + +endif() + +if (UNIX) + + if(NOT ZeroMQ_FIND_QUIETLY) + message(STATUS "Config-file not installed for ZeroMQ -- checking for pkg-config") + endif() + + ign_pkg_check_modules(ZeroMQ "libzmq >= ${ZeroMQ_FIND_VERSION}") + +endif() diff --git a/cmake/IgnBenchmark.cmake b/cmake/IgnBenchmark.cmake index 5ee8be4d..2adbe909 100644 --- a/cmake/IgnBenchmark.cmake +++ b/cmake/IgnBenchmark.cmake @@ -35,12 +35,14 @@ # See the License for the specific language governing permissions and # limitations under the License. +# Generate the version_info_target for generating version_info.json function(ign_add_version_info_target) # generate a version_info.json file that can be used to embed project # version information # While this command may look a bit unweildy, it creates a target # that forces the file to be regenerated at build time. add_custom_target(version_info_target + COMMENT "Generate version_info.json" COMMAND ${CMAKE_COMMAND} -Dinput_file=${IGNITION_CMAKE_DIR}/version_info.json.in -Doutput_file=${CMAKE_CURRENT_BINARY_DIR}/version_info.json @@ -58,6 +60,12 @@ function(ign_add_version_info_target) ) endfunction() +################################################# +# ign_add_benchmarks( +# SOURCES ) +# +# Generate benchmark tests using google benchmark +# function(ign_add_benchmarks) cmake_parse_arguments(BENCHMARK "" "" "SOURCES" ${ARGN}) @@ -78,9 +86,9 @@ function(ign_add_benchmarks) EXEC_LIST BENCHMARK_TARGETS ) - set(BENCHMARK_TARGETS_LIST "") + set(benchmark_targets_list "") foreach(benchmark ${BENCHMARK_TARGETS}) - list(APPEND BENCHMARK_TARGETS_LIST "$") + list(APPEND benchmark_targets_list "$") endforeach() ign_add_version_info_target() @@ -89,10 +97,11 @@ function(ign_add_benchmarks) OUTPUT "${CMAKE_CURRENT_BINARY_DIR}/$/benchmark_targets" CONTENT - "${BENCHMARK_TARGETS_LIST}") + "${benchmark_targets_list}") add_custom_target( run_benchmarks + COMMENT "Execute run_benchmarks script" COMMAND python3 ${IGNITION_CMAKE_BENCHMARK_DIR}/run_benchmarks.py --project-name ${PROJECT_NAME} --version-file ${CMAKE_CURRENT_BINARY_DIR}/version_info.json diff --git a/cmake/IgnCheckSSE.cmake b/cmake/IgnCheckSSE.cmake index dc5b498e..477df35a 100644 --- a/cmake/IgnCheckSSE.cmake +++ b/cmake/IgnCheckSSE.cmake @@ -75,82 +75,83 @@ set(archdetect_c_code " # will be treated as invalid architectures since they are no longer supported by Apple if(APPLE AND CMAKE_OSX_ARCHITECTURES) - # On OS X we use CMAKE_OSX_ARCHITECTURES *if* it was set - # First let's normalize the order of the values - - # Note that it's not possible to compile PowerPC applications if you are using - # the OS X SDK version 10.6 or later - you'll need 10.4/10.5 for that, so we - # disable it by default - # See this page for more information: - # http://stackoverflow.com/questions/5333490/how-can-we-restore-ppc-ppc64-as-well-as-full-10-4-10-5-sdk-support-to-xcode-4 - - # Architecture defaults to i386 or ppc on OS X 10.5 and earlier, depending on the CPU type detected at runtime. - # On OS X 10.6+ the default is x86_64 if the CPU supports it, i386 otherwise. - - foreach(osx_arch ${CMAKE_OSX_ARCHITECTURES}) - if("${osx_arch}" STREQUAL "ppc" AND ppc_support) - set(osx_arch_ppc TRUE) - elseif("${osx_arch}" STREQUAL "i386") - set(osx_arch_i386 TRUE) - elseif("${osx_arch}" STREQUAL "x86_64") - set(osx_arch_x86_64 TRUE) - elseif("${osx_arch}" STREQUAL "ppc64" AND ppc_support) - set(osx_arch_ppc64 TRUE) - else() - message(FATAL_ERROR "Invalid OS X arch name: ${osx_arch}") - endif() - endforeach() - - # Now add all the architectures in our normalized order - if(osx_arch_ppc) - list(APPEND ARCH ppc) + # On OS X we use CMAKE_OSX_ARCHITECTURES *if* it was set + # First let's normalize the order of the values + + # Note that it's not possible to compile PowerPC applications if you are using + # the OS X SDK version 10.6 or later - you'll need 10.4/10.5 for that, so we + # disable it by default + # See this page for more information: + # http://stackoverflow.com/questions/5333490 + + # Architecture defaults to i386 or ppc on OS X 10.5 and earlier, depending on + # the CPU type detected at runtime. + # On OS X 10.6+ the default is x86_64 if the CPU supports it, i386 otherwise. + + foreach(osx_arch ${CMAKE_OSX_ARCHITECTURES}) + if("${osx_arch}" STREQUAL "ppc" AND ppc_support) + set(osx_arch_ppc TRUE) + elseif("${osx_arch}" STREQUAL "i386") + set(osx_arch_i386 TRUE) + elseif("${osx_arch}" STREQUAL "x86_64") + set(osx_arch_x86_64 TRUE) + elseif("${osx_arch}" STREQUAL "ppc64" AND ppc_support) + set(osx_arch_ppc64 TRUE) + else() + message(FATAL_ERROR "Invalid OS X arch name: ${osx_arch}") endif() + endforeach() - if(osx_arch_i386) - list(APPEND ARCH i386) - endif() + # Now add all the architectures in our normalized order + if(osx_arch_ppc) + list(APPEND ARCH ppc) + endif() - if(osx_arch_x86_64) - list(APPEND ARCH x86_64) - endif() + if(osx_arch_i386) + list(APPEND ARCH i386) + endif() - if(osx_arch_ppc64) - list(APPEND ARCH ppc64) - endif() + if(osx_arch_x86_64) + list(APPEND ARCH x86_64) + endif() + + if(osx_arch_ppc64) + list(APPEND ARCH ppc64) + endif() else() - file(WRITE "${CMAKE_BINARY_DIR}/arch.c" "${archdetect_c_code}") - - enable_language(C) - - # Detect the architecture in a rather creative way... - # This compiles a small C program which is a series of ifdefs that selects a - # particular #error preprocessor directive whose message string contains the - # target architecture. The program will always fail to compile (both because - # file is not a valid C program, and obviously because of the presence of the - # #error preprocessor directives... but by exploiting the preprocessor in this - # way, we can detect the correct target architecture even when cross-compiling, - # since the program itself never needs to be run (only the compiler/preprocessor) - try_run( - run_result_unused - compile_result_unused - "${CMAKE_BINARY_DIR}" - "${CMAKE_BINARY_DIR}/arch.c" - COMPILE_OUTPUT_VARIABLE ARCH - CMAKE_FLAGS CMAKE_OSX_ARCHITECTURES=${CMAKE_OSX_ARCHITECTURES} - ) - - # Parse the architecture name from the compiler output - string(REGEX MATCH "cmake_ARCH ([a-zA-Z0-9_]+)" ARCH "${ARCH}") - - # Get rid of the value marker leaving just the architecture name - string(REPLACE "cmake_ARCH " "" ARCH "${ARCH}") - - # If we are compiling with an unknown architecture this variable should - # already be set to "unknown" but in the case that it's empty (i.e. due - # to a typo in the code), then set it to unknown - if (NOT ARCH) - set(ARCH unknown) - endif() + file(WRITE "${CMAKE_BINARY_DIR}/arch.c" "${archdetect_c_code}") + + enable_language(C) + + # Detect the architecture in a rather creative way... + # This compiles a small C program which is a series of ifdefs that selects a + # particular #error preprocessor directive whose message string contains the + # target architecture. The program will always fail to compile (both because + # file is not a valid C program, and obviously because of the presence of the + # #error preprocessor directives... but by exploiting the preprocessor in this + # way, we can detect the correct target architecture even when cross-compiling, + # since the program itself never needs to be run (only the compiler/preprocessor) + try_run( + run_result_unused + compile_result_unused + "${CMAKE_BINARY_DIR}" + "${CMAKE_BINARY_DIR}/arch.c" + COMPILE_OUTPUT_VARIABLE ARCH + CMAKE_FLAGS CMAKE_OSX_ARCHITECTURES=${CMAKE_OSX_ARCHITECTURES} + ) + + # Parse the architecture name from the compiler output + string(REGEX MATCH "cmake_ARCH ([a-zA-Z0-9_]+)" ARCH "${ARCH}") + + # Get rid of the value marker leaving just the architecture name + string(REPLACE "cmake_ARCH " "" ARCH "${ARCH}") + + # If we are compiling with an unknown architecture this variable should + # already be set to "unknown" but in the case that it's empty (i.e. due + # to a typo in the code), then set it to unknown + if (NOT ARCH) + set(ARCH unknown) + endif() endif() @@ -159,125 +160,125 @@ endif() IF (ARCH MATCHES "i386" OR ARCH MATCHES "x86_64") IF(CMAKE_SYSTEM_NAME MATCHES "Linux") - EXEC_PROGRAM(cat ARGS "/proc/cpuinfo" OUTPUT_VARIABLE CPUINFO) - - STRING(REGEX REPLACE "^.*(sse2).*$" "\\1" SSE_THERE ${CPUINFO}) - STRING(COMPARE EQUAL "sse2" "${SSE_THERE}" SSE2_TRUE) - IF (SSE2_TRUE) - set(SSE2_FOUND true CACHE BOOL "SSE2 available on host") - ELSE (SSE2_TRUE) - set(SSE2_FOUND false CACHE BOOL "SSE2 available on host") - ENDIF (SSE2_TRUE) - - # /proc/cpuinfo apparently omits sse3 :( - STRING(REGEX REPLACE "^.*[^s](sse3).*$" "\\1" SSE_THERE ${CPUINFO}) - STRING(COMPARE EQUAL "sse3" "${SSE_THERE}" SSE3_TRUE) - IF (NOT SSE3_TRUE) - STRING(REGEX REPLACE "^.*(T2300).*$" "\\1" SSE_THERE ${CPUINFO}) - STRING(COMPARE EQUAL "T2300" "${SSE_THERE}" SSE3_TRUE) - ENDIF (NOT SSE3_TRUE) - - STRING(REGEX REPLACE "^.*(ssse3).*$" "\\1" SSE_THERE ${CPUINFO}) - STRING(COMPARE EQUAL "ssse3" "${SSE_THERE}" SSSE3_TRUE) - IF (SSE3_TRUE OR SSSE3_TRUE) - set(SSE3_FOUND true CACHE BOOL "SSE3 available on host") - ELSE (SSE3_TRUE OR SSSE3_TRUE) - set(SSE3_FOUND false CACHE BOOL "SSE3 available on host") - ENDIF (SSE3_TRUE OR SSSE3_TRUE) - IF (SSSE3_TRUE) - set(SSSE3_FOUND true CACHE BOOL "SSSE3 available on host") - ELSE (SSSE3_TRUE) - set(SSSE3_FOUND false CACHE BOOL "SSSE3 available on host") - ENDIF (SSSE3_TRUE) - - STRING(REGEX REPLACE "^.*(sse4_1).*$" "\\1" SSE_THERE ${CPUINFO}) - STRING(COMPARE EQUAL "sse4_1" "${SSE_THERE}" SSE41_TRUE) - IF (SSE41_TRUE) - set(SSE4_1_FOUND true CACHE BOOL "SSE4.1 available on host") - ELSE (SSE41_TRUE) - set(SSE4_1_FOUND false CACHE BOOL "SSE4.1 available on host") - ENDIF (SSE41_TRUE) - - STRING(REGEX REPLACE "^.*(sse4_2).*$" "\\1" SSE_THERE ${CPUINFO}) - STRING(COMPARE EQUAL "sse4_2" "${SSE_THERE}" SSE42_TRUE) - IF (SSE42_TRUE) - set(SSE4_2_FOUND true CACHE BOOL "SSE4.2 available on host") - ELSE (SSE42_TRUE) - set(SSE4_2_FOUND false CACHE BOOL "SSE4.2 available on host") - ENDIF (SSE42_TRUE) + EXEC_PROGRAM(cat ARGS "/proc/cpuinfo" OUTPUT_VARIABLE CPUINFO) + + STRING(REGEX REPLACE "^.*(sse2).*$" "\\1" SSE_THERE ${CPUINFO}) + STRING(COMPARE EQUAL "sse2" "${SSE_THERE}" SSE2_TRUE) + IF (SSE2_TRUE) + set(SSE2_FOUND true CACHE BOOL "SSE2 available on host") + ELSE (SSE2_TRUE) + set(SSE2_FOUND false CACHE BOOL "SSE2 available on host") + ENDIF (SSE2_TRUE) + + # /proc/cpuinfo apparently omits sse3 :( + STRING(REGEX REPLACE "^.*[^s](sse3).*$" "\\1" SSE_THERE ${CPUINFO}) + STRING(COMPARE EQUAL "sse3" "${SSE_THERE}" SSE3_TRUE) + IF (NOT SSE3_TRUE) + STRING(REGEX REPLACE "^.*(T2300).*$" "\\1" SSE_THERE ${CPUINFO}) + STRING(COMPARE EQUAL "T2300" "${SSE_THERE}" SSE3_TRUE) + ENDIF (NOT SSE3_TRUE) + + STRING(REGEX REPLACE "^.*(ssse3).*$" "\\1" SSE_THERE ${CPUINFO}) + STRING(COMPARE EQUAL "ssse3" "${SSE_THERE}" SSSE3_TRUE) + IF (SSE3_TRUE OR SSSE3_TRUE) + set(SSE3_FOUND true CACHE BOOL "SSE3 available on host") + ELSE (SSE3_TRUE OR SSSE3_TRUE) + set(SSE3_FOUND false CACHE BOOL "SSE3 available on host") + ENDIF (SSE3_TRUE OR SSSE3_TRUE) + IF (SSSE3_TRUE) + set(SSSE3_FOUND true CACHE BOOL "SSSE3 available on host") + ELSE (SSSE3_TRUE) + set(SSSE3_FOUND false CACHE BOOL "SSSE3 available on host") + ENDIF (SSSE3_TRUE) + + STRING(REGEX REPLACE "^.*(sse4_1).*$" "\\1" SSE_THERE ${CPUINFO}) + STRING(COMPARE EQUAL "sse4_1" "${SSE_THERE}" SSE41_TRUE) + IF (SSE41_TRUE) + set(SSE4_1_FOUND true CACHE BOOL "SSE4.1 available on host") + ELSE (SSE41_TRUE) + set(SSE4_1_FOUND false CACHE BOOL "SSE4.1 available on host") + ENDIF (SSE41_TRUE) + + STRING(REGEX REPLACE "^.*(sse4_2).*$" "\\1" SSE_THERE ${CPUINFO}) + STRING(COMPARE EQUAL "sse4_2" "${SSE_THERE}" SSE42_TRUE) + IF (SSE42_TRUE) + set(SSE4_2_FOUND true CACHE BOOL "SSE4.2 available on host") + ELSE (SSE42_TRUE) + set(SSE4_2_FOUND false CACHE BOOL "SSE4.2 available on host") + ENDIF (SSE42_TRUE) ELSEIF(CMAKE_SYSTEM_NAME MATCHES "Darwin") - EXEC_PROGRAM("/usr/sbin/sysctl -n machdep.cpu.features" OUTPUT_VARIABLE - CPUINFO) - - STRING(REGEX REPLACE "^.*[^S](SSE2).*$" "\\1" SSE_THERE ${CPUINFO}) - STRING(COMPARE EQUAL "SSE2" "${SSE_THERE}" SSE2_TRUE) - IF (SSE2_TRUE) - set(SSE2_FOUND true CACHE BOOL "SSE2 available on host") - ELSE (SSE2_TRUE) - set(SSE2_FOUND false CACHE BOOL "SSE2 available on host") - ENDIF (SSE2_TRUE) - - STRING(REGEX REPLACE "^.*[^S](SSE3).*$" "\\1" SSE_THERE ${CPUINFO}) - STRING(COMPARE EQUAL "SSE3" "${SSE_THERE}" SSE3_TRUE) - IF (SSE3_TRUE) - set(SSE3_FOUND true CACHE BOOL "SSE3 available on host") - ELSE (SSE3_TRUE) - set(SSE3_FOUND false CACHE BOOL "SSE3 available on host") - ENDIF (SSE3_TRUE) - - STRING(REGEX REPLACE "^.*(SSSE3).*$" "\\1" SSE_THERE ${CPUINFO}) - STRING(COMPARE EQUAL "SSSE3" "${SSE_THERE}" SSSE3_TRUE) - IF (SSSE3_TRUE) - set(SSSE3_FOUND true CACHE BOOL "SSSE3 available on host") - ELSE (SSSE3_TRUE) - set(SSSE3_FOUND false CACHE BOOL "SSSE3 available on host") - ENDIF (SSSE3_TRUE) - - STRING(REGEX REPLACE "^.*(SSE4.1).*$" "\\1" SSE_THERE ${CPUINFO}) - STRING(COMPARE EQUAL "SSE4.1" "${SSE_THERE}" SSE41_TRUE) - IF (SSE41_TRUE) - set(SSE4_1_FOUND true CACHE BOOL "SSE4.1 available on host") - ELSE (SSE41_TRUE) - set(SSE4_1_FOUND false CACHE BOOL "SSE4.1 available on host") - ENDIF (SSE41_TRUE) - - STRING(REGEX REPLACE "^.*(SSE4.2).*$" "\\1" SSE_THERE ${CPUINFO}) - STRING(COMPARE EQUAL "SSE4.2" "${SSE_THERE}" SSE42_TRUE) - IF (SSE42_TRUE) - set(SSE4_2_FOUND true CACHE BOOL "SSE4.2 available on host") - ELSE (SSE42_TRUE) - set(SSE4_2_FOUND false CACHE BOOL "SSE4.2 available on host") - ENDIF (SSE42_TRUE) + EXEC_PROGRAM("/usr/sbin/sysctl -n machdep.cpu.features" + OUTPUT_VARIABLE CPUINFO) + + STRING(REGEX REPLACE "^.*[^S](SSE2).*$" "\\1" SSE_THERE ${CPUINFO}) + STRING(COMPARE EQUAL "SSE2" "${SSE_THERE}" SSE2_TRUE) + IF (SSE2_TRUE) + set(SSE2_FOUND true CACHE BOOL "SSE2 available on host") + ELSE (SSE2_TRUE) + set(SSE2_FOUND false CACHE BOOL "SSE2 available on host") + ENDIF (SSE2_TRUE) + + STRING(REGEX REPLACE "^.*[^S](SSE3).*$" "\\1" SSE_THERE ${CPUINFO}) + STRING(COMPARE EQUAL "SSE3" "${SSE_THERE}" SSE3_TRUE) + IF (SSE3_TRUE) + set(SSE3_FOUND true CACHE BOOL "SSE3 available on host") + ELSE (SSE3_TRUE) + set(SSE3_FOUND false CACHE BOOL "SSE3 available on host") + ENDIF (SSE3_TRUE) + + STRING(REGEX REPLACE "^.*(SSSE3).*$" "\\1" SSE_THERE ${CPUINFO}) + STRING(COMPARE EQUAL "SSSE3" "${SSE_THERE}" SSSE3_TRUE) + IF (SSSE3_TRUE) + set(SSSE3_FOUND true CACHE BOOL "SSSE3 available on host") + ELSE (SSSE3_TRUE) + set(SSSE3_FOUND false CACHE BOOL "SSSE3 available on host") + ENDIF (SSSE3_TRUE) + + STRING(REGEX REPLACE "^.*(SSE4.1).*$" "\\1" SSE_THERE ${CPUINFO}) + STRING(COMPARE EQUAL "SSE4.1" "${SSE_THERE}" SSE41_TRUE) + IF (SSE41_TRUE) + set(SSE4_1_FOUND true CACHE BOOL "SSE4.1 available on host") + ELSE (SSE41_TRUE) + set(SSE4_1_FOUND false CACHE BOOL "SSE4.1 available on host") + ENDIF (SSE41_TRUE) + + STRING(REGEX REPLACE "^.*(SSE4.2).*$" "\\1" SSE_THERE ${CPUINFO}) + STRING(COMPARE EQUAL "SSE4.2" "${SSE_THERE}" SSE42_TRUE) + IF (SSE42_TRUE) + set(SSE4_2_FOUND true CACHE BOOL "SSE4.2 available on host") + ELSE (SSE42_TRUE) + set(SSE4_2_FOUND false CACHE BOOL "SSE4.2 available on host") + ENDIF (SSE42_TRUE) ELSEIF(CMAKE_SYSTEM_NAME MATCHES "Windows") - # TODO - set(SSE2_FOUND true CACHE BOOL "SSE2 available on host") - set(SSE3_FOUND false CACHE BOOL "SSE3 available on host") - set(SSSE3_FOUND false CACHE BOOL "SSSE3 available on host") - set(SSE4_1_FOUND false CACHE BOOL "SSE4.1 available on host") - set(SSE4_2_FOUND false CACHE BOOL "SSE4.2 available on host") + # TODO + set(SSE2_FOUND true CACHE BOOL "SSE2 available on host") + set(SSE3_FOUND false CACHE BOOL "SSE3 available on host") + set(SSSE3_FOUND false CACHE BOOL "SSSE3 available on host") + set(SSE4_1_FOUND false CACHE BOOL "SSE4.1 available on host") + set(SSE4_2_FOUND false CACHE BOOL "SSE4.2 available on host") ELSE(CMAKE_SYSTEM_NAME MATCHES "Linux") - set(SSE2_FOUND true CACHE BOOL "SSE2 available on host") - set(SSE3_FOUND false CACHE BOOL "SSE3 available on host") - set(SSSE3_FOUND false CACHE BOOL "SSSE3 available on host") - set(SSE4_1_FOUND false CACHE BOOL "SSE4.1 available on host") - set(SSE4_2_FOUND false CACHE BOOL "SSE4.2 available on host") + set(SSE2_FOUND true CACHE BOOL "SSE2 available on host") + set(SSE3_FOUND false CACHE BOOL "SSE3 available on host") + set(SSSE3_FOUND false CACHE BOOL "SSSE3 available on host") + set(SSE4_1_FOUND false CACHE BOOL "SSE4.1 available on host") + set(SSE4_2_FOUND false CACHE BOOL "SSE4.2 available on host") ENDIF(CMAKE_SYSTEM_NAME MATCHES "Linux") ENDIF(ARCH MATCHES "i386" OR ARCH MATCHES "x86_64") if(NOT SSE2_FOUND) - MESSAGE(STATUS "Could not find hardware support for SSE2 on this machine.") + MESSAGE(STATUS "Could not find hardware support for SSE2 on this machine.") endif(NOT SSE2_FOUND) if(NOT SSE3_FOUND) - MESSAGE(STATUS "Could not find hardware support for SSE3 on this machine.") + MESSAGE(STATUS "Could not find hardware support for SSE3 on this machine.") endif(NOT SSE3_FOUND) if(NOT SSSE3_FOUND) - MESSAGE(STATUS "Could not find hardware support for SSSE3 on this machine.") + MESSAGE(STATUS "Could not find hardware support for SSSE3 on this machine.") endif(NOT SSSE3_FOUND) if(NOT SSE4_1_FOUND) - MESSAGE(STATUS "Could not find hardware support for SSE4.1 on this machine.") + MESSAGE(STATUS "Could not find hardware support for SSE4.1 on this machine.") endif(NOT SSE4_1_FOUND) if(NOT SSE4_2_FOUND) - MESSAGE(STATUS "Could not find hardware support for SSE4.2 on this machine.") + MESSAGE(STATUS "Could not find hardware support for SSE4.2 on this machine.") endif(NOT SSE4_2_FOUND) diff --git a/cmake/IgnCodeCheck.cmake b/cmake/IgnCodeCheck.cmake index 95ef267f..60d7fd68 100644 --- a/cmake/IgnCodeCheck.cmake +++ b/cmake/IgnCodeCheck.cmake @@ -2,57 +2,67 @@ function(ign_setup_target_for_codecheck) include(IgnPython) - find_program(CPPCHECK_PATH cppcheck) + find_program(cppcheck_path cppcheck) find_program(FIND_PATH find) - - if(NOT CPPCHECK_PATH) + + if(NOT cppcheck_path) message(STATUS "The program [cppcheck] was not found! Skipping codecheck setup") return() endif() - + if(NOT FIND_PATH) message(STATUS "The program [find] was not found! Skipping codecheck setup.") return() endif() # Base set of cppcheck option - set (CPPCHECK_BASE -q --inline-suppr -j 4 --language=c++ --std=c++14 --force) + set (cppcheck_base -q --inline-suppr -j 4 --language=c++ --std=c++14 --force) if (EXISTS "${PROJECT_BINARY_DIR}/cppcheck.suppress") - set (CPPCHECK_BASE ${CPPCHECK_BASE} --suppressions-list=${PROJECT_BINARY_DIR}/cppcheck.suppress) + set (cppcheck_base ${cppcheck_base} --suppressions-list=${PROJECT_BINARY_DIR}/cppcheck.suppress) endif() # Extra cppcheck option - set (CPPCHECK_EXTRA --enable=style,performance,portability,information) + set (cppcheck_extra --enable=style,performance,portability,information) # Rules for cppcheck - set (CPPCHECK_RULES "-UM_PI --rule-file=${IGNITION_CMAKE_CODECHECK_DIR}/header_guard.rule --rule-file=${IGNITION_CMAKE_CODECHECK_DIR}/namespace_AZ.rule") + set (cppcheck_rules "\ + -UM_PI \ + --rule-file=${IGNITION_CMAKE_CODECHECK_DIR}/header_guard.rule \ + --rule-file=${IGNITION_CMAKE_CODECHECK_DIR}/namespace_AZ.rule") # The find command - set (CPPCHECK_FIND ${FIND_PATH} ${CPPCHECK_DIRS} -name '*.cc' -o -name '*.hh' -o -name '*.c' -o -name '*.h') + set (cppcheck_find + ${FIND_PATH} ${CPPCHECK_DIRS} -name '*.cc' -o -name '*.hh' -o -name '*.c' -o -name '*.h') message(STATUS "Adding codecheck target") # Each include directory needs an -I flag - set(CPPCHECK_INCLUDE_DIRS_FLAGS) - foreach(dir ${CPPCHECK_INCLUDE_DIRS}) - list(APPEND CPPCHECK_INCLUDE_DIRS_FLAGS "-I${dir}") + set(cppcheck_include_dirs_FLAGS) + foreach(dir ${cppcheck_include_dirs}) + list(APPEND cppcheck_include_dirs_FLAGS "-I${dir}") endforeach() add_custom_target(cppcheck + COMMENT "cppcheck target" # First cppcheck - COMMAND ${CPPCHECK_PATH} ${CPPCHECK_BASE} ${CPPCHECK_EXTRA} ${CPPCHECK_INCLUDE_DIRS_FLAGS} ${CPPCHECK_RULES} `${CPPCHECK_FIND}` - + COMMAND ${cppcheck_path} ${cppcheck_base} ${cppcheck_extra} + ${cppcheck_include_dirs_FLAGS} + ${cppcheck_rules} `${cppcheck_find}` # Second cppcheck - COMMAND ${CPPCHECK_PATH} ${CPPCHECK_BASE} --enable=missingInclude `${CPPCHECK_FIND}` + COMMAND ${cppcheck_path} ${cppcheck_base} --enable=missingInclude + `${cppcheck_find}` ) add_custom_target(codecheck + COMMENT "codecheck execution" DEPENDS cppcheck ) if(Python3_Interpreter_FOUND) add_custom_target(cpplint - COMMAND ${Python3_EXECUTABLE} ${IGNITION_CMAKE_CODECHECK_DIR}/cpplint.py --extensions=cc,hh --quiet `${CPPCHECK_FIND}` + COMMENT "cpplint execution" + COMMAND ${Python3_EXECUTABLE} ${IGNITION_CMAKE_CODECHECK_DIR}/cpplint.py + --extensions=cc,hh --quiet `${cppcheck_find}` ) add_dependencies(codecheck cpplint) diff --git a/tools/cmakelang-config.py b/tools/cmakelang-config.py new file mode 100644 index 00000000..dcf0c8ab --- /dev/null +++ b/tools/cmakelang-config.py @@ -0,0 +1,30 @@ +# ----------------------------- +# Options affecting formatting. +# ----------------------------- +with section("format"): + line_width = 120 + +# ---------------------------- +# Options affecting the linter +# ---------------------------- +with section("lint"): + # regular expression pattern describing valid function names + # ign-cmake customization: accept mix of uppercase/lowercase + function_pattern = '[0-9a-zA-Z_]+' + + # regular expression pattern describing valid names for privatedirectory + # variables + # ign-cmake customization: accept private variables that don't start with _ + # accept mix of uppercase/lowercase + # TODO(jrivero): change all private variable to start with _ in new major + # version ign-cmake3 + private_var_pattern = '_?[0-9A-Za-z_]+' + + # regular expression pattern describing valid names for variables with global + # (cache) scope + # ign-cmake customization: accept mix of uppercase/lowercase + global_var_pattern = '[A-Z][0-9A-Za-z_]+' + + # regular expression pattern describing valid macro names + # ign-cmake customization: accept lower case chars + macro_pattern = '[0-9A-Za-z_]+'