Add UDP socket client/server multiplayer protocol
Implements the multiplayer transport layer from ROADMAP.md: UUID-based client identity, a reliable-packet channel over UDP, handshake/ack/ ping/disconnect/player-joined/player-left/player-state packet types, and split online (networked) vs offline (in-process singleplayer) server modes wired into the engine's update/dispose loop.
This commit is contained in:
@@ -0,0 +1,62 @@
|
||||
/**
|
||||
* Copyright (c) 2026 Dominic Masters
|
||||
*
|
||||
* This software is released under the MIT License.
|
||||
* https://opensource.org/licenses/MIT
|
||||
*/
|
||||
|
||||
#include "dusktest.h"
|
||||
#include "network/network.h"
|
||||
#include "network/networkinfo.h"
|
||||
#include "util/memory.h"
|
||||
|
||||
typedef struct {
|
||||
bool_t connected;
|
||||
bool_t failed;
|
||||
} networkevents_t;
|
||||
|
||||
static void onConnected(void *user) {
|
||||
((networkevents_t *)user)->connected = true;
|
||||
}
|
||||
|
||||
static void onFailed(errorret_t error, void *user) {
|
||||
errorCatch(error);
|
||||
((networkevents_t *)user)->failed = true;
|
||||
}
|
||||
|
||||
static void onDisconnect(errorret_t error, void *user) {
|
||||
errorCatch(error);
|
||||
}
|
||||
|
||||
// Regression test: networkIsConnected() reports physical connectivity and
|
||||
// is NOT the same thing as NETWORK.state -- networkGetInfo() asserts on
|
||||
// the latter. Code must gate networkGetInfo() on NETWORK.state, reached
|
||||
// only via networkRequestConnection(), not on networkIsConnected() alone.
|
||||
static void test_request_connection_enables_get_info(void **state) {
|
||||
assert_true(errorIsOk(networkInit()));
|
||||
|
||||
networkevents_t events;
|
||||
memoryZero(&events, sizeof(events));
|
||||
|
||||
// Resolves synchronously on Linux (no networkPlatformRequestConnection).
|
||||
networkRequestConnection(onConnected, onFailed, onDisconnect, &events);
|
||||
assert_true(events.connected || events.failed);
|
||||
|
||||
if(events.connected) {
|
||||
assert_int_equal(NETWORK.state, NETWORK_STATE_CONNECTED);
|
||||
const networkinfo_t info = networkGetInfo(); // must not assert/crash
|
||||
(void)info;
|
||||
} else {
|
||||
assert_int_equal(NETWORK.state, NETWORK_STATE_DISCONNECTED);
|
||||
}
|
||||
|
||||
assert_true(errorIsOk(networkDispose()));
|
||||
assert_int_equal(memoryGetAllocatedCount(), 0);
|
||||
}
|
||||
|
||||
int main(void) {
|
||||
const struct CMUnitTest tests[] = {
|
||||
cmocka_unit_test(test_request_connection_enables_get_info),
|
||||
};
|
||||
return cmocka_run_group_tests(tests, NULL, NULL);
|
||||
}
|
||||
Reference in New Issue
Block a user