Commit graph

2615 commits

Author SHA1 Message Date
Dirk Hohndel
795cf1bee2 libdc integration: correctly parse DC_FIELD_SALINITY response
libdivecomputer tries to be super careful in what it tells us. It only offers a
density value if that is something that the dive computer explicitly supports,
otherwise it just offers back a flag. We need to then update the density value
ourselves.

Signed-off-by: Dirk Hohndel <dirk@hohndel.org>
2022-04-12 22:29:17 -07:00
Dirk Hohndel
fe53644150 translations: fix Portuguese parent translation
I didn't pay attention and entered the wrong flavor of Portuguese as the
parent translation. The one for Portugal is complete and should be the
parent, back-filling the one for Brazil where needed.

Suggested-by: Christof Arnosti <charno@charno.ch>
Signed-off-by: Dirk Hohndel <dirk@hohndel.org>
2022-03-27 17:11:05 -07:00
Quentin Young
7136ee463c core: allow separators ,; after degree-style coord
Tweak the Lat/Long coordinate parser to allow coordinates of the form:

12.1049° N, 68.2296° W

The coordinate parser works by tokenizing coordinates one at a time.
Consequently it is invoked twice on user input to get latitude and then
longitude. Normally, after parsing the first coordinate, intervening
characters such as , or ; and any whitespace would be discarded from the
input before parsing the second coordinate. Prior to this patch, if the
coordinate format was in degrees followed by a sign (N is a sign in this
example), the parser would skip the bit of code that fast forwards past
any intervening separators and whitespace (, in this example). This
resulted in coordinates of this form not being accepted, because the
second parse would start with , 68.2296° W and reject this as an invalid
coordinate.

To rectify this, the bit of code that fast forwards past separators and
whitespace has been broken out from the tokenization loop and performed
as a final step after a single coordinate has been completely parsed and
validated. Doing it this way makes it independent of the state of the
tokenizer, so that the fast-forward code will always execute once a
coordinate has been successfully parsed.

I've also centralized the list of allowed separators into its own static
string; this is necessary as part of the patch but should also make
allowing additional separator characters between coordinates trivial in
the future, if needed.

Signed-off-by: Quentin Young <qlyoung@qlyoung.net>
2022-03-27 16:37:10 -07:00
Dirk Hohndel
9745f80431 translations: load parent language translations
Many language have country specific differences. We recognize different
flavors of English (US, UK (and South Africa)), German (Germany and
Switzerland), and Portuguese (Brazil and Portugal). For many other
flavors of the languages that we have translations for we have no
support and the way we hard-coded the fallbacks in the past was odd and
meant that in the cases where we do have two flavors, missing strings in
one weren't taken from the other (English as the default language being
the exception).

This tries to do a better job of recognizing some of those parent
languages and loading translators for them, first. Which means if we
then find a translator for the specific language (i.e., de_CH), strings
missing in that translation are next searched in the parent language
(de_DE), before finally providing the source language string (en_US).

Signed-off-by: Dirk Hohndel <dirk@hohndel.org>
2022-03-26 14:10:16 -07:00
Michael Andreen
386a3a35bc profile: Plot sensor data from other dive computers
If the current dive computer doesn't have a sensor for the cylinder then
check if another dive computer has sensor data available and use that
for the plot.

Signed-off-by: Michael Andreen <michael@andreen.dev>
2022-03-26 07:32:50 -07:00
Berthold Stoeger
8577b00cb7 core: add class that collects global objects to be deleted on exit
We have a prevailing problem with global QObjects defined as
static global variables. These get destructed after main()
exits, which means that the QApplication object does not
exist anymore. This more often than not leads to crashes.

In a quick search I didn't find a mechanism to register
objects for deletion with QApplication. Therefore, let's
do our own list of global objects that get destructed
before destroying the QApplication.

Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>
2022-03-16 13:06:06 -07:00
Berthold Stoeger
f9b9582a64 core: fold display.h into profile.h
The only things in display.h were profile related, so the
split between these two files is not comprehensible.
In fact profile.h includes display.h, because it needs the
struct defined therein. Let's just merge these two files.

Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>
2022-03-13 15:07:33 -07:00
Berthold Stoeger
1496bbc314 core: move device related functions from display.h to device.h
It is ominous that these functions were declared in display.h.

Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>
2022-03-13 15:07:33 -07:00
Berthold Stoeger
04241ebb9d core: remove select_dc() function
The only caller misused this function to get access to the
current divecomputer. Remove it, since selection of the
current divecomputer is handled by the MainWindow.

Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>
2022-03-13 15:07:33 -07:00
Berthold Stoeger
e9aaab3c19 core: remove dc_number declaration from display.h
The global variable is already declared in dive.h

Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>
2022-03-13 15:07:33 -07:00
Berthold Stoeger
d5fafc0e44 core: remove current_dc macro
There were only three users of that. For now do it inline, but
we may think about a separate function, which is only available
on desktop.

Moreover, add nullptr-checks, even if they are not strictly
necessary.

Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>
2022-03-13 15:07:33 -07:00
Berthold Stoeger
12406786f1 core: pass dc-number to update_event_name()
The dive was passed as an argument to update_event_name(), but
the divecomputer was derived from the global dc_number variable.
That makes no sense. Therefore, pass the dc_number as argument
and update the only caller (smtk-import).

Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>
2022-03-13 15:07:33 -07:00
Berthold Stoeger
0c4be83b31 core: split proper divecomputer in split_divecomputer()
split_divecomputer() is passed a dive and a divecomputer number.
However, it accesses the currently visible dc!

