Implement better handling of command/response bits
Implement better handling of command/response bits whilst decoding and encoding addresses Changes: * Add an enum patty_ax25_frame_cr argument to functions in src/sock.c which send specific types of frames * Detect AX.25 version >2.0 based on the command/response SSID bits * Simplify address copying/encoding by usage of the new function patty_ax25_addr_copy() * Implement showing AX.25 version, command/response indicator for frames in src/print.c
This commit is contained in:
parent
79d1393e74
commit
9066fe10da
6 changed files with 99 additions and 55 deletions
|
@ -13,6 +13,7 @@ enum patty_ax25_frame_format {
|
||||||
};
|
};
|
||||||
|
|
||||||
enum patty_ax25_frame_cr {
|
enum patty_ax25_frame_cr {
|
||||||
|
PATTY_AX25_FRAME_OLD,
|
||||||
PATTY_AX25_FRAME_COMMAND,
|
PATTY_AX25_FRAME_COMMAND,
|
||||||
PATTY_AX25_FRAME_RESPONSE
|
PATTY_AX25_FRAME_RESPONSE
|
||||||
};
|
};
|
||||||
|
@ -72,7 +73,9 @@ typedef struct _patty_ax25_frame {
|
||||||
|
|
||||||
uint16_t control;
|
uint16_t control;
|
||||||
uint8_t nr, ns, pf;
|
uint8_t nr, ns, pf;
|
||||||
|
enum patty_ax25_frame_cr cr;
|
||||||
enum patty_ax25_frame_type type;
|
enum patty_ax25_frame_type type;
|
||||||
|
enum patty_ax25_version version;
|
||||||
|
|
||||||
uint8_t proto;
|
uint8_t proto;
|
||||||
void *info;
|
void *info;
|
||||||
|
|
|
@ -75,17 +75,22 @@ void patty_ax25_sock_seq_send_incr(patty_ax25_sock *sock);
|
||||||
void patty_ax25_sock_seq_recv_incr(patty_ax25_sock *sock);
|
void patty_ax25_sock_seq_recv_incr(patty_ax25_sock *sock);
|
||||||
|
|
||||||
ssize_t patty_ax25_sock_send(patty_ax25_sock *sock,
|
ssize_t patty_ax25_sock_send(patty_ax25_sock *sock,
|
||||||
|
enum patty_ax25_frame_cr cr,
|
||||||
uint16_t control,
|
uint16_t control,
|
||||||
void *info,
|
void *info,
|
||||||
size_t infolen);
|
size_t infolen);
|
||||||
|
|
||||||
ssize_t patty_ax25_sock_send_rr(patty_ax25_sock *sock);
|
ssize_t patty_ax25_sock_send_rr(patty_ax25_sock *sock,
|
||||||
|
enum patty_ax25_frame_cr cr);
|
||||||
|
|
||||||
ssize_t patty_ax25_sock_send_rnr(patty_ax25_sock *sock);
|
ssize_t patty_ax25_sock_send_rnr(patty_ax25_sock *sock,
|
||||||
|
enum patty_ax25_frame_cr cr);
|
||||||
|
|
||||||
ssize_t patty_ax25_sock_send_rej(patty_ax25_sock *sock);
|
ssize_t patty_ax25_sock_send_rej(patty_ax25_sock *sock,
|
||||||
|
enum patty_ax25_frame_cr cr);
|
||||||
|
|
||||||
ssize_t patty_ax25_sock_send_srej(patty_ax25_sock *sock);
|
ssize_t patty_ax25_sock_send_srej(patty_ax25_sock *sock,
|
||||||
|
enum patty_ax25_frame_cr cr);
|
||||||
|
|
||||||
ssize_t patty_ax25_sock_send_sabm(patty_ax25_sock *sock, int flag);
|
ssize_t patty_ax25_sock_send_sabm(patty_ax25_sock *sock, int flag);
|
||||||
|
|
||||||
|
|
38
src/frame.c
38
src/frame.c
|
@ -109,6 +109,18 @@ ssize_t patty_ax25_frame_decode_address(patty_ax25_frame *frame,
|
||||||
offset += decoded;
|
offset += decoded;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (PATTY_AX25_ADDR_SSID_C(frame->dest.ssid) != PATTY_AX25_ADDR_SSID_C(frame->src.ssid)) {
|
||||||
|
frame->cr = PATTY_AX25_ADDR_SSID_C(frame->dest.ssid)?
|
||||||
|
PATTY_AX25_FRAME_COMMAND:
|
||||||
|
PATTY_AX25_FRAME_RESPONSE;
|
||||||
|
|
||||||
|
frame->version = PATTY_AX25_2_0;
|
||||||
|
|
||||||
|
} else {
|
||||||
|
frame->cr = PATTY_AX25_FRAME_OLD;
|
||||||
|
frame->version = PATTY_AX25_OLD;
|
||||||
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* If the source address is not the final address in the frame, begin
|
* If the source address is not the final address in the frame, begin
|
||||||
* decoding repeater addresses.
|
* decoding repeater addresses.
|
||||||
|
@ -313,29 +325,21 @@ static ssize_t encode_reply_address(patty_ax25_frame *frame,
|
||||||
hops = frame->hops > PATTY_AX25_MAX_HOPS?
|
hops = frame->hops > PATTY_AX25_MAX_HOPS?
|
||||||
PATTY_AX25_MAX_HOPS: frame->hops;
|
PATTY_AX25_MAX_HOPS: frame->hops;
|
||||||
|
|
||||||
|
uint8_t *buf = dest;
|
||||||
|
|
||||||
if ((2 + hops) * sizeof(patty_ax25_addr) > len) {
|
if ((2 + hops) * sizeof(patty_ax25_addr) > len) {
|
||||||
goto error_toobig;
|
goto error_toobig;
|
||||||
}
|
}
|
||||||
|
|
||||||
memcpy((uint8_t *)dest + offset, &frame->src, sizeof(patty_ax25_addr));
|
offset += patty_ax25_addr_copy(buf + offset, &frame->src, 0x00);
|
||||||
offset += sizeof(patty_ax25_addr);
|
offset += patty_ax25_addr_copy(buf + offset, &frame->dest, 0x80);
|
||||||
((uint8_t *)dest)[offset-1] &= ~1;
|
|
||||||
|
|
||||||
memcpy((uint8_t *)dest + offset, &frame->dest, sizeof(patty_ax25_addr));
|
|
||||||
offset += sizeof(patty_ax25_addr);
|
|
||||||
((uint8_t *)dest)[offset-1] &= ~1;
|
|
||||||
|
|
||||||
for (i=0; i<hops; i++) {
|
for (i=0; i<hops; i++) {
|
||||||
if (frame->repeaters[i].callsign[0] == '\0') {
|
if (frame->repeaters[i].callsign[0] == '\0') {
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
memcpy((uint8_t *)dest + offset,
|
offset += patty_ax25_addr_copy(buf + offset, &frame->repeaters[hops-1-i], 0);
|
||||||
&frame->repeaters[hops-1-i],
|
|
||||||
sizeof(patty_ax25_addr));
|
|
||||||
|
|
||||||
offset += sizeof(patty_ax25_addr);
|
|
||||||
((uint8_t *)dest)[offset-1] &= ~1;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
((uint8_t *)dest)[offset-1] |= 1;
|
((uint8_t *)dest)[offset-1] |= 1;
|
||||||
|
@ -435,9 +439,7 @@ error_toobig:
|
||||||
}
|
}
|
||||||
|
|
||||||
enum patty_ax25_version patty_ax25_frame_version(patty_ax25_frame *frame) {
|
enum patty_ax25_version patty_ax25_frame_version(patty_ax25_frame *frame) {
|
||||||
return PATTY_AX25_ADDR_SSID_C(frame->src.ssid) ==
|
return frame->version;
|
||||||
PATTY_AX25_ADDR_SSID_C(frame->dest.ssid)?
|
|
||||||
PATTY_AX25_2_0: PATTY_AX25_OLD;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
enum patty_ax25_frame_type patty_ax25_frame_type(patty_ax25_frame *frame) {
|
enum patty_ax25_frame_type patty_ax25_frame_type(patty_ax25_frame *frame) {
|
||||||
|
@ -445,9 +447,7 @@ enum patty_ax25_frame_type patty_ax25_frame_type(patty_ax25_frame *frame) {
|
||||||
}
|
}
|
||||||
|
|
||||||
enum patty_ax25_frame_cr patty_ax25_frame_cr(patty_ax25_frame *frame) {
|
enum patty_ax25_frame_cr patty_ax25_frame_cr(patty_ax25_frame *frame) {
|
||||||
return PATTY_AX25_ADDR_SSID_C(frame->src.ssid)?
|
return frame->cr;
|
||||||
PATTY_AX25_FRAME_RESPONSE:
|
|
||||||
PATTY_AX25_FRAME_COMMAND;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
ssize_t patty_ax25_frame_info(patty_ax25_frame *frame,
|
ssize_t patty_ax25_frame_info(patty_ax25_frame *frame,
|
||||||
|
|
40
src/print.c
40
src/print.c
|
@ -7,7 +7,7 @@
|
||||||
#define printable(c) \
|
#define printable(c) \
|
||||||
(c >= 0x20 && c < 0x7f)
|
(c >= 0x20 && c < 0x7f)
|
||||||
|
|
||||||
static char *frame_type_name(enum patty_ax25_frame_type type) {
|
static char *frame_type(enum patty_ax25_frame_type type) {
|
||||||
switch (type) {
|
switch (type) {
|
||||||
case PATTY_AX25_FRAME_I: return "I";
|
case PATTY_AX25_FRAME_I: return "I";
|
||||||
case PATTY_AX25_FRAME_RR: return "RR";
|
case PATTY_AX25_FRAME_RR: return "RR";
|
||||||
|
@ -31,6 +31,26 @@ static char *frame_type_name(enum patty_ax25_frame_type type) {
|
||||||
return "unknown";
|
return "unknown";
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static char *version(enum patty_ax25_version version) {
|
||||||
|
switch (version) {
|
||||||
|
case PATTY_AX25_2_0: return "v2.0";
|
||||||
|
case PATTY_AX25_2_2: return "v2.2";
|
||||||
|
case PATTY_AX25_OLD: return "old";
|
||||||
|
}
|
||||||
|
|
||||||
|
return "unknown";
|
||||||
|
}
|
||||||
|
|
||||||
|
static char *frame_cr(enum patty_ax25_frame_cr cr) {
|
||||||
|
switch (cr) {
|
||||||
|
case PATTY_AX25_FRAME_COMMAND: return "command";
|
||||||
|
case PATTY_AX25_FRAME_RESPONSE: return "response";
|
||||||
|
case PATTY_AX25_FRAME_OLD: return "?";
|
||||||
|
}
|
||||||
|
|
||||||
|
return "unknown";
|
||||||
|
}
|
||||||
|
|
||||||
int patty_print_hexdump(FILE *fh, void *data, size_t len) {
|
int patty_print_hexdump(FILE *fh, void *data, size_t len) {
|
||||||
size_t i;
|
size_t i;
|
||||||
|
|
||||||
|
@ -128,8 +148,10 @@ int patty_print_frame(FILE *fh,
|
||||||
}
|
}
|
||||||
|
|
||||||
if (PATTY_AX25_FRAME_CONTROL_I(frame->control)) {
|
if (PATTY_AX25_FRAME_CONTROL_I(frame->control)) {
|
||||||
if (fprintf(fh, " type I (%s) nr %d ns %d pf %d info %zu bytes",
|
if (fprintf(fh, " type I (%s) %s %s nr %d ns %d pf %d info %zu bytes",
|
||||||
frame_type_name(frame->type),
|
frame_type(frame->type),
|
||||||
|
version(frame->version),
|
||||||
|
frame_cr(frame->cr),
|
||||||
(int)frame->nr,
|
(int)frame->nr,
|
||||||
(int)frame->ns,
|
(int)frame->ns,
|
||||||
(int)frame->pf,
|
(int)frame->pf,
|
||||||
|
@ -137,8 +159,10 @@ int patty_print_frame(FILE *fh,
|
||||||
goto error_io;
|
goto error_io;
|
||||||
}
|
}
|
||||||
} else if (PATTY_AX25_FRAME_CONTROL_U(frame->control)) {
|
} else if (PATTY_AX25_FRAME_CONTROL_U(frame->control)) {
|
||||||
if (fprintf(fh, " type U (%s) pf %d",
|
if (fprintf(fh, " type U (%s) %s %s pf %d",
|
||||||
frame_type_name(frame->type),
|
frame_type(frame->type),
|
||||||
|
version(frame->version),
|
||||||
|
frame_cr(frame->cr),
|
||||||
(int)frame->pf) < 0) {
|
(int)frame->pf) < 0) {
|
||||||
goto error_io;
|
goto error_io;
|
||||||
}
|
}
|
||||||
|
@ -149,8 +173,10 @@ int patty_print_frame(FILE *fh,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
} else if (PATTY_AX25_FRAME_CONTROL_S(frame->control)) {
|
} else if (PATTY_AX25_FRAME_CONTROL_S(frame->control)) {
|
||||||
if (fprintf(fh, " type S (%s) nr %d pf %d",
|
if (fprintf(fh, " type S (%s) %s %s nr %d pf %d",
|
||||||
frame_type_name(frame->type),
|
frame_type(frame->type),
|
||||||
|
version(frame->version),
|
||||||
|
frame_cr(frame->cr),
|
||||||
(int)frame->nr,
|
(int)frame->nr,
|
||||||
(int)frame->pf) < 0) {
|
(int)frame->pf) < 0) {
|
||||||
goto error_io;
|
goto error_io;
|
||||||
|
|
|
@ -1244,7 +1244,7 @@ static int handle_i(patty_ax25_server *server,
|
||||||
if (sock->seq_recv == frame->ns) {
|
if (sock->seq_recv == frame->ns) {
|
||||||
patty_ax25_sock_seq_recv_incr(sock);
|
patty_ax25_sock_seq_recv_incr(sock);
|
||||||
} else {
|
} else {
|
||||||
return patty_ax25_sock_send_rej(sock);
|
return patty_ax25_sock_send_rej(sock, PATTY_AX25_FRAME_RESPONSE);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (write(sock->fd, frame->info, frame->infolen) < 0) {
|
if (write(sock->fd, frame->info, frame->infolen) < 0) {
|
||||||
|
@ -1252,7 +1252,7 @@ static int handle_i(patty_ax25_server *server,
|
||||||
}
|
}
|
||||||
|
|
||||||
if (frame->pf) {
|
if (frame->pf) {
|
||||||
return patty_ax25_sock_send_rr(sock);
|
return patty_ax25_sock_send_rr(sock, PATTY_AX25_FRAME_RESPONSE);
|
||||||
}
|
}
|
||||||
|
|
||||||
return 0;
|
return 0;
|
||||||
|
|
56
src/sock.c
56
src/sock.c
|
@ -154,29 +154,27 @@ void patty_ax25_sock_seq_recv_incr(patty_ax25_sock *sock) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
static size_t copy_addr_to_tx_buf(patty_ax25_sock *sock) {
|
static size_t addr_copy_to_tx_buf(patty_ax25_sock *sock,
|
||||||
void *buf = sock->iface->tx_buf;
|
enum patty_ax25_frame_cr cr) {
|
||||||
|
uint8_t *buf = sock->iface->tx_buf;
|
||||||
|
size_t offset = 0;
|
||||||
|
|
||||||
|
uint8_t flags_remote = 0x00,
|
||||||
|
flags_local = 0x00;
|
||||||
|
|
||||||
unsigned int i;
|
unsigned int i;
|
||||||
|
|
||||||
size_t offset = 0;
|
switch (cr) {
|
||||||
|
case PATTY_AX25_FRAME_COMMAND: flags_remote = 0x80; break;
|
||||||
|
case PATTY_AX25_FRAME_RESPONSE: flags_local = 0x80; break;
|
||||||
|
case PATTY_AX25_FRAME_OLD: break;
|
||||||
|
}
|
||||||
|
|
||||||
memcpy((uint8_t *)buf + offset, &sock->remote, sizeof(patty_ax25_addr));
|
offset += patty_ax25_addr_copy(buf + offset, &sock->remote, flags_remote);
|
||||||
offset += sizeof(patty_ax25_addr);
|
offset += patty_ax25_addr_copy(buf + offset, &sock->local, flags_local);
|
||||||
((uint8_t *)buf)[offset-1] &= ~1;
|
|
||||||
|
|
||||||
memcpy((uint8_t *)buf + offset, &sock->local, sizeof(patty_ax25_addr));
|
|
||||||
offset += sizeof(patty_ax25_addr);
|
|
||||||
((uint8_t *)buf)[offset-1] &= ~1;
|
|
||||||
|
|
||||||
for (i=0; i<sock->hops; i++) {
|
for (i=0; i<sock->hops; i++) {
|
||||||
memcpy((uint8_t *)buf + offset,
|
offset += patty_ax25_addr_copy(buf + offset, &sock->repeaters[i], 0);
|
||||||
&sock->repeaters[i],
|
|
||||||
sizeof(patty_ax25_addr));
|
|
||||||
|
|
||||||
offset += sizeof(patty_ax25_addr);
|
|
||||||
|
|
||||||
((uint8_t *)buf)[offset-1] &= ~1;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
((uint8_t *)buf)[offset-1] |= 1;
|
((uint8_t *)buf)[offset-1] |= 1;
|
||||||
|
@ -196,6 +194,7 @@ static inline int toobig(patty_ax25_sock *sock,
|
||||||
}
|
}
|
||||||
|
|
||||||
ssize_t patty_ax25_sock_send(patty_ax25_sock *sock,
|
ssize_t patty_ax25_sock_send(patty_ax25_sock *sock,
|
||||||
|
enum patty_ax25_frame_cr cr,
|
||||||
uint16_t control,
|
uint16_t control,
|
||||||
void *info,
|
void *info,
|
||||||
size_t infolen) {
|
size_t infolen) {
|
||||||
|
@ -206,7 +205,7 @@ ssize_t patty_ax25_sock_send(patty_ax25_sock *sock,
|
||||||
goto error_toobig;
|
goto error_toobig;
|
||||||
}
|
}
|
||||||
|
|
||||||
offset = copy_addr_to_tx_buf(sock);
|
offset = addr_copy_to_tx_buf(sock, cr);
|
||||||
|
|
||||||
if (sock->mode == PATTY_AX25_SOCK_SABME) {
|
if (sock->mode == PATTY_AX25_SOCK_SABME) {
|
||||||
buf[offset++] = (control & 0xff00) >> 8;
|
buf[offset++] = (control & 0xff00) >> 8;
|
||||||
|
@ -270,29 +269,37 @@ static uint16_t control_u(enum patty_ax25_frame_type type,
|
||||||
| (flag << 4);
|
| (flag << 4);
|
||||||
}
|
}
|
||||||
|
|
||||||
ssize_t patty_ax25_sock_send_rr(patty_ax25_sock *sock) {
|
ssize_t patty_ax25_sock_send_rr(patty_ax25_sock *sock,
|
||||||
|
enum patty_ax25_frame_cr cr) {
|
||||||
return patty_ax25_sock_send(sock,
|
return patty_ax25_sock_send(sock,
|
||||||
|
cr,
|
||||||
control_s(sock, PATTY_AX25_FRAME_RR, 1),
|
control_s(sock, PATTY_AX25_FRAME_RR, 1),
|
||||||
NULL,
|
NULL,
|
||||||
0);
|
0);
|
||||||
}
|
}
|
||||||
|
|
||||||
ssize_t patty_ax25_sock_send_rnr(patty_ax25_sock *sock) {
|
ssize_t patty_ax25_sock_send_rnr(patty_ax25_sock *sock,
|
||||||
|
enum patty_ax25_frame_cr cr) {
|
||||||
return patty_ax25_sock_send(sock,
|
return patty_ax25_sock_send(sock,
|
||||||
|
cr,
|
||||||
control_s(sock, PATTY_AX25_FRAME_RNR, 1),
|
control_s(sock, PATTY_AX25_FRAME_RNR, 1),
|
||||||
NULL,
|
NULL,
|
||||||
0);
|
0);
|
||||||
}
|
}
|
||||||
|
|
||||||
ssize_t patty_ax25_sock_send_rej(patty_ax25_sock *sock) {
|
ssize_t patty_ax25_sock_send_rej(patty_ax25_sock *sock,
|
||||||
|
enum patty_ax25_frame_cr cr) {
|
||||||
return patty_ax25_sock_send(sock,
|
return patty_ax25_sock_send(sock,
|
||||||
|
cr,
|
||||||
control_s(sock, PATTY_AX25_FRAME_REJ, 1),
|
control_s(sock, PATTY_AX25_FRAME_REJ, 1),
|
||||||
NULL,
|
NULL,
|
||||||
0);
|
0);
|
||||||
}
|
}
|
||||||
|
|
||||||
ssize_t patty_ax25_sock_send_srej(patty_ax25_sock *sock) {
|
ssize_t patty_ax25_sock_send_srej(patty_ax25_sock *sock,
|
||||||
|
enum patty_ax25_frame_cr cr) {
|
||||||
return patty_ax25_sock_send(sock,
|
return patty_ax25_sock_send(sock,
|
||||||
|
cr,
|
||||||
control_s(sock, PATTY_AX25_FRAME_SREJ, 1),
|
control_s(sock, PATTY_AX25_FRAME_SREJ, 1),
|
||||||
NULL,
|
NULL,
|
||||||
0);
|
0);
|
||||||
|
@ -300,6 +307,7 @@ ssize_t patty_ax25_sock_send_srej(patty_ax25_sock *sock) {
|
||||||
|
|
||||||
ssize_t patty_ax25_sock_send_sabm(patty_ax25_sock *sock, int flag) {
|
ssize_t patty_ax25_sock_send_sabm(patty_ax25_sock *sock, int flag) {
|
||||||
return patty_ax25_sock_send(sock,
|
return patty_ax25_sock_send(sock,
|
||||||
|
PATTY_AX25_FRAME_COMMAND,
|
||||||
control_u(PATTY_AX25_FRAME_SABM, flag),
|
control_u(PATTY_AX25_FRAME_SABM, flag),
|
||||||
NULL,
|
NULL,
|
||||||
0);
|
0);
|
||||||
|
@ -307,6 +315,7 @@ ssize_t patty_ax25_sock_send_sabm(patty_ax25_sock *sock, int flag) {
|
||||||
|
|
||||||
ssize_t patty_ax25_sock_send_sabme(patty_ax25_sock *sock, int flag) {
|
ssize_t patty_ax25_sock_send_sabme(patty_ax25_sock *sock, int flag) {
|
||||||
return patty_ax25_sock_send(sock,
|
return patty_ax25_sock_send(sock,
|
||||||
|
PATTY_AX25_FRAME_COMMAND,
|
||||||
control_u(PATTY_AX25_FRAME_SABME, flag),
|
control_u(PATTY_AX25_FRAME_SABME, flag),
|
||||||
NULL,
|
NULL,
|
||||||
0);
|
0);
|
||||||
|
@ -314,6 +323,7 @@ ssize_t patty_ax25_sock_send_sabme(patty_ax25_sock *sock, int flag) {
|
||||||
|
|
||||||
ssize_t patty_ax25_sock_send_disc(patty_ax25_sock *sock, int flag) {
|
ssize_t patty_ax25_sock_send_disc(patty_ax25_sock *sock, int flag) {
|
||||||
return patty_ax25_sock_send(sock,
|
return patty_ax25_sock_send(sock,
|
||||||
|
PATTY_AX25_FRAME_COMMAND,
|
||||||
control_u(PATTY_AX25_FRAME_DISC, flag),
|
control_u(PATTY_AX25_FRAME_DISC, flag),
|
||||||
NULL,
|
NULL,
|
||||||
0);
|
0);
|
||||||
|
@ -336,7 +346,7 @@ ssize_t patty_ax25_sock_write(patty_ax25_sock *sock,
|
||||||
|
|
||||||
control = control_i(sock, 0);
|
control = control_i(sock, 0);
|
||||||
|
|
||||||
if (patty_ax25_sock_send(sock, control, buf, len) < 0) {
|
if (patty_ax25_sock_send(sock, PATTY_AX25_FRAME_RESPONSE, control, buf, len) < 0) {
|
||||||
goto error_send;
|
goto error_send;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
Loading…
Add table
Reference in a new issue