cem-dt-885x: Support for sound pressure level measurement range
This commit is contained in:
parent
8417ebad12
commit
f157b2eebb
|
@ -37,6 +37,7 @@ static const int32_t hwcaps[] = {
|
|||
SR_CONF_SPL_WEIGHT_TIME,
|
||||
SR_CONF_HOLD_MAX,
|
||||
SR_CONF_HOLD_MIN,
|
||||
SR_CONF_SPL_MEASUREMENT_RANGE,
|
||||
};
|
||||
|
||||
static const char *weight_freq[] = {
|
||||
|
@ -49,6 +50,13 @@ static const char *weight_time[] = {
|
|||
"S",
|
||||
};
|
||||
|
||||
static const uint64_t meas_ranges[][2] = {
|
||||
{ 30, 130 },
|
||||
{ 30, 80 },
|
||||
{ 50, 100 },
|
||||
{ 80, 130 },
|
||||
};
|
||||
|
||||
SR_PRIV struct sr_dev_driver cem_dt_885x_driver_info;
|
||||
static struct sr_dev_driver *di = &cem_dt_885x_driver_info;
|
||||
|
||||
|
@ -102,6 +110,7 @@ static GSList *scan(GSList *options)
|
|||
}
|
||||
devc->cur_mqflags = 0;
|
||||
devc->recording = -1;
|
||||
devc->cur_meas_range = 0;
|
||||
|
||||
if (!(sdi->conn = sr_serial_dev_inst_new(conn, SERIALCOMM)))
|
||||
return NULL;
|
||||
|
@ -173,6 +182,8 @@ static int cleanup(void)
|
|||
static int config_get(int key, GVariant **data, const struct sr_dev_inst *sdi)
|
||||
{
|
||||
struct dev_context *devc;
|
||||
GVariant *range[2];
|
||||
uint64_t low, high;
|
||||
int tmp, ret;
|
||||
|
||||
if (!sdi)
|
||||
|
@ -214,6 +225,13 @@ static int config_get(int key, GVariant **data, const struct sr_dev_inst *sdi)
|
|||
if ((ret = cem_dt_885x_holdmode_get(sdi, &tmp)) == SR_OK)
|
||||
*data = g_variant_new_boolean(tmp == SR_MQFLAG_MIN);
|
||||
break;
|
||||
case SR_CONF_SPL_MEASUREMENT_RANGE:
|
||||
if ((ret = cem_dt_885x_meas_range_get(sdi, &low, &high)) == SR_OK) {
|
||||
range[0] = g_variant_new_uint64(low);
|
||||
range[1] = g_variant_new_uint64(high);
|
||||
*data = g_variant_new_tuple(range, 2);
|
||||
}
|
||||
break;
|
||||
default:
|
||||
return SR_ERR_NA;
|
||||
}
|
||||
|
@ -224,7 +242,8 @@ static int config_get(int key, GVariant **data, const struct sr_dev_inst *sdi)
|
|||
static int config_set(int key, GVariant *data, const struct sr_dev_inst *sdi)
|
||||
{
|
||||
struct dev_context *devc;
|
||||
uint64_t tmp_u64;
|
||||
uint64_t tmp_u64, low, high;
|
||||
unsigned int i;
|
||||
int tmp, ret;
|
||||
const char *tmp_str;
|
||||
|
||||
|
@ -276,6 +295,16 @@ static int config_set(int key, GVariant *data, const struct sr_dev_inst *sdi)
|
|||
tmp = g_variant_get_boolean(data) ? SR_MQFLAG_MIN : 0;
|
||||
ret = cem_dt_885x_holdmode_set(sdi, tmp);
|
||||
break;
|
||||
case SR_CONF_SPL_MEASUREMENT_RANGE:
|
||||
g_variant_get(data, "(tt)", &low, &high);
|
||||
ret = SR_ERR_ARG;
|
||||
for (i = 0; i < ARRAY_SIZE(meas_ranges); i++) {
|
||||
if (meas_ranges[i][0] == low && meas_ranges[i][1] == high) {
|
||||
ret = cem_dt_885x_meas_range_set(sdi, low, high);
|
||||
break;
|
||||
}
|
||||
}
|
||||
break;
|
||||
default:
|
||||
ret = SR_ERR_NA;
|
||||
}
|
||||
|
@ -285,6 +314,9 @@ static int config_set(int key, GVariant *data, const struct sr_dev_inst *sdi)
|
|||
|
||||
static int config_list(int key, GVariant **data, const struct sr_dev_inst *sdi)
|
||||
{
|
||||
GVariant *tuple, *range[2];
|
||||
GVariantBuilder gvb;
|
||||
unsigned int i;
|
||||
int ret;
|
||||
|
||||
(void)sdi;
|
||||
|
@ -305,6 +337,16 @@ static int config_list(int key, GVariant **data, const struct sr_dev_inst *sdi)
|
|||
case SR_CONF_SPL_WEIGHT_TIME:
|
||||
*data = g_variant_new_strv(weight_time, ARRAY_SIZE(weight_time));
|
||||
break;
|
||||
case SR_CONF_SPL_MEASUREMENT_RANGE:
|
||||
g_variant_builder_init(&gvb, G_VARIANT_TYPE_ARRAY);
|
||||
for (i = 0; i < ARRAY_SIZE(meas_ranges); i++) {
|
||||
range[0] = g_variant_new_uint64(meas_ranges[i][0]);
|
||||
range[1] = g_variant_new_uint64(meas_ranges[i][1]);
|
||||
tuple = g_variant_new_tuple(range, 2);
|
||||
g_variant_builder_add_value(&gvb, tuple);
|
||||
}
|
||||
*data = g_variant_builder_end(&gvb);
|
||||
break;
|
||||
default:
|
||||
return SR_ERR_NA;
|
||||
}
|
||||
|
|
|
@ -152,6 +152,12 @@ static void process_mset(const struct sr_dev_inst *sdi)
|
|||
case TOKEN_RECORDING_OFF:
|
||||
devc->recording = FALSE;
|
||||
break;
|
||||
case TOKEN_MEAS_RANGE_30_80:
|
||||
case TOKEN_MEAS_RANGE_30_130:
|
||||
case TOKEN_MEAS_RANGE_50_100:
|
||||
case TOKEN_MEAS_RANGE_80_130:
|
||||
devc->cur_meas_range = devc->token;
|
||||
break;
|
||||
case TOKEN_TIME:
|
||||
case TOKEN_STORE_OK:
|
||||
case TOKEN_STORE_FULL:
|
||||
|
@ -160,10 +166,6 @@ static void process_mset(const struct sr_dev_inst *sdi)
|
|||
case TOKEN_MEAS_RANGE_OK:
|
||||
case TOKEN_MEAS_RANGE_OVER:
|
||||
case TOKEN_MEAS_RANGE_UNDER:
|
||||
case TOKEN_MEAS_RANGE_30_80:
|
||||
case TOKEN_MEAS_RANGE_30_130:
|
||||
case TOKEN_MEAS_RANGE_50_100:
|
||||
case TOKEN_MEAS_RANGE_80_130:
|
||||
/* Not useful, or not expressable in sigrok. */
|
||||
break;
|
||||
}
|
||||
|
@ -594,3 +596,92 @@ SR_PRIV int cem_dt_885x_holdmode_set(const struct sr_dev_inst *sdi, int holdmode
|
|||
|
||||
return ret;
|
||||
}
|
||||
|
||||
SR_PRIV int cem_dt_885x_meas_range_get(const struct sr_dev_inst *sdi,
|
||||
uint64_t *low, uint64_t *high)
|
||||
{
|
||||
struct dev_context *devc;
|
||||
char tokens[5];
|
||||
|
||||
devc = sdi->priv;
|
||||
if (devc->cur_meas_range == 0) {
|
||||
tokens[0] = TOKEN_MEAS_RANGE_30_130;
|
||||
tokens[1] = TOKEN_MEAS_RANGE_30_80;
|
||||
tokens[2] = TOKEN_MEAS_RANGE_50_100;
|
||||
tokens[3] = TOKEN_MEAS_RANGE_80_130;
|
||||
tokens[4] = -1;
|
||||
if (wait_for_token(sdi, tokens, 0) != SR_OK)
|
||||
return SR_ERR;
|
||||
devc->cur_meas_range = devc->token;
|
||||
}
|
||||
|
||||
switch (devc->cur_meas_range) {
|
||||
case TOKEN_MEAS_RANGE_30_130:
|
||||
*low = 30;
|
||||
*high = 130;
|
||||
break;
|
||||
case TOKEN_MEAS_RANGE_30_80:
|
||||
*low = 30;
|
||||
*high = 80;
|
||||
break;
|
||||
case TOKEN_MEAS_RANGE_50_100:
|
||||
*low = 50;
|
||||
*high = 100;
|
||||
break;
|
||||
case TOKEN_MEAS_RANGE_80_130:
|
||||
*low = 80;
|
||||
*high = 130;
|
||||
break;
|
||||
default:
|
||||
return SR_ERR;
|
||||
}
|
||||
|
||||
return SR_OK;
|
||||
}
|
||||
|
||||
SR_PRIV int cem_dt_885x_meas_range_set(const struct sr_dev_inst *sdi,
|
||||
uint64_t low, uint64_t high)
|
||||
{
|
||||
struct dev_context *devc;
|
||||
int ret;
|
||||
char token, tokens[6];
|
||||
|
||||
devc = sdi->priv;
|
||||
if (low == 30 && high == 130)
|
||||
token = TOKEN_MEAS_RANGE_30_130;
|
||||
else if (low == 30 && high == 80)
|
||||
token = TOKEN_MEAS_RANGE_30_80;
|
||||
else if (low == 50 && high == 100)
|
||||
token = TOKEN_MEAS_RANGE_50_100;
|
||||
else if (low == 80 && high == 130)
|
||||
token = TOKEN_MEAS_RANGE_80_130;
|
||||
else
|
||||
return SR_ERR;
|
||||
|
||||
sr_dbg("want 0x%.2x", token);
|
||||
/* The toggle below needs the desired state in first position. */
|
||||
tokens[0] = token;
|
||||
tokens[1] = TOKEN_MEAS_RANGE_30_130;
|
||||
tokens[2] = TOKEN_MEAS_RANGE_30_80;
|
||||
tokens[3] = TOKEN_MEAS_RANGE_50_100;
|
||||
tokens[4] = TOKEN_MEAS_RANGE_80_130;
|
||||
tokens[5] = -1;
|
||||
|
||||
if (devc->cur_meas_range == 0) {
|
||||
/* 110ms should be enough for two of these announcements */
|
||||
if (wait_for_token(sdi, tokens, 110) != SR_OK)
|
||||
return SR_ERR;
|
||||
devc->cur_meas_range = devc->token;
|
||||
}
|
||||
|
||||
if (devc->cur_meas_range == token)
|
||||
/* Already set to this range. */
|
||||
return SR_OK;
|
||||
|
||||
/* For measurement range, it works best to ignore announcements of the
|
||||
* current setting and keep resending the toggle quickly. */
|
||||
tokens[1] = -1;
|
||||
ret = cem_dt_885x_toggle(sdi, CMD_TOGGLE_MEAS_RANGE, tokens, 11);
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
|
|
@ -71,6 +71,7 @@ enum {
|
|||
CMD_TOGGLE_WEIGHT_FREQ = 0x99,
|
||||
CMD_TOGGLE_WEIGHT_TIME = 0x77,
|
||||
CMD_TOGGLE_HOLD_MAX_MIN = 0x11,
|
||||
CMD_TOGGLE_MEAS_RANGE = 0x88,
|
||||
};
|
||||
|
||||
/** Private, per-device-instance driver context. */
|
||||
|
@ -78,6 +79,7 @@ struct dev_context {
|
|||
/* Device state */
|
||||
uint64_t cur_mqflags;
|
||||
int recording;
|
||||
int cur_meas_range;
|
||||
|
||||
/* Acquisition settings */
|
||||
uint64_t limit_samples;
|
||||
|
@ -115,5 +117,9 @@ SR_PRIV int cem_dt_885x_weight_time_set(const struct sr_dev_inst *sdi, int timew
|
|||
SR_PRIV int cem_dt_885x_holdmode_get(const struct sr_dev_inst *sdi,
|
||||
gboolean *holdmode);
|
||||
SR_PRIV int cem_dt_885x_holdmode_set(const struct sr_dev_inst *sdi, int holdmode);
|
||||
SR_PRIV int cem_dt_885x_meas_range_get(const struct sr_dev_inst *sdi,
|
||||
uint64_t *low, uint64_t *high);
|
||||
SR_PRIV int cem_dt_885x_meas_range_set(const struct sr_dev_inst *sdi,
|
||||
uint64_t low, uint64_t high);
|
||||
|
||||
#endif
|
||||
|
|
Loading…
Reference in New Issue