This would be a nasty bug if it werent for the fact that it is
called when placing an undo command and there it is passed the
current dive and divecomputer anyway.

Nevertheless, fix this.

Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>
2022-03-13 15:07:33 -07:00
Michael Andreen
4e92cb2567 Maintain sensor index for uemis and liquivision
Previosuly they always used index 0 for the active sensor, use
add_sample_pressure instead.

Signed-off-by: Michael Andreen <michael@andreen.dev>
Signed-off-by: Dirk Hohndel <dirk@hohndel.org>
2022-03-12 11:26:00 -08:00
Michael Andreen
9b4263aa87 Allow editing sensors through equipment tab
Add a column to the equipment table that shows if a sensor is attached to a
tank, or which sensors would be available to attach to a tank that currently
doesn't have a pressure sensor associated with it.

Changing the sensor assignement can be undone.

This column is hidden by default as this is a somewhat unusual activity.

Signed-off-by: Michael Andreen <michael@andreen.dev>
Signed-off-by: Dirk Hohndel <dirk@hohndel.org>
2022-03-12 11:24:50 -08:00
Dirk Hohndel
2ede1a4563 cleanup: replace deprecated methods
Sadly the replacements are new in Qt6.

Signed-off-by: Dirk Hohndel <dirk@hohndel.org>
2022-03-12 08:28:32 -08:00
Dirk Hohndel
300248f446 Qt6: use the newer createCentral() API
This will cause us problems when using Qt6 on Android - but I don't see
this happening any time soon.

Signed-off-by: Dirk Hohndel <dirk@hohndel.org>
2022-03-12 08:28:32 -08:00
Dirk Hohndel
6700d617b8 Qt6: the help button is now opt in instead of opt out
This seems much more reasonable.

Signed-off-by: Dirk Hohndel <dirk@hohndel.org>
2022-03-12 08:28:32 -08:00
Dirk Hohndel
e29ecf2c9a Qt6: update to newer APIs for QDateTime
Fortunately, these were already available in Qt5.

Signed-off-by: Dirk Hohndel <dirk@hohndel.org>
2022-03-12 08:28:32 -08:00
Dirk Hohndel
6f46238fc4 Qt6: Bluetooth API changes
Use the explicit QBluetoothUuid instead of just QUuid and deal with new
constants and signal names.
At least with Qt6 we no longer need the ugly QOverload hack.

Signed-off-by: Dirk Hohndel <dirk@hohndel.org>
2022-03-12 08:28:32 -08:00
Dirk Hohndel
78361ef8e3 Qt6: deal with changes from QStringRef to QStringView
QStringRef is gone in Qt6 and mostly replaced by QStringView.  The one major
difference is that direct comparisons with string literals are no longer
possible.

Thanks to Thiago Macieira for helping me avoid more conditional compilation
here.

Signed-off-by: Dirk Hohndel <dirk@hohndel.org>
2022-03-12 08:28:32 -08:00
Dirk Hohndel
47d900bee5 Qt6: don't build MapWidget
Since Qt6 doesn't include QtLocation anymore, we can't build MapWidget.

Signed-off-by: Dirk Hohndel <dirk@hohndel.org>
2022-03-12 08:28:32 -08:00
Dirk Hohndel
59fe2f3d7e cleanup: prevent distracing conversion warnings
We do want the -Wfloat-conversion warnings where they point out
potential bugs. But they are very distracting when they are triggered by
floating point literals (which the standard defines as double) passed to
a function expecting float arguments.

The fact that Qt6 changes the arguments to all these functions from
double to float is... hard to explain, but it is what it is. With these
changes, for the majority of cases we create inlined helpers that
conditionally compile to do the right thing. And in a handful of other
cases we simply cast to float (and accept that on Qt5 this then gets
cast back to double... for none of these cases the potential loss in
precision makes any difference, anyway - which likely is why the Qt
community made the decision to change the type of the arguments in the
first place).

Signed-off-by: Dirk Hohndel <dirk@hohndel.org>
2022-03-12 08:28:32 -08:00
Dirk Hohndel
43ed2e1224 Android: use a sharable location for our files
The first location we should try is one that allows us to share files.
In theory this should work on every device, but we do have a few
fall-backs, just in case.

This also moves the Android specific include to the top which seems much
more standard.

Signed-off-by: Dirk Hohndel <dirk@hohndel.org>
2022-03-01 14:16:25 -08:00
Dirk Hohndel
3b42aada18 core: avoid crash when reading corrupted git data
If a merge mishap creates inconsistent data for a dive in git storage,
where the dive references a dive site that no longer exists, the app
would crash when trying to open the cloud storage.

I don't think a NULL dive could ever happen, but this seems fairly cheap
insurance.

Signed-off-by: Dirk Hohndel <dirk@hohndel.org>
2022-02-28 14:31:19 -08:00
Dirk Hohndel
36af99591c bugfix: call fprintf() instead of printf()
This is an embarrassing oversight.

Signed-off-by: Dirk Hohndel <dirk@hohndel.org>
2022-02-15 14:26:43 -08:00
Berthold Stoeger
9e0712d5dc core: replace dive master by dive guide
In general, replace "dive master" by "dive guide".

However, do not change written dive logs for now. On reading,
accept both versions.

Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>
2022-02-15 09:35:43 -08:00
Oliver Schwaneberg
04c5ab0e36 Uemis support: hack around the need to reconnect the Uemis Zurich
When the file system of the Zurich gets full, the only way to continue to
download from it, is to disconnect and reconnect the dive computer (which
resets the FAT file system that it emulates to 'empty').

