From 73468b0bb2ae55be2fc01f51952e189f70ca9639 Mon Sep 17 00:00:00 2001
From: Jan David Mol <mol@astron.nl>
Date: Wed, 3 Apr 2013 09:15:19 +0000
Subject: [PATCH] Task #4315: Made casacore optional in delay compensation

---
 RTCP/Cobalt/InputProc/CMakeLists.txt       |  2 +-
 RTCP/Cobalt/InputProc/src/Delays/Delays.cc | 90 ++++++++++++++--------
 RTCP/Cobalt/InputProc/src/Delays/Delays.h  | 34 ++++----
 RTCP/Cobalt/InputProc/test/tDelays.cc      |  2 +
 lofar_config.h.cmake                       |  3 +
 5 files changed, 87 insertions(+), 44 deletions(-)

diff --git a/RTCP/Cobalt/InputProc/CMakeLists.txt b/RTCP/Cobalt/InputProc/CMakeLists.txt
index 2eae20c8d01..541a133aacd 100644
--- a/RTCP/Cobalt/InputProc/CMakeLists.txt
+++ b/RTCP/Cobalt/InputProc/CMakeLists.txt
@@ -5,7 +5,7 @@ lofar_package(InputProc 1.0
 
 include(LofarFindPackage)
 lofar_find_package(Boost REQUIRED COMPONENTS date_time)
-lofar_find_package(Casacore COMPONENTS measures REQUIRED)
+lofar_find_package(Casacore COMPONENTS measures)
 lofar_find_package(OpenMP REQUIRED)
 lofar_find_package(MPI REQUIRED)
 lofar_find_package(UnitTest++)
diff --git a/RTCP/Cobalt/InputProc/src/Delays/Delays.cc b/RTCP/Cobalt/InputProc/src/Delays/Delays.cc
index 74772f04f4a..f7b8c309343 100644
--- a/RTCP/Cobalt/InputProc/src/Delays/Delays.cc
+++ b/RTCP/Cobalt/InputProc/src/Delays/Delays.cc
@@ -38,10 +38,6 @@ namespace LOFAR
   namespace Cobalt
   {
 
-    using namespace casa;
-
-    static LOFAR::Mutex casacoreMutex; // casacore is not thread safe
-
     //##----------------  Public methods  ----------------##//
 
     Delays::Delays(const Parset &parset, const std::string &stationName, const TimeStamp &startTime, size_t blockSize)
@@ -79,6 +75,24 @@ namespace LOFAR
     }
 
 
+    void Delays::setAllDelaysSize( AllDelays &result ) const {
+        result.resize(parset.settings.SAPs.size());
+
+        for (size_t sap = 0; sap < parset.settings.SAPs.size(); ++sap) {
+          if (parset.settings.beamFormer.enabled) {
+            const struct ObservationSettings::BeamFormer::SAP &bfSap = parset.settings.beamFormer.SAPs[sap];
+
+            result[sap].TABs.resize(bfSap.TABs.size());
+          }
+        }
+    }
+
+
+#ifdef HAVE_CASACORE
+    using namespace casa;
+
+    static LOFAR::Mutex casacoreMutex; // casacore is not thread safe
+
     // convert a time in samples to a (day,fraction) pair in UTC in a CasaCore format
     MVEpoch Delays::toUTC(const TimeStamp &timestamp) const
     {
@@ -132,42 +146,60 @@ namespace LOFAR
     struct Delays::Delay Delays::convert( casa::MDirection::Convert &converter, const casa::MVDirection &direction ) const {
       struct Delay d;
 
-       d.direction = converter(direction).getValue();
-       d.delay     = d.direction * itsPhasePositionDiff * (1.0 / speedOfLight);
+      MVDirection casaDir = converter(direction).getValue();
+
+      // Compute direction and convert it 
+      casa::Vector<double> dir = casaDir.getValue();
+      std::copy(dir.begin(), dir.end(), d.direction);
 
-       return d;
+      d.delay = casaDir * itsPhasePositionDiff * (1.0 / speedOfLight);
+
+      return d;
     }
 
 
     void Delays::calcDelays( const TimeStamp &timestamp, AllDelays &result ) {
-      // Set the instant in time in the itsFrame
-      itsFrame.resetEpoch(toUTC(timestamp));
+      try {
+        ScopedLock lock(casacoreMutex);
+        ScopedDelayCancellation dc;
 
-      // Convert directions for all beams
-      result.resize(parset.settings.SAPs.size());
+        // Set the instant in time in the itsFrame
+        itsFrame.resetEpoch(toUTC(timestamp));
 
-      for (size_t sap = 0; sap < parset.settings.SAPs.size(); ++sap) {
-        const struct ObservationSettings::SAP &sapInfo = parset.settings.SAPs[sap];
+        // Convert directions for all beams
+        for (size_t sap = 0; sap < parset.settings.SAPs.size(); ++sap) {
+          const struct ObservationSettings::SAP &sapInfo = parset.settings.SAPs[sap];
 
-        // Fetch the relevant convert engine
-        MDirection::Convert &converter = itsConverters[itsDirectionTypes[sap]];
+          // Fetch the relevant convert engine
+          MDirection::Convert &converter = itsConverters[itsDirectionTypes[sap]];
 
-        // Convert the SAP directions using the convert engine
-        result[sap].SAP = convert(converter, MVDirection(sapInfo.direction.angle1, sapInfo.direction.angle2));
+          // Convert the SAP directions using the convert engine
+          result[sap].SAP = convert(converter, MVDirection(sapInfo.direction.angle1, sapInfo.direction.angle2));
 
-        if (parset.settings.beamFormer.enabled) {
-          // Convert the TAB directions using the convert engine
-          const struct ObservationSettings::BeamFormer::SAP &bfSap = parset.settings.beamFormer.SAPs[sap];
-          result[sap].TABs.resize(bfSap.TABs.size());
-          for (size_t tab = 0; tab < bfSap.TABs.size(); tab++) {
-            const MVDirection dir(sapInfo.direction.angle1 + bfSap.TABs[tab].directionDelta.angle1,
-                                  sapInfo.direction.angle2 + bfSap.TABs[tab].directionDelta.angle2);
+          if (parset.settings.beamFormer.enabled) {
+            // Convert the TAB directions using the convert engine
+            const struct ObservationSettings::BeamFormer::SAP &bfSap = parset.settings.beamFormer.SAPs[sap];
+            for (size_t tab = 0; tab < bfSap.TABs.size(); tab++) {
+              const MVDirection dir(sapInfo.direction.angle1 + bfSap.TABs[tab].directionDelta.angle1,
+                                    sapInfo.direction.angle2 + bfSap.TABs[tab].directionDelta.angle2);
 
-            result[sap].TABs[tab] = convert(converter, dir);
+              result[sap].TABs[tab] = convert(converter, dir);
+            }
           }
         }
+      } catch (AipsError &ex) {
+        THROW(Exception, "AipsError: " << ex.what());
       }
     }
+#else
+    void Delays::init() {
+    }
+
+    void Delays::calcDelays( const TimeStamp &timestamp, AllDelays &result ) {
+      (void)timestamp;
+      (void)result;
+    }
+#endif
 
 
     void Delays::mainLoop()
@@ -190,14 +222,12 @@ namespace LOFAR
           // prevent the few excess delays from being calculated.
 
           {
-            ScopedLock lock(casacoreMutex);
-            ScopedDelayCancellation dc;
-
             for (size_t i = 0; i < nrCalcDelays; i++) {
               // Check whether we will store results in a valid place
               ASSERTSTR(tail < bufferSize, tail << " < " << bufferSize);
 
               // Calculate the delays and store them in itsBuffer[tail]
+              setAllDelaysSize(itsBuffer[tail]);
               calcDelays(currentTime, itsBuffer[tail]);
 
               // Advance time for the next calculation
@@ -218,12 +248,12 @@ namespace LOFAR
 
           bufferUsed.up(nrCalcDelays);
         }
-      } catch (AipsError &ex) {
+      } catch (Exception &ex) {
         // trigger getNextDelays and force it to stop
         stop = true;
         bufferUsed.up(1);
 
-        THROW(Exception, "AipsError: " << ex.what());
+        throw;
       }
 
       LOG_DEBUG("Delay compensation thread stopped");
diff --git a/RTCP/Cobalt/InputProc/src/Delays/Delays.h b/RTCP/Cobalt/InputProc/src/Delays/Delays.h
index a4a8a45b689..d9183b32432 100644
--- a/RTCP/Cobalt/InputProc/src/Delays/Delays.h
+++ b/RTCP/Cobalt/InputProc/src/Delays/Delays.h
@@ -40,12 +40,14 @@
 #include <CoInterface/RSPTimeStamp.h>
 #include <CoInterface/SmartPtr.h>
 
+#ifdef HAVE_CASACORE
 #include <measures/Measures/MeasConvert.h>
 #include <measures/Measures/MDirection.h>
 #include <measures/Measures/MPosition.h>
 #include <casa/Quanta/MVDirection.h>
 #include <casa/Quanta/MVPosition.h>
 #include <casa/Quanta/MVEpoch.h>
+#endif
 
 namespace LOFAR
 {
@@ -92,8 +94,8 @@ namespace LOFAR
 
       // Output structures for adjusted directions and delays
       struct Delay {
-        casa::MVDirection direction;
-        double            delay;
+        double  direction[3];
+        double  delay;
       };
 
       struct BeamDelays {
@@ -112,10 +114,6 @@ namespace LOFAR
       const TimeStamp itsStartTime;
       const size_t blockSize;
 
-      casa::MVEpoch                       toUTC( const TimeStamp &timestamp ) const;
-
-      void                                init();
-
       // do the delay compensation calculations in a separate thread to allow bulk
       // calculations and to avoid blocking other threads
       void                                mainLoop();
@@ -129,13 +127,6 @@ namespace LOFAR
       // the number of delays to calculate in a single run
       static const size_t nrCalcDelays = 16;
 
-      // Converts a sky direction to a direction and delay
-      struct Delay convert( casa::MDirection::Convert &converter, const casa::MVDirection &direction ) const;
-
-      // Computes the delays for a specific moment in time and stores them
-      // in `result'.
-      void calcDelays( const TimeStamp &timestamp, AllDelays &result );
-
       // the circular buffer to hold the moving beam directions for every second of data
       std::vector<AllDelays> itsBuffer;
       size_t head, tail;
@@ -144,6 +135,22 @@ namespace LOFAR
       // another to trigger the consumer that data is available.
       Semaphore bufferFree, bufferUsed;
 
+      // Resize the given delay set to the right proportions.
+      void setAllDelaysSize( AllDelays &result ) const;
+
+      // Initialise computing/converting engines
+      void init();
+
+      // Computes the delays for a specific moment in time and stores them
+      // in `result'.
+      void calcDelays( const TimeStamp &timestamp, AllDelays &result );
+
+#ifdef HAVE_CASACORE
+      casa::MVEpoch                       toUTC( const TimeStamp &timestamp ) const;
+
+      // Converts a sky direction to a direction and delay
+      struct Delay convert( casa::MDirection::Convert &converter, const casa::MVDirection &direction ) const;
+
       casa::MeasFrame itsFrame;
 
       std::vector<casa::MDirection::Types> itsDirectionTypes; // [sap]
@@ -151,6 +158,7 @@ namespace LOFAR
 
       // Station to reference station position difference vector.
       casa::MVPosition itsPhasePositionDiff;
+#endif
 
       NSTimer itsDelayTimer;
 
diff --git a/RTCP/Cobalt/InputProc/test/tDelays.cc b/RTCP/Cobalt/InputProc/test/tDelays.cc
index c8a3ca7c9b1..11d3aedb27e 100644
--- a/RTCP/Cobalt/InputProc/test/tDelays.cc
+++ b/RTCP/Cobalt/InputProc/test/tDelays.cc
@@ -61,10 +61,12 @@ TEST(Tracking) {
     CHECK_EQUAL(1U, delaySet.size());
     CHECK_EQUAL(0U, delaySet[0].TABs.size());
 
+#ifdef HAVE_CASACORE
     // Delays must change over time
     if (block > 0) {
       CHECK(delaySet[0].SAP.delay != prevDelaySet[0].SAP.delay);
     }
+#endif
 
     prevDelaySet = delaySet;
   }
diff --git a/lofar_config.h.cmake b/lofar_config.h.cmake
index 901d33f2077..1428222eec7 100644
--- a/lofar_config.h.cmake
+++ b/lofar_config.h.cmake
@@ -105,6 +105,9 @@
 /* Define if BOOST component date_time is installed */
 #cmakedefine HAVE_BOOST_DATE_TIME 1
 
+/* Define if CASACORE is installed with the requested components */
+#cmakedefine HAVE_CASACORE 1
+
 /* Define if DAL is installed */
 #cmakedefine HAVE_DAL
 
-- 
GitLab