1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
|
#include <string.h>
#include "dive.h"
#include "device.h"
static struct device_info *device_info_list;
struct device_info *head_of_device_info_list(void)
{
return device_info_list;
}
void remove_dive_computer(const char *model, uint32_t deviceid)
{
free(remove_device_info(model, deviceid));
}
static int match_device_info(struct device_info *entry, const char *model, uint32_t deviceid)
{
return !strcmp(entry->model, model) && entry->deviceid == deviceid;
}
/* just find the entry for this divecomputer */
struct device_info *get_device_info(const char *model, uint32_t deviceid)
{
struct device_info *known = device_info_list;
/* a 0 deviceid doesn't get a nickname - those come from development
* versions of Subsurface that didn't store the deviceid in the divecomputer entries */
if (!deviceid || !model)
return NULL;
while (known) {
if (match_device_info(known, model, deviceid))
return known;
known = known->next;
}
return NULL;
}
/*
* Sort the device_info list, so that we write it out
* in a stable order. Otherwise we'll end up having the
* XML file have the devices listed in some arbitrary
* order, which is annoying.
*/
static void add_entry_sorted(struct device_info *entry)
{
struct device_info *p, **pp = &device_info_list;
while ((p = *pp) != NULL) {
int cmp = strcmp(p->model, entry->model);
if (cmp > 0)
break;
if (!cmp && p->deviceid > entry->deviceid)
break;
pp = &p->next;
}
entry->next = p;
*pp = entry;
}
/* Get an existing device info model or create a new one if valid */
struct device_info *create_device_info(const char *model, uint32_t deviceid)
{
struct device_info *entry;
if (!deviceid || !model || !*model)
return NULL;
entry = get_device_info(model, deviceid);
if (entry)
return entry;
entry = calloc(1, sizeof(*entry));
if (entry) {
entry->model = strdup(model);
entry->deviceid = deviceid;
add_entry_sorted(entry);
}
return entry;
}
/* do we have a DIFFERENT divecomputer of the same model? */
struct device_info *get_different_device_info(const char *model, uint32_t deviceid)
{
struct device_info *known = device_info_list;
/* a 0 deviceid matches any DC of the same model - those come from development
* versions of Subsurface that didn't store the deviceid in the divecomputer entries */
if (!deviceid)
return NULL;
if (!model)
model = "";
while (known) {
if (known->model && !strcmp(known->model, model) &&
known->deviceid != deviceid)
return known;
known = known->next;
}
return NULL;
}
struct device_info *remove_device_info(const char *model, uint32_t deviceid)
{
struct device_info *entry, **p;
if (!deviceid || !model || !*model)
return NULL;
p = &device_info_list;
while ((entry = *p) != NULL) {
if (match_device_info(entry, model, deviceid)) {
*p = entry->next;
break;
}
p = &entry->next;
}
return entry;
}
|