This solution is rather hacky and weird because it does a hard count down in a
busy loop, but given the narrow use case, this may be acceptable.

This also adds support for the UEMIS_DIVE_OFFSET environment variable that
allows the user to skip dives on the device.

[refactored by Dirk Hohndel]

Signed-off-by: Oliver Schwaneberg <oliver.schwaneberg@gmail.com>
Signed-off-by: Dirk Hohndel <dirk@hohndel.org>
2022-02-15 09:31:35 -08:00
Jef Driesen
3a77d15eef Add support for the new OSTC hardware
In the latest OSTC hardware, the Telit/Stollman bluetooth module has
been replaced with a u-Blox Nina B2 bluetooth module. The BLE
communication protocol remains roughly the same, except for a few minor
differences:

 - New UUIDs for services and characteristics
 - Only one common characteristic for Rx and Tx
 - Credit based flow control is optional
 - Credit value of 255 corresponds to a disconnect

[Dirk Hohndel: small edit to a comment]

Signed-off-by: Jef Driesen <jef@libdivecomputer.org>
Signed-off-by: Dirk Hohndel <dirk@hohndel.org>
2022-01-31 12:28:32 -08:00
Miika Turkia
f8c794e11c DM5 import: Add dive mode support (OC and CCR)
Signed-off-by: Miika Turkia <miika.turkia@gmail.com>
2022-01-31 09:35:21 -08:00
Berthold Stoeger
efab955d85 cleanup: make feet_to_mm signed
Depths are pretty much universally stored using signed integers
(e.g. depth_t is signed int). For consistency, make feet_to_mm()
likewise return a signed value.

Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>
2022-01-02 13:51:07 -08:00
Berthold Stoeger
4f1034b605 cleanup: make a variable signed
The prev_time variable was defined as unsigned and mixed
with signed variables. gcc rightfully complains with -Wextra.

Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>
2022-01-02 13:51:07 -08:00
Berthold Stoeger
c43311614e cleanup: remove obsolete includes in core/device.cpp
Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>
2022-01-02 13:51:07 -08:00
Berthold Stoeger
72ad4cedf5 cleanup: replace strcmp by std::string methods
Since these are std::strings anyway, there seems to be no point
in using the C-lib functions. YMMV, but to me that code is
distinctly more easy to parse.

Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>
2022-01-02 13:51:07 -08:00
Berthold Stoeger
66896ad7d7 cleaup: remove device::operator==()
The last user was removed when including devices in the undo
system.

Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>
2022-01-02 13:51:07 -08:00
Berthold Stoeger
c893d19ea4 cleanup: pass all parameters to weightsystem_t
With -Wextra, gcc/g++ complains that compound initialization
of weightsystem_t misses the auto_filled parameter. Add it.
For C++ code we might think about writing a constructor. However,
we use two versions: with and without copied string.

Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>
2022-01-02 13:51:07 -08:00
Berthold Stoeger
d89ef3d906 cleanup: fix narrowing type conversion warning
In pscr_o2() the result of a double calculation was implicitly
converted to int, which resulted in a gcc warning.

Part of the expression was explicitly converted to int, but then
subtracted from a double.

Instead, do all the calculations in double and cast the final
expression to int. This is probably the prudent thing to do.

Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>
2022-01-02 13:51:07 -08:00
Berthold Stoeger
2645fa1495 profile: remove fast argument of create_plot_info_new()
This prevented calculation of the pressure data when dragging
planner handles. However, this lead to weird artifacts.

As an alternative, if this turns out to be too slow, we might
disable the plotting of the pressure curves instead.

That said, even on my super-slow fanless laptop, this performs
reasonably.

Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>
2021-12-17 11:54:23 -08:00
Berthold Stoeger
725fda3cd1 profile: don't add excessive depth
The old get_maxdepth() function in profile.c was accounting for
two things:
- the partial pressure graphs
- rounding to sane value

Both are now taken care of by the profile itself. This leads to
excessive max-depths. Remove the code from profile.c.

Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>
2021-12-17 11:54:23 -08:00
Berthold Stoeger
789eb2c620 profile: clear plot_info structure when freeing data
free_plot_info_data() frees the sample and pressure arrays
and accordingly sets the corresponding pointers to NULL.

However, it doesn't clear the element-count and thus leaves
the structure in an inconsistent state.

Clear the whole structure with memset(). I am not a fan of
doing so, but there are existing memset() calls in the
same source file, so let's keep it like that for consistency.

Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>
2021-12-17 11:54:23 -08:00
Berthold Stoeger
01af4bcd00 profile: remove min/max entries from plot_data
These were the minimum and maximum of a 9-min window.
The profile now uses an adaptive peak-search, so this is not
used anymore.

Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>
2021-12-17 11:54:23 -08:00
Berthold Stoeger
0e9eee0a7f core: return floating point from to_PSI() functions
Dive data are stored internally using integral types using
appropriately fine units (mm, mbar, mkelvin, etc.). These
are converted with functions defined in units.h for display
(m, bar, C, etc.). Usually floating points are returned by
these functions, to retain the necessary precision. There
is one exception: the to_PSI() and mbar_to_PSI() functions.

