Skip to content

Cmake improvements and Coverage for C API #242

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 9 commits into from
Jan 20, 2021
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
163 changes: 90 additions & 73 deletions dpctl-capi/CMakeLists.txt
Original file line number Diff line number Diff line change
@@ -1,45 +1,39 @@
cmake_minimum_required(VERSION 3.10 FATAL_ERROR)
project("dpCtl - A lightweight SYCL wrapper for Python")
project("dpCtl C API - A C wrapper for a subset of SYCL")

# The function checks is DPCPP_ROOT is valid and points to a dpcpp installation
function (check_for_dpcpp)
string(COMPARE EQUAL "${DPCPP_ROOT}" "" no_dpcpp_root)
if(${no_dpcpp_root})
message(FATAL_ERROR "Set the DPCPP_ROOT argument providing the path to \
a dpcpp installation.")
endif()

if(WIN32)
set (dpcpp_cmd "${DPCPP_ROOT}/bin/dpcpp")
set (dpcpp_arg "--version")
elseif(UNIX)
set (dpcpp_cmd "${DPCPP_ROOT}/bin/dpcpp")
set (dpcpp_arg "--version")
else()
message(FATAL_ERROR "Unsupported system.")
endif()
# Option to turn on support for creating Level Zero interoperability programs
# from a SPIR-V binary file.
option(DPCTL_ENABLE_LO_PROGRAM_CREATION
"Enable Level Zero Program creation from SPIR-V"
OFF
)
# Option to generate code coverage report using llvm-cov and lcov.
option(DPCTL_GENERATE_COVERAGE
"Build dpctl C API with coverage instrumentation instrumentation"
OFF
)
# Option to output html coverage report at a specific location.
option(DPCTL_COVERAGE_REPORT_OUTPUT_DIR
"Save the generated lcov html report to the specified location"
OFF
)
# Option to build the Gtests for dpctl C API
option(DPCTL_BUILD_CAPI_TESTS
"Build dpctl C API google tests"
OFF
)

# Check if dpcpp is available
execute_process(
COMMAND ${dpcpp_cmd} ${dpcpp_arg}
WORKING_DIRECTORY ${PROJECT_SOURCE_DIR}
RESULT_VARIABLE dpcpp_result
OUTPUT_VARIABLE dpcpp_ver
)
# Load our CMake modules to search for DPCPP and Level Zero
set(CMAKE_MODULE_PATH ${CMAKE_MODULE_PATH} "${CMAKE_SOURCE_DIR}/cmake/modules/")
find_package(DPCPP REQUIRED)

if(${dpcpp_result} MATCHES "0")
string(REPLACE "\n" ";" DPCPP_VERSION_LIST "${dpcpp_ver}")
list(GET DPCPP_VERSION_LIST 0 dpcpp_ver_line)
foreach(X ${DPCPP_VERSION_LIST})
message(STATUS "dpcpp ver[${dpcpp_result}]: ${X}")
endforeach()
else()
message(FATAL_ERROR "DPCPP needed to build dpctl_sycl_interface")
endif()
endfunction()
if(DPCTL_ENABLE_LO_PROGRAM_CREATION)
set(DPCTL_ENABLE_LO_PROGRAM_CREATION 1)
find_package(LevelZero REQUIRED)
endif()

# Check for dpcpp in the specified DPCPP_ROOT
check_for_dpcpp()
configure_file(${CMAKE_SOURCE_DIR}/include/Config/dpctl_config.h.in
${CMAKE_SOURCE_DIR}/include/Config/dpctl_config.h)

