From bd09e9a22e4d9d4516ee3b7988a66ac5832f7882 Mon Sep 17 00:00:00 2001 From: Ruud Overeem <overeem@astron.nl> Date: Fri, 15 Jan 2010 11:07:28 +0000 Subject: [PATCH] Bug 1237: AMCserver is not used anymore. Also not in the IBS protocol. All conversion are now done in the J2000Converter class. Since we link direct to casacore we also support B1950 and solarsystem objects. iBeamServer is still working for LBA antenna's only. --- MAC/APL/PAC/IBS_Protocol/configure.in | 1 + .../include/APL/IBS_Protocol/Pointing.h | 130 ++++------- MAC/APL/PAC/IBS_Protocol/src/Pointing.cc | 114 ++-------- MAC/APL/PAC/ITRFBeamServer/configure.in | 2 + MAC/APL/PAC/ITRFBeamServer/src/Beam.cc | 4 - MAC/APL/PAC/ITRFBeamServer/src/BeamServer.cc | 67 +++--- MAC/APL/PAC/ITRFBeamServer/src/BeamServer.h | 7 +- .../PAC/ITRFBeamServer/src/J2000Converter.cc | 207 ++++++++++++++++++ .../PAC/ITRFBeamServer/src/J2000Converter.h | 94 ++++++++ MAC/APL/PAC/ITRFBeamServer/src/Makefile.am | 2 +- MAC/APL/PAC/ITRFBeamServer/src/beamctl.cc | 10 +- 11 files changed, 390 insertions(+), 248 deletions(-) create mode 100644 MAC/APL/PAC/ITRFBeamServer/src/J2000Converter.cc create mode 100644 MAC/APL/PAC/ITRFBeamServer/src/J2000Converter.h diff --git a/MAC/APL/PAC/IBS_Protocol/configure.in b/MAC/APL/PAC/IBS_Protocol/configure.in index c8cb32f50f9..117ac030b21 100644 --- a/MAC/APL/PAC/IBS_Protocol/configure.in +++ b/MAC/APL/PAC/IBS_Protocol/configure.in @@ -52,6 +52,7 @@ dnl Check for LOFAR specific things dnl lofar_GENERAL lofar_INTERNAL(LCS/Common, Common, , 1, Common/LofarTypes.h,,) +lofar_INTERNAL(MAC/MACIO, MACIO, , 1, MACIO/Marshalling.h,,) lofar_INTERNAL(MAC/APL/RTCCommon, RTCCommon, , 1, APL/RTCCommon/MarshallBlitz.h,,) lofar_EXTERNAL(BLITZ,1,blitz/blitz.h,,,,'gnu3:-Wno-unused gnu3:-ftemplate-depth-30',,-lm) diff --git a/MAC/APL/PAC/IBS_Protocol/include/APL/IBS_Protocol/Pointing.h b/MAC/APL/PAC/IBS_Protocol/include/APL/IBS_Protocol/Pointing.h index 7c9eda16fa1..d0365c9a315 100644 --- a/MAC/APL/PAC/IBS_Protocol/include/APL/IBS_Protocol/Pointing.h +++ b/MAC/APL/PAC/IBS_Protocol/include/APL/IBS_Protocol/Pointing.h @@ -23,129 +23,73 @@ #ifndef POINTING_H_ #define POINTING_H_ -#include <blitz/array.h> #include <APL/RTCCommon/Timestamp.h> namespace LOFAR { - - // forward declarations - namespace AMC { - class Converter; - class Position; - }; - namespace IBS_Protocol { - /** - * Class with - */ - class Pointing - { - public: - /** - * A direction can have one of these three types. - */ - enum Type { - J2000 = 1, - AZEL = 2, - - /** - * The LOFAR station local coordinate system. - * For the definition of this coordinate system see [ref]. - */ - LOFAR_LMN = 3, - }; - +class Pointing +{ +public: //@{ - /** - * Constructors and destructors for a pointing. - */ + // Constructors and destructors for a pointing. Pointing(); - Pointing(double angle0, double angle1, RTC::Timestamp time, Type type); + Pointing(double angle0, double angle1, RTC::Timestamp time, const string& type); virtual ~Pointing(); //@} //@{ - /** - * 'set' methods to set the time and - * direction of a pointing. - */ + // 'set' methods to set the time and + // direction of a pointing. void setDirection(double angle0, double angle1); void setTime(RTC::Timestamp time); - void setType(Type type); + void setType(const string& type); //@} //@{ - /** - * Accessor methods. Get the time and - * direction of a pointing. - */ + // Accessor methods. Get the time and + // direction of a pointing. double angle0() const; double angle1() const; RTC::Timestamp time() const; bool isTimeSet() const; - blitz::Array<double,1> cartesian() const; // convert the 2 angles to xyz elements. + string getType() const; //@} - /** - * Get the type of pointing. - */ - Type getType() const; - - /** - * Convert pointing from J2000 or AZEL format to LMN format - * if it is not already in LMN format. - * param conv Pointer to the converter (must be != 0 for J2000 type). - * param pos Pointer to position on earth for conversion (must be != 0 for J2000 type). - */ - Pointing convert(AMC::Converter* conv, AMC::Position* pos, Type reqtype = LOFAR_LMN); - - /** - * Compare the time of two pointings. - * Needed for priority queue of pointings. - */ + // Compare the time of two pointings. + // Needed for priority queue of pointings. bool operator<(Pointing const & right) const; - public: /*@{*/ - /** - * marshalling methods - */ + // marshalling methods unsigned int getSize(); unsigned int pack (void* buffer); unsigned int unpack(void *buffer); /*@}*/ - private: - double m_angle0_2pi; - double m_angle1_pi; - RTC::Timestamp m_time; - Type m_type; - }; - - inline void Pointing::setTime(RTC::Timestamp time) { m_time = time; } - inline void Pointing::setType(Type type) { m_type = type; } - inline void Pointing::setDirection(double angle0, double angle1) { m_angle0_2pi = angle0; m_angle1_pi = angle1; } - inline RTC::Timestamp Pointing::time() const { return m_time; } - inline bool Pointing::isTimeSet() const { return !(0 == m_time.sec() && 0 == m_time.usec()); } - inline Pointing::Type Pointing::getType() const { return m_type; } - inline double Pointing::angle0() const { return m_angle0_2pi; } - inline double Pointing::angle1() const { return m_angle1_pi; } - - inline blitz::Array<double,1> Pointing::cartesian() const { - blitz::Array<double,1> tmpArr(3); - tmpArr(0) = ::cos(m_angle1_pi) * ::cos(m_angle0_2pi); // x - tmpArr(1) = ::cos(m_angle1_pi) * ::sin(m_angle0_2pi); // y - tmpArr(2) = ::sin(m_angle1_pi); // z - return (tmpArr); - } - - inline bool Pointing::operator<(Pointing const & right) const - { - // inverse priority, earlier times are at the front of the queue - return (m_time > right.m_time); - } - }; +private: + double itsAngle2Pi; + double itsAnglePi; + RTC::Timestamp itsTime; + string itsType; }; +inline void Pointing::setTime(RTC::Timestamp time) { itsTime = time; } +inline void Pointing::setType(const string& type) { itsType = type; } +inline void Pointing::setDirection(double angle0, double angle1) { itsAngle2Pi = angle0; itsAnglePi = angle1; } +inline RTC::Timestamp Pointing::time() const { return itsTime; } +inline bool Pointing::isTimeSet() const { return !(0 == itsTime.sec() && 0 == itsTime.usec()); } +inline string Pointing::getType() const { return itsType; } +inline double Pointing::angle0() const { return itsAngle2Pi; } +inline double Pointing::angle1() const { return itsAnglePi; } + +inline bool Pointing::operator<(Pointing const & right) const +{ + // inverse priority, earlier times are at the front of the queue + return (itsTime > right.itsTime); +} + + }; // namespace IBS_Protocol +}; // namespace LOFAR + #endif /* POINTING_H_ */ diff --git a/MAC/APL/PAC/IBS_Protocol/src/Pointing.cc b/MAC/APL/PAC/IBS_Protocol/src/Pointing.cc index ed5407b7805..42c6ccb3b77 100644 --- a/MAC/APL/PAC/IBS_Protocol/src/Pointing.cc +++ b/MAC/APL/PAC/IBS_Protocol/src/Pointing.cc @@ -24,29 +24,23 @@ #include <Common/LofarLogger.h> #include <Common/LofarTypes.h> #include <APL/IBS_Protocol/Pointing.h> - -#include <AMCBase/Converter.h> -#include <AMCBase/RequestData.h> -#include <AMCBase/ResultData.h> - -#include <cmath> +#include <MACIO/Marshalling.h> using namespace LOFAR; using namespace IBS_Protocol; -using namespace AMC; // // Pointing() // Pointing::Pointing() : - m_angle0_2pi(0.0), m_angle1_pi(0.0), m_time(), m_type(LOFAR_LMN) + itsAngle2Pi(0.0), itsAnglePi(0.0), itsTime(), itsType("NONE") {} // // Pointing(angle, angle, time, type) // -Pointing::Pointing(double angle0, double angle1, RTC::Timestamp time, Type type) : - m_angle0_2pi(angle0), m_angle1_pi(angle1), m_time(time), m_type(type) +Pointing::Pointing(double angle0, double angle1, RTC::Timestamp time, const string& type) : + itsAngle2Pi(angle0), itsAnglePi(angle1), itsTime(time), itsType(type) {} // @@ -55,90 +49,13 @@ Pointing::Pointing(double angle0, double angle1, RTC::Timestamp time, Type type) Pointing::~Pointing() {} -// -// convert(converter, position, requestedType) -// -// Converts a pointing to another coordinatesystem. -// Supports: -// J2000 --> AZEL -// J2000 --> LMN -// AZEL --> LMN -// -Pointing Pointing::convert(Converter* conv, Position* pos, Pointing::Type reqType) -{ - if (getType() == reqType) { // no conversion needed? - return (*this); - } - - ASSERT(conv && pos); // always need converter and position - - // start with current coordinates - // angle0 = longitude = RA, Az or l - // angle1 = latitude = Dec, El or m - Direction resultDir = Direction(angle0(), angle1()); - double - mjd = 0.0, - fraction = 0.0, - az = angle0(), - el = angle1(), - l = angle0(), - m = angle1(), - n = 0.0; - - // setup the AMC classes. - time().convertToMJD(mjd, fraction); // mjd,fraction in UTC - RequestData request(resultDir, *pos, Epoch(mjd, fraction)); - ResultData resultdata; - - switch (getType()) { // determines when conversion chain begins - case J2000: - // convert J2000 to LMN - LOG_TRACE_VAR_STR("J2000(rad)=(" << resultDir.longitude() << ", " - << resultDir.latitude() << ")"); - conv->j2000ToAzel(resultdata, request); - resultDir = resultdata.direction[0]; - az = resultDir.longitude(); - el = resultDir.latitude(); - - // now convert from azel to lmn by falling through to AZEL label - // Note: break omitted intentionally - - case AZEL: - // convert AZEL to LMN - LOG_TRACE_VAR_STR("AZEL(rad)=(" << az << ", " << el << ")"); - - if (reqType == AZEL) { // return AZEL pointing? - return (Pointing(az, el, time(), AZEL)); - } - - // See LOFAR-ASTRON-MEM-105, top of page 7 - l = ::cos(el) * ::sin(az); - m = ::cos(el) * ::cos(az); - n = ::sin(el); - - // Note: break omitted intentionally - - case LOFAR_LMN: - // coordinates are already in LMN format - LOG_DEBUG_STR("lmn=(" << l << ", " << m << ", " << n << ")"); - break; - - default: - LOG_FATAL("invalid switch value"); - exit(EXIT_FAILURE); - break; - } - - return Pointing(l, m, time(), LOFAR_LMN); // return LOFAR_LMN pointing -} - // -------------------- routines for streaming the object -------------------- // // getSize() // unsigned int Pointing::getSize() { - return (sizeof(double) * 2) + m_time.getSize() + sizeof(uint8); + return (sizeof(double) * 2) + itsTime.getSize() + MSH_STRING_SIZE(itsType); } // @@ -148,14 +65,12 @@ unsigned int Pointing::pack (void* buffer) { unsigned int offset = 0; - memcpy((char*)buffer + offset, &m_angle0_2pi, sizeof(double)); + memcpy((char*)buffer + offset, &itsAngle2Pi, sizeof(double)); offset += sizeof(double); - memcpy((char*)buffer + offset, &m_angle1_pi, sizeof(double)); + memcpy((char*)buffer + offset, &itsAnglePi, sizeof(double)); offset += sizeof(double); - offset += m_time.pack((char*)buffer + offset); - uint8 type = m_type; - memcpy((char*)buffer + offset, &type, sizeof(uint8)); - offset += sizeof(uint8); + offset += itsTime.pack((char*)buffer + offset); + MSH_PACK_STRING(buffer, offset, itsType); return (offset); } @@ -167,15 +82,12 @@ unsigned int Pointing::unpack(void *buffer) { unsigned int offset = 0; - memcpy(&m_angle0_2pi, (char*)buffer + offset, sizeof(double)); + memcpy(&itsAngle2Pi, (char*)buffer + offset, sizeof(double)); offset += sizeof(double); - memcpy(&m_angle1_pi, (char*)buffer + offset, sizeof(double)); + memcpy(&itsAnglePi, (char*)buffer + offset, sizeof(double)); offset += sizeof(double); - offset += m_time.unpack((char*)buffer + offset); - uint8 type = 0; - memcpy(&type, (char*)buffer + offset, sizeof(uint8)); - m_type = (Type)type; - offset += sizeof(uint8); + offset += itsTime.unpack((char*)buffer + offset); + MSH_UNPACK_STRING(buffer , offset, itsType); return (offset); } diff --git a/MAC/APL/PAC/ITRFBeamServer/configure.in b/MAC/APL/PAC/ITRFBeamServer/configure.in index 3f795fbca9d..b0560a9e5f6 100644 --- a/MAC/APL/PAC/ITRFBeamServer/configure.in +++ b/MAC/APL/PAC/ITRFBeamServer/configure.in @@ -60,6 +60,7 @@ dnl Check for LOFAR specific things dnl lofar_GENERAL lofar_COMPILETOOLS +lofar_AIPSPP(1,"-lmeasures -ltables -lscimath -lscimath_f -lcasa") lofar_INTERNAL(LCS/Common, Common, , 1, Common/LofarTypes.h,,) lofar_INTERNAL(LCS/ApplCommon, ApplCommon, , 1, ApplCommon/StationConfig.h,,) @@ -81,4 +82,5 @@ AC_CONFIG_FILES([test/runctest.sh:autoconf_share/runctest.sh.in], AC_OUTPUT( Makefile src/Makefile + test/Makefile ) diff --git a/MAC/APL/PAC/ITRFBeamServer/src/Beam.cc b/MAC/APL/PAC/ITRFBeamServer/src/Beam.cc index 00b0b0e4b3c..fd4592bb90d 100644 --- a/MAC/APL/PAC/ITRFBeamServer/src/Beam.cc +++ b/MAC/APL/PAC/ITRFBeamServer/src/Beam.cc @@ -25,9 +25,6 @@ #include <Common/LofarLocators.h> #include <Common/LofarConstants.h> -#include <AMCBase/Converter.h> -#include <AMCBase/Position.h> - #include <APL/RTCCommon/PSAccess.h> #include "BeamServerConstants.h" #include "Beam.h" @@ -43,7 +40,6 @@ using namespace blitz; using namespace LOFAR; -using namespace AMC; using namespace BS; using namespace IBS_Protocol; using namespace std; diff --git a/MAC/APL/PAC/ITRFBeamServer/src/BeamServer.cc b/MAC/APL/PAC/ITRFBeamServer/src/BeamServer.cc index c1c6899c423..12bbb3c0b50 100644 --- a/MAC/APL/PAC/ITRFBeamServer/src/BeamServer.cc +++ b/MAC/APL/PAC/ITRFBeamServer/src/BeamServer.cc @@ -35,13 +35,6 @@ #include <APL/RSP_Protocol/RSP_Protocol.ph> #include <APL/CAL_Protocol/CAL_Protocol.ph> -#include <AMCBase/Converter.h> -#include <AMCBase/RequestData.h> -#include <AMCBase/ResultData.h> -#include <AMCBase/Position.h> -#include <AMCBase/Direction.h> -#include <AMCBase/Epoch.h> - #include "BeamServer.h" #include "BeamServerConstants.h" #include "Package__Version.h" @@ -63,7 +56,6 @@ namespace LOFAR { using namespace IBS_Protocol; using namespace RSP_Protocol; using namespace GCF::TM; - using namespace AMC; namespace BS { int gBeamformerGain = 0; @@ -78,7 +70,6 @@ BeamServer::BeamServer(const string& name, long timestamp) : itsListener (0), itsRSPDriver (0), itsCalServer (0), - itsAMCclient ("localhost"), itsBeamsModified (false), itsUpdateInterval (UPDATE_INTERVAL), itsComputeInterval (COMPUTE_INTERVAL), @@ -1354,7 +1345,7 @@ inline complex<int16_t> convert2complex_int16_t(complex<double> cd) // This method is called once every period of COMPUTE_INTERVAL seconds // to calculate the weights for all beamlets. // -void BeamServer::compute_weights(Timestamp weightTime) +bool BeamServer::compute_weights(Timestamp weightTime) { // TEMP CODE FOR EASY TESTING THE BEAMSERVER VALUES if (itsTestSingleShotTimestamp) { @@ -1382,10 +1373,16 @@ void BeamServer::compute_weights(Timestamp weightTime) blitz::Array<double, 2> rcuPosITRF = LBAfield ? itsAntennaPos->LBARCUPos() : itsAntennaPos->HBARCUPos(); LOG_DEBUG_STR("ITRFRCUPos = " << rcuPosITRF); - // Get geographical location of subarray in ITRF and place it in an AMC Position class. + // Get geographical location of subarray in ITRF blitz::Array<double, 1> fieldCentreITRF = LBAfield ? itsAntennaPos->LBACentre() : itsAntennaPos->HBACentre(); - Position fieldPositionITRF(Coord3D(blitz2vector(fieldCentreITRF)), Position::ITRF); - LOG_DEBUG_STR("ITRF position antennaField: " << fieldPositionITRF); + LOG_DEBUG_STR("ITRF position antennaField: " << fieldCentreITRF); + + // convert ITRF position of all antennas to J2000 for timestamp t + blitz::Array<double,2> rcuJ2000Pos; + if (!itsJ2000Converter.doConversion("ITRF", rcuPosITRF, fieldCentreITRF, weightTime, rcuJ2000Pos)) { + LOG_FATAL_STR("Conversion of antennas to J2000 failed"); + return(false); + } // Lengths of the vector of the antennaPosition i.r.t. the fieldCentre, blitz::Array<double,1> rcuPosLengths = LBAfield ? itsAntennaPos->LBARCULengths() : itsAntennaPos->HBARCULengths(); @@ -1400,19 +1397,16 @@ void BeamServer::compute_weights(Timestamp weightTime) } // Get the right pointing Pointing currentPointing = beamIter->second->currentPointing(weightTime); - double mjd(0); - double mjd_fraction(0); - currentPointing.time().convertToMJD(mjd, mjd_fraction); - - // Convert pointing of source to J2000 for centre of Antennafield - // TODO: REO 111109: next line wil only work for J2000, AZEL to J2000 is not implemented in Pointing.cc - blitz::Array<double,1> sourceJ2000xyz(3); - sourceJ2000xyz(Range::all()) = currentPointing.convert(&itsAMCclient, &fieldPositionITRF, Pointing::J2000).cartesian(); + blitz::Array<double,2> sourceJ2000xyz; + blitz::Array<double,2> curPoint(1,2); + curPoint(0,0) = currentPointing.angle0(); + curPoint(0,1) = currentPointing.angle1(); + if (!itsJ2000Converter.doConversion(currentPointing.getType(), curPoint, fieldCentreITRF, weightTime, sourceJ2000xyz)) { + LOG_FATAL_STR("Conversion of source to J2000 failed"); + return(false); + } LOG_DEBUG_STR("sourceJ2000xyz:" << sourceJ2000xyz); - // declare J2000SingleRCUPos - blitz::Array<double,1> J2000SingleRCUPos(3); - bitset<MAX_RCUS> RCUallocation(beamIter->second->rcuMask()); for (int rcu = 0; rcu < MAX_RCUS; rcu++) { if (!RCUallocation.test(rcu)) { // all RCUS switched on in LBA/HBA mode @@ -1424,19 +1418,8 @@ void BeamServer::compute_weights(Timestamp weightTime) // // Convert the ITRF position of this RCU to J2000 for time=weightTime // - RequestData request(Direction(Coord3D(blitz2vector(rcuPosITRF(rcu, Range::all()))), Direction::ITRF), - fieldPositionITRF, - Epoch(mjd, mjd_fraction)); - ResultData result; - itsAMCclient.itrfToJ2000(result, request); - vector<double> direction = result.direction[0].coord().get(); - - // Note AMCServer returns an unit vector. - J2000SingleRCUPos(0) = direction[0] * rcuPosLengths(rcu); - J2000SingleRCUPos(1) = direction[1] * rcuPosLengths(rcu); - J2000SingleRCUPos(2) = direction[2] * rcuPosLengths(rcu); - LOG_DEBUG_STR("J2000RCUPos[" << rcu << "]=[" << J2000SingleRCUPos(0) << ", " << - J2000SingleRCUPos(1) << ", " << J2000SingleRCUPos(2) << "]"); + rcuJ2000Pos(rcu, Range::all()) *= rcuPosLengths(rcu); + LOG_DEBUG_STR("J2000RCUPos[" << rcu << "]=" << rcuJ2000Pos(rcu, Range::all())); // END OF NOTE. // @@ -1451,9 +1434,9 @@ void BeamServer::compute_weights(Timestamp weightTime) } itsWeights(rcu, beamlet) = exp(itsBeamletAllocation[beamlet].scaling * - (J2000SingleRCUPos(0) * sourceJ2000xyz(0) + - J2000SingleRCUPos(1) * sourceJ2000xyz(1) + - J2000SingleRCUPos(2) * sourceJ2000xyz(2))); + (rcuJ2000Pos(rcu, 0) * sourceJ2000xyz(0) + + rcuJ2000Pos(rcu, 1) * sourceJ2000xyz(1) + + rcuJ2000Pos(rcu, 2) * sourceJ2000xyz(2))); // some debugging if (itsWeights(rcu, beamlet) != complex<double>(1,0)) { @@ -1462,7 +1445,7 @@ void BeamServer::compute_weights(Timestamp weightTime) // some more debugging if (rcu==4 && beamlet==6) { LOG_DEBUG_STR("###scaling = " << itsBeamletAllocation[beamlet].scaling); - LOG_DEBUG_STR("###J2000RCUpos = " << J2000SingleRCUPos(Range::all())); + LOG_DEBUG_STR("###J2000RCUpos = " << rcuJ2000Pos(rcu, Range::all())); LOG_DEBUG_STR("###J2000xyz = " << sourceJ2000xyz(Range::all())); } } // beamlets @@ -1474,6 +1457,8 @@ void BeamServer::compute_weights(Timestamp weightTime) itsWeights16 = convert2complex_int16_t(itsWeights); LOG_DEBUG(formatString("sizeof(itsWeights16) = %d", itsWeights16.size()*sizeof(int16_t))); + + return (true); } // diff --git a/MAC/APL/PAC/ITRFBeamServer/src/BeamServer.h b/MAC/APL/PAC/ITRFBeamServer/src/BeamServer.h index cea46a7c5a1..517dfa714fe 100644 --- a/MAC/APL/PAC/ITRFBeamServer/src/BeamServer.h +++ b/MAC/APL/PAC/ITRFBeamServer/src/BeamServer.h @@ -25,10 +25,9 @@ #include <Common/lofar_string.h> #include <APL/IBS_Protocol/IBS_Protocol.ph> +#include "J2000Converter.h" #include "Beam.h" -#include <AMCBase/ConverterClient.h> - #include <GCF/TM/GCF_Control.h> //#include <GCF/TM/GCF_TimerPort.h> #include <APL/APLCommon/AntennaSets.h> @@ -147,7 +146,7 @@ public: // Time to compute some more weights. // @param current_seconds Time in seconds since 1 Jan 1970 - void compute_weights(RTC::Timestamp time); + bool compute_weights(RTC::Timestamp time); // Send weights to the board. void send_weights(RTC::Timestamp time); @@ -227,9 +226,9 @@ private: BeamTransaction itsBeamTransaction; // current beam transaction + J2000Converter itsJ2000Converter; // casacore based converter to J2000 GCFTCPPort* itsRSPDriver; // connection to RSPDriver GCFTCPPort* itsCalServer; // connection to CalServer - AMC::ConverterClient itsAMCclient; GCFTimerPort* itsHeartbeatTimer; // GCFTimerPort* itsTimerPort; // General purpose timer bool itsBeamsModified; // diff --git a/MAC/APL/PAC/ITRFBeamServer/src/J2000Converter.cc b/MAC/APL/PAC/ITRFBeamServer/src/J2000Converter.cc new file mode 100644 index 00000000000..ec1efea6265 --- /dev/null +++ b/MAC/APL/PAC/ITRFBeamServer/src/J2000Converter.cc @@ -0,0 +1,207 @@ +//# J2000Converter.cc: one_line_description +//# +//# Copyright (C) 2010 +//# ASTRON (Netherlands Foundation for Research in Astronomy) +//# P.O.Box 2, 7990 AA Dwingeloo, The Netherlands, seg@astron.nl +//# +//# This program is free software; you can redistribute it and/or modify +//# it under the terms of the GNU General Public License as published by +//# the Free Software Foundation; either version 2 of the License, or +//# (at your option) any later version. +//# +//# This program is distributed in the hope that it will be useful, +//# but WITHOUT ANY WARRANTY; without even the implied warranty of +//# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +//# GNU General Public License for more details. +//# +//# You should have received a copy of the GNU General Public License +//# along with this program; if not, write to the Free Software +//# Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA +//# +//# $Id$ + +//# Always #include <lofar_config.h> first! +#include <lofar_config.h> + +//# Includes +#include <Common/LofarLogger.h> + +#include <measures/Measures.h> +#include <measures/Measures/MEpoch.h> +#include <measures/Measures/MPosition.h> +#include <measures/Measures/MDirection.h> +#include <measures/Measures/MeasConvert.h> +#include <measures/Measures/MCDirection.h> + +#include "J2000Converter.h" + +namespace LOFAR { + namespace BS { + +using namespace casa; +using namespace blitz; +using namespace RTC; + +char* supportedTypes[] = { "ITRF", "B1950", "AZEL", + "MERCURY", "VENUS", "MARS", "JUPITER", "SATURN", "URANUS", "NEPTUNE", "PLUTO", "SUN", "MOON" + "" }; + + +// +// J2000Converter() +// +J2000Converter::J2000Converter() +{ + // First setup a map with the supported conversion types. + MDirection::Types aType; + int t = 0; + while (supportedTypes[t]) { + if (!MDirection::getType(aType, supportedTypes[t])) { + LOG_ERROR_STR("Type " << supportedTypes[t] << " not supported by this version of casacore!"); + } + LOG_DEBUG_STR("Adding support for " << supportedTypes[t]); + itsDirectionTypes[supportedTypes[t]] = aType; + t++; + } + ASSERTSTR(!itsDirectionTypes.empty(), "Can not resolve any coordinatesystem in casacore."); +} + +// +// ~J2000Converter() +// +J2000Converter::~J2000Converter() +{ + // cleanup all our variables. + itsConverters.clear(); + itsDirectionTypes.clear(); +} + +// +// _getConverter(types) +// +J2000Converter::converter_t* J2000Converter::_getConverter(MDirection::Types theType) +{ + // simplify logging + string typeName(MDirection::showType(theType)); + + // try to find the converter. If it is already there then we are done + map<MDirection::Types, converter_t>::iterator iter(itsConverters.find(theType)); + if (iter != itsConverters.end()) { + LOG_INFO_STR("Using existing " << typeName << " to J2000 converter"); + return (&(iter->second)); + } + + // convertor not yet defined + converter_t newConverter; + try { + newConverter.frame.set(MEpoch(Quantity(55000.0, "d"), MEpoch::UTC)); // somewhere in 2009 + newConverter.frame.set(MPosition(MVPosition(0.0, 0.0, 0.0), MPosition::ITRF)); + newConverter.conv = MDirection::Convert(MDirection::Ref(theType), + MDirection::Ref(MDirection::J2000, newConverter.frame)); + } + catch (AipsError& e) { + LOG_FATAL_STR("CASA ERROR while creating an convertor from "<< typeName << " to J2000: " << e.what()); + return (NULL); + } + + if (newConverter.conv.isNOP()) { + LOG_FATAL_STR("Unable to create a converter from " << typeName << " to J2000"); + return (NULL); + } + + LOG_INFO_STR("Created a converter from " << typeName << " to J2000"); + itsConverters[theType] = newConverter; + return (&itsConverters[theType]); +} + +// +// _cartesian(angle2Pi, angle1Pi) +// +blitz::Array<double,1> J2000Converter::_cartesian(double angle2Pi, double angle1Pi) { + blitz::Array<double,1> tmpArr(3); + double cosPi = ::cos(angle1Pi); + tmpArr(0) = cosPi * ::cos(angle2Pi); // x + tmpArr(1) = cosPi * ::sin(angle2Pi); // y + tmpArr(2) = ::sin(angle1Pi); // z + return (tmpArr); +} + +// +// doConversion(vector<MDirectoin>, MPosition, timestamp) +// +// Convert directions or position from whatever coordinate system to J2000 positions. +// +bool J2000Converter::doConversion(const string& sourceType, + const blitz::Array<double,2>& antPos, + const blitz::Array<double,1>& ITRFfieldPos, + Timestamp theTime, + blitz::Array<double,2>& result) +{ + // Are the sources directions or positions? + bool srcIsDirection = (antPos.extent(secondDim) == 2); + + // sanity check + ASSERTSTR(antPos.extent(secondDim) == 3 || antPos.extent(secondDim) == 2, + "antPos must have 2 or 3 elements per row not " << antPos.extent(secondDim)); + ASSERTSTR(ITRFfieldPos.extent(firstDim) == 3, + "ITRFfieldPos must have 3 elements not " << ITRFfieldPos.extent(firstDim)); + + // clear result array + result.free(); + + // sleeping user? + if (sourceType == "J2000") { + if (srcIsDirection) { + result.resize(antPos.extent(firstDim), 3); + for (int i = antPos.extent(firstDim)-1; i >= 0; i--) { + result(i, Range::all()) = _cartesian(antPos(i,0), antPos(i,1)); + } + return (true); + } + // source are positions, just copy to the result array. + result.resize(antPos.shape()); + result = antPos; + return (true); + } + + // find converter + map<string, MDirection::Types>::const_iterator iter(itsDirectionTypes.find(sourceType)); + if (iter == itsDirectionTypes.end()) { + LOG_FATAL_STR("No support for conversion from " << sourceType << " to J2000"); + return (false); + } + + converter_t* theConv = _getConverter(iter->second); + if (theConv->conv.isNOP()) { + LOG_FATAL_STR("No converter available, returning empty result"); + return (false); + } + + // reinit the frame of the converter + theConv->frame.resetPosition(MPosition(MVPosition(ITRFfieldPos(0),ITRFfieldPos(1),ITRFfieldPos(2)), MPosition::ITRF)); + double mjd; + double mjdFraction; + theTime.convertToMJD(mjd, mjdFraction); + theConv->frame.resetEpoch(MVEpoch(mjd, mjdFraction)); + + // do the conversions + int nrDirections(antPos.extent(firstDim)); + result.resize(nrDirections, 3); + MDirection J2000Dir; + for (int d = 0; d < nrDirections; d++) { + if (srcIsDirection) { + J2000Dir = theConv->conv(MVDirection(antPos(d,0), antPos(d,1))); + } + else { + J2000Dir = theConv->conv(MVDirection(antPos(d,0), antPos(d,1), antPos(d,2))); + } + casa::Vector<Double> angles = J2000Dir.getValue().get(); + result(d, Range::all()) = _cartesian(angles(0), angles(1)); + } + + return (true); +} + + + } // namespace BS +} // namespace LOFAR diff --git a/MAC/APL/PAC/ITRFBeamServer/src/J2000Converter.h b/MAC/APL/PAC/ITRFBeamServer/src/J2000Converter.h new file mode 100644 index 00000000000..323c7493934 --- /dev/null +++ b/MAC/APL/PAC/ITRFBeamServer/src/J2000Converter.h @@ -0,0 +1,94 @@ +//# J2000Converter.h: one_line_description +//# +//# Copyright (C) 2010 +//# ASTRON (Netherlands Foundation for Research in Astronomy) +//# P.O.Box 2, 7990 AA Dwingeloo, The Netherlands, seg@astron.nl +//# +//# This program is free software; you can redistribute it and/or modify +//# it under the terms of the GNU General Public License as published by +//# the Free Software Foundation; either version 2 of the License, or +//# (at your option) any later version. +//# +//# This program is distributed in the hope that it will be useful, +//# but WITHOUT ANY WARRANTY; without even the implied warranty of +//# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +//# GNU General Public License for more details. +//# +//# You should have received a copy of the GNU General Public License +//# along with this program; if not, write to the Free Software +//# Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA +//# +//# $Id$ + +#ifndef BS_J2000_CONVERTER_H +#define BS_J2000_CONVERTER_H + +// \file J2000Converter.h +// one_line_description + +//# Never #include <config.h> or #include <lofar_config.h> in a header file! +//# Includes +#include <blitz/array.h> +#include <measures/Measures.h> +#include <measures/Measures/MEpoch.h> +#include <measures/Measures/MPosition.h> +#include <measures/Measures/MDirection.h> +#include <measures/Measures/MeasConvert.h> +#include <measures/Measures/MCDirection.h> +#include <APL/RTCCommon/Timestamp.h> + +// Avoid 'using namespace' in headerfiles + +namespace LOFAR { + namespace BS { + +// \addtogroup package +// @{ + +//# --- Forward Declarations --- +//# classes mentioned as parameter or returntype without virtual functions. + + +// class_description +// ... +class J2000Converter +{ +public: + J2000Converter(); + ~J2000Converter(); + + // Converts the given directions to J2000 directions for Position on Earth at time Timestamp + bool doConversion(const string& sourceType, + const blitz::Array<double,2>& antPos, + const blitz::Array<double,1>& ITRFfieldPos, + RTC::Timestamp theTime, + blitz::Array<double,2>& result); + +private: + // internal admin structures + typedef struct converter { + casa::MDirection::Convert conv; + casa::MeasFrame frame; + } converter_t; + + // private helper routines + converter_t* _getConverter(casa::MDirection::Types); + blitz::Array<double,1> _cartesian(double angle2Pi, double angle1Pi); + + // Copying is not allowed + J2000Converter(const J2000Converter& that); + J2000Converter& operator=(const J2000Converter& that); + + //# --- Datamembers --- + // name, type map + map<string, casa::MDirection::Types> itsDirectionTypes; + + // type, converter_t map + map<casa::MDirection::Types, converter_t> itsConverters; +}; + +// @} + } // namespace PACKAGE +} // namespace LOFAR + +#endif diff --git a/MAC/APL/PAC/ITRFBeamServer/src/Makefile.am b/MAC/APL/PAC/ITRFBeamServer/src/Makefile.am index c85be739ee2..ab7eb3bf97f 100644 --- a/MAC/APL/PAC/ITRFBeamServer/src/Makefile.am +++ b/MAC/APL/PAC/ITRFBeamServer/src/Makefile.am @@ -20,7 +20,7 @@ sysconf_DATA = bin_PROGRAMS = iBeamServer ibeamctl iBeamServer_SOURCES = BeamServerMain.cc BeamServer.h BeamServerConstants.h BeamServer.cc \ - Beam.h Beam.cc + Beam.h Beam.cc J2000Converter.h J2000Converter.cc iBeamServer_LDADD = iBeamServer_DEPENDENCIES = $(LOFAR_DEPEND) diff --git a/MAC/APL/PAC/ITRFBeamServer/src/beamctl.cc b/MAC/APL/PAC/ITRFBeamServer/src/beamctl.cc index 54d05924be4..ea2dcd733f8 100644 --- a/MAC/APL/PAC/ITRFBeamServer/src/beamctl.cc +++ b/MAC/APL/PAC/ITRFBeamServer/src/beamctl.cc @@ -384,12 +384,13 @@ void beamctl::send_direction(double longitude, double latitude, const string& di pointto.beamName = itsBeamHandle; pointto.pointing.setDirection(longitude, latitude); pointto.analogue = isAnalogue; + // TODO UPDATE THIS TO THE NEW CASACORE INTERFACE if (dirType == "J2000") { - pointto.pointing.setType(Pointing::J2000); + pointto.pointing.setType(dirType); } else if (dirType == "AZEL") { - pointto.pointing.setType(Pointing::AZEL); + pointto.pointing.setType(dirType); } else if (dirType == "LOFAR_LMN") { - pointto.pointing.setType(Pointing::LOFAR_LMN); + pointto.pointing.setType(dirType); } else if (dirType != "SKYSCAN") { LOG_FATAL_STR("Error: invalid coordinate type '" << dirType << "'"); exit(EXIT_FAILURE); @@ -403,7 +404,8 @@ void beamctl::send_direction(double longitude, double latitude, const string& di // SKYSCAN Timestamp time, end_time; time.setNow(SKYSCAN_STARTDELAY); // start after appropriate delay - pointto.pointing.setType(Pointing::LOFAR_LMN); + // TODO HOW TO CONVERT THIS? +// pointto.pointing.setType(Pointing::LOFAR_LMN); // step through l and m int l_steps = static_cast<int>(longitude); -- GitLab