For consistency, make these functions likewise return floats.
This will be needed for the rework of the profile-axes.
The plan is to use the conversion functions to make the
axes aware of the displayed values. This in turn will be
necessary to place the ticks at sensible distances. However,
the conversions need to be precise, which is not the
case for the current to_PSI() functions.

Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>
2021-12-17 11:54:23 -08:00
Berthold Stoeger
9e831c5001 core: remove DPR from IconMetrics class
There is no user of this left, because the device-pixel-ratio
is now passed directly to the profile.

Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>
2021-12-17 11:54:23 -08:00
Berthold Stoeger
f7565c4a0f core: clear image before rendering SVGs
In renderSVGIconWidth() the image was not cleared, leading
to garbage backgrounds. This should have affected the video
icons. Apparently, nobody is using them..?

Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>
2021-12-17 11:54:23 -08:00
Berthold Stoeger
f82ae2be7f profile: cache pixmaps for dive event items
For better scalability, we might replace the dive event icons
by SVGs. Since rendering SVGs is potentially very slow, cache
the pixmaps when the scene is generated.

Note: this does not yet do any SVG rendering, only the caching
of pixmaps.

Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>
2021-12-17 11:54:23 -08:00
Berthold Stoeger
24cf6709e3 profile: simplify get_maxtime()
This function has accumulated quite some cruft. It seems to add
additional space to make place for certain chart features
(e.g. the average depth text item).

However, it makes no sense to solve this here, as only the
profile knows how much place is needed to display these
features.

Therefore, basically revert this to the original version,
which simply returns the maximum time for long dives
and a threshhold for short dives that depends on the
zoomed_plot setting.

The result looks more reasonable to me, as there is no
(varying!) empty space to the right of the profile.

Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>
2021-12-17 11:54:23 -08:00
Berthold Stoeger
d1b8f1ca3d formatting: move get_trip_title to string-format.h and split it
To enable grouping by trip in the statistics module, split
the get_trip_title() function in a version that appends
a "(n dive(s)" string an one that doesn't. The statistics
module doesn't want that added string, since it displays
the number of dives in a different way.

Also, move the functions to string-format.h, where these
are collected. And rename them to camelCase. Yes, it's
ugly, but consistent with most other C++ code in the code
base.

Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>
2021-12-17 10:36:13 -08:00
Berthold Stoeger
afa989e32c cleanup: replace std::size() replacement by real deal
At other places, we already used std::size().

Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>
2021-12-17 10:36:13 -08:00
Dirk Hohndel
61e8ceef05 core: avoid resource leak
That code was obviously wrong from the start.

Fixes CID 373921

Signed-off-by: Dirk Hohndel <dirk@hohndel.org>
2021-12-17 09:23:34 -08:00
Dirk Hohndel
cffcce77bb core: avoid uninitialized data
In an abundance of caution, make sure all fields are initialized.

Fixes CID 350734

Signed-off-by: Dirk Hohndel <dirk@hohndel.org>
2021-12-17 09:23:10 -08:00
Berthold Stoeger
1af67512a1 cylinders: add cylinder before hidden cylinders
When adding a cylinder, it was added at the end of the list.
This would make hidden cylinders visible as the new rule is
to only hide unused cylinders at the end of the list.

Therefore, add the cylinder after the last used cylinder,
i.e. before the first hidden cylinder.

This means that the position where the cylinder is added has
to be hidden in the undo command.

Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>
2021-12-13 11:54:24 -08:00
Robert C. Helling
9fd531dcc5 Round gas depth properly
The D in MOD, EAD, END, and EADD stands for "depth" and
as such these should be mm in int rather than double.

The intermediate fn2 and fhe2, however, as intermediate
value should not be rounded to an integer.

The upshot of this is a litle more numerical stability.
It should lead to more stable values in TestProfile
when run on architectures with different floating
point precision.

Signed-off-by: Robert C. Helling <helling@atdotde.de>
2021-12-06 22:29:04 +01:00
Robert C. Helling
07745893e5 Don't attempt to compute SAC for CCR dives
CCRs are different. It does not make sense to compute
a depth dependent SAC. You could compute the rate of O2
consumption but even that is likely wrong (as O2 in the
diluent would enter that as well), so simply don't attempt
it.

Signed-off-by: Robert C. Helling <helling@atdotde.de>
2021-11-24 11:03:51 -08:00
Dirk Hohndel
cfd6a1634f cleanup: fix SkipEmptyParts warning for mobile
And while doing that, have all the cases where we already include
qthelper.h simply use a define in that header file - but keep the two
other instances of the define where the C++ source don't need qthelper.h
otherwise.

Signed-off-by: Dirk Hohndel <dirk@hohndel.org>
2021-11-24 10:53:26 -08:00
Dirk Hohndel
31e688ec00 core: load and save fingerprint to cloud storage
Very similar structure to the XML format. Raw data is again saved as a
hex string (which implicitly provides us with its length). The rest of
components are in a more human readable format.

Signed-off-by: Dirk Hohndel <dirk@hohndel.org>
2021-11-12 12:45:22 -08:00
Dirk Hohndel
2b1db9da82 core: load and save fingerprints to XML
We always use the global fingerprint table - maybe this should just not
be a parameter of the accessor functions?

The syntax is very simple - the raw data is encoded as a hex string, the
rest of the components are hex numbers.

Signed-off-by: Dirk Hohndel <dirk@hohndel.org>
2021-11-12 12:45:22 -08:00
Dirk Hohndel
33527cb9e5 core: add more C interfaces for fingerprint table
These are used to read/write fingerprint records as git or XML data from
C code.

Signed-off-by: Dirk Hohndel <dirk@hohndel.org>
2021-11-12 12:45:22 -08:00
Dirk Hohndel
02c770d997 core: use fingerprint table and on disk fingerprints
In order to not break existing behavior, we still store fingerprints on disk, but
we first check the data in the in-memory table, and we remember the fingerprint data
in the fingerprint table as well (which is then saved as part of the dive log data).

