[PATCH] gr-osmosdr/rtl: two concurrency bugfixes

This is merely a historical archive of years 2008-2021, before the migration to mailman3.

A maintained and still updated list archive can be found at https://lists.osmocom.org/hyperkitty/list/osmocom-sdr@lists.osmocom.org/.

Karl Semich 0xloem at gmail.com
Sun Sep 23 12:43:18 UTC 2018


1. _running is guarded with a lock in the rtl event loop epilogue.
   this prevents a possible hang that could arise from _buf_cond
   being notified prior to work() waiting on _buf_cond, but after
   work() checks _running.

2. _buf_used is guarded with a lock in the work function to prevent
   it from spuriously reading zero if it is nonatomically written
   from the rtl event callback.
---
 lib/rtl/rtl_source_c.cc | 11 +++++++++--
 1 file changed, 9 insertions(+), 2 deletions(-)

diff --git a/lib/rtl/rtl_source_c.cc b/lib/rtl/rtl_source_c.cc
index a371464..bbd0140 100644
--- a/lib/rtl/rtl_source_c.cc
+++ b/lib/rtl/rtl_source_c.cc
@@ -323,7 +323,11 @@ void rtl_source_c::rtlsdr_wait()
 {
   int ret = rtlsdr_read_async( _dev, _rtlsdr_callback, (void *)this, _buf_num, _buf_len );
 
-  _running = false;
+  {
+    boost::mutex::scoped_lock lock( _buf_mutex );
+
+    _running = false;
+  }
 
   if ( ret != 0 )
     std::cerr << "rtlsdr_read_async returned with " << ret << std::endl;
@@ -347,7 +351,7 @@ int rtl_source_c::work( int noutput_items,
   if (!_running)
     return WORK_DONE;
 
-  while (noutput_items && _buf_used) {
+  while (noutput_items) {
     const int nout = std::min(noutput_items, _samp_avail);
     const unsigned char *buf = _buf[_buf_head] + _buf_offset * 2;
 
@@ -363,6 +367,9 @@ int rtl_source_c::work( int noutput_items,
 
         _buf_head = (_buf_head + 1) % _buf_num;
         _buf_used--;
+
+        if (_buf_used == 0)
+          break;
       }
       _samp_avail = _buf_len / BYTES_PER_SAMPLE;
       _buf_offset = 0;
-- 
2.11.0




More information about the osmocom-sdr mailing list