if(WIN32)
set(CMAKE_CXX_COMPILER:PATH "${DPCPP_ROOT}/bin/dpcpp")
Expand All @@ -54,6 +48,9 @@ if(WIN32)
set(CMAKE_C_FLAGS_DEBUG "${CMAKE_C_FLAGS_DEBUG} ${WARNING_FLAGS} -ggdb3 -DDEBUG")
set(CMAKE_CXX_FLAGS_DEBUG "${CMAKE_CXX_FLAGS_DEBUG} ${WARNING_FLAGS} -ggdb3 -DDEBUG -Qstd=c++17")
elseif(UNIX)
set(CMAKE_CXX_COMPILER:PATH "${DPCPP_ROOT}/bin/dpcpp")
set(CMAKE_C_COMPILER:PATH "${DPCPP_ROOT}/bin/clang")
set(CMAKE_LINKER:PATH "${DPCPP_ROOT}/bin/lld")
set(SDL_FLAGS "-fstack-protector -fstack-protector-all -fpic -fPIC -D_FORTIFY_SOURCE=2 -Wformat -Wformat-security -fno-strict-overflow -fno-delete-null-pointer-checks")
set(WARNING_FLAGS "-Wall -Wextra -Winit-self -Wunused-function -Wuninitialized -Wmissing-declarations -fdiagnostics-color=auto")
set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} ${WARNING_FLAGS} ${SDL_FLAGS}")
Expand All @@ -80,30 +77,32 @@ add_library(
helper/source/dpctl_utils_helper.cpp
)