Signed-off-by: Dirk Hohndel <dirk@hohndel.org>
2021-11-12 12:45:22 -08:00
Dirk Hohndel
fa250906c9 core: add structures for handling fingerprints
This just adds the basic structures and the accessor functions needed to
manage a table of fingerprint data. The table is indexed by the hash of
the model name and binary serial number as created by libdivcecomputer.
This way the data is accessible when libdivecomputer fist accesses a
dive computer (which is the point in time when we need to use the
fingerprint.

The table also contains the corresponding device id and dive id so we
can verify that the current dive table still contains that dive.

Signed-off-by: Dirk Hohndel <dirk@hohndel.org>
2021-11-05 10:36:56 -07:00
Dirk Hohndel
95192bdf83 core: move has_dive helper function
This way it can be used by other code that needs this capability.

Signed-off-by: Dirk Hohndel <dirk@hohndel.org>
2021-10-30 20:22:52 -07:00
Dirk Hohndel
838151835b dc-download: use short date string
In both places in the UI where we show the date of a dive during
download we are actually pressed for space. So let's use the short
version of the date string to save some space.

Signed-off-by: Dirk Hohndel <dirk@hohndel.org>
2021-10-29 15:14:59 -07:00
Dirk Hohndel
44691dae10 dc-download: fingerprint details are debug info
In the normal use of the app this information is simply too verbose.

Signed-off-by: Dirk Hohndel <dirk@hohndel.org>
2021-10-29 15:14:59 -07:00
Dirk Hohndel
10e6519ad5 dc-download: give progress update for long downloads
Most divecomputers download data dive by dive - so we get reasonably
frequent updates during the download (as new dives are found and posted
in the progress text area). But some (like the G2) download all of the
new dives at once and only then start parsing them. As a result the
download can look like it is hung.

As a compromise this shows updates on the data received in 10kB
increments. Which for most cases should never be shown and therefore not
make the user experience any worse - but for cases like the G2 will make
a huge difference.

Signed-off-by: Dirk Hohndel <dirk@hohndel.org>
2021-10-29 15:14:59 -07:00
Dirk Hohndel
8e4b2d9b82 cleanup: replace QRegExp with QRegularExpression
Qt 6 will drop support for QRegExp.
Use QRegularExpression instead.

Much of this is a simple replacement of one class with the other, but
there are some changes to the way matches are tracked and captures are
created. Also, the exactMatch now needs to be implemented via anchors in
the regular expression itself.

Signed-off-by: Dirk Hohndel <dirk@hohndel.org>
2021-10-27 12:35:09 -07:00
Dirk Hohndel
4d0c863d61 cleanup: replace QRegExp with QRegularExpression
Qt 6 will drop support for QRegExp.
Use QRegularExpression instead.

This is a straight forward replacement without any other code changes.

Signed-off-by: Dirk Hohndel <dirk@hohndel.org>
2021-10-27 12:33:20 -07:00
Berthold Stoeger
540e4437d5 cleanup: fix conversion warning
Fix a pair of warnings, which annoyed me for a long time:
For some reasons prefs.bottompo2 is an integer (mbar)
whereas prefs.modpO2 is a float (bar). This results
in mixed integer/floating point arithmetics when
conditionally using either of them. And ultimately
a warning, when storing a mbar value as an integer.
Fix this by an explicit cast to int after converting
modpO2 to mbar.

Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>
2021-10-16 15:32:56 -07:00
Robert C. Helling
41258647d2 Don't access gasmix.o2.fraction
Air is a special gas that does not contain oxygen according
to gasmix.o2.fraction. If you want to use the fo2, you
need to use get_o2() to treat this special case correctly.

This fixes a bug when setting the MND of a gas containing
21% oxygen when o2 is considered not narcotic.

Reported-by: Christoph Gruen <gruen.christoph@gmail.com>
Signed-off-by: Robert C. Helling <helling@atdotde.de>
2021-10-01 08:50:36 -07:00
Berthold Stoeger
a481cdc13d core: don't write pressure samples with "no sensor"
This has led to broken XML files, don't do it.

Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>
2021-09-22 09:11:00 -07:00
Berthold Stoeger
d9c77a27da core: properly clear pressure data of invalid sensors
When we found an invalid sensor (referring to a non
existing cylinder) in fixup_dive() the sensor-id was
set to NO_SENSOR.

This led to invalid XML files, because the code decides
to switch into legacy mode. However, there are two
pressure readings, which is invalid in legacy mode.

Therefore, also clear the pressure data.

Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>
2021-09-22 09:11:00 -07:00
Dirk Hohndel
8525b2e274 core: remove superfluous arguments
Fixes CID 373231

Signed-off-by: Dirk Hohndel <dirk@hohndel.org>
2021-09-20 14:49:57 -07:00
Linus Torvalds
85392343fa Re-do the libdivecomputer fingerprint save/load code
This tries to make our fingerprinting code work better, by avoiding
using the "deviceid" field that has always been unreliable because we've
calculated it multiple different ways, and even for the same version of
subsurface, it ends up changing in the middle (ie we calculate one value
initially, then re-calculate it when we have a proper serial number
string).

So instead, the fingerprinting code will look up and save the
fingerprint file using purely "stable" information that is available
early during the download:

 - the device model name (which is a string with vendor and product name
   separated by a space)

 - the DC_EVENT_DEVINFO 32-bit 'serial' number (which is not necessarily
   a real serial number at all, but hopefully at least a unique number
   for the particular product)

but because the model name is not necessarily a good filename (think
slashes and other possibly invalid characters), we hash that model name
and use the resulting hex number in the fingerprint file name.

This way the fingerprint file is unambiguous at load and save time, and
depends purely on libdivecomputer data.

But because we also need to verify that we have the actual _dive_
associated with that fingerprint, we also need to save the final
deviceid and diveid when saving the fingerprint file, so that when we
load it again we can look up the dive and verify that we have it before
we use the fingerprint data.

To do that, the fingerprint file itself contains not just the
fingerprint data from libdivecomputer, but the last 8 bytes of the file
are the (subsurface) deviceid and the diveid of the dive that is
associated with the fingerprint.

Signed-off-by: Linus Torvalds <torvalds@linux-foundation.org>
2021-09-19 16:51:46 -07:00
Dirk Hohndel
2a0d14b100 core: remove location service preferences
Including the related tests.

Signed-off-by: Dirk Hohndel <dirk@hohndel.org>
2021-09-13 11:21:34 -07:00
Dirk Hohndel
6f813b9f8e mobile: remove GpsLocation
Only used in context of acquiring GPS locations with the mobile app, which
we no longer do.

Keep the DiveAndLocation structure around as that's needed by the
ApplyGpsFixes command.

Signed-off-by: Dirk Hohndel <dirk@hohndel.org>
2021-09-13 11:21:34 -07:00
Dirk Hohndel
bea552bf0d mobile: remove GpsListModel
This is only needed to show the list of GPS fixes obtained with
the now removed location service.

Signed-off-by: Dirk Hohndel <dirk@hohndel.org>
2021-09-13 11:21:34 -07:00
Josh Torres
7e6d9935f1 core: fix off-by-one causing incorrect profile display
In commit 4724c88 get_plot_details_new was updated to pass an index
instead of the entry into plot_string. This means we are passing "i" to
plot_string after the final increment of the for loop, instead of
getting the entry[i] within the loop before the final increment. This
means if we are mousing over the far right of the graph, where the time
based break is not hit, we will end up passing an index equal to nr-2
instead of nr-3, which is intended to shave off the final two rows
containing data not useful to the display.

There are a handful of ways to fix this. This commit intends to be
consistent with stylistic choices made elsewhere in the project.

Signed-off-by: Josh Torres <torres.josh.j@gmail.com>
Signed-off-by: Dirk Hohndel <dirk@hohndel.org>
2021-09-06 13:00:37 -07:00
Berthold Stoeger
28fe6a7b38 core: add a function to test for sensors of a given cylinder
We want to prevent the user from accidentally deleting a
cylinder with sensor readings. Therefore, we need such a
function.

Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>
2021-09-03 13:35:28 -07:00
Berthold Stoeger
5eda1c0e39 parser: XML_PARSE_RECOVER to xmlReadMemory()
Due to changes in the handling of sensor-ids, invalid XMLs were
generated. In particular, these contained duplicate attributes
in the sample tags.

Even though these files shouldn't exist, let's try to parse
them anyway. Some data will be lost, but that's better than
not opening the file.

libxml2 can be told to try to recover from such petty(?) errors
by passing the XML_PARSE_RECOVER flag.

Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>
2021-09-03 09:30:34 -07:00
Robert C. Helling
c634a07e38 Planner: Correctly compute CNS and OTU for bailout segments
For dives with mixed divemode, one needs to check sample.setpoint
to figure out if the segment is an OC segment and the po2 needs
to be computed from the gasmix and ambient pressure.

This fixes #3310

Signed-off-by: Robert C. Helling <helling@atdotde.de>
2021-08-19 10:58:08 -07:00
Dirk Hohndel
e7a5ec46f5 undo/device: adjust device management infrastructure
We no longer need the remove infrastructure, and the edit nickname function
becomes much more intuitive to use by passing in the dive computer for
which we want to create a nickname instead of the internal index into
the array of devices.

This also removes / simplifies the device list update signals in the
DiveListNotifier.

Signed-off-by: Dirk Hohndel <dirk@hohndel.org>
2021-08-18 13:22:02 -07:00
Dirk Hohndel
fbe17e620e core: add get_or_add helper for dc table
This makes it much easier to manipulate dc nickname entries. In order
for that to work we can't simply remove entries with empty nickname (but
that isn't needed, anyway, as the code that saves XML or git already
handles that case correctly).

