cmake_minimum_required(VERSION 3.13)
project(setprotocol C)

set(CMAKE_C_STANDARD 99)
set(CMAKE_C_STANDARD_REQUIRED ON)

# SET protocol v2: управление, телеметрия, CAN segmentation и firmware flow.
set(SETPROTOCOL_V2_SOURCES
    src/set_protocol.c
    src/set_can.c
    src/set_firmware.c
    src/set_telemetry.c
    src/set_plot.c
    src/set_trends.c
    src/set_spectrum.c
)

# Совместимые ProtoCAN/SETGUI v1 форматы переходного периода.
set(SETPROTOCOL_LEGACY_SOURCES
    src/balsam_can.c
    src/periph28335.c
    src/gui_catalog.c
    src/gui_frame.c
    src/pcan_abi.c
    src/pcan_crc.c
    src/pcan_frame.c
    src/pcan_gas.c
    src/pcan_id.c
    src/pcan_link.c
    src/pcan_ring.c
)

set(SETPROTOCOL_SOURCES
    ${SETPROTOCOL_V2_SOURCES}
    ${SETPROTOCOL_LEGACY_SOURCES}
)

add_library(setprotocol_static STATIC ${SETPROTOCOL_SOURCES})
target_include_directories(setprotocol_static PUBLIC include)
if(NOT MSVC)
    target_link_libraries(setprotocol_static PUBLIC m)
endif()

# Совместимое имя цели для проектов, уже использовавших SET protocol v2.
add_library(set_protocol ALIAS setprotocol_static)

option(SETP_BUILD_SHARED "Build stable host ABI shared library" ON)
if(SETP_BUILD_SHARED)
    add_library(setprotocol SHARED ${SETPROTOCOL_SOURCES})
    target_include_directories(setprotocol PUBLIC include)
    if(NOT MSVC)
        target_link_libraries(setprotocol PRIVATE m)
    endif()
    target_compile_definitions(setprotocol PRIVATE PCAN_ABI_BUILD_DLL)
    set_target_properties(setprotocol PROPERTIES
        C_VISIBILITY_PRESET hidden
        VISIBILITY_INLINES_HIDDEN YES
        OUTPUT_NAME setprotocol
    )
endif()

function(setprotocol_warnings target)
    if(MSVC)
        target_compile_options(${target} PRIVATE /W4)
    else()
        target_compile_options(${target} PRIVATE -Wall -Wextra -Wpedantic)
    endif()
endfunction()

setprotocol_warnings(setprotocol_static)
if(TARGET setprotocol)
    setprotocol_warnings(setprotocol)
endif()

# JNI/CMSIS-порты подключаются целевым проектом и в host CMake не входят.
option(SETP_BUILD_TESTS "Build host tests" ON)
if(SETP_BUILD_TESTS)
    enable_testing()

    add_executable(test_plot tests/test_plot.c)
    target_link_libraries(test_plot PRIVATE setprotocol_static)
    add_test(NAME shared_plot COMMAND test_plot)

    add_executable(test_set_protocol tests/test_set_protocol.c)
    target_link_libraries(test_set_protocol PRIVATE setprotocol_static)
    add_test(NAME set_protocol_v2 COMMAND test_set_protocol)

    add_executable(test_transport tests/test_transport.c)
    target_link_libraries(test_transport PRIVATE setprotocol_static)
    add_test(NAME legacy_transport COMMAND test_transport)

    add_executable(test_gui tests/test_gui.c)
    target_link_libraries(test_gui PRIVATE setprotocol_static)
    add_test(NAME legacy_gui COMMAND test_gui)

    add_executable(test_abi tests/test_abi.c)
    target_link_libraries(test_abi PRIVATE setprotocol_static)
    add_test(NAME stable_abi COMMAND test_abi)
    add_executable(test_balsam_can tests/test_balsam_can.c)
    target_link_libraries(test_balsam_can PRIVATE setprotocol_static)
    add_test(NAME legacy_balsam_can COMMAND test_balsam_can)
    add_executable(test_periph28335 tests/test_periph28335.c)
    target_link_libraries(test_periph28335 PRIVATE setprotocol_static)
    add_test(NAME shared_periph28335 COMMAND test_periph28335)
    add_executable(test_trends tests/test_trends.c)
    target_link_libraries(test_trends PRIVATE setprotocol_static)
    add_test(NAME shared_trends COMMAND test_trends)
    add_executable(test_spectrum tests/test_spectrum.c)
    target_link_libraries(test_spectrum PRIVATE setprotocol_static)
    add_test(NAME shared_spectrum COMMAND test_spectrum)
endif()
