Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
27 changes: 21 additions & 6 deletions .github/workflows/ci.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -2,16 +2,31 @@ name: CI

on:
push:
branches: [ "main" ]
branches-ignore:
- main
pull_request:
branches: [ "main" ]
branches:
- main

jobs:
build:

runs-on: ubuntu-latest

steps:
- uses: actions/checkout@v4
- name: make
run: make
- name: Checkout Cactus repository
uses: actions/checkout@v4
with:
path: csky

- name: Checkout Crux repository as a sibling
uses: actions/checkout@v4
with:
repository: meslab/crux # Replace with actual org/user
path: crux

- name: Build Crux
run: make -C crux

- name: Build CSky
run: make -C csky

12 changes: 6 additions & 6 deletions include/ads_b.h
Original file line number Diff line number Diff line change
Expand Up @@ -12,21 +12,21 @@
#define ADSB_SHORT_LEN 7

typedef struct {
uint32_t header; // 4 bytes (DF, CA, ICAO)
uint8_t data[7]; // 7 bytes (ADS-B payload)
uint8_t parity[3]; // 3 bytes (Parity)
uint32_t header; // 4 bytes (DF, CA, ICAO)
uint8_t data[7]; // 7 bytes (ADS-B payload)
uint8_t parity[3]; // 3 bytes (Parity)
} adsbExtendedMessage;

typedef struct {
uint32_t header; // 4 bytes (DF, CA, ICAO)
uint8_t parity[3]; // 3 bytes (Parity)
uint32_t header; // 4 bytes (DF, CA, ICAO)
uint8_t parity[3]; // 3 bytes (Parity)
} adsbShortMessage;

void adsb_squitter_parse(Logger *logger, const char *hex_str);

void adsb_ext_message_parse(uint8_t full_message[ADSB_EXT_LEN], Logger *logger);

void adsb_short_message_parse(uint8_t full_message[ADSB_SHORT_LEN],
Logger *logger);
Logger *logger);

#endif // ADS_B_H
12 changes: 6 additions & 6 deletions include/arg_parser.h
Original file line number Diff line number Diff line change
Expand Up @@ -5,12 +5,12 @@
#include <stdint.h>

typedef struct Options {
uint16_t tcp_port;
uint8_t verbose;
char *tcp_server;
char *log_level;
char *err_log;
char *out_log;
uint16_t tcp_port;
uint8_t verbose;
char *tcp_server;
char *log_level;
char *err_log;
char *out_log;
} Options;

void arguments_parse(int argc, char *argv[], Options *opt);
Expand Down
10 changes: 5 additions & 5 deletions include/client.h
Original file line number Diff line number Diff line change
Expand Up @@ -6,14 +6,14 @@
#include "../include/ring_buffer.h"

typedef struct {
ringBuffer *rb;
Options *opts;
Logger *logger;
ringBuffer *rb;
Options *opts;
Logger *logger;
} TcpClientArgs;

int8_t tcp_client_thread_init(TcpClientArgs *tcp_client_args,
ringBuffer *ring_buffer, Options *opts,
Logger *logger);
ringBuffer *ring_buffer, Options *opts,
Logger *logger);
void *tcp_client_thread(void *arg);

void lines_read(int sockfd, ringBuffer *rb);
Expand Down
10 changes: 5 additions & 5 deletions include/processor.h
Original file line number Diff line number Diff line change
Expand Up @@ -6,14 +6,14 @@
#include "../include/ring_buffer.h"

typedef struct {
ringBuffer *rb;
Options *opts;
Logger *logger;
ringBuffer *rb;
Options *opts;
Logger *logger;
} ProcessorArgs;

int8_t data_processor_thread_args_init(ProcessorArgs *data_processor_args,
ringBuffer *ring_buffer, Options *opts,
Logger *logger);
ringBuffer *ring_buffer, Options *opts,
Logger *logger);

void *data_processor_thread(void *arg);
size_t squitter_strip_chars(char *str);
Expand Down
12 changes: 6 additions & 6 deletions include/ring_buffer.h
Original file line number Diff line number Diff line change
Expand Up @@ -8,12 +8,12 @@
#define MAX_LINE_LENGTH 63 // Max length of a single line

typedef struct {
char buffer[BUFFER_SIZE][MAX_LINE_LENGTH + 1]; // Extra byte for '\0'
unsigned int head;
unsigned int tail;
pthread_mutex_t mutex;
pthread_cond_t not_empty;
pthread_cond_t not_full;
char buffer[BUFFER_SIZE][MAX_LINE_LENGTH + 1]; // Extra byte for '\0'
unsigned int head;
unsigned int tail;
pthread_mutex_t mutex;
pthread_cond_t not_empty;
pthread_cond_t not_full;
} ringBuffer;