Signed-off-by: Dirk Hohndel <dirk@hohndel.org>
2021-08-18 13:22:02 -07:00
Linus Torvalds
47b0a9ce65 Don't share dive computer data allocations
... it just causes problems later when we free them, since we don't do
any reference counting.

Signed-off-by: Linus Torvalds <torvalds@linux-foundation.org>
2021-08-18 13:22:02 -07:00
Linus Torvalds
d141bbf38f Update the serial number and deviceid in sync when loading
When we save the divecomputer data, we never actually save the serial
value as a field.  We used to rely on saving the very dodgy 'deviceid',
and then look up the serial number from there.  And that never really
worked reliably, but we didn't really notice, because we never really
_used_ the serial number anywhere.

The only place the serial number is actually reliably displayed is in
the "Extra data" tab, which contains the key value pairs, and that's
where the original dive download code got the serial number from.

So just parse that at load time too, the same way we parsed it at dive
download time.

In fact, do the firmware version the same way, and remove the code from
the downloader, since it too can rely on 'add_extra_data()' just picking
up the information directly.

Signed-off-by: Linus Torvalds <torvalds@linux-foundation.org>
2021-08-18 13:22:02 -07:00
Linus Torvalds
6c4e890960 Clean up divecomputer 'device' handling
We have this odd legacy notion of a divecomputer 'device', that was
originally just basically the libdivecomputer 'EVENT_DEVINFO' report
that was associated with each dive.  So it had firmware version,
deviceid, and serial number.

