Wait using a condition variable in server
Currently, server_stop() is called from the same thread as server_connect_to(), so interruption may never happen. This is a step to prepare executing the server from a dedicated thread.
This commit is contained in:
parent
a54dc8212f
commit
5b9c88693e
2 changed files with 45 additions and 4 deletions
|
@ -367,7 +367,8 @@ connect_and_read_byte(sc_socket socket, uint16_t port) {
|
||||||
}
|
}
|
||||||
|
|
||||||
static sc_socket
|
static sc_socket
|
||||||
connect_to_server(uint16_t port, uint32_t attempts, uint32_t delay) {
|
connect_to_server(struct server *server, uint32_t attempts, sc_tick delay) {
|
||||||
|
uint16_t port = server->local_port;
|
||||||
do {
|
do {
|
||||||
LOGD("Remaining connection attempts: %d", (int) attempts);
|
LOGD("Remaining connection attempts: %d", (int) attempts);
|
||||||
sc_socket socket = net_socket();
|
sc_socket socket = net_socket();
|
||||||
|
@ -381,7 +382,20 @@ connect_to_server(uint16_t port, uint32_t attempts, uint32_t delay) {
|
||||||
net_close(socket);
|
net_close(socket);
|
||||||
}
|
}
|
||||||
if (attempts) {
|
if (attempts) {
|
||||||
SDL_Delay(delay);
|
sc_mutex_lock(&server->mutex);
|
||||||
|
sc_tick deadline = sc_tick_now() + delay;
|
||||||
|
bool timed_out = false;
|
||||||
|
while (!server->stopped && !timed_out) {
|
||||||
|
timed_out = !sc_cond_timedwait(&server->cond_stopped,
|
||||||
|
&server->mutex, deadline);
|
||||||
|
}
|
||||||
|
bool stopped = server->stopped;
|
||||||
|
sc_mutex_unlock(&server->mutex);
|
||||||
|
|
||||||
|
if (stopped) {
|
||||||
|
LOGI("Connection attempt stopped");
|
||||||
|
break;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
} while (--attempts > 0);
|
} while (--attempts > 0);
|
||||||
return SC_INVALID_SOCKET;
|
return SC_INVALID_SOCKET;
|
||||||
|
@ -395,7 +409,23 @@ server_init(struct server *server, const struct server_params *params) {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
ok = sc_mutex_init(&server->mutex);
|
||||||
|
if (!ok) {
|
||||||
|
LOGE("Could not create server mutex");
|
||||||
|
server_params_destroy(&server->params);
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
ok = sc_cond_init(&server->cond_stopped);
|
||||||
|
if (!ok) {
|
||||||
|
LOGE("Could not create server cond_stopped");
|
||||||
|
sc_mutex_destroy(&server->mutex);
|
||||||
|
server_params_destroy(&server->params);
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
server->process = SC_PROCESS_NONE;
|
server->process = SC_PROCESS_NONE;
|
||||||
|
server->stopped = false;
|
||||||
|
|
||||||
server->server_socket = SC_INVALID_SOCKET;
|
server->server_socket = SC_INVALID_SOCKET;
|
||||||
server->video_socket = SC_INVALID_SOCKET;
|
server->video_socket = SC_INVALID_SOCKET;
|
||||||
|
@ -453,8 +483,8 @@ server_connect_to(struct server *server, struct server_info *info) {
|
||||||
server->server_socket = SC_INVALID_SOCKET;
|
server->server_socket = SC_INVALID_SOCKET;
|
||||||
} else {
|
} else {
|
||||||
uint32_t attempts = 100;
|
uint32_t attempts = 100;
|
||||||
uint32_t delay = 100; // ms
|
sc_tick delay = SC_TICK_FROM_MS(100);
|
||||||
video_socket = connect_to_server(server->local_port, attempts, delay);
|
video_socket = connect_to_server(server, attempts, delay);
|
||||||
if (video_socket == SC_INVALID_SOCKET) {
|
if (video_socket == SC_INVALID_SOCKET) {
|
||||||
goto fail;
|
goto fail;
|
||||||
}
|
}
|
||||||
|
@ -563,6 +593,11 @@ error:
|
||||||
|
|
||||||
void
|
void
|
||||||
server_stop(struct server *server) {
|
server_stop(struct server *server) {
|
||||||
|
sc_mutex_lock(&server->mutex);
|
||||||
|
server->stopped = true;
|
||||||
|
sc_cond_signal(&server->cond_stopped);
|
||||||
|
sc_mutex_unlock(&server->mutex);
|
||||||
|
|
||||||
if (server->server_socket != SC_INVALID_SOCKET) {
|
if (server->server_socket != SC_INVALID_SOCKET) {
|
||||||
if (!net_interrupt(server->server_socket)) {
|
if (!net_interrupt(server->server_socket)) {
|
||||||
LOGW("Could not interrupt server socket");
|
LOGW("Could not interrupt server socket");
|
||||||
|
@ -627,4 +662,6 @@ server_destroy(struct server *server) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
server_params_destroy(&server->params);
|
server_params_destroy(&server->params);
|
||||||
|
sc_cond_destroy(&server->cond_stopped);
|
||||||
|
sc_mutex_destroy(&server->mutex);
|
||||||
}
|
}
|
||||||
|
|
|
@ -47,6 +47,10 @@ struct server {
|
||||||
// alive only between start() and stop()
|
// alive only between start() and stop()
|
||||||
struct sc_process_observer observer;
|
struct sc_process_observer observer;
|
||||||
|
|
||||||
|
sc_mutex mutex;
|
||||||
|
sc_cond cond_stopped;
|
||||||
|
bool stopped;
|
||||||
|
|
||||||
sc_socket server_socket; // only used if !tunnel_forward
|
sc_socket server_socket; // only used if !tunnel_forward
|
||||||
sc_socket video_socket;
|
sc_socket video_socket;
|
||||||
sc_socket control_socket;
|
sc_socket control_socket;
|
||||||
|
|
Loading…
Reference in a new issue