diff --git a/plugins/channelrx/sigmffilesink/readme.md b/plugins/channelrx/sigmffilesink/readme.md
index 21691249a..f5e1690ef 100644
--- a/plugins/channelrx/sigmffilesink/readme.md
+++ b/plugins/channelrx/sigmffilesink/readme.md
@@ -13,6 +13,8 @@ As per SigMF specifications two files are created in fact.
If a filename is given without `.sigmf-meta` extension then the `.sigmf-meta` extension is appended automatically.
If a filename is given with an extension different of `.sigmf-meta` then the extension is replaced by `.sigmf-meta` automatically.
+If the couple `.sigmf-meta`, `.sigmf-data` exists for a file set and it was recorded by SDRangel then new data will be appended as new captures.
+
It adds a dependency to the [libsigmf library](https://github.com/f4exb/libsigmf) more specifically the `f4exb` fork that supports `multirecordings` and `sdrangel` extensions.
Interface
diff --git a/plugins/channelrx/sigmffilesink/sigmffilesinksink.cpp b/plugins/channelrx/sigmffilesink/sigmffilesinksink.cpp
index 0687a46cd..283b9872e 100644
--- a/plugins/channelrx/sigmffilesink/sigmffilesinksink.cpp
+++ b/plugins/channelrx/sigmffilesink/sigmffilesinksink.cpp
@@ -264,8 +264,8 @@ void SigMFFileSinkSink::applySettings(const SigMFFileSinkSettings& settings, boo
{
m_fileSink.setFileName(fileBase);
m_fileSink.setHardwareId(m_deviceHwId);
- m_msCount = 0;
- m_byteCount = 0;
+ m_msCount = m_fileSink.getInitialMsCount();
+ m_byteCount = m_fileSink.getInitialBytesCount();
m_recordEnabled = true;
}
else
diff --git a/sdrbase/dsp/sigmffilerecord.cpp b/sdrbase/dsp/sigmffilerecord.cpp
index a98407fa5..a1ff6fec1 100644
--- a/sdrbase/dsp/sigmffilerecord.cpp
+++ b/sdrbase/dsp/sigmffilerecord.cpp
@@ -19,6 +19,7 @@
#include
#include
+#include
#include
#include "libsigmf/sigmf_core_generated.h"
@@ -39,7 +40,9 @@ SigMFFileRecord::SigMFFileRecord() :
m_recordOn(false),
m_recordStart(true),
m_sampleStart(0),
- m_sampleCount(0)
+ m_sampleCount(0),
+ m_initialMsCount(0),
+ m_initialBytesCount(0)
{
qDebug("SigMFFileRecord::SigMFFileRecord: test");
setObjectName("SigMFFileSink");
@@ -57,7 +60,9 @@ SigMFFileRecord::SigMFFileRecord(const QString& fileName, const QString& hardwar
m_recordOn(false),
m_recordStart(true),
m_sampleStart(0),
- m_sampleCount(0)
+ m_sampleCount(0),
+ m_initialMsCount(0),
+ m_initialBytesCount(0)
{
qDebug("SigMFFileRecord::SigMFFileRecord: %s", qPrintable(fileName));
setObjectName("SigMFFileSink");
@@ -98,7 +103,66 @@ void SigMFFileRecord::setFileName(const QString& fileName)
}
m_fileName = fileName;
- m_recordStart = true;
+
+ if (QFile::exists(fileName + ".sigmf-data") && QFile::exists(fileName + ".sigmf-meta"))
+ {
+ m_metaFileName = m_fileName + ".sigmf-meta";
+ std::ifstream metaStream;
+#ifdef Q_OS_WIN
+ metaStream.open(m_metaFileName.toStdWString().c_str());
+#else
+ metaStream.open(m_metaFileName.toStdString().c_str());
+#endif
+ std::ostringstream meta_buffer;
+ meta_buffer << metaStream.rdbuf();
+ try
+ {
+ from_json(json::parse(meta_buffer.str()), *m_metaRecord);
+ metaStream.close();
+ std::string sdrAngelVersion = m_metaRecord->global.access().version;
+
+ if (sdrAngelVersion.size() != 0)
+ {
+ qDebug("SigMFFileRecord::setFileName: appending mode");
+ m_metaFile.open(m_metaFileName.toStdString().c_str(), std::ofstream::out);
+ m_initialMsCount = 0;
+
+ for (auto capture : m_metaRecord->captures)
+ {
+ uint64_t length = capture.get().length;
+ int32_t sampleRate = capture.get().sample_rate;
+ m_initialMsCount += (length * 1000) / sampleRate;
+ }
+
+ m_sampleFileName = m_fileName + ".sigmf-data";
+ m_sampleFile.open(m_sampleFileName.toStdString().c_str(), std::ios::binary & std::ios::app);
+ m_initialBytesCount = (uint64_t) m_sampleFile.tellp();
+ m_sampleStart = m_initialBytesCount / sizeof(Sample);
+
+ m_recordStart = false;
+ }
+ else
+ {
+ qDebug("SigMFFileRecord::setFileName: SigMF not recorded with SDRangel. Recreating files...");
+ m_initialBytesCount = 0;
+ m_initialMsCount = 0;
+ m_recordStart = true;
+ }
+ }
+ catch(const std::exception& e)
+ {
+ qInfo("SigMFFileRecord::setFileName: exception: %s. Recreating files...", qPrintable(e.what()));
+ m_initialBytesCount = 0;
+ m_initialMsCount = 0;
+ m_recordStart = true;
+ }
+ }
+ else
+ {
+ m_initialBytesCount = 0;
+ m_initialMsCount = 0;
+ m_recordStart = true;
+ }
}
}
diff --git a/sdrbase/dsp/sigmffilerecord.h b/sdrbase/dsp/sigmffilerecord.h
index 5ab1d714e..0648c5e50 100644
--- a/sdrbase/dsp/sigmffilerecord.h
+++ b/sdrbase/dsp/sigmffilerecord.h
@@ -52,6 +52,8 @@ public:
void setHardwareId(const QString& hardwareId) { m_hardwareId = hardwareId; }
void setMsShift(qint64 msShift) { m_msShift = msShift; }
unsigned int getNbCaptures() const;
+ uint64_t getInitialMsCount() const { return m_initialMsCount; }
+ uint64_t getInitialBytesCount() const { return m_initialBytesCount; }
private:
QString m_hardwareId;
@@ -68,6 +70,8 @@ private:
std::ofstream m_sampleFile;
quint64 m_sampleStart;
quint64 m_sampleCount;
+ quint64 m_initialMsCount;
+ quint64 m_initialBytesCount;
sigmf::SigMF,
sigmf::Capture,
sigmf::Annotation > *m_metaRecord;