It had also gotten extended to do 'nickname' handling, and it was all
confusing, ugly and bad.  It was particularly bad because it wasn't
actually a 'per device' thing at all: due to the firmware field, a dive
computer that got a firmware update forced a new 'device'.

To make matters worse, the 'deviceid' was also almost random, because
we've calculated it a couple of different ways, and libdivecomputer
itself has changed how the legacy 32-bit 'serial number' is expressed.

Finally, because of all these issues, we didn't even try to make the
thing unique, so it really ended up being a random snapshot of the state
of the dive computer at the time of a dive, and sometimes we'd pick one,
and sometimes another, since they weren't really well-defined.

So get rid of all this confusion.

The new rules:

 - the actual random dive computer state at the time of a dive is kept
   in the dive data. So if you want to know the firmware version, it
   should be in the 'extra data'

 - the only serial number that matters is the string one in the extra
   data, because that's the one that actually matches what the dive
   computer reports, and isn't some random 32-bit integer with ambiguous
   formatting.

 - the 'device id' - the thing we match with (together with the model
   name, eg "Suunto EON Steel") is purely a hash of the real serial
   number.

   The device ID that libdivecomputer reports in EVENT_DEVINFO is
   ignored, as is the device ID we've saved in the XML or git files. If
   we have a serial number, the device ID will be uniquely associated
   with that serial number, and if we don't have one, the device ID will
   be zero (for 'match anything').

   So now 'deviceid' is literally just a shorthand for the serial number
   string, and the two are joined at the hip.

 - the 'device' managament is _only_ used to track devices that have
   serial numbers _and_ nicknames. So no more different device
   structures just because one had a nickname and the other didn't etc.

   Without a serial number, the device is 'anonymous' and fundamentally
   cannot be distinguished from other devices of the same model, so a
   nickname is meaningless. And without a nickname, there is no point in
   creating a device data structure, since all the data is in the dive
   itself and the device structure wouldn't add any value..

These rules mean that we no longer have ambiguous 'device' structures,
and we can never have duplicates that can confuse us.

This does mean that you can't give a nickname to a device that cannot be
uniquely identified with a serial number, but those are happily fairly
rare (and mostly older ones).  Dirk said he'd look at what it takes to
give more dive computers proper serial numbers, and I already did it for
the Garmin Descent family yesterday.

(Honesty in advertizing: right now you can't add a nickname to a dive
computer that doesn't already have one, because such a dive computer
will not have a device structure.  But that's a UI issue, and I'll sort
that out separately)

Signed-off-by: Linus Torvalds <torvalds@linux-foundation.org>
2021-08-18 13:22:02 -07:00
Dirk Hohndel
75fdb8676b core: add downloaded GPS to existing dive site
If we download a first dive computer and add a dive site to the dive (by
setting a location name for example), and then download from another
dive computer that provides us with GPS data, we should keep the
existing dive site information, but add the GPS data from the freshly
downloaded dive computer.

Signed-off-by: Dirk Hohndel <dirk@hohndel.org>
2021-08-15 09:31:17 -07:00
Richard Fuchs
f308a6b57b export: clean up temp file after divelogs.de upload
This adds a cleanup function to be called after a divelogs.de upload
finishes (successful or not) to make sure the temporary zip file is
closed and removed.

Signed-off-by: Richard Fuchs <dfx@dfx.at>
2021-08-06 11:05:06 -07:00
Richard Fuchs
cf78e4cb20 export: use unique temporary file for divelogs.de upload
On multi-user systems with a shared directory for temporary files, using
a static file name can lead to permissions problems and subsequent
errors due to collisions. Use a random unique file name for each
generated file to avoid these problems.

Note: the temporary file generated from the divelogs.de upload is still
left behind after the upload finishes.

Signed-off-by: Richard Fuchs <dfx@dfx.at>
2021-08-03 08:34:18 -07:00
Dirk Hohndel
096de0efd0 core/import: fix string check logic
The intent of the code was to check that there is a string and it has at least
two characters. Since iter is the result of a strchr(iter, '|') call, we
know that if iter isn't NULL, iter[0] is '|', so we only need to check the next
character.

Signed-off-by: Dirk Hohndel <dirk@hohndel.org>
2021-07-23 11:30:17 -07:00
Dirk Hohndel
c90352008b core/csv-import: don't do pointer math after realloc
try_to_xslt_open_csv() re-allocates the memory passed in (not really great as
far as design goes, maybe something that should be reimplemented). Doing
pointer arithmatic with the returned base pointer results in garbage, unless
one gets super lucky and the realloc manages to not move the memory.

It's a wonder this ever worked.

Signed-off-by: Dirk Hohndel <dirk@hohndel.org>
2021-07-23 11:30:17 -07:00
Berthold Stoeger
846e1ba53e core: always create a fake profile if there are no samples
Before making the cylinder-table dynamic, dives always
had at least one cylinger. When such a dive is displayed,
the TabDiveInformation class calls per_cylinder_mean_depth().
If there are no samples, this function generates a "fake
profile" with fake_dc(). Thus, effectively dives always
had samples once the user was displaying them.