# Install DPCTLSyclInterface
target_include_directories(
DPCTLSyclInterface
PRIVATE
${CMAKE_SOURCE_DIR}/include/
${CMAKE_SOURCE_DIR}/helper/include/
target_include_directories(DPCTLSyclInterface
PRIVATE
${CMAKE_SOURCE_DIR}/include/
${CMAKE_SOURCE_DIR}/helper/include/
${DPCPP_SYCL_INCLUDE_DIR}
)
target_link_libraries(DPCTLSyclInterface
PRIVATE ${DPCPP_SYCL_LIBRARY}
PRIVATE ${DPCPP_OPENCL_LIBRARY}
)

if(WIN32)
message(
STATUS
"SYCL_INCLUDE_DIR: "
${DPCPP_ROOT}/include/sycl
)
target_include_directories(
DPCTLSyclInterface
PUBLIC
${DPCPP_ROOT}/include/sycl
)
target_link_libraries(
DPCTLSyclInterface
PRIVATE ${DPCPP_ROOT}/lib/sycl.lib
PRIVATE ${DPCPP_ROOT}/lib/OpenCL.lib
)
if(DPCTL_ENABLE_LO_PROGRAM_CREATION)
if(UNIX)
target_include_directories(DPCTLSyclInterface
PRIVATE
${LEVEL_ZERO_INCLUDE_DIR}
)
target_link_libraries(DPCTLSyclInterface
PRIVATE ${LEVEL_ZERO_LIBRARY}
)
else()
message(WARNING
"DPCTL support Level Zero program creation not supported "
"on this system."
)
endif()
endif()

install(
Expand All @@ -114,34 +113,52 @@ install(
)

# Install all headers
file(GLOB HEADERS "${CMAKE_SOURCE_DIR}/include/*.h*")
file(GLOB HEADERS "${CMAKE_SOURCE_DIR}/include/*.h")
foreach(HEADER ${HEADERS})
install(FILES "${HEADER}" DESTINATION include)
endforeach()

# Install all headers in include/Support
file(GLOB HEADERS "${CMAKE_SOURCE_DIR}/include/Support/*.h*")
file(GLOB HEADERS "${CMAKE_SOURCE_DIR}/include/Support/*.h")
foreach(HEADER ${HEADERS})
install(FILES "${HEADER}" DESTINATION include/Support)
endforeach()

# Install all headers in helper/include
file(GLOB HEADERS "${CMAKE_SOURCE_DIR}/helper/include/*.h*")
file(GLOB HEADERS "${CMAKE_SOURCE_DIR}/helper/include/*.h")
foreach(HEADER ${HEADERS})
install(FILES "${HEADER}" DESTINATION helper/include)
endforeach()

option(
BUILD_CAPI_TESTS
"Build dpctl C API google tests"
OFF
)
# Install all headers in include/Config
file(GLOB HEADERS "${CMAKE_SOURCE_DIR}/include/Config/*.h")
foreach(HEADER ${HEADERS})
install(FILES "${HEADER}" DESTINATION include/Config)
endforeach()

# Enable to build the dpCtl backend test cases
if(BUILD_CAPI_TESTS)
add_subdirectory(tests)
# Enable code coverage related settings
if(DPCTL_GENERATE_COVERAGE)
# check if llvm-cov and lcov are available
find_package(Lcov REQUIRED)
# These flags are set inside FindDPCPP
if(NOT (${LLVM_COV_FOUND} AND ${LLVM_PROFDATA_FOUND}))
message(FATAL_ERROR
"llvm-cov and llvm-profdata are needed to generate coverage."
)
endif()
# Turn on DPCTL_BUILD_CAPI_TESTS as building tests is needed to generate
# coverage reports
set(DPCTL_BUILD_CAPI_TESTS "ON")
if(DPCTL_COVERAGE_REPORT_OUTPUT_DIR)
set(COVERAGE_OUTPUT_DIR ${DPCTL_COVERAGE_REPORT_OUTPUT_DIR})
message(STATUS "Coverage reports to be saved at ${COVERAGE_OUTPUT_DIR}")
else()
set(COVERAGE_OUTPUT_DIR ${CMAKE_CURRENT_BINARY_DIR})
message(STATUS "Coverage reports to be saved at ${COVERAGE_OUTPUT_DIR}")
endif()
endif()


# Todo : Add build rules for doxygen
# maybe refer https://devblogs.microsoft.com/cppblog/clear-functional-c-documentation-with-sphinx-breathe-doxygen-cmake/
# Add sub-directory to build the dpCtl C API test cases
if(DPCTL_BUILD_CAPI_TESTS)
add_subdirectory(tests)
endif()
115 changes: 115 additions & 0 deletions dpctl-capi/cmake/modules/FindDPCPP.cmake
Original file line number Diff line number Diff line change
@@ -0,0 +1,115 @@
# Data Parallel Control Library (dpCtl)
#
# Copyright 2020 Intel Corporation
#
# Licensed under the Apache License, Version 2.0 (the "License");
# you may not use this file except in compliance with the License.
# You may obtain a copy of the License at
#
# http://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS,
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
# See the License for the specific language governing permissions and
# limitations under the License.
#
# CMake find_package() module for the DPCPP compiler and development
# environment.
#
# Example usage:
#
# find_package(DPCPP)
#
# If successful, the following variables will be defined:
# DPCPP_FOUND
# DPCPP_VERSION
# DPCPP_INCLUDE_DIR
# DPCPP_SYCL_INCLUDE_DIR
# DPCPP_LIBRARY_DIR
# DPCPP_SYCL_LIBRARY
# DPCPP_OPENCL_LIBRARY

include( FindPackageHandleStandardArgs )

string(COMPARE EQUAL "${DPCPP_INSTALL_DIR}" "" no_dpcpp_root)
if(${no_dpcpp_root})
message(STATUS "Set the DPCPP_ROOT argument providing the path to \
a dpcpp installation.")
return()
endif()

if(WIN32 OR UNIX)
set(dpcpp_cmd "${DPCPP_INSTALL_DIR}/bin/dpcpp")
set(dpcpp_arg "--version")
else()
message(FATAL_ERROR "Unsupported system.")
endif()

# Check if dpcpp is available
execute_process(
COMMAND ${dpcpp_cmd} ${dpcpp_arg}
WORKING_DIRECTORY ${PROJECT_SOURCE_DIR}
RESULT_VARIABLE dpcpp_result
OUTPUT_VARIABLE dpcpp_ver
)

# If dpcpp is found then set then set the package variables
if(${dpcpp_result} MATCHES "0")
string(REPLACE "\n" ";" DPCPP_VERSION_LIST "${dpcpp_ver}")
list(GET DPCPP_VERSION_LIST 0 dpcpp_ver_line)
foreach(X ${DPCPP_VERSION_LIST})
message(STATUS "dpcpp ver[${dpcpp_result}]: ${X}")
endforeach()

# check if llvm-cov and llvm-profdata are packaged as part of dpcpp
find_program(LLVM_COV_EXE
llvm-cov
PATHS ${DPCPP_INSTALL_DIR}/bin
NO_DEFAULT_PATH
)

if(LLVM_COV_EXE)
set(LLVM_COV_FOUND TRUE)
else()
set(LLVM_COV_FOUND FALSE)
endif()

find_program(LLVM_PROFDATA_EXE
llvm-profdata
PATHS ${DPCPP_INSTALL_DIR}/bin
NO_DEFAULT_PATH
)

if(LLVM_PROFDATA_EXE)
set(LLVM_PROFDATA_FOUND TRUE)
else()
set(LLVM_PROFDATA_FOUND FALSE)
endif()

# set package-level variables
set(DPCPP_ROOT ${DPCPP_INSTALL_DIR})
list(POP_FRONT DPCPP_VERSION_LIST DPCPP_VERSION)
set(DPCPP_INCLUDE_DIR ${DPCPP_INSTALL_DIR}/include)
set(DPCPP_SYCL_INCLUDE_DIR ${DPCPP_INSTALL_DIR}/include/sycl)
set(DPCPP_LIBRARY_DIR ${DPCPP_INSTALL_DIR}/lib)
if(WIN32)
set(DPCPP_SYCL_LIBRARY ${DPCPP_INSTALL_DIR}/lib/sycl.lib)
set(DPCPP_OPENCL_LIBRARY ${DPCPP_INSTALL_DIR}/lib/OpenCL.lib)
elseif(UNIX)
set(DPCPP_SYCL_LIBRARY ${DPCPP_INSTALL_DIR}/lib/libsycl.so)
set(DPCPP_OPENCL_LIBRARY ${DPCPP_INSTALL_DIR}/lib/libOpenCL.so)
endif()
else()
message(STATUS "DPCPP needed to build dpctl_sycl_interface")
return()
endif()

find_package_handle_standard_args(DPCPP DEFAULT_MSG
DPCPP_VERSION
DPCPP_INCLUDE_DIR
DPCPP_SYCL_INCLUDE_DIR
DPCPP_LIBRARY_DIR
DPCPP_SYCL_LIBRARY
DPCPP_OPENCL_LIBRARY
)
33 changes: 33 additions & 0 deletions dpctl-capi/cmake/modules/FindLcov.cmake
Original file line number Diff line number Diff line change
@@ -0,0 +1,33 @@
# Data Parallel Control Library (dpCtl)
#
# Copyright 2020 Intel Corporation
#
# Licensed under the Apache License, Version 2.0 (the "License");
# you may not use this file except in compliance with the License.
# You may obtain a copy of the License at
#
# http://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS,
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
# See the License for the specific language governing permissions and
# limitations under the License.
#
# CMake find_package() module for lcov.
#
# Example usage:
#
# find_package(Lcov)
#
# If successful, the following variables will be defined:
# LCOV_EXE- The path to lcov executable
# LCOV_FOUND

find_program(LCOV_EXE lcov)
find_program(GENHTML_EXE genhtml)

find_package_handle_standard_args(Lcov DEFAULT_MSG
LCOV_EXE
GENHTML_EXE
)
34 changes: 34 additions & 0 deletions dpctl-capi/cmake/modules/FindLevelZero.cmake
Original file line number Diff line number Diff line change
@@ -0,0 +1,34 @@
# Data Parallel Control Library (dpCtl)
#
# Copyright 2020 Intel Corporation
#
# Licensed under the Apache License, Version 2.0 (the "License");
# you may not use this file except in compliance with the License.
# You may obtain a copy of the License at
#
# http://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS,
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
# See the License for the specific language governing permissions and
# limitations under the License.
#
# CMake find_package() module for the Level Zero loader library and headers.
#
# Example usage:
#
# find_package(LevelZero)
#
# If successful, the following variables will be defined:
# LEVEL_ZERO_INCLUDE_DIR
# LEVEL_ZERO_LIBRARY - the full path to the ze_loader library
# TODO: Add a way to record the version of the level_zero library

find_library(LEVEL_ZERO_LIBRARY ze_loader)
find_path(LEVEL_ZERO_INCLUDE_DIR NAMES level_zero/zet_api.h)

find_package_handle_standard_args(LevelZero DEFAULT_MSG
LEVEL_ZERO_INCLUDE_DIR
LEVEL_ZERO_LIBRARY
)
Loading