void ring_buffer_init(ringBuffer *rb);
Expand Down
88 changes: 44 additions & 44 deletions src/ads_b.c
Original file line number Diff line number Diff line change
Expand Up @@ -5,74 +5,74 @@
/// @param bytes
/// @param len
void hex_to_bytes(const char *hex_str, uint8_t *bytes, size_t len) {
for (size_t i = 0; i < len; i++) {
sscanf(hex_str + 2 * i, "%2hhx", &bytes[i]);
}
for (size_t i = 0; i < len; i++) {
sscanf(hex_str + 2 * i, "%2hhx", &bytes[i]);
}
}

/// @brief Process the ADS-B hex string
/// @param logger
/// @param hex_str The hex string to process
void adsb_squitter_parse(Logger *logger, const char *hex_str) {
size_t len = strlen(hex_str);
size_t len = strlen(hex_str);

uint8_t short_message[7]; // Maximum size: 7 bytes (56 bits)
uint8_t full_message[14]; // Maximum size: 14 bytes (112 bits)
uint8_t short_message[7]; // Maximum size: 7 bytes (56 bits)
uint8_t full_message[14]; // Maximum size: 14 bytes (112 bits)

switch (len) {
case 26:
hex_to_bytes(hex_str + 12, short_message, len / 2 - 6);
adsb_short_message_parse(short_message, logger);
break;
case 40:
hex_to_bytes(hex_str + 12, full_message, len / 2 - 6);
adsb_ext_message_parse(full_message, logger);
break;
default:
error_log(logger, "Invalid hex string length\n");
break;
}
switch (len) {
case 26:
hex_to_bytes(hex_str + 12, short_message, len / 2 - 6);
adsb_short_message_parse(short_message, logger);
break;
case 40:
hex_to_bytes(hex_str + 12, full_message, len / 2 - 6);
adsb_ext_message_parse(full_message, logger);
break;
default:
error_log(logger, "Invalid hex string length\n");
break;
}
}

/// @brief Process an extended message
/// @param full_message
/// @param logger
void adsb_ext_message_parse(uint8_t full_message[ADSB_EXT_LEN],
Logger *logger) {
adsbExtendedMessage msg_ext;
msg_ext.header = (full_message[0] << 24) | (full_message[1] << 16) |
(full_message[2] << 8) | full_message[3];
memcpy(msg_ext.data, full_message + 4, 7);
memcpy(msg_ext.parity, full_message + 11, 3);
Logger *logger) {
adsbExtendedMessage msg_ext;
msg_ext.header = (full_message[0] << 24) | (full_message[1] << 16) |
(full_message[2] << 8) | full_message[3];
memcpy(msg_ext.data, full_message + 4, 7);
memcpy(msg_ext.parity, full_message + 11, 3);

char data_str[3 * 7]; // Each byte: "XX " (3 chars), 7 bytes -> 21 chars
char parity_str[3 * 3]; // Each byte: "XX " (3 chars), 3 bytes -> 9 chars
char data_str[3 * 7]; // Each byte: "XX " (3 chars), 7 bytes -> 21 chars
char parity_str[3 * 3]; // Each byte: "XX " (3 chars), 3 bytes -> 9 chars

snprintf(data_str, sizeof(data_str), "%02X %02X %02X %02X %02X %02X %02X",
msg_ext.data[0], msg_ext.data[1], msg_ext.data[2], msg_ext.data[3],
msg_ext.data[4], msg_ext.data[5], msg_ext.data[6]);
snprintf(data_str, sizeof(data_str), "%02X %02X %02X %02X %02X %02X %02X",
msg_ext.data[0], msg_ext.data[1], msg_ext.data[2], msg_ext.data[3],
msg_ext.data[4], msg_ext.data[5], msg_ext.data[6]);

snprintf(parity_str, sizeof(parity_str), "%02X %02X %02X", msg_ext.parity[0],
msg_ext.parity[1], msg_ext.parity[2]);
snprintf(parity_str, sizeof(parity_str), "%02X %02X %02X", msg_ext.parity[0],
msg_ext.parity[1], msg_ext.parity[2]);

info_log_formatted(logger, "\nHeader: 0x%08X\nData: %s\nParity: %s",
msg_ext.header, data_str, parity_str);
info_log_formatted(logger, "\nHeader: 0x%08X\nData: %s\nParity: %s",
msg_ext.header, data_str, parity_str);
}