When the cylinder-table was made dynamic, dives without
cylinders were supported. This can notably happen, when
importing from CSV (this could actually be a bug).
per_cylinder_mean_depth() exits early in that case and
doesn't create a fake profile. This lead to crashes
of the profile-widget, which were fixed in 6b2e56e513.
Non-sample dives were now shown with the Subsurface-logo.

To restore the previous behavior, genarate a fake profile
for sample-less dives in fixup_dive(), which is called
anytime  a dive is loaded or imported. This seems to
have been the intention anyway and this worked only
"by chance". This will make a few fake_dc() calls obsolete,
but so be it.

Since fake profiles are now generated on loading,
the parse-tests need to be fixed to account for that.

Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>
Signed-off-by: Dirk Hohndel <dirk@hohndel.org>
2021-07-23 11:30:17 -07:00
Berthold Stoeger
63e1516579 core: recalculate CNS values on merge
When merging two dives, the higher CNS value was taken. This could
result in inconsistent CNS values if two dives were merged where
one dive's CNS was calculated from a "fake profile", i.e. a dive
without dive-computer profile. In that case, the most conservative
value (all time spent at the bottom) was assumed. The merged dive
then consisted of the dive-computer profile and the conservative
CNS estimate.

This is fixed by setting the CNS value to "0" after merging,
which means "unknown". The correct value will then be recalculated
in "fixup_dive" from the actual sample data.

Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>
2021-07-23 11:30:17 -07:00
Berthold Stoeger
b18b3119b5 cleanup: don't NUL-terminate membuffer in uploadDiveLogsDE
The data of the membuffer is passed as a data/length pair
to xmlReadMemory(). There is no point in NUL-terminating it.

Moreover, pass the data directly to xmlReadMemory()
instead of via variables. These variables are reused
later with a different meaning, making this super-confusing.

The membuf variable is turned from "const char *" to "char *"
to signal that we own the buffer.

Amazingly, zip_source_buffer() frees the buffer, even though
a "const void *" is passed in. This API is pure madness. Add
a comment.

Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>
2021-07-23 11:22:43 -07:00
Berthold Stoeger
16b31985c3 cleanup: replace membuffer by membufferpp in C-code
Thus, the membuffer data is automatically freed when going
out of scope - one thing less to worry about.

This fixes one use-after-free bug in uploadDiveLogsDE.cpp
and one extremely questionable practice in divetooltipitem.cpp:
The membuffer was a shared instance across all instances
of the DiveToolTipItem.

Remves unnecessary #include directives in files that didn't
even use membuffer.

Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>
2021-07-23 11:22:43 -07:00
Berthold Stoeger
f142e9a9c6 core: C++-ify membuffer
C-style memory management is a pain and nearly nobody seems to get
it right. Add a C++-version of membuffer that frees the buffer
when it gets out-of-scope. Originally, I was thinking about
conditionally adding a constructor/destructor pair when compiling
with C++. But then decided to create a derived class membufferpp,
because it would be extremely confusing to have behavioral change
when changing a source from from C to C++ or vice-versa.

Also add a comment about the dangers of returned pointer: They
become dangling on changes to the membuffer.

Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>
2021-07-23 11:22:43 -07:00
Berthold Stoeger
0c84f369c3 core: use int16_t for sensor-id
The sensor-id in the sample struct was a uint8_t, with all
the known problems of unsigned integers. In the rest of the
code cylinder ids are signed integers. To avoid confusion,
make it a signed int. int8_t should be enough (max. 127
cylinders). To allow for degenerate cases, use an int16_t.
16k cylinders should be enough for everyone.

Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>
2021-07-23 11:16:00 -07:00
Dirk Hohndel
2193f09006 core/ble: add auto detection for Aladin A2
This way it will be recognized as a dive computer when it is scanned via BLE.

Signed-off-by: Dirk Hohndel <dirk@hohndel.org>
2021-07-20 09:28:38 -07:00
Berthold Stoeger
82f967ddb3 core: sanitize pressure-sensor cylinder ids in fixup_dive()
The code will happily perform out-of-bound accesses if
pressure-sensors refer to non-existing cylinders. Therefore,
sanitize these values in fixup_dive(), which is called
everytime a dive is loaded or imported.

Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>
2021-07-19 10:13:51 -07:00
Berthold Stoeger
361678dcbe parser: don't create samples with invalid cylinder ids
By default, the parser would create samples with cylinder
ids 0 and 1. This creates out-of-bound accesses for the
common one-cylinder (or even no-cylinder) dives. These
were harmless when the cylinder-table was of a fixed size.
Since changing to a dynamic cylinder-table, these became
actual out-of-bound accesses. Don't create such samples
in the parser.

Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>
2021-07-19 10:13:51 -07:00
Berthold Stoeger
7e11a35371 core: add a special NO_SENSOR value for sample::sensor
The sensor member of sample refers to a cylinder from which
the pressure was read. However, some dives don't even have
a cylinder. Therefore, introduce a special NO_SENSOR value
for these dives. Since the cylinder is given as a uint8_t,
0xff seems to be a sensible choice.

Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>
2021-07-19 10:13:51 -07:00
Miika Turkia
48c2929f48 Fix coverity reported memory leaks
Signed-off-by: Miika Turkia <miika.turkia@gmail.com>
2021-07-19 09:07:48 -07:00
Miika Turkia
63795a84f4 Export unused cylinders to divelogs.de
When user has selected to show unused cylinders in equipment tab,
respect this setting when exporting to divelogs.de.

Fixes #3277

Signed-off-by: Miika Turkia <miika.turkia@gmail.com>
2021-07-18 13:43:54 +03:00