Merge branch 'master' into Subsurface-branch
This commit is contained in:
commit
da0073c971
@ -215,6 +215,8 @@ atomics_cobalt_device_version (dc_device_t *abstract, unsigned char data[], unsi
|
|||||||
return EXITCODE(rc);
|
return EXITCODE(rc);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
HEXDUMP (abstract->context, DC_LOGLEVEL_INFO, "Write", &bRequest, 1);
|
||||||
|
|
||||||
// Receive the answer from the dive computer.
|
// Receive the answer from the dive computer.
|
||||||
int length = 0;
|
int length = 0;
|
||||||
unsigned char packet[SZ_VERSION + 2] = {0};
|
unsigned char packet[SZ_VERSION + 2] = {0};
|
||||||
@ -225,6 +227,8 @@ atomics_cobalt_device_version (dc_device_t *abstract, unsigned char data[], unsi
|
|||||||
return EXITCODE(rc);
|
return EXITCODE(rc);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
HEXDUMP (abstract->context, DC_LOGLEVEL_INFO, "Read", packet, length);
|
||||||
|
|
||||||
// Verify the checksum of the packet.
|
// Verify the checksum of the packet.
|
||||||
unsigned short crc = array_uint16_le (packet + SZ_VERSION);
|
unsigned short crc = array_uint16_le (packet + SZ_VERSION);
|
||||||
unsigned short ccrc = checksum_add_uint16 (packet, SZ_VERSION, 0x0);
|
unsigned short ccrc = checksum_add_uint16 (packet, SZ_VERSION, 0x0);
|
||||||
@ -271,6 +275,8 @@ atomics_cobalt_read_dive (dc_device_t *abstract, dc_buffer_t *buffer, int init,
|
|||||||
return EXITCODE(rc);
|
return EXITCODE(rc);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
HEXDUMP (abstract->context, DC_LOGLEVEL_INFO, "Write", &bRequest, 1);
|
||||||
|
|
||||||
unsigned int nbytes = 0;
|
unsigned int nbytes = 0;
|
||||||
while (1) {
|
while (1) {
|
||||||
// Receive the answer from the dive computer.
|
// Receive the answer from the dive computer.
|
||||||
@ -283,6 +289,8 @@ atomics_cobalt_read_dive (dc_device_t *abstract, dc_buffer_t *buffer, int init,
|
|||||||
return EXITCODE(rc);
|
return EXITCODE(rc);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
HEXDUMP (abstract->context, DC_LOGLEVEL_INFO, "Read", packet, length);
|
||||||
|
|
||||||
// Update and emit a progress event.
|
// Update and emit a progress event.
|
||||||
if (progress) {
|
if (progress) {
|
||||||
progress->current += length;
|
progress->current += length;
|
||||||
|
|||||||
@ -199,7 +199,8 @@ static const dc_descriptor_t g_descriptors[] = {
|
|||||||
{"Mares", "Airlab", DC_FAMILY_MARES_DARWIN , 1},
|
{"Mares", "Airlab", DC_FAMILY_MARES_DARWIN , 1},
|
||||||
/* Mares Icon HD */
|
/* Mares Icon HD */
|
||||||
{"Mares", "Matrix", DC_FAMILY_MARES_ICONHD , 0x0F},
|
{"Mares", "Matrix", DC_FAMILY_MARES_ICONHD , 0x0F},
|
||||||
{"Mares", "Smart", DC_FAMILY_MARES_ICONHD , 0x10},
|
{"Mares", "Smart", DC_FAMILY_MARES_ICONHD , 0x000010},
|
||||||
|
{"Mares", "Smart Apnea", DC_FAMILY_MARES_ICONHD , 0x010010},
|
||||||
{"Mares", "Icon HD", DC_FAMILY_MARES_ICONHD , 0x14},
|
{"Mares", "Icon HD", DC_FAMILY_MARES_ICONHD , 0x14},
|
||||||
{"Mares", "Icon HD Net Ready", DC_FAMILY_MARES_ICONHD , 0x15},
|
{"Mares", "Icon HD Net Ready", DC_FAMILY_MARES_ICONHD , 0x15},
|
||||||
{"Mares", "Puck Pro", DC_FAMILY_MARES_ICONHD , 0x18},
|
{"Mares", "Puck Pro", DC_FAMILY_MARES_ICONHD , 0x18},
|
||||||
|
|||||||
@ -859,6 +859,8 @@ hw_ostc_parser_samples_foreach (dc_parser_t *abstract, dc_sample_callback_t call
|
|||||||
return DC_STATUS_DATAFORMAT;
|
return DC_STATUS_DATAFORMAT;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
unsigned int ppo2[3] = {0};
|
||||||
|
unsigned int count = 0;
|
||||||
unsigned int value = 0;
|
unsigned int value = 0;
|
||||||
switch (info[i].type) {
|
switch (info[i].type) {
|
||||||
case 0: // Temperature (0.1 °C).
|
case 0: // Temperature (0.1 °C).
|
||||||
@ -880,12 +882,18 @@ hw_ostc_parser_samples_foreach (dc_parser_t *abstract, dc_sample_callback_t call
|
|||||||
case 3: // ppO2 (0.01 bar).
|
case 3: // ppO2 (0.01 bar).
|
||||||
for (unsigned int j = 0; j < 3; ++j) {
|
for (unsigned int j = 0; j < 3; ++j) {
|
||||||
if (info[i].size == 3) {
|
if (info[i].size == 3) {
|
||||||
value = data[offset + j];
|
ppo2[j] = data[offset + j];
|
||||||
} else {
|
} else {
|
||||||
value = data[offset + j * 3];
|
ppo2[j] = data[offset + j * 3];
|
||||||
|
}
|
||||||
|
if (ppo2[j] != 0)
|
||||||
|
count++;
|
||||||
|
}
|
||||||
|
if (count) {
|
||||||
|
for (unsigned int j = 0; j < 3; ++j) {
|
||||||
|
sample.ppo2 = ppo2[j] / 100.0;
|
||||||
|
if (callback) callback (DC_SAMPLE_PPO2, sample, userdata);
|
||||||
}
|
}
|
||||||
sample.ppo2 = value / 100.0;
|
|
||||||
if (callback) callback (DC_SAMPLE_PPO2, sample, userdata);
|
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case 5: // CNS
|
case 5: // CNS
|
||||||
|
|||||||
@ -40,7 +40,8 @@
|
|||||||
)
|
)
|
||||||
|
|
||||||
#define MATRIX 0x0F
|
#define MATRIX 0x0F
|
||||||
#define SMART 0x10
|
#define SMART 0x000010
|
||||||
|
#define SMARTAPNEA 0x010010
|
||||||
#define ICONHD 0x14
|
#define ICONHD 0x14
|
||||||
#define ICONHDNET 0x15
|
#define ICONHDNET 0x15
|
||||||
#define PUCKPRO 0x18
|
#define PUCKPRO 0x18
|
||||||
@ -122,6 +123,7 @@ mares_iconhd_get_model (mares_iconhd_device_t *device)
|
|||||||
const mares_iconhd_model_t models[] = {
|
const mares_iconhd_model_t models[] = {
|
||||||
{"Matrix", MATRIX},
|
{"Matrix", MATRIX},
|
||||||
{"Smart", SMART},
|
{"Smart", SMART},
|
||||||
|
{"Smart Apnea", SMARTAPNEA},
|
||||||
{"Icon HD", ICONHD},
|
{"Icon HD", ICONHD},
|
||||||
{"Icon AIR", ICONHDNET},
|
{"Icon AIR", ICONHDNET},
|
||||||
{"Puck Pro", PUCKPRO},
|
{"Puck Pro", PUCKPRO},
|
||||||
@ -463,6 +465,8 @@ mares_iconhd_extract_dives (dc_device_t *abstract, const unsigned char data[], u
|
|||||||
header = 0x80;
|
header = 0x80;
|
||||||
else if (model == SMART)
|
else if (model == SMART)
|
||||||
header = 4; // Type and number of samples only!
|
header = 4; // Type and number of samples only!
|
||||||
|
else if (model == SMARTAPNEA)
|
||||||
|
header = 6; // Type and number of samples only!
|
||||||
|
|
||||||
// Get the end of the profile ring buffer.
|
// Get the end of the profile ring buffer.
|
||||||
unsigned int eop = 0;
|
unsigned int eop = 0;
|
||||||
@ -491,7 +495,7 @@ mares_iconhd_extract_dives (dc_device_t *abstract, const unsigned char data[], u
|
|||||||
while (offset >= header + 4) {
|
while (offset >= header + 4) {
|
||||||
// Get the number of samples in the profile data.
|
// Get the number of samples in the profile data.
|
||||||
unsigned int type = 0, nsamples = 0;
|
unsigned int type = 0, nsamples = 0;
|
||||||
if (model == SMART) {
|
if (model == SMART || model == SMARTAPNEA) {
|
||||||
type = array_uint16_le (buffer + offset - header + 2);
|
type = array_uint16_le (buffer + offset - header + 2);
|
||||||
nsamples = array_uint16_le (buffer + offset - header + 0);
|
nsamples = array_uint16_le (buffer + offset - header + 0);
|
||||||
} else {
|
} else {
|
||||||
@ -521,6 +525,10 @@ mares_iconhd_extract_dives (dc_device_t *abstract, const unsigned char data[], u
|
|||||||
samplesize = 8;
|
samplesize = 8;
|
||||||
fingerprint = 2;
|
fingerprint = 2;
|
||||||
}
|
}
|
||||||
|
} else if (model == SMARTAPNEA) {
|
||||||
|
headersize = 0x50;
|
||||||
|
samplesize = 14;
|
||||||
|
fingerprint = 0x40;
|
||||||
}
|
}
|
||||||
|
|
||||||
// Calculate the total number of bytes for this dive.
|
// Calculate the total number of bytes for this dive.
|
||||||
@ -528,8 +536,18 @@ mares_iconhd_extract_dives (dc_device_t *abstract, const unsigned char data[], u
|
|||||||
// end of the ringbuffer. The current dive is incomplete (partially
|
// end of the ringbuffer. The current dive is incomplete (partially
|
||||||
// overwritten with newer data), and processing should stop.
|
// overwritten with newer data), and processing should stop.
|
||||||
unsigned int nbytes = 4 + headersize + nsamples * samplesize;
|
unsigned int nbytes = 4 + headersize + nsamples * samplesize;
|
||||||
if (model == ICONHDNET)
|
if (model == ICONHDNET) {
|
||||||
nbytes += (nsamples / 4) * 8;
|
nbytes += (nsamples / 4) * 8;
|
||||||
|
} else if (model == SMARTAPNEA) {
|
||||||
|
if (offset < headersize)
|
||||||
|
break;
|
||||||
|
|
||||||
|
unsigned int settings = array_uint16_le (buffer + offset - headersize + 0x1C);
|
||||||
|
unsigned int divetime = array_uint32_le (buffer + offset - headersize + 0x24);
|
||||||
|
unsigned int samplerate = 1 << ((settings >> 9) & 0x03);
|
||||||
|
|
||||||
|
nbytes += divetime * samplerate * 2;
|
||||||
|
}
|
||||||
if (offset < nbytes)
|
if (offset < nbytes)
|
||||||
break;
|
break;
|
||||||
|
|
||||||
|
|||||||
@ -29,7 +29,8 @@
|
|||||||
|
|
||||||
#define ISINSTANCE(parser) dc_parser_isinstance((parser), &mares_iconhd_parser_vtable)
|
#define ISINSTANCE(parser) dc_parser_isinstance((parser), &mares_iconhd_parser_vtable)
|
||||||
|
|
||||||
#define SMART 0x10
|
#define SMART 0x000010
|
||||||
|
#define SMARTAPNEA 0x010010
|
||||||
#define ICONHD 0x14
|
#define ICONHD 0x14
|
||||||
#define ICONHDNET 0x15
|
#define ICONHDNET 0x15
|
||||||
|
|
||||||
@ -86,6 +87,8 @@ mares_iconhd_parser_cache (mares_iconhd_parser_t *parser)
|
|||||||
header = 0x80;
|
header = 0x80;
|
||||||
else if (parser->model == SMART)
|
else if (parser->model == SMART)
|
||||||
header = 4; // Type and number of samples only!
|
header = 4; // Type and number of samples only!
|
||||||
|
else if (parser->model == SMARTAPNEA)
|
||||||
|
header = 6; // Type and number of samples only!
|
||||||
|
|
||||||
if (size < header + 4) {
|
if (size < header + 4) {
|
||||||
ERROR (abstract->context, "Buffer overflow detected!");
|
ERROR (abstract->context, "Buffer overflow detected!");
|
||||||
@ -100,7 +103,7 @@ mares_iconhd_parser_cache (mares_iconhd_parser_t *parser)
|
|||||||
|
|
||||||
// Get the number of samples in the profile data.
|
// Get the number of samples in the profile data.
|
||||||
unsigned int type = 0, nsamples = 0;
|
unsigned int type = 0, nsamples = 0;
|
||||||
if (parser->model == SMART) {
|
if (parser->model == SMART || parser->model == SMARTAPNEA) {
|
||||||
type = array_uint16_le (data + length - header + 2);
|
type = array_uint16_le (data + length - header + 2);
|
||||||
nsamples = array_uint16_le (data + length - header + 0);
|
nsamples = array_uint16_le (data + length - header + 0);
|
||||||
} else {
|
} else {
|
||||||
@ -125,19 +128,34 @@ mares_iconhd_parser_cache (mares_iconhd_parser_t *parser)
|
|||||||
headersize = 0x5C;
|
headersize = 0x5C;
|
||||||
samplesize = 8;
|
samplesize = 8;
|
||||||
}
|
}
|
||||||
|
} else if (parser->model == SMARTAPNEA) {
|
||||||
|
headersize = 0x50;
|
||||||
|
samplesize = 14;
|
||||||
}
|
}
|
||||||
|
|
||||||
// Calculate the total number of bytes for this dive.
|
// Calculate the total number of bytes for this dive.
|
||||||
unsigned int nbytes = 4 + headersize + nsamples * samplesize;
|
unsigned int nbytes = 4 + headersize + nsamples * samplesize;
|
||||||
if (parser->model == ICONHDNET)
|
if (parser->model == ICONHDNET) {
|
||||||
nbytes += (nsamples / 4) * 8;
|
nbytes += (nsamples / 4) * 8;
|
||||||
|
} else if (parser->model == SMARTAPNEA) {
|
||||||
|
if (length < headersize) {
|
||||||
|
ERROR (abstract->context, "Buffer overflow detected!");
|
||||||
|
return DC_STATUS_DATAFORMAT;
|
||||||
|
}
|
||||||
|
|
||||||
|
unsigned int settings = array_uint16_le (data + length - headersize + 0x1C);
|
||||||
|
unsigned int divetime = array_uint32_le (data + length - headersize + 0x24);
|
||||||
|
unsigned int samplerate = 1 << ((settings >> 9) & 0x03);
|
||||||
|
|
||||||
|
nbytes += divetime * samplerate * 2;
|
||||||
|
}
|
||||||
if (length != nbytes) {
|
if (length != nbytes) {
|
||||||
ERROR (abstract->context, "Calculated and stored size are not equal.");
|
ERROR (abstract->context, "Calculated and stored size are not equal.");
|
||||||
return DC_STATUS_DATAFORMAT;
|
return DC_STATUS_DATAFORMAT;
|
||||||
}
|
}
|
||||||
|
|
||||||
const unsigned char *p = data + length - headersize;
|
const unsigned char *p = data + length - headersize;
|
||||||
if (parser->model != SMART) {
|
if (parser->model != SMART && parser->model != SMARTAPNEA) {
|
||||||
p += 4;
|
p += 4;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -258,6 +276,8 @@ mares_iconhd_parser_get_datetime (dc_parser_t *abstract, dc_datetime_t *datetime
|
|||||||
} else {
|
} else {
|
||||||
p += 2;
|
p += 2;
|
||||||
}
|
}
|
||||||
|
} else if (parser->model == SMARTAPNEA) {
|
||||||
|
p += 0x40;
|
||||||
} else {
|
} else {
|
||||||
p += 6;
|
p += 6;
|
||||||
}
|
}
|
||||||
@ -286,7 +306,7 @@ mares_iconhd_parser_get_field (dc_parser_t *abstract, dc_field_type_t type, unsi
|
|||||||
return rc;
|
return rc;
|
||||||
|
|
||||||
const unsigned char *p = abstract->data + parser->footer;
|
const unsigned char *p = abstract->data + parser->footer;
|
||||||
if (parser->model != SMART) {
|
if (parser->model != SMART && parser->model != SMARTAPNEA) {
|
||||||
p += 4;
|
p += 4;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -295,7 +315,9 @@ mares_iconhd_parser_get_field (dc_parser_t *abstract, dc_field_type_t type, unsi
|
|||||||
if (value) {
|
if (value) {
|
||||||
switch (type) {
|
switch (type) {
|
||||||
case DC_FIELD_DIVETIME:
|
case DC_FIELD_DIVETIME:
|
||||||
if (parser->mode == FREEDIVE) {
|
if (parser->model == SMARTAPNEA) {
|
||||||
|
*((unsigned int *) value) = array_uint16_le (p + 0x24);
|
||||||
|
} else if (parser->mode == FREEDIVE) {
|
||||||
unsigned int divetime = 0;
|
unsigned int divetime = 0;
|
||||||
unsigned int offset = 4;
|
unsigned int offset = 4;
|
||||||
for (unsigned int i = 0; i < parser->nsamples; ++i) {
|
for (unsigned int i = 0; i < parser->nsamples; ++i) {
|
||||||
@ -308,7 +330,9 @@ mares_iconhd_parser_get_field (dc_parser_t *abstract, dc_field_type_t type, unsi
|
|||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case DC_FIELD_MAXDEPTH:
|
case DC_FIELD_MAXDEPTH:
|
||||||
if (parser->mode == FREEDIVE)
|
if (parser->model == SMARTAPNEA)
|
||||||
|
*((double *) value) = array_uint16_le (p + 0x3A) / 10.0;
|
||||||
|
else if (parser->mode == FREEDIVE)
|
||||||
*((double *) value) = array_uint16_le (p + 0x1A) / 10.0;
|
*((double *) value) = array_uint16_le (p + 0x1A) / 10.0;
|
||||||
else
|
else
|
||||||
*((double *) value) = array_uint16_le (p + 0x00) / 10.0;
|
*((double *) value) = array_uint16_le (p + 0x00) / 10.0;
|
||||||
@ -323,19 +347,25 @@ mares_iconhd_parser_get_field (dc_parser_t *abstract, dc_field_type_t type, unsi
|
|||||||
break;
|
break;
|
||||||
case DC_FIELD_ATMOSPHERIC:
|
case DC_FIELD_ATMOSPHERIC:
|
||||||
// Pressure (1/8 millibar)
|
// Pressure (1/8 millibar)
|
||||||
if (parser->mode == FREEDIVE)
|
if (parser->model == SMARTAPNEA)
|
||||||
|
*((double *) value) = array_uint16_le (p + 0x38) / 1000.0;
|
||||||
|
else if (parser->mode == FREEDIVE)
|
||||||
*((double *) value) = array_uint16_le (p + 0x18) / 1000.0;
|
*((double *) value) = array_uint16_le (p + 0x18) / 1000.0;
|
||||||
else
|
else
|
||||||
*((double *) value) = array_uint16_le (p + 0x22) / 8000.0;
|
*((double *) value) = array_uint16_le (p + 0x22) / 8000.0;
|
||||||
break;
|
break;
|
||||||
case DC_FIELD_TEMPERATURE_MINIMUM:
|
case DC_FIELD_TEMPERATURE_MINIMUM:
|
||||||
if (parser->mode == FREEDIVE)
|
if (parser->model == SMARTAPNEA)
|
||||||
|
*((double *) value) = (signed short) array_uint16_le (p + 0x3C) / 10.0;
|
||||||
|
else if (parser->mode == FREEDIVE)
|
||||||
*((double *) value) = (signed short) array_uint16_le (p + 0x1C) / 10.0;
|
*((double *) value) = (signed short) array_uint16_le (p + 0x1C) / 10.0;
|
||||||
else
|
else
|
||||||
*((double *) value) = (signed short) array_uint16_le (p + 0x42) / 10.0;
|
*((double *) value) = (signed short) array_uint16_le (p + 0x42) / 10.0;
|
||||||
break;
|
break;
|
||||||
case DC_FIELD_TEMPERATURE_MAXIMUM:
|
case DC_FIELD_TEMPERATURE_MAXIMUM:
|
||||||
if (parser->mode == FREEDIVE)
|
if (parser->model == SMARTAPNEA)
|
||||||
|
*((double *) value) = (signed short) array_uint16_le (p + 0x3E) / 10.0;
|
||||||
|
else if (parser->mode == FREEDIVE)
|
||||||
*((double *) value) = (signed short) array_uint16_le (p + 0x1E) / 10.0;
|
*((double *) value) = (signed short) array_uint16_le (p + 0x1E) / 10.0;
|
||||||
else
|
else
|
||||||
*((double *) value) = (signed short) array_uint16_le (p + 0x44) / 10.0;
|
*((double *) value) = (signed short) array_uint16_le (p + 0x44) / 10.0;
|
||||||
@ -379,6 +409,19 @@ mares_iconhd_parser_samples_foreach (dc_parser_t *abstract, dc_sample_callback_t
|
|||||||
|
|
||||||
unsigned int time = 0;
|
unsigned int time = 0;
|
||||||
unsigned int interval = 5;
|
unsigned int interval = 5;
|
||||||
|
unsigned int samplerate = 1;
|
||||||
|
if (parser->model == SMARTAPNEA) {
|
||||||
|
unsigned int settings = array_uint16_le (data + parser->footer + 0x1C);
|
||||||
|
samplerate = 1 << ((settings >> 9) & 0x03);
|
||||||
|
if (samplerate > 1) {
|
||||||
|
// The Smart Apnea supports multiple samples per second
|
||||||
|
// (e.g. 2, 4 or 8). Since our smallest unit of time is one
|
||||||
|
// second, we can't represent this, and the extra samples
|
||||||
|
// will get dropped.
|
||||||
|
WARNING(abstract->context, "Multiple samples per second are not supported!");
|
||||||
|
}
|
||||||
|
interval = 1;
|
||||||
|
}
|
||||||
|
|
||||||
// Previous gas mix - initialize with impossible value
|
// Previous gas mix - initialize with impossible value
|
||||||
unsigned int gasmix_previous = 0xFFFFFFFF;
|
unsigned int gasmix_previous = 0xFFFFFFFF;
|
||||||
@ -388,7 +431,37 @@ mares_iconhd_parser_samples_foreach (dc_parser_t *abstract, dc_sample_callback_t
|
|||||||
while (nsamples < parser->nsamples) {
|
while (nsamples < parser->nsamples) {
|
||||||
dc_sample_value_t sample = {0};
|
dc_sample_value_t sample = {0};
|
||||||
|
|
||||||
if (parser->mode == FREEDIVE) {
|
if (parser->model == SMARTAPNEA) {
|
||||||
|
unsigned int maxdepth = array_uint16_le (data + offset + 0);
|
||||||
|
unsigned int divetime = array_uint16_le (data + offset + 2);
|
||||||
|
unsigned int surftime = array_uint16_le (data + offset + 4);
|
||||||
|
|
||||||
|
// Surface Time (seconds).
|
||||||
|
time += surftime;
|
||||||
|
sample.time = time;
|
||||||
|
if (callback) callback (DC_SAMPLE_TIME, sample, userdata);
|
||||||
|
|
||||||
|
// Surface Depth (0 m).
|
||||||
|
sample.depth = 0.0;
|
||||||
|
if (callback) callback (DC_SAMPLE_DEPTH, sample, userdata);
|
||||||
|
|
||||||
|
offset += parser->samplesize;
|
||||||
|
nsamples++;
|
||||||
|
|
||||||
|
for (unsigned int i = 0; i < divetime; ++i) {
|
||||||
|
// Time (seconds).
|
||||||
|
time += interval;
|
||||||
|
sample.time = time;
|
||||||
|
if (callback) callback (DC_SAMPLE_TIME, sample, userdata);
|
||||||
|
|
||||||
|
// Depth (1/10 m).
|
||||||
|
unsigned int depth = array_uint16_le (data + offset);
|
||||||
|
sample.depth = depth / 10.0;
|
||||||
|
if (callback) callback (DC_SAMPLE_DEPTH, sample, userdata);
|
||||||
|
|
||||||
|
offset += 2 * samplerate;
|
||||||
|
}
|
||||||
|
} else if (parser->mode == FREEDIVE) {
|
||||||
unsigned int maxdepth = array_uint16_le (data + offset + 0);
|
unsigned int maxdepth = array_uint16_le (data + offset + 0);
|
||||||
unsigned int divetime = array_uint16_le (data + offset + 2);
|
unsigned int divetime = array_uint16_le (data + offset + 2);
|
||||||
unsigned int surftime = array_uint16_le (data + offset + 4);
|
unsigned int surftime = array_uint16_le (data + offset + 4);
|
||||||
|
|||||||
@ -111,7 +111,6 @@ static const oceanic_common_version_t oceanic_atom2b_version[] = {
|
|||||||
{"ELEMENT2 \0\0 512K"},
|
{"ELEMENT2 \0\0 512K"},
|
||||||
{"OCEVEO20 \0\0 512K"},
|
{"OCEVEO20 \0\0 512K"},
|
||||||
{"TUSAZEN \0\0 512K"},
|
{"TUSAZEN \0\0 512K"},
|
||||||
{"PROPLUS3 \0\0 512K"},
|
|
||||||
};
|
};
|
||||||
|
|
||||||
static const oceanic_common_version_t oceanic_atom2c_version[] = {
|
static const oceanic_common_version_t oceanic_atom2c_version[] = {
|
||||||
@ -129,6 +128,10 @@ static const oceanic_common_version_t oceanic_default_version[] = {
|
|||||||
{"HOLLDG03 \0\0 512K"},
|
{"HOLLDG03 \0\0 512K"},
|
||||||
};
|
};
|
||||||
|
|
||||||
|
static const oceanic_common_version_t oceanic_proplus3_version[] = {
|
||||||
|
{"PROPLUS3 \0\0 512K"},
|
||||||
|
};
|
||||||
|
|
||||||
static const oceanic_common_version_t tusa_zenair_version[] = {
|
static const oceanic_common_version_t tusa_zenair_version[] = {
|
||||||
{"TUZENAIR \0\0 512K"},
|
{"TUZENAIR \0\0 512K"},
|
||||||
{"AMPHOSSW \0\0 512K"},
|
{"AMPHOSSW \0\0 512K"},
|
||||||
@ -266,6 +269,19 @@ static const oceanic_common_layout_t oceanic_atom2c_layout = {
|
|||||||
0 /* pt_mode_logbook */
|
0 /* pt_mode_logbook */
|
||||||
};
|
};
|
||||||
|
|
||||||
|
static const oceanic_common_layout_t oceanic_proplus3_layout = {
|
||||||
|
0x10000, /* memsize */
|
||||||
|
0x0000, /* cf_devinfo */
|
||||||
|
0x0040, /* cf_pointers */
|
||||||
|
0x03E0, /* rb_logbook_begin */
|
||||||
|
0x0A40, /* rb_logbook_end */
|
||||||
|
8, /* rb_logbook_entry_size */
|
||||||
|
0x0A40, /* rb_profile_begin */
|
||||||
|
0xFE00, /* rb_profile_end */
|
||||||
|
0, /* pt_mode_global */
|
||||||
|
0 /* pt_mode_logbook */
|
||||||
|
};
|
||||||
|
|
||||||
static const oceanic_common_layout_t tusa_zenair_layout = {
|
static const oceanic_common_layout_t tusa_zenair_layout = {
|
||||||
0xFFF0, /* memsize */
|
0xFFF0, /* memsize */
|
||||||
0x0000, /* cf_devinfo */
|
0x0000, /* cf_devinfo */
|
||||||
@ -597,6 +613,8 @@ oceanic_atom2_device_open2 (dc_device_t **out, dc_context_t *context, const char
|
|||||||
device->base.layout = &oceanic_atom2b_layout;
|
device->base.layout = &oceanic_atom2b_layout;
|
||||||
} else if (OCEANIC_COMMON_MATCH (device->base.version, oceanic_atom2c_version)) {
|
} else if (OCEANIC_COMMON_MATCH (device->base.version, oceanic_atom2c_version)) {
|
||||||
device->base.layout = &oceanic_atom2c_layout;
|
device->base.layout = &oceanic_atom2c_layout;
|
||||||
|
} else if (OCEANIC_COMMON_MATCH (device->base.version, oceanic_proplus3_version)) {
|
||||||
|
device->base.layout = &oceanic_proplus3_layout;
|
||||||
} else if (OCEANIC_COMMON_MATCH (device->base.version, tusa_zenair_version)) {
|
} else if (OCEANIC_COMMON_MATCH (device->base.version, tusa_zenair_version)) {
|
||||||
device->base.layout = &tusa_zenair_layout;
|
device->base.layout = &tusa_zenair_layout;
|
||||||
} else if (OCEANIC_COMMON_MATCH (device->base.version, oceanic_oc1_version)) {
|
} else if (OCEANIC_COMMON_MATCH (device->base.version, oceanic_oc1_version)) {
|
||||||
|
|||||||
@ -22,6 +22,7 @@
|
|||||||
#include <stdlib.h>
|
#include <stdlib.h>
|
||||||
|
|
||||||
#include <libdivecomputer/uwatec_memomouse.h>
|
#include <libdivecomputer/uwatec_memomouse.h>
|
||||||
|
#include <libdivecomputer/units.h>
|
||||||
|
|
||||||
#include "context-private.h"
|
#include "context-private.h"
|
||||||
#include "parser-private.h"
|
#include "parser-private.h"
|
||||||
@ -141,6 +142,7 @@ uwatec_memomouse_parser_get_field (dc_parser_t *abstract, dc_field_type_t type,
|
|||||||
header += 3;
|
header += 3;
|
||||||
|
|
||||||
dc_gasmix_t *gasmix = (dc_gasmix_t *) value;
|
dc_gasmix_t *gasmix = (dc_gasmix_t *) value;
|
||||||
|
dc_tank_t *tank = (dc_tank_t *) value;
|
||||||
|
|
||||||
if (value) {
|
if (value) {
|
||||||
switch (type) {
|
switch (type) {
|
||||||
@ -167,6 +169,25 @@ uwatec_memomouse_parser_get_field (dc_parser_t *abstract, dc_field_type_t type,
|
|||||||
}
|
}
|
||||||
gasmix->nitrogen = 1.0 - gasmix->oxygen - gasmix->helium;
|
gasmix->nitrogen = 1.0 - gasmix->oxygen - gasmix->helium;
|
||||||
break;
|
break;
|
||||||
|
case DC_FIELD_TANK_COUNT:
|
||||||
|
if (data[10]) {
|
||||||
|
*((unsigned int *) value) = 1;
|
||||||
|
} else {
|
||||||
|
*((unsigned int *) value) = 0;
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
case DC_FIELD_TANK:
|
||||||
|
tank->type = DC_TANKVOLUME_NONE;
|
||||||
|
tank->volume = 0.0;
|
||||||
|
tank->workpressure = 0.0;
|
||||||
|
if (model == 0x1C) {
|
||||||
|
tank->beginpressure = data[10] * 20.0 * PSI / BAR;
|
||||||
|
} else {
|
||||||
|
tank->beginpressure = data[10];
|
||||||
|
}
|
||||||
|
tank->endpressure = 0.0;
|
||||||
|
tank->gasmix = 0;
|
||||||
|
break;
|
||||||
case DC_FIELD_TEMPERATURE_MINIMUM:
|
case DC_FIELD_TEMPERATURE_MINIMUM:
|
||||||
*((double *) value) = (signed char) data[15] / 4.0;
|
*((double *) value) = (signed char) data[15] / 4.0;
|
||||||
break;
|
break;
|
||||||
|
|||||||
@ -374,6 +374,12 @@ uwatec_smart_event_info_t uwatec_smart_galileo_events_2[] = {
|
|||||||
{EV_UNKNOWN, 0xFF, 0},
|
{EV_UNKNOWN, 0xFF, 0},
|
||||||
};
|
};
|
||||||
|
|
||||||
|
static const
|
||||||
|
uwatec_smart_event_info_t uwatec_smart_trimix_events_2[] = {
|
||||||
|
{EV_UNKNOWN, 0x0F, 0},
|
||||||
|
{EV_GASMIX, 0xF0, 4},
|
||||||
|
};
|
||||||
|
|
||||||
static unsigned int
|
static unsigned int
|
||||||
uwatec_smart_find_gasmix (uwatec_smart_parser_t *parser, unsigned int id)
|
uwatec_smart_find_gasmix (uwatec_smart_parser_t *parser, unsigned int id)
|
||||||
{
|
{
|
||||||
@ -419,6 +425,14 @@ uwatec_smart_parser_cache (uwatec_smart_parser_t *parser)
|
|||||||
if (data[43] & 0x80) {
|
if (data[43] & 0x80) {
|
||||||
trimix = 1;
|
trimix = 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (trimix) {
|
||||||
|
parser->events[2] = uwatec_smart_trimix_events_2;
|
||||||
|
parser->nevents[2] = C_ARRAY_SIZE (uwatec_smart_trimix_events_2);
|
||||||
|
} else {
|
||||||
|
parser->events[2] = uwatec_smart_galileo_events_2;
|
||||||
|
parser->nevents[2] = C_ARRAY_SIZE (uwatec_smart_galileo_events_2);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// Get the gas mixes and tanks.
|
// Get the gas mixes and tanks.
|
||||||
@ -459,7 +473,8 @@ uwatec_smart_parser_cache (uwatec_smart_parser_t *parser)
|
|||||||
endpressure = array_uint16_le(data + offset + 2);
|
endpressure = array_uint16_le(data + offset + 2);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if (beginpressure != 0 || endpressure != 0) {
|
if ((beginpressure != 0 || endpressure != 0) &&
|
||||||
|
(beginpressure != 0xFFFF) && (endpressure != 0xFFFF)) {
|
||||||
tank[ntanks].id = id;
|
tank[ntanks].id = id;
|
||||||
tank[ntanks].beginpressure = beginpressure;
|
tank[ntanks].beginpressure = beginpressure;
|
||||||
tank[ntanks].endpressure = endpressure;
|
tank[ntanks].endpressure = endpressure;
|
||||||
@ -1068,7 +1083,8 @@ uwatec_smart_parser_samples_foreach (dc_parser_t *abstract, dc_sample_callback_t
|
|||||||
mixidx = idx;
|
mixidx = idx;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (beginpressure != 0 || endpressure != 0) {
|
if ((beginpressure != 0 || endpressure != 0) &&
|
||||||
|
(beginpressure != 0xFFFF) && (endpressure != 0xFFFF)) {
|
||||||
idx = uwatec_smart_find_tank (parser, mixid);
|
idx = uwatec_smart_find_tank (parser, mixid);
|
||||||
if (idx >= parser->ntanks) {
|
if (idx >= parser->ntanks) {
|
||||||
if (idx >= NGASMIXES) {
|
if (idx >= NGASMIXES) {
|
||||||
|
|||||||
Loading…
x
Reference in New Issue
Block a user