basic implementation of client/server for AERPAW, whole lot of mess included
This commit is contained in:
83
aerpaw/basic_demo/comms.cpp
Normal file
83
aerpaw/basic_demo/comms.cpp
Normal file
@@ -0,0 +1,83 @@
|
||||
#include <iostream>
|
||||
#include <thread>
|
||||
#include <vector>
|
||||
#include <cstring>
|
||||
#include <sys/socket.h>
|
||||
#include <arpa/inet.h>
|
||||
#include <unistd.h>
|
||||
|
||||
#define SERVER_PORT 5000
|
||||
#define SERVER_IP "127.0.0.1"
|
||||
|
||||
// Socket init
|
||||
void initSockets() {}
|
||||
void cleanupSockets() {}
|
||||
|
||||
int serverSocket = -1;
|
||||
std::vector<int> clientSockets;
|
||||
|
||||
extern "C" {
|
||||
|
||||
// Initialize server (call once)
|
||||
void initServer() {
|
||||
initSockets();
|
||||
serverSocket = socket(AF_INET, SOCK_STREAM, 0);
|
||||
if(serverSocket < 0) { std::cerr << "Socket creation failed\n"; return; }
|
||||
|
||||
sockaddr_in serverAddr;
|
||||
serverAddr.sin_family = AF_INET;
|
||||
serverAddr.sin_addr.s_addr = INADDR_ANY;
|
||||
serverAddr.sin_port = htons(SERVER_PORT);
|
||||
|
||||
int opt = 1;
|
||||
setsockopt(serverSocket, SOL_SOCKET, SO_REUSEADDR, (char*)&opt, sizeof(opt));
|
||||
|
||||
if(bind(serverSocket, (sockaddr*)&serverAddr, sizeof(serverAddr)) < 0) {
|
||||
std::cerr << "Bind failed\n"; return;
|
||||
}
|
||||
if(listen(serverSocket, 5) < 0) {
|
||||
std::cerr << "Listen failed\n"; return;
|
||||
}
|
||||
|
||||
std::cout << "Server initialized, waiting for clients...\n";
|
||||
}
|
||||
|
||||
// Accept client connections (call once per client)
|
||||
void acceptClient(int clientId) {
|
||||
sockaddr_in clientAddr;
|
||||
socklen_t addrLen = sizeof(clientAddr);
|
||||
int clientSock = accept(serverSocket, (sockaddr*)&clientAddr, &addrLen);
|
||||
if(clientSock < 0) { std::cerr << "Accept failed for client " << clientId << "\n"; return; }
|
||||
clientSockets.push_back(clientSock);
|
||||
std::cout << "Client " << clientId << " connected\n";
|
||||
}
|
||||
|
||||
// Send a message to a specific client
|
||||
void sendMessage(int clientId) {
|
||||
if(clientId <= 0 || clientId > clientSockets.size()) return;
|
||||
const char* msg = "Hello from server";
|
||||
send(clientSockets[clientId-1], msg, strlen(msg), 0);
|
||||
std::cout << "Sent message to client " << clientId << "\n";
|
||||
}
|
||||
|
||||
// Receive ACK from a specific client
|
||||
int receiveAck(int clientId) {
|
||||
if(clientId <= 0 || clientId > clientSockets.size()) return 0;
|
||||
char buffer[1024];
|
||||
int len = recv(clientSockets[clientId-1], buffer, sizeof(buffer)-1, 0);
|
||||
if(len <= 0) return 0;
|
||||
buffer[len] = '\0';
|
||||
std::cout << "Received ACK from client " << clientId << ": " << buffer << "\n";
|
||||
return 1;
|
||||
}
|
||||
|
||||
// Cleanup server
|
||||
void closeServer() {
|
||||
for(auto sock : clientSockets) {
|
||||
close(sock);
|
||||
}
|
||||
close(serverSocket);
|
||||
cleanupSockets();
|
||||
}
|
||||
|
||||
}
|
||||
37
aerpaw/basic_demo/controller.cpp
Normal file
37
aerpaw/basic_demo/controller.cpp
Normal file
@@ -0,0 +1,37 @@
|
||||
//
|
||||
// Academic License - for use in teaching, academic research, and meeting
|
||||
// course requirements at degree granting institutions only. Not for
|
||||
// government, commercial, or other organizational use.
|
||||
//
|
||||
// controller.cpp
|
||||
//
|
||||
// Code generation for function 'controller'
|
||||
//
|
||||
|
||||
// Include files
|
||||
#include "controller.h"
|
||||
#include "controller_impl.h"
|
||||
|
||||
// Function Definitions
|
||||
void controller(int numClients)
|
||||
{
|
||||
// Initialize server
|
||||
initServer();
|
||||
// Accept clients
|
||||
for (int i{0}; i < numClients; i++) {
|
||||
acceptClient(i + 1);
|
||||
}
|
||||
// Send messages to clients
|
||||
for (int i{0}; i < numClients; i++) {
|
||||
sendMessage(i + 1);
|
||||
}
|
||||
// Receive acknowledgements
|
||||
for (int i{0}; i < numClients; i++) {
|
||||
receiveAck(i + 1);
|
||||
}
|
||||
// Digest ACKs
|
||||
// Close server
|
||||
closeServer();
|
||||
}
|
||||
|
||||
// End of code generation (controller.cpp)
|
||||
23
aerpaw/basic_demo/controller.h
Normal file
23
aerpaw/basic_demo/controller.h
Normal file
@@ -0,0 +1,23 @@
|
||||
//
|
||||
// Academic License - for use in teaching, academic research, and meeting
|
||||
// course requirements at degree granting institutions only. Not for
|
||||
// government, commercial, or other organizational use.
|
||||
//
|
||||
// controller.h
|
||||
//
|
||||
// Code generation for function 'controller'
|
||||
//
|
||||
|
||||
#ifndef CONTROLLER_H
|
||||
#define CONTROLLER_H
|
||||
|
||||
// Include files
|
||||
#include "rtwtypes.h"
|
||||
#include <cstddef>
|
||||
#include <cstdlib>
|
||||
|
||||
// Function Declarations
|
||||
extern void controller(int numClients);
|
||||
|
||||
#endif
|
||||
// End of code generation (controller.h)
|
||||
BIN
aerpaw/basic_demo/controller_app
Executable file
BIN
aerpaw/basic_demo/controller_app
Executable file
Binary file not shown.
73
aerpaw/basic_demo/controller_impl.cpp
Normal file
73
aerpaw/basic_demo/controller_impl.cpp
Normal file
@@ -0,0 +1,73 @@
|
||||
#include "controller_impl.h"
|
||||
#include <iostream>
|
||||
#include <vector>
|
||||
#include <cstring>
|
||||
#include <sys/socket.h>
|
||||
#include <arpa/inet.h>
|
||||
#include <unistd.h>
|
||||
|
||||
#define SERVER_PORT 5000
|
||||
#define SERVER_IP "127.0.0.1"
|
||||
|
||||
static int serverSocket = -1;
|
||||
static std::vector<int> clientSockets;
|
||||
|
||||
void initSockets() {}
|
||||
void cleanupSockets() {}
|
||||
|
||||
void initServer() {
|
||||
initSockets();
|
||||
serverSocket = socket(AF_INET, SOCK_STREAM, 0);
|
||||
if(serverSocket < 0) { std::cerr << "Socket creation failed\n"; return; }
|
||||
|
||||
sockaddr_in serverAddr;
|
||||
serverAddr.sin_family = AF_INET;
|
||||
serverAddr.sin_addr.s_addr = INADDR_ANY;
|
||||
serverAddr.sin_port = htons(SERVER_PORT);
|
||||
|
||||
int opt = 1;
|
||||
setsockopt(serverSocket, SOL_SOCKET, SO_REUSEADDR, (char*)&opt, sizeof(opt));
|
||||
|
||||
if(bind(serverSocket, (sockaddr*)&serverAddr, sizeof(serverAddr)) < 0) {
|
||||
std::cerr << "Bind failed\n"; return;
|
||||
}
|
||||
if(listen(serverSocket, 5) < 0) {
|
||||
std::cerr << "Listen failed\n"; return;
|
||||
}
|
||||
|
||||
std::cout << "Server initialized\n";
|
||||
}
|
||||
|
||||
void acceptClient(int clientId) {
|
||||
sockaddr_in clientAddr;
|
||||
socklen_t addrLen = sizeof(clientAddr);
|
||||
int clientSock = accept(serverSocket, (sockaddr*)&clientAddr, &addrLen);
|
||||
if(clientSock < 0) { std::cerr << "Accept failed for client " << clientId << "\n"; return; }
|
||||
clientSockets.push_back(clientSock);
|
||||
std::cout << "Client " << clientId << " connected\n";
|
||||
}
|
||||
|
||||
void sendMessage(int clientId) {
|
||||
if(clientId <= 0 || clientId > clientSockets.size()) return;
|
||||
const char* msg = "Hello from server";
|
||||
send(clientSockets[clientId-1], msg, strlen(msg), 0);
|
||||
std::cout << "Sent message to client " << clientId << "\n";
|
||||
}
|
||||
|
||||
int receiveAck(int clientId) {
|
||||
if(clientId <= 0 || clientId > clientSockets.size()) return 0;
|
||||
char buffer[1024];
|
||||
int len = recv(clientSockets[clientId-1], buffer, sizeof(buffer)-1, 0);
|
||||
if(len <= 0) return 0;
|
||||
buffer[len] = '\0';
|
||||
std::cout << "Received ACK from client " << clientId << ": " << buffer << "\n";
|
||||
return 1;
|
||||
}
|
||||
|
||||
void closeServer() {
|
||||
for(auto sock : clientSockets) {
|
||||
close(sock);
|
||||
}
|
||||
close(serverSocket);
|
||||
cleanupSockets();
|
||||
}
|
||||
18
aerpaw/basic_demo/controller_impl.h
Normal file
18
aerpaw/basic_demo/controller_impl.h
Normal file
@@ -0,0 +1,18 @@
|
||||
#ifndef CONTROLLER_IMPL_H
|
||||
#define CONTROLLER_IMPL_H
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
void initServer();
|
||||
void acceptClient(int clientId);
|
||||
void sendMessage(int clientId);
|
||||
int receiveAck(int clientId);
|
||||
void closeServer();
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif // CONTROLLER_IMPL_H
|
||||
16
aerpaw/basic_demo/controller_main.cpp
Normal file
16
aerpaw/basic_demo/controller_main.cpp
Normal file
@@ -0,0 +1,16 @@
|
||||
#include <iostream>
|
||||
#include "controller.h" // Generated by MATLAB Coder
|
||||
#include "controller_impl.h" // Your TCP implementation header
|
||||
|
||||
int main() {
|
||||
// Number of clients to handle
|
||||
int numClients = 2; // Example: change as needed
|
||||
|
||||
std::cout << "Initializing TCP server...\n";
|
||||
|
||||
// Call MATLAB-generated server function
|
||||
controller(numClients);
|
||||
|
||||
std::cout << "Server finished.\n";
|
||||
return 0;
|
||||
}
|
||||
44
aerpaw/basic_demo/rtwtypes.h
Normal file
44
aerpaw/basic_demo/rtwtypes.h
Normal file
@@ -0,0 +1,44 @@
|
||||
//
|
||||
// Academic License - for use in teaching, academic research, and meeting
|
||||
// course requirements at degree granting institutions only. Not for
|
||||
// government, commercial, or other organizational use.
|
||||
//
|
||||
// rtwtypes.h
|
||||
//
|
||||
// Code generation for function 'controller'
|
||||
//
|
||||
|
||||
#ifndef RTWTYPES_H
|
||||
#define RTWTYPES_H
|
||||
|
||||
/*=======================================================================*
|
||||
* Fixed width word size data types: *
|
||||
* int64_T - signed 64 bit integers *
|
||||
* uint64_T - unsigned 64 bit integers *
|
||||
*=======================================================================*/
|
||||
|
||||
#if defined(__APPLE__)
|
||||
#ifndef INT64_T
|
||||
#define INT64_T long
|
||||
#define FMT64 "l"
|
||||
#if defined(__LP64__) && !defined(INT_TYPE_64_IS_LONG)
|
||||
#define INT_TYPE_64_IS_LONG
|
||||
#endif
|
||||
#endif
|
||||
#endif
|
||||
|
||||
#if defined(__APPLE__)
|
||||
#ifndef UINT64_T
|
||||
#define UINT64_T unsigned long
|
||||
#define FMT64 "l"
|
||||
#if defined(__LP64__) && !defined(INT_TYPE_64_IS_LONG)
|
||||
#define INT_TYPE_64_IS_LONG
|
||||
#endif
|
||||
#endif
|
||||
#endif
|
||||
|
||||
// Include files
|
||||
#include "tmwtypes.h"
|
||||
|
||||
#endif
|
||||
// End of code generation (rtwtypes.h)
|
||||
13
aerpaw/basic_demo/uav.py
Executable file
13
aerpaw/basic_demo/uav.py
Executable file
@@ -0,0 +1,13 @@
|
||||
#!/bin/python3
|
||||
import socket
|
||||
|
||||
SERVER_IP = "127.0.0.1"
|
||||
SERVER_PORT = 5000
|
||||
|
||||
for client_id in range(2): # match numClients
|
||||
s = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
|
||||
s.connect((SERVER_IP, SERVER_PORT))
|
||||
data = s.recv(1024) # receive message from server
|
||||
print(f"Client {client_id+1} received: {data.decode()}")
|
||||
s.sendall(b"ACK") # send acknowledgment
|
||||
s.close()
|
||||
Reference in New Issue
Block a user