kopia lustrzana https://github.com/Hamlib/Hamlib
Refactor WIN32 I/O port routines to be hopefully compatible with async data reader (not tested). Fix some incomplete data fields in UDP snapshot packets.
rodzic
d857f18163
commit
c20f397c24
|
@ -211,12 +211,14 @@ typedef struct s_rig RIG;
|
|||
#define HAMLIB_MAX_SPECTRUM_MODES 5 /* max number of spectrum modes supported */
|
||||
#define HAMLIB_MAX_SPECTRUM_AVG_MODES 12 /* max number of spectrum averaging modes supported */
|
||||
#define HAMLIB_MAX_SPECTRUM_SPANS 20 /* max number of spectrum modes supported */
|
||||
#define HAMLIB_MAX_SPECTRUM_DATA 2048 /* max number of data bytes in a single spectrum line */
|
||||
#define HAMLIB_MAX_CAL_LENGTH 32 /* max calibration plots in cal_table_t */
|
||||
#define HAMLIB_MAX_MODES 63
|
||||
#define HAMLIB_MAX_VFOS 31
|
||||
#define HAMLIB_MAX_ROTORS 63
|
||||
#define HAMLIB_MAX_VFO_OPS 31
|
||||
#define HAMLIB_MAX_RSCANS 31
|
||||
#define HAMLIB_MAX_SNAPSHOT_PACKET_SIZE 16384 /* maximum number of bytes in a UDP snapshot packet */
|
||||
//! @endcond
|
||||
|
||||
|
||||
|
|
|
@ -751,11 +751,11 @@ int rig_fire_spectrum_event(RIG *rig, struct rig_spectrum_line *line)
|
|||
{
|
||||
ENTERFUNC;
|
||||
|
||||
if (rig_need_debug(RIG_DEBUG_ERR))
|
||||
if (rig_need_debug(RIG_DEBUG_TRACE))
|
||||
{
|
||||
char spectrum_debug[line->spectrum_data_length * 4];
|
||||
print_spectrum_line(spectrum_debug, sizeof(spectrum_debug), line);
|
||||
rig_debug(RIG_DEBUG_ERR, "%s: ASCII Spectrum Scope: %s\n", __func__,
|
||||
rig_debug(RIG_DEBUG_TRACE, "%s: ASCII Spectrum Scope: %s\n", __func__,
|
||||
spectrum_debug);
|
||||
}
|
||||
|
||||
|
|
69
src/iofunc.c
69
src/iofunc.c
|
@ -310,26 +310,26 @@ extern int is_uh_radio_fd(int fd);
|
|||
/* On MinGW32/MSVC/.. the appropriate accessor must be used
|
||||
* depending on the port type, sigh.
|
||||
*/
|
||||
static ssize_t port_read(hamlib_port_t *p, void *buf, size_t count)
|
||||
static ssize_t port_read_generic(hamlib_port_t *p, void *buf, size_t count, int direct)
|
||||
{
|
||||
int fd = direct ? p->fd : p->fd_sync_read;
|
||||
int i;
|
||||
ssize_t ret;
|
||||
|
||||
//ENTERFUNC; // too verbose
|
||||
/*
|
||||
* Since WIN32 does its special serial read, we have
|
||||
* to catch the microHam case to do just "read".
|
||||
* Note that we always have RIG_PORT_SERIAL in the
|
||||
* microHam case.
|
||||
*/
|
||||
if (is_uh_radio_fd(p->fd))
|
||||
if (direct && is_uh_radio_fd(fd))
|
||||
{
|
||||
return read(p->fd, buf, count);
|
||||
return read(fd, buf, count);
|
||||
}
|
||||
|
||||
if (p->type.rig == RIG_PORT_SERIAL)
|
||||
if (direct && p->type.rig == RIG_PORT_SERIAL)
|
||||
{
|
||||
ret = win32_serial_read(p->fd, buf, count);
|
||||
ret = win32_serial_read(fd, buf, (int) count);
|
||||
|
||||
if (p->parm.serial.data_bits == 7)
|
||||
{
|
||||
|
@ -342,17 +342,15 @@ static ssize_t port_read(hamlib_port_t *p, void *buf, size_t count)
|
|||
}
|
||||
}
|
||||
|
||||
//RETURNFUNC(ret); // too verbose
|
||||
return ret;
|
||||
}
|
||||
else if (p->type.rig == RIG_PORT_NETWORK
|
||||
|| p->type.rig == RIG_PORT_UDP_NETWORK)
|
||||
else if (direct && (p->type.rig == RIG_PORT_NETWORK || p->type.rig == RIG_PORT_UDP_NETWORK))
|
||||
{
|
||||
return recv(p->fd, buf, count, 0);
|
||||
return recv(fd, buf, count, 0);
|
||||
}
|
||||
else
|
||||
{
|
||||
return read(p->fd, buf, count);
|
||||
return read(fd, buf, count);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -371,7 +369,7 @@ static ssize_t port_write(hamlib_port_t *p, const void *buf, size_t count)
|
|||
|
||||
if (p->type.rig == RIG_PORT_SERIAL)
|
||||
{
|
||||
return win32_serial_write(p->fd, buf, count);
|
||||
return win32_serial_write(p->fd, buf, (int) count);
|
||||
}
|
||||
else if (p->type.rig == RIG_PORT_NETWORK
|
||||
|| p->type.rig == RIG_PORT_UDP_NETWORK)
|
||||
|
@ -390,7 +388,8 @@ static int port_select(hamlib_port_t *p,
|
|||
fd_set *readfds,
|
||||
fd_set *writefds,
|
||||
fd_set *exceptfds,
|
||||
struct timeval *timeout)
|
||||
struct timeval *timeout,
|
||||
int direct)
|
||||
{
|
||||
#if 1
|
||||
|
||||
|
@ -417,12 +416,12 @@ static int port_select(hamlib_port_t *p,
|
|||
* Note that we always have RIG_PORT_SERIAL in the
|
||||
* microHam case.
|
||||
*/
|
||||
if (is_uh_radio_fd(p->fd))
|
||||
if (direct && is_uh_radio_fd(p->fd))
|
||||
{
|
||||
return select(n, readfds, writefds, exceptfds, timeout);
|
||||
}
|
||||
|
||||
if (p->type.rig == RIG_PORT_SERIAL)
|
||||
if (direct && p->type.rig == RIG_PORT_SERIAL)
|
||||
{
|
||||
return win32_serial_select(n, readfds, writefds, exceptfds, timeout);
|
||||
}
|
||||
|
@ -465,7 +464,7 @@ static ssize_t port_read_generic(hamlib_port_t *p, void *buf, size_t count, int
|
|||
|
||||
//! @cond Doxygen_Suppress
|
||||
#define port_write(p,b,c) write((p)->fd,(b),(c))
|
||||
#define port_select(p,n,r,w,e,t) select((n),(r),(w),(e),(t))
|
||||
#define port_select(p,n,r,w,e,t,d) select((n),(r),(w),(e),(t))
|
||||
//! @endcond
|
||||
|
||||
#endif
|
||||
|
@ -503,8 +502,6 @@ int HAMLIB_API write_block(hamlib_port_t *p, const unsigned char *txbuffer, size
|
|||
{
|
||||
int ret;
|
||||
|
||||
//rig_debug(RIG_DEBUG_VERBOSE, "%s called\n", __func__);
|
||||
|
||||
#ifdef WANT_NON_ACTIVE_POST_WRITE_DELAY
|
||||
|
||||
if (p->post_write_date.tv_sec != 0)
|
||||
|
@ -599,14 +596,22 @@ int HAMLIB_API write_block(hamlib_port_t *p, const unsigned char *txbuffer, size
|
|||
|
||||
int HAMLIB_API write_block_sync(hamlib_port_t *p, const unsigned char *txbuffer, size_t count)
|
||||
{
|
||||
// TODO: Macro for write()
|
||||
return (int) write((p)->fd_sync_write, txbuffer, count);
|
||||
if (!p->async)
|
||||
{
|
||||
return -RIG_EINTERNAL;
|
||||
}
|
||||
|
||||
return (int) write(p->fd_sync_write, txbuffer, count);
|
||||
}
|
||||
|
||||
int HAMLIB_API write_block_sync_error(hamlib_port_t *p, const unsigned char *txbuffer, size_t count)
|
||||
{
|
||||
// TODO: Macro for write()
|
||||
return (int) write((p)->fd_sync_error_write, txbuffer, count);
|
||||
if (!p->async)
|
||||
{
|
||||
return -RIG_EINTERNAL;
|
||||
}
|
||||
|
||||
return (int) write(p->fd_sync_error_write, txbuffer, count);
|
||||
}
|
||||
|
||||
static int read_block_generic(hamlib_port_t *p, unsigned char *rxbuffer, size_t count, int direct)
|
||||
|
@ -618,6 +623,11 @@ static int read_block_generic(hamlib_port_t *p, unsigned char *rxbuffer, size_t
|
|||
|
||||
rig_debug(RIG_DEBUG_VERBOSE, "%s called\n", __func__);
|
||||
|
||||
if (!p->async && !direct)
|
||||
{
|
||||
return -RIG_EINTERNAL;
|
||||
}
|
||||
|
||||
fd = direct ? p->fd : p->fd_sync_read;
|
||||
|
||||
/*
|
||||
|
@ -639,7 +649,7 @@ static int read_block_generic(hamlib_port_t *p, unsigned char *rxbuffer, size_t
|
|||
FD_SET(fd, &rfds);
|
||||
efds = rfds;
|
||||
|
||||
retval = port_select(p, fd + 1, &rfds, NULL, &efds, &tv);
|
||||
retval = port_select(p, fd + 1, &rfds, NULL, &efds, &tv, direct);
|
||||
|
||||
if (retval == 0)
|
||||
{
|
||||
|
@ -753,7 +763,7 @@ int HAMLIB_API read_block_direct(hamlib_port_t *p, unsigned char *rxbuffer, size
|
|||
return read_block_generic(p, rxbuffer, count, 1);
|
||||
}
|
||||
|
||||
static int flush_and_read_last_byte(int fd)
|
||||
static int flush_and_read_last_byte(hamlib_port_t *p, int fd, int direct)
|
||||
{
|
||||
fd_set rfds, efds;
|
||||
ssize_t bytes_read;
|
||||
|
@ -769,7 +779,7 @@ static int flush_and_read_last_byte(int fd)
|
|||
FD_SET(fd, &rfds);
|
||||
efds = rfds;
|
||||
|
||||
retval = port_select(p, fd + 1, &rfds, NULL, &efds, &tv_timeout);
|
||||
retval = port_select(p, fd + 1, &rfds, NULL, &efds, &tv_timeout, direct);
|
||||
if (retval < 0)
|
||||
{
|
||||
return -RIG_ETIMEOUT;
|
||||
|
@ -804,6 +814,11 @@ static int read_string_generic(hamlib_port_t *p,
|
|||
int total_count = 0;
|
||||
int i = 0;
|
||||
|
||||
if (!p->async && !direct)
|
||||
{
|
||||
return -RIG_EINTERNAL;
|
||||
}
|
||||
|
||||
rig_debug(RIG_DEBUG_TRACE, "%s called, rxmax=%d\n", __func__, (int)rxmax);
|
||||
|
||||
if (!p || !rxbuffer)
|
||||
|
@ -849,7 +864,7 @@ static int read_string_generic(hamlib_port_t *p,
|
|||
}
|
||||
efds = rfds;
|
||||
|
||||
retval = port_select(p, maxfd + 1, &rfds, NULL, &efds, &tv);
|
||||
retval = port_select(p, maxfd + 1, &rfds, NULL, &efds, &tv, direct);
|
||||
|
||||
if (retval == 0)
|
||||
{
|
||||
|
@ -915,7 +930,7 @@ static int read_string_generic(hamlib_port_t *p,
|
|||
|
||||
if (FD_ISSET(errorfd, &rfds))
|
||||
{
|
||||
return flush_and_read_last_byte(errorfd);
|
||||
return flush_and_read_last_byte(p, errorfd, 0);
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -658,12 +658,13 @@ static int multicast_publisher_read_packet(int fd, uint8_t *type, struct rig_spe
|
|||
|
||||
void *multicast_publisher(void *arg)
|
||||
{
|
||||
unsigned char spectrum_data[HAMLIB_MAX_SPECTRUM_DATA];
|
||||
char snapshot_buffer[HAMLIB_MAX_SNAPSHOT_PACKET_SIZE];
|
||||
|
||||
struct multicast_publisher_args_s *args = (struct multicast_publisher_args_s *)arg;
|
||||
RIG *rig = args->rig;
|
||||
struct rig_state *rs = &rig->state;
|
||||
struct rig_spectrum_line spectrum_line;
|
||||
unsigned char spectrum_data[2048];
|
||||
char snapshot_buffer[16 * 1024];
|
||||
uint8_t packet_type;
|
||||
|
||||
struct sockaddr_in dest_addr;
|
||||
|
|
|
@ -6376,7 +6376,7 @@ int HAMLIB_API rig_get_rig_info(RIG *rig, char *response, int max_response_len)
|
|||
|
||||
if (ret != RIG_OK) { RETURNFUNC(ret); }
|
||||
|
||||
// we need both vfo and mode targtable to avoid vfo swapping
|
||||
// we need both vfo and mode targetable to avoid vfo swapping
|
||||
if ((rig->caps->targetable_vfo & RIG_TARGETABLE_FREQ)
|
||||
&& (rig->caps->targetable_vfo & RIG_TARGETABLE_MODE))
|
||||
{
|
||||
|
|
|
@ -9,14 +9,65 @@
|
|||
|
||||
#include "cJSON.h"
|
||||
|
||||
// Maximum number of data bytes in a single spectrum line
|
||||
#define SPECTRUM_DATA_MAX_LENGTH 2048
|
||||
|
||||
#define MAX_VFO_COUNT 4
|
||||
|
||||
#define SPECTRUM_MODE_FIXED "FIXED"
|
||||
#define SPECTRUM_MODE_CENTER "CENTER"
|
||||
|
||||
static int snapshot_serialize_rig(cJSON *rig_node, RIG *rig)
|
||||
{
|
||||
cJSON *node;
|
||||
|
||||
// TODO: need to assign rig an ID, e.g. from command line
|
||||
node = cJSON_AddStringToObject(rig_node, "id", "rig_id");
|
||||
if (node == NULL)
|
||||
{
|
||||
goto error;
|
||||
}
|
||||
|
||||
// TODO: what kind of status should this reflect?
|
||||
node = cJSON_AddStringToObject(rig_node, "status", rig->state.comm_state ? "OK" : "CLOSED");
|
||||
if (node == NULL)
|
||||
{
|
||||
goto error;
|
||||
}
|
||||
// TODO: need to store last error code
|
||||
node = cJSON_AddStringToObject(rig_node, "errorMsg", "");
|
||||
if (node == NULL)
|
||||
{
|
||||
goto error;
|
||||
}
|
||||
|
||||
node = cJSON_AddStringToObject(rig_node, "name", rig->caps->model_name);
|
||||
if (node == NULL)
|
||||
{
|
||||
goto error;
|
||||
}
|
||||
|
||||
node = cJSON_AddBoolToObject(rig_node, "split", rig->state.cache.split == RIG_SPLIT_ON ? 1 : 0);
|
||||
if (node == NULL)
|
||||
{
|
||||
goto error;
|
||||
}
|
||||
|
||||
node = cJSON_AddStringToObject(rig_node, "splitVfo", rig_strvfo(rig->state.cache.split_vfo));
|
||||
if (node == NULL)
|
||||
{
|
||||
goto error;
|
||||
}
|
||||
|
||||
node = cJSON_AddBoolToObject(rig_node, "satMode", rig->state.cache.satmode ? 1 : 0);
|
||||
if (node == NULL)
|
||||
{
|
||||
goto error;
|
||||
}
|
||||
|
||||
RETURNFUNC(RIG_OK);
|
||||
|
||||
error:
|
||||
RETURNFUNC(-RIG_EINTERNAL);
|
||||
}
|
||||
|
||||
static int snapshot_serialize_vfo(cJSON *vfo_node, RIG *rig, vfo_t vfo)
|
||||
{
|
||||
freq_t freq;
|
||||
|
@ -91,7 +142,7 @@ static int snapshot_serialize_vfo(cJSON *vfo_node, RIG *rig, vfo_t vfo)
|
|||
static int snapshot_serialize_spectrum(cJSON *spectrum_node, RIG *rig, struct rig_spectrum_line *spectrum_line)
|
||||
{
|
||||
// Spectrum data is represented as a hexadecimal ASCII string where each data byte is represented as 2 ASCII letters
|
||||
char spectrum_data_string[SPECTRUM_DATA_MAX_LENGTH * 2];
|
||||
char spectrum_data_string[HAMLIB_MAX_SPECTRUM_DATA * 2];
|
||||
cJSON *node;
|
||||
int i;
|
||||
struct rig_spectrum_scope *scopes = rig->caps->spectrum_scopes;
|
||||
|
@ -243,49 +294,15 @@ int snapshot_serialize(size_t buffer_length, char *buffer, RIG *rig, struct rig_
|
|||
goto error;
|
||||
}
|
||||
|
||||
result = snapshot_serialize_rig(rig_node, rig);
|
||||
if (result != RIG_OK)
|
||||
{
|
||||
cJSON_Delete(rig_node);
|
||||
goto error;
|
||||
}
|
||||
|
||||
cJSON_AddItemToObject(root_node, "rig", rig_node);
|
||||
|
||||
node = cJSON_AddStringToObject(rig_node, "id", "rig_id");
|
||||
if (node == NULL)
|
||||
{
|
||||
goto error;
|
||||
}
|
||||
|
||||
node = cJSON_AddStringToObject(rig_node, "status", "");
|
||||
if (node == NULL)
|
||||
{
|
||||
goto error;
|
||||
}
|
||||
node = cJSON_AddStringToObject(rig_node, "errorMsg", "");
|
||||
if (node == NULL)
|
||||
{
|
||||
goto error;
|
||||
}
|
||||
|
||||
node = cJSON_AddStringToObject(rig_node, "name", rig->caps->model_name);
|
||||
if (node == NULL)
|
||||
{
|
||||
goto error;
|
||||
}
|
||||
|
||||
node = cJSON_AddBoolToObject(rig_node, "split", rig->state.cache.split == RIG_SPLIT_ON ? 1 : 0);
|
||||
if (node == NULL)
|
||||
{
|
||||
goto error;
|
||||
}
|
||||
|
||||
node = cJSON_AddStringToObject(rig_node, "splitVfo", rig_strvfo(rig->state.cache.split_vfo));
|
||||
if (node == NULL)
|
||||
{
|
||||
goto error;
|
||||
}
|
||||
|
||||
node = cJSON_AddBoolToObject(rig_node, "satMode", 0);
|
||||
if (node == NULL)
|
||||
{
|
||||
goto error;
|
||||
}
|
||||
|
||||
vfos_array = cJSON_CreateArray();
|
||||
if (vfos_array == NULL)
|
||||
{
|
||||
|
|
Ładowanie…
Reference in New Issue