/// @brief Process a short message
/// @param full_message
/// @param logger
void adsb_short_message_parse(uint8_t full_message[ADSB_SHORT_LEN],
Logger *logger) {
adsbShortMessage msg_short;
msg_short.header = (full_message[0] << 24) | (full_message[1] << 16) |
(full_message[2] << 8) | full_message[3];
memcpy(msg_short.parity, full_message + 4, 3);
Logger *logger) {
adsbShortMessage msg_short;
msg_short.header = (full_message[0] << 24) | (full_message[1] << 16) |
(full_message[2] << 8) | full_message[3];
memcpy(msg_short.parity, full_message + 4, 3);

char parity_str[3 * 3]; // Enough for "XX XX XX\0"
snprintf(parity_str, sizeof(parity_str), "%02X %02X %02X",
msg_short.parity[0], msg_short.parity[1], msg_short.parity[2]);
char parity_str[3 * 3]; // Enough for "XX XX XX\0"
snprintf(parity_str, sizeof(parity_str), "%02X %02X %02X",
msg_short.parity[0], msg_short.parity[1], msg_short.parity[2]);

info_log_formatted(logger, "\nHeader: 0x%08X\nParity: %s", msg_short.header,
parity_str);
info_log_formatted(logger, "\nHeader: 0x%08X\nParity: %s", msg_short.header,
parity_str);
}
116 changes: 58 additions & 58 deletions src/arg_parser.c
Original file line number Diff line number Diff line change
Expand Up @@ -13,64 +13,64 @@
*/
void arguments_parse(int argc, char *argv[], Options *opts) {

opts->tcp_server = "172.22.132.124";
opts->tcp_port = 30002;
opts->verbose = 0;
opts->err_log = NULL;
opts->out_log = NULL;
opts->log_level = "ERROR";
opts->tcp_server = "172.22.132.124";
opts->tcp_port = 30002;
opts->verbose = 0;
opts->err_log = NULL;
opts->out_log = NULL;
opts->log_level = "ERROR";

static struct option long_options[] = {
{"tcp-server", optional_argument, 0, 't'},
{"tcp-port", optional_argument, 0, 'p'},
{"log", optional_argument, 0, 'o'},
{"error-log", optional_argument, 0, 'e'},
{"log-level", optional_argument, 0, 'l'},
{"verbose", no_argument, 0, 'v'},
{"help", no_argument, 0, 'h'},
{0, 0, 0, 0}};
static struct option long_options[] = {
{"tcp-server", optional_argument, 0, 't'},
{"tcp-port", optional_argument, 0, 'p'},
{"log", optional_argument, 0, 'o'},
{"error-log", optional_argument, 0, 'e'},
{"log-level", optional_argument, 0, 'l'},
{"verbose", no_argument, 0, 'v'},
{"help", no_argument, 0, 'h'},
{0, 0, 0, 0}};

int opt;
while ((opt = getopt_long(argc, argv, "t:p:o:e:l:vh", long_options, NULL)) !=
-1) {
switch (opt) {
case 't':
if (optarg) {
opts->tcp_server = optarg;
}
break;
case 'p':
if (optarg) {
opts->tcp_port = atoi(optarg);
}
break;
case 'o':
if (optarg) {
opts->out_log = optarg;
}
break;
case 'e':
if (optarg) {
opts->err_log = optarg;
}
break;
case 'l':
if (optarg) {
opts->log_level = optarg;
to_upper_case(opts->log_level);
}
break;
case 'v':
opts->verbose = 1;
break;
case 'h':
printf("Usage: %s [-t | --tcp-server <ip.ad.dr.es>] [-p | --tcp-port "
"value] [-o | --log value] [-e | --error-log value] [-l | "
"--log-level value [-v | --verbose] [-h | --help]\n",
argv[0]);
exit(0);
default:
exit(1);
}
}
int opt;
while ((opt = getopt_long(argc, argv, "t:p:o:e:l:vh", long_options, NULL)) !=
-1) {
switch (opt) {
case 't':
if (optarg) {
opts->tcp_server = optarg;
}
break;
case 'p':
if (optarg) {
opts->tcp_port = atoi(optarg);
}
break;
case 'o':
if (optarg) {
opts->out_log = optarg;
}
break;
case 'e':
if (optarg) {
opts->err_log = optarg;
}
break;
case 'l':
if (optarg) {
opts->log_level = optarg;
to_upper_case(opts->log_level);
}
break;
case 'v':
opts->verbose = 1;
break;
case 'h':
printf("Usage: %s [-t | --tcp-server <ip.ad.dr.es>] [-p | --tcp-port "
"value] [-o | --log value] [-e | --error-log value] [-l | "
"--log-level value [-v | --verbose] [-h | --help]\n",
argv[0]);
exit(0);
default:
exit(1);
}
}
}
Loading