-
Notifications
You must be signed in to change notification settings - Fork 1
/
Copy pathCMakeLists.txt
357 lines (318 loc) · 11.7 KB
/
CMakeLists.txt
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
cmake_minimum_required(VERSION 3.10)
project(SupaMCPServer VERSION 1.0.0 LANGUAGES C)
# Set C standard
set(CMAKE_C_STANDARD 99)
set(CMAKE_C_STANDARD_REQUIRED ON)
# Add compiler flags
if(MSVC)
# MSVC flags
add_compile_options(/W4)
# Enable multi-threaded compilation
add_compile_options(/MP)
# Enable function-level linking
add_compile_options(/Gy)
# Enable intrinsic functions
add_compile_options(/Oi)
# Specify runtime library
set(CMAKE_MSVC_RUNTIME_LIBRARY "MultiThreaded$<$<CONFIG:Debug>:Debug>")
else()
# GCC/Clang flags
add_compile_options(-Wall -Wextra -pedantic)
endif()
# Check for pthreads on non-Windows platforms
if(NOT WIN32)
find_package(Threads REQUIRED)
endif()
# Use manually installed libwebsockets
message(STATUS "Using libwebsockets")
# Set paths to libwebsockets
if(APPLE)
# On macOS, try to use Homebrew installed libwebsockets
execute_process(
COMMAND brew --prefix libwebsockets
OUTPUT_VARIABLE BREW_LIBWEBSOCKETS_PREFIX
OUTPUT_STRIP_TRAILING_WHITESPACE
)
if(BREW_LIBWEBSOCKETS_PREFIX)
message(STATUS "Using Homebrew libwebsockets at ${BREW_LIBWEBSOCKETS_PREFIX}")
set(LIBWEBSOCKETS_INCLUDE_DIR "${BREW_LIBWEBSOCKETS_PREFIX}/include")
set(LIBWEBSOCKETS_LIBRARY "${BREW_LIBWEBSOCKETS_PREFIX}/lib/libwebsockets.dylib")
else()
# Fallback to manually installed
set(LIBWEBSOCKETS_INCLUDE_DIR ${CMAKE_CURRENT_SOURCE_DIR}/include)
set(LIBWEBSOCKETS_LIBRARY_DIR ${CMAKE_CURRENT_SOURCE_DIR}/libs/libwebsockets)
set(LIBWEBSOCKETS_LIBRARY ${LIBWEBSOCKETS_LIBRARY_DIR}/libwebsockets.a)
endif()
else()
# Original path for other platforms
set(LIBWEBSOCKETS_INCLUDE_DIR ${CMAKE_CURRENT_SOURCE_DIR}/include)
set(LIBWEBSOCKETS_LIBRARY_DIR ${CMAKE_CURRENT_SOURCE_DIR}/libs/libwebsockets)
# Check if the library files exist
if(WIN32)
set(LIBWEBSOCKETS_LIBRARY ${LIBWEBSOCKETS_LIBRARY_DIR}/websockets.lib)
else()
set(LIBWEBSOCKETS_LIBRARY ${LIBWEBSOCKETS_LIBRARY_DIR}/libwebsockets.a)
endif()
endif()
# Check if the library files exist
if(NOT EXISTS ${LIBWEBSOCKETS_LIBRARY})
message(FATAL_ERROR "Could not find libwebsockets library at ${LIBWEBSOCKETS_LIBRARY}")
endif()
# Create an imported target for libwebsockets
if(APPLE AND BREW_LIBWEBSOCKETS_PREFIX)
add_library(websockets SHARED IMPORTED)
else()
add_library(websockets STATIC IMPORTED)
endif()
set_target_properties(websockets PROPERTIES
IMPORTED_LOCATION ${LIBWEBSOCKETS_LIBRARY}
INTERFACE_INCLUDE_DIRECTORIES "${LIBWEBSOCKETS_INCLUDE_DIR};${CMAKE_CURRENT_SOURCE_DIR}/include"
)
# Add include directory to system include paths for OpenSSL headers
include_directories(SYSTEM ${CMAKE_CURRENT_SOURCE_DIR}/include)
# Set up OpenSSL
if(WIN32)
set(OPENSSL_ROOT_DIR ${CMAKE_CURRENT_SOURCE_DIR}/libs/OpenSSL)
set(OPENSSL_INCLUDE_DIR ${CMAKE_CURRENT_SOURCE_DIR}/include/openssl)
set(OPENSSL_LIBRARIES
${OPENSSL_ROOT_DIR}/libssl.lib
${OPENSSL_ROOT_DIR}/libcrypto.lib
)
# Create imported targets for OpenSSL
add_library(ssl STATIC IMPORTED)
set_target_properties(ssl PROPERTIES
IMPORTED_LOCATION ${OPENSSL_ROOT_DIR}/libssl.lib
INTERFACE_INCLUDE_DIRECTORIES ${OPENSSL_INCLUDE_DIR}
)
add_library(crypto STATIC IMPORTED)
set_target_properties(crypto PROPERTIES
IMPORTED_LOCATION ${OPENSSL_ROOT_DIR}/libcrypto.lib
INTERFACE_INCLUDE_DIRECTORIES ${OPENSSL_INCLUDE_DIR}
)
else()
find_package(OpenSSL REQUIRED)
endif()
# Check if we need to link against additional dependencies
if(WIN32)
# On Windows, libwebsockets might need ws2_32 and other libraries
set_property(TARGET websockets PROPERTY
INTERFACE_LINK_LIBRARIES ws2_32 crypt32 secur32)
endif()
# Common library source files
set(COMMON_SOURCES
src/json/mcp_json.c
src/json/mcp_json_parser.c
src/json/mcp_json_stringifier.c
src/json/mcp_json_utils.c
src/json/mcp_json_message.c
src/json/mcp_json_rpc.c
src/json/mcp_json_format.c
src/json/mcp_json_parse_direct.c
src/json/mcp_json_schema_cache.c
src/json/mcp_json_schema_validate.c
src/transport/mcp_transport.c
src/transport/mcp_transport_factory.c
src/transport/mcp_stdio_transport.c
src/transport/mcp_tcp_transport.c
src/transport/mcp_tcp_client_handler.c
src/transport/mcp_tcp_acceptor.c
src/transport/mcp_tcp_client_transport.c
src/transport/mcp_tcp_client_receiver.c
src/transport/mcp_tcp_client_reconnect.c
src/transport/mcp_tcp_pool_transport.c
src/transport/mcp_websocket_transport.c
src/common/mcp_types.c
src/common/mcp_arena.c
src/common/mcp_log.c
src/common/mcp_thread_local.c
src/common/mcp_string_utils.c
src/common/mcp_sync.c
src/common/mcp_socket_utils.c
src/common/mcp_framing.c
src/common/mcp_thread_pool.c
src/common/mcp_object_pool.c
src/common/mcp_memory_pool.c
src/common/mcp_thread_cache.c
src/common/mcp_memory_tracker.c
src/common/mcp_template.c
src/common/mcp_template_optimized.c
src/common/mcp_rwlock.c
src/common/mcp_list.c
src/server/mcp_buffer_pool.c
src/server/mcp_cache_lru.c
src/server/mcp_rate_limiter.c
src/server/mcp_profiler.c
src/common/mcp_hashtable.c
src/common/mcp_performance_metrics.c
src/server/mcp_performance_collector.c
src/common/mcp_object_cache.c
src/server/mcp_advanced_rate_limiter.c
client/src/mcp_client_template.c
client/src/mcp_client_core.c
client/src/mcp_client_hash_table.c
client/src/mcp_client_request.c
client/src/mcp_client_api.c
client/src/mcp_client_batch.c
src/server/mcp_server.c
src/server/mcp_server_dispatch.c
src/server/mcp_server_handlers.c
src/server/mcp_server_task.c
src/server/mcp_server_response.c
src/server/mcp_server_ping.c
src/server/mcp_server_template_router.c
src/server/mcp_template_security.c
src/server/mcp_server_template_security.c
src/server/mcp_auth.c
src/server/mcp_performance_metrics_handlers.c
src/connection_pool/mcp_connection_pool.c
src/connection_pool/mcp_connection_pool_socket.c
src/connection_pool/mcp_connection_pool_sync.c
src/connection_pool/mcp_connection_pool_utils.c
src/connection_pool/mcp_connection_pool_maintenance.c
src/connection_pool/mcp_connection_pool_health.c
src/server/mcp_plugin.c
src/gateway/gateway_config.c
src/gateway/gateway_routing.c
src/gateway/gateway_pool.c
src/gateway/gateway_config_manager.c
src/gateway/gateway_socket_utils.c
)
# Create common library
add_library(mcp_common SHARED ${COMMON_SOURCES})
target_include_directories(mcp_common PUBLIC
${CMAKE_CURRENT_SOURCE_DIR}/include # Public API headers
${CMAKE_CURRENT_SOURCE_DIR}/client/include # Make client headers public too
)
target_link_libraries(mcp_common PUBLIC websockets ssl crypto)
# Windows-specific settings for mcp_common
if(MSVC)
# Generate import library
set_target_properties(mcp_common PROPERTIES
WINDOWS_EXPORT_ALL_SYMBOLS ON
RUNTIME_OUTPUT_DIRECTORY ${CMAKE_BINARY_DIR}
LIBRARY_OUTPUT_DIRECTORY ${CMAKE_BINARY_DIR}
ARCHIVE_OUTPUT_DIRECTORY ${CMAKE_BINARY_DIR}
)
endif()
# Make module source directories as private include paths so internal headers can be found
target_include_directories(mcp_common PRIVATE
${CMAKE_CURRENT_SOURCE_DIR}/src/common
${CMAKE_CURRENT_SOURCE_DIR}/src/common/internal
${CMAKE_CURRENT_SOURCE_DIR}/src/json
${CMAKE_CURRENT_SOURCE_DIR}/src/json/internal
${CMAKE_CURRENT_SOURCE_DIR}/src/transport
${CMAKE_CURRENT_SOURCE_DIR}/src/transport/internal
${CMAKE_CURRENT_SOURCE_DIR}/src/server
${CMAKE_CURRENT_SOURCE_DIR}/src/server/internal
${CMAKE_CURRENT_SOURCE_DIR}/src/connection_pool
${CMAKE_CURRENT_SOURCE_DIR}/src/connection_pool/internal
${CMAKE_CURRENT_SOURCE_DIR}/src/gateway
)
# KMCP library sources
set(KMCP_SOURCES
src/kmcp/kmcp_server_manager.c
src/kmcp/kmcp_client.c
src/kmcp/kmcp_tool_access.c
src/kmcp/kmcp_config_parser.c
src/kmcp/kmcp_http_client.c
src/kmcp/kmcp_error.c
src/kmcp/kmcp_version.c
src/kmcp/kmcp_profile_manager.c
src/kmcp/kmcp_registry.c
src/kmcp/kmcp_tool_sdk.c
src/kmcp/kmcp_cli.c
src/kmcp/kmcp_event.c
)
# Add platform-specific process implementation
if(WIN32)
list(APPEND KMCP_SOURCES src/kmcp/kmcp_process_win.c)
else()
list(APPEND KMCP_SOURCES src/kmcp/kmcp_process_posix.c)
endif()
# Create KMCP library
add_library(kmcp SHARED ${KMCP_SOURCES})
target_link_libraries(kmcp PRIVATE mcp_common)
target_include_directories(kmcp PUBLIC
${CMAKE_CURRENT_SOURCE_DIR}/include
${CMAKE_CURRENT_SOURCE_DIR}/include/kmcp
)
# Windows-specific settings for kmcp
if(MSVC)
# Generate import library
set_target_properties(kmcp PROPERTIES
WINDOWS_EXPORT_ALL_SYMBOLS ON
RUNTIME_OUTPUT_DIRECTORY ${CMAKE_BINARY_DIR}
LIBRARY_OUTPUT_DIRECTORY ${CMAKE_BINARY_DIR}
ARCHIVE_OUTPUT_DIRECTORY ${CMAKE_BINARY_DIR}
)
target_compile_definitions(kmcp PRIVATE -DKMCP_EXPORTS)
target_compile_definitions(kmcp PUBLIC -DKMCP_DLL)
endif()
# Server-specific source files
set(SERVER_SOURCES
src/main.c
)
# Client-specific source files
set(CLIENT_SOURCES
client/src/main.c
)
# Create server executable
add_executable(mcp_server ${SERVER_SOURCES})
target_link_libraries(mcp_server PRIVATE mcp_common kmcp)
# Create client executable
add_executable(mcp_client ${CLIENT_SOURCES})
target_link_libraries(mcp_client PRIVATE mcp_common)
# Link platform-specific libraries
if(WIN32)
target_link_libraries(mcp_common INTERFACE ws2_32) # Use INTERFACE so consumers link it too
else()
# Link pthreads and dl (for dynamic loading) on non-Windows
target_link_libraries(mcp_common INTERFACE Threads::Threads dl) # Use modern Threads target and INTERFACE
endif()
# Install
install(TARGETS mcp_server mcp_client DESTINATION bin)
install(DIRECTORY include/ DESTINATION include) # Install public headers
install(DIRECTORY client/include/ DESTINATION include) # Install public client headers
# --- Benchmark Setup ---
# Define benchmark sources
set(BENCHMARK_SOURCES
benchmark/mcp_benchmark.c
benchmark/benchmark_cli.c
)
set(BENCHMARK_HEADERS
benchmark/mcp_benchmark.h
)
# Create benchmark executable
add_executable(mcp_benchmark_cli ${BENCHMARK_SOURCES} ${BENCHMARK_HEADERS})
target_link_libraries(mcp_benchmark_cli PRIVATE mcp_common)
# Benchmark needs access to its own headers
target_include_directories(mcp_benchmark_cli PRIVATE
${CMAKE_CURRENT_SOURCE_DIR}/benchmark
)
# Common/Client headers are inherited via mcp_common PUBLIC include directories
# Optionally install the benchmark tool
# install(TARGETS mcp_benchmark_cli DESTINATION bin)
# Print configuration
message(STATUS "CMAKE_SYSTEM_NAME: ${CMAKE_SYSTEM_NAME}")
message(STATUS "CMAKE_C_COMPILER: ${CMAKE_C_COMPILER}")
message(STATUS "CMAKE_BUILD_TYPE: ${CMAKE_BUILD_TYPE}")
# --- Testing Setup ---
enable_testing()
# Add Unity library
set(UNITY_SOURCES tests/unity/unity.c)
set(UNITY_HEADERS tests/unity/unity.h tests/unity/unity_internals.h)
add_library(unity_lib STATIC ${UNITY_SOURCES} ${UNITY_HEADERS})
target_include_directories(unity_lib PUBLIC tests/unity) # Make headers available
# Add tests subdirectory (will contain test runner definition)
add_subdirectory(tests)
# Add examples subdirectory (optional, if examples exist)
add_subdirectory(examples)
# Add Python bindings
add_subdirectory(python)
# Create KMCP CLI executable
add_executable(kmcp_cli src/kmcp/kmcp_cli_main.c)
target_link_libraries(kmcp_cli PRIVATE kmcp mcp_common)
# Install KMCP library, headers, and CLI
install(TARGETS kmcp DESTINATION lib)
install(TARGETS kmcp_cli DESTINATION bin)
install(DIRECTORY include/kmcp/ DESTINATION include/kmcp)