## Overview
DAP Net Server provides comprehensive server-side infrastructure for creating robust, scalable DAP services and applications. This module implements multi-threaded server architecture, connection management, and request processing capabilities, enabling the development of high-performance server applications within the DAP ecosystem.
**Based on:** `dap-sdk/net/server/include/dap_server.h`, `dap-sdk/net/server/src/dap_server.c`
## Document Structure
- [[#Overview|Overview]]
- [[#Module Structures|Module Structures]]
- [[#dap_server_t|dap_server_t - Server Instance]]
- [[#dap_server_config_t|dap_server_config_t - Configuration]]
- [[#dap_server_client_t|dap_server_client_t - Client Connection]]
- [[#dap_server_service_t|dap_server_service_t - Service Registration]]
- [[#dap_server_handler_t|dap_server_handler_t - Request Handler]]
- [[#Module Functions|Module Functions]]
- [[#Server Management|Server Creation and Lifecycle]]
- [[#Service Operations|Service Registration and Management]]
- [[#Client Management|Connection Handling]]
- [[#Request Processing|Request and Response Handling]]
- [[#Error Codes|Error Codes]]
- [[#Typical Examples|Typical Examples]]
## Module Structures
### dap_server_t
Core server instance structure managing all server operations and connections.
```c
typedef struct dap_server {
struct {
char *server_name; // Server identifier name
uint16_t port; // Server listening port
char *bind_address; // Bind address
bool is_running; // Server running status
bool is_listening; // Listening status
uint32_t active_connections; // Current active connections
uint32_t max_connections; // Maximum allowed connections
uint64_t total_requests; // Total requests processed
dap_time_t startup_time; // Server startup timestamp
} pub;
struct {
dap_events_socket_t *listening_socket; // Main listening socket
dap_list_t *client_list; // Connected clients list
dap_htable_t *service_table; // Registered services
dap_server_config_t *config; // Server configuration
dap_worker_pool_t *worker_pool; // Worker thread pool
dap_server_callbacks_t *callbacks; // Server event callbacks
pthread_mutex_t server_mutex; // Server synchronization
dap_server_stats_t *statistics; // Performance statistics
bool shutdown_requested; // Graceful shutdown flag
dap_ssl_context_t *ssl_context; // SSL/TLS context
} priv;
} dap_server_t;
```
**Public Fields:**
- `server_name` - Unique identifier for the server instance
- `port` - Port number the server is listening on
- `bind_address` - Network interface address for binding
- `is_running` - Server operational status
- `is_listening` - Listening socket status
- `active_connections` - Current number of active client connections
- `max_connections` - Maximum concurrent connections allowed
- `total_requests` - Counter of total requests processed
### dap_server_config_t
Server configuration structure defining operational parameters.
```c
typedef struct dap_server_config {
struct {
uint32_t max_connections; // Maximum client connections
uint32_t worker_threads; // Number of worker threads
uint32_t connection_timeout_sec; // Client connection timeout
uint32_t request_timeout_sec; // Request processing timeout
bool enable_ssl; // SSL/TLS encryption enabled
bool enable_compression; // Response compression
uint32_t keepalive_timeout_sec; // Keep-alive timeout
uint32_t max_request_size; // Maximum request size
} pub;
struct {
uint32_t socket_buffer_size; // Socket buffer size
uint32_t thread_stack_size; // Worker thread stack size
bool enable_nagle; // Nagle algorithm
uint32_t backlog_size; // Listen backlog size
bool enable_metrics; // Performance metrics
char *ssl_cert_path; // SSL certificate path
char *ssl_key_path; // SSL private key path
dap_server_security_policy_t security; // Security policies
} priv;
} dap_server_config_t;
```
### dap_server_client_t
Client connection structure representing connected clients.
```c
typedef struct dap_server_client {
struct {
uint64_t client_id; // Unique client identifier
dap_events_socket_t *socket; // Client socket
struct sockaddr_storage client_addr; // Client address
dap_time_t connected_time; // Connection timestamp
dap_time_t last_activity; // Last activity time
uint64_t requests_processed; // Requests from this client
uint64_t bytes_sent; // Bytes sent to client
uint64_t bytes_received; // Bytes received from client
dap_client_state_t state; // Client connection state
} pub;
struct {
dap_server_t *server; // Parent server reference
dap_buffer_t *request_buffer; // Request buffer
dap_buffer_t *response_buffer; // Response buffer
dap_client_session_t *session; // Client session data
pthread_mutex_t client_mutex; // Client synchronization
dap_timer_t *timeout_timer; // Client timeout timer
bool is_authenticated; // Authentication status
dap_auth_context_t *auth_context; // Authentication context
} priv;
} dap_server_client_t;
```
### dap_server_service_t
Service registration structure for server endpoints.
```c
typedef struct dap_server_service {
struct {
char *service_name; // Service identifier
char *service_path; // URL path or endpoint
dap_service_type_t type; // Service type
bool is_enabled; // Service enabled status
uint64_t requests_handled; // Total requests handled
dap_time_t registration_time; // Service registration time
uint32_t average_response_time_ms; // Average response time
} pub;
struct {
dap_server_handler_t *handler; // Request handler function
void *handler_context; // Handler context data
dap_service_middleware_t *middleware; // Middleware chain
dap_service_config_t *config; // Service configuration
dap_service_stats_t *statistics; // Service statistics
pthread_mutex_t service_mutex; // Service synchronization
} priv;
} dap_server_service_t;
```
### dap_server_handler_t
Request handler structure for processing client requests.
```c
typedef struct dap_server_handler {
dap_server_handler_callback_t callback; // Handler callback function
void *callback_context; // Callback context
dap_handler_priority_t priority; // Handler priority
char *content_type; // Response content type
bool requires_auth; // Authentication required
dap_handler_method_t methods; // Supported HTTP methods
dap_handler_config_t *config; // Handler configuration
} dap_server_handler_t;
```
## Module Functions
### Server Management
#### `dap_server_create()`
Creates new server instance with specified configuration.
```c
dap_server_t* dap_server_create(const char *a_server_name, const dap_server_config_t *a_config);
```
**Parameters:**
- `a_server_name` (const char*) - Unique name for the server instance
- `a_config` (const dap_server_config_t*) - Server configuration parameters
**Returns:**
- `dap_server_t*` - Created server instance
- `NULL` - Server creation failed
**Error Conditions:**
- Returns NULL if a_server_name is NULL or empty
- Returns NULL if a_config is NULL or invalid
- Returns NULL if memory allocation fails
- Returns NULL if socket creation fails
**Description:** Creates a new server instance with the specified configuration. The server is created in a stopped state and requires explicit startup.
#### `dap_server_destroy()`
Destroys server instance and frees all resources.
```c
void dap_server_destroy(dap_server_t *a_server);
```
**Parameters:**
- `a_server` (dap_server_t*) - Server instance to destroy
**Description:** Safely destroys the server by stopping all operations, disconnecting clients, and freeing allocated resources.
#### `dap_server_start()`
Starts server and begins accepting connections.
```c
int dap_server_start(dap_server_t *a_server, const char *a_bind_addr, uint16_t a_port);
```
**Parameters:**
- `a_server` (dap_server_t*) - Server instance to start
- `a_bind_addr` (const char*) - Address to bind to ("0.0.0.0" for all interfaces)
- `a_port` (uint16_t) - Port number to listen on
**Returns:**
- `0` - Server started successfully
- `-1` - Invalid parameters
- `-2` - Address binding failed
- `-3` - Listen operation failed
- `-4` - Worker pool creation failed
**Error Conditions:**
- Returns -1 if a_server is NULL or a_port is 0
- Returns -2 if bind() system call fails
- Returns -3 if listen() system call fails
- Returns -4 if worker thread creation fails
#### `dap_server_stop()`
Stops server gracefully and closes all connections.
```c
int dap_server_stop(dap_server_t *a_server);
```
**Parameters:**
- `a_server` (dap_server_t*) - Server instance to stop
**Returns:**
- `0` - Server stopped successfully
- `-1` - Invalid server parameter
- `-2` - Server not running
### Service Operations
#### `dap_server_register_service()`
Registers new service endpoint with the server.
```c
int dap_server_register_service(dap_server_t *a_server, const char *a_service_name, const char *a_path, dap_server_handler_t *a_handler);
```
**Parameters:**
- `a_server` (dap_server_t*) - Server instance
- `a_service_name` (const char*) - Service identifier name
- `a_path` (const char*) - URL path or endpoint
- `a_handler` (dap_server_handler_t*) - Request handler
**Returns:**
- `0` - Service registered successfully
- `-1` - Invalid parameters
- `-2` - Service already exists
- `-3` - Handler registration failed
#### `dap_server_unregister_service()`
Unregisters service from the server.
```c
int dap_server_unregister_service(dap_server_t *a_server, const char *a_service_name);
```
#### `dap_server_get_service()`
Retrieves service by name.
```c
dap_server_service_t* dap_server_get_service(dap_server_t *a_server, const char *a_service_name);
```
### Client Management
#### `dap_server_accept_client()`
Accepts new client connection.
```c
dap_server_client_t* dap_server_accept_client(dap_server_t *a_server, dap_events_socket_t *a_socket);
```
**Parameters:**
- `a_server` (dap_server_t*) - Server instance
- `a_socket` (dap_events_socket_t*) - Accepted client socket
**Returns:**
- `dap_server_client_t*` - New client structure
- `NULL` - Client acceptance failed
#### `dap_server_disconnect_client()`
Disconnects client from server.
```c
int dap_server_disconnect_client(dap_server_t *a_server, dap_server_client_t *a_client);
```
### Request Processing
#### `dap_server_process_request()`
Processes client request through registered handlers.
```c
int dap_server_process_request(dap_server_client_t *a_client, const void *a_request, size_t a_request_size);
```
**Parameters:**
- `a_client` (dap_server_client_t*) - Client connection
- `a_request` (const void*) - Request data
- `a_request_size` (size_t) - Size of request data
**Returns:**
- `0` - Request processed successfully
- `-1` - Invalid parameters
- `-2` - No handler found
- `-3` - Handler execution failed
#### `dap_server_send_response()`
Sends response to client.
```c
int dap_server_send_response(dap_server_client_t *a_client, const void *a_response, size_t a_response_size);
```
## Error Codes
### Server Error Codes
```c
typedef enum dap_server_error {
DAP_SERVER_ERROR_SUCCESS = 0, // Operation successful
DAP_SERVER_ERROR_INVALID_PARAM = -1, // Invalid parameter provided
DAP_SERVER_ERROR_NO_MEMORY = -2, // Memory allocation failed
DAP_SERVER_ERROR_SOCKET_FAILED = -3, // Socket operation failed
DAP_SERVER_ERROR_BIND_FAILED = -4, // Address binding failed
DAP_SERVER_ERROR_LISTEN_FAILED = -5, // Listen operation failed
DAP_SERVER_ERROR_ACCEPT_FAILED = -6, // Client accept failed
DAP_SERVER_ERROR_SSL_FAILED = -7, // SSL/TLS operation failed
DAP_SERVER_ERROR_HANDLER_FAILED = -8, // Request handler failed
DAP_SERVER_ERROR_SERVICE_EXISTS = -9, // Service already registered
DAP_SERVER_ERROR_SERVICE_NOT_FOUND = -10, // Service not found
DAP_SERVER_ERROR_CLIENT_LIMIT = -11, // Client limit reached
DAP_SERVER_ERROR_NOT_RUNNING = -12, // Server not running
DAP_SERVER_ERROR_ALREADY_RUNNING = -13 // Server already running
} dap_server_error_t;
```
## Typical Examples
### Basic HTTP Server Example
```c
#include "dap_common.h"
#include "dap_server.h"
// HTTP request handler
int http_handler(dap_server_client_t *a_client, const void *a_request, size_t a_request_size, void *a_context) {
log_it(L_INFO, "Processing HTTP request from client %lu", a_client->pub.client_id);
// Simple HTTP response
const char *response =
"HTTP/1.1 200 OK\r\n"
"Content-Type: text/html\r\n"
"Content-Length: 48\r\n"
"Connection: close\r\n"
"\r\n"
"<html><body><h1>Hello from DAP Server!</h1></body></html>";
int result = dap_server_send_response(a_client, response, strlen(response));
if (result == 0) {
log_it(L_INFO, "✓ HTTP response sent to client %lu", a_client->pub.client_id);
} else {
log_it(L_ERROR, "✗ Failed to send response: %d", result);
}
return result;
}
int example_http_server() {
log_it(L_INFO, "=== DAP HTTP Server Example ===");
// Step 1: Create server configuration
dap_server_config_t config = {
.pub.max_connections = 100,
.pub.worker_threads = 4,
.pub.connection_timeout_sec = 30,
.pub.request_timeout_sec = 60,
.pub.enable_ssl = false,
.pub.enable_compression = true,
.pub.keepalive_timeout_sec = 300,
.pub.max_request_size = 1024 * 1024, // 1MB
.priv.socket_buffer_size = 8192,
.priv.enable_metrics = true,
.priv.backlog_size = 128
};
// Step 2: Create server instance
dap_server_t *server = dap_server_create("http_server", &config);
if (!server) {
log_it(L_ERROR, "✗ Failed to create HTTP server");
return -1;
}
log_it(L_INFO, "✓ HTTP server created successfully");
// Step 3: Register HTTP service
dap_server_handler_t handler = {
.callback = http_handler,
.callback_context = NULL,
.priority = DAP_HANDLER_PRIORITY_NORMAL,
.content_type = "text/html",
.requires_auth = false,
.methods = DAP_HANDLER_METHOD_GET | DAP_HANDLER_METHOD_POST
};
int result = dap_server_register_service(server, "http_service", "/", &handler);
if (result != 0) {
log_it(L_ERROR, "✗ Failed to register HTTP service: %d", result);
dap_server_destroy(server);
return -1;
}
log_it(L_INFO, "✓ HTTP service registered at path '/'");
// Step 4: Start server
result = dap_server_start(server, "0.0.0.0", 8080);
if (result != 0) {
log_it(L_ERROR, "✗ Failed to start server: %d", result);
switch (result) {
case -2:
log_it(L_ERROR, "Address binding failed - port may be in use");
break;
case -3:
log_it(L_ERROR, "Listen operation failed");
break;
case -4:
log_it(L_ERROR, "Worker pool creation failed");
break;
}
dap_server_destroy(server);
return -1;
}
log_it(L_INFO, "✓ HTTP server started on 0.0.0.0:8080");
log_it(L_INFO, "Server ready to accept connections...");
// Step 5: Let server run (in real application, this would be event-driven)
log_it(L_INFO, "Server running for 30 seconds...");
sleep(30);
// Step 6: Display server statistics
log_it(L_INFO, "Server Statistics:");
log_it(L_INFO, " Active connections: %u", server->pub.active_connections);
log_it(L_INFO, " Total requests: %lu", server->pub.total_requests);
log_it(L_INFO, " Uptime: %lu seconds", dap_time_now() - server->pub.startup_time);
// Step 7: Graceful shutdown
log_it(L_INFO, "Shutting down server...");
result = dap_server_stop(server);
if (result == 0) {
log_it(L_INFO, "✓ Server stopped gracefully");
} else {
log_it(L_ERROR, "✗ Server stop failed: %d", result);
}
// Step 8: Cleanup
dap_server_destroy(server);
log_it(L_INFO, "✓ HTTP Server example completed");
return 0;
}
```
### Multi-Service Server Example
```c
#include "dap_common.h"
#include "dap_server.h"
// API endpoint handler
int api_handler(dap_server_client_t *a_client, const void *a_request, size_t a_request_size, void *a_context) {
log_it(L_INFO, "Processing API request from client %lu", a_client->pub.client_id);
const char *json_response =
"HTTP/1.1 200 OK\r\n"
"Content-Type: application/json\r\n"
"Content-Length: 54\r\n"
"\r\n"
"{\"status\":\"success\",\"message\":\"DAP API is running\"}";
return dap_server_send_response(a_client, json_response, strlen(json_response));
}
// Status endpoint handler
int status_handler(dap_server_client_t *a_client, const void *a_request, size_t a_request_size, void *a_context) {
dap_server_t *server = (dap_server_t*)a_context;
char status_response[512];
snprintf(status_response, sizeof(status_response),
"HTTP/1.1 200 OK\r\n"
"Content-Type: application/json\r\n"
"Content-Length: %d\r\n"
"\r\n"
"{\"server\":\"%s\",\"connections\":%u,\"requests\":%lu,\"uptime\":%lu}",
0, // Will be calculated
server->pub.server_name,
server->pub.active_connections,
server->pub.total_requests,
dap_time_now() - server->pub.startup_time);
// Update content length
char *content_start = strstr(status_response, "\r\n\r\n") + 4;
size_t content_length = strlen(content_start);
snprintf(status_response, sizeof(status_response),
"HTTP/1.1 200 OK\r\n"
"Content-Type: application/json\r\n"
"Content-Length: %zu\r\n"
"\r\n"
"{\"server\":\"%s\",\"connections\":%u,\"requests\":%lu,\"uptime\":%lu}",
content_length,
server->pub.server_name,
server->pub.active_connections,
server->pub.total_requests,
dap_time_now() - server->pub.startup_time);
return dap_server_send_response(a_client, status_response, strlen(status_response));
}
int example_multi_service_server() {
log_it(L_INFO, "=== Multi-Service Server Example ===");
// Step 1: Create server with enhanced configuration
dap_server_config_t config = {
.pub.max_connections = 200,
.pub.worker_threads = 8,
.pub.connection_timeout_sec = 60,
.pub.request_timeout_sec = 30,
.pub.enable_compression = true,
.priv.enable_metrics = true
};
dap_server_t *server = dap_server_create("multi_service_server", &config);
if (!server) {
log_it(L_ERROR, "✗ Failed to create server");
return -1;
}
// Step 2: Register API service
dap_server_handler_t api_handler_struct = {
.callback = api_handler,
.callback_context = server,
.priority = DAP_HANDLER_PRIORITY_HIGH,
.content_type = "application/json",
.requires_auth = false,
.methods = DAP_HANDLER_METHOD_GET | DAP_HANDLER_METHOD_POST
};
if (dap_server_register_service(server, "api_service", "/api", &api_handler_struct) != 0) {
log_it(L_ERROR, "✗ Failed to register API service");
goto cleanup;
}
log_it(L_INFO, "✓ API service registered at '/api'");
// Step 3: Register status service
dap_server_handler_t status_handler_struct = {
.callback = status_handler,
.callback_context = server,
.priority = DAP_HANDLER_PRIORITY_NORMAL,
.content_type = "application/json",
.requires_auth = false,
.methods = DAP_HANDLER_METHOD_GET
};
if (dap_server_register_service(server, "status_service", "/status", &status_handler_struct) != 0) {
log_it(L_ERROR, "✗ Failed to register status service");
goto cleanup;
}
log_it(L_INFO, "✓ Status service registered at '/status'");
// Step 4: Start server
if (dap_server_start(server, "127.0.0.1", 9090) != 0) {
log_it(L_ERROR, "✗ Failed to start server");
goto cleanup;
}
log_it(L_INFO, "✓ Multi-service server started on 127.0.0.1:9090");
// Step 5: Display registered services
log_it(L_INFO, "Registered Services:");
dap_server_service_t *api_service = dap_server_get_service(server, "api_service");
if (api_service) {
log_it(L_INFO, " API Service: %s (enabled: %s)",
api_service->pub.service_path,
api_service->pub.is_enabled ? "yes" : "no");
}
dap_server_service_t *status_service = dap_server_get_service(server, "status_service");
if (status_service) {
log_it(L_INFO, " Status Service: %s (enabled: %s)",
status_service->pub.service_path,
status_service->pub.is_enabled ? "yes" : "no");
}
// Step 6: Run server
log_it(L_INFO, "Server running - try accessing:");
log_it(L_INFO, " http://127.0.0.1:9090/api");
log_it(L_INFO, " http://127.0.0.1:9090/status");
sleep(60);
cleanup:
dap_server_stop(server);
dap_server_destroy(server);
log_it(L_INFO, "✓ Multi-Service Server example completed");
return 0;
}
```
---
**See also:** [[Module DAP Net - Client|Module DAP Net - Client]], [[Module DAP Net - Stream|Module DAP Net - Stream]], [[Module DAP IO|Module DAP IO]]
---
*Based on: `dap-sdk/net/server/include/dap_server.h`, `dap-sdk/net/server/src/dap_server.c`*