From 7d80a48d9482ac29d6fe152e3b108469e60aeeb6 Mon Sep 17 00:00:00 2001
From: Bertrand Coconnier <bcoconni@users.sourceforge.net>
Date: Mon, 5 Jun 2017 13:09:00 +0200
Subject: [PATCH] Sync. w/ JSBSim

External moments can now be specified in addition to external forces. This feature is needed for the AI wakes.
Headers clean up to reduce the amount of recompilation when modifying an header file.
---
 src/FDM/JSBSim/math/FGFunction.cpp            |   0
 src/FDM/JSBSim/math/FGFunction.h              |   0
 src/FDM/JSBSim/models/FGBuoyantForces.cpp     |   4 +-
 src/FDM/JSBSim/models/FGExternalForce.cpp     | 196 ++++++++++-------
 src/FDM/JSBSim/models/FGExternalForce.h       | 197 +++++++++++-------
 src/FDM/JSBSim/models/FGExternalReactions.cpp |  25 ++-
 src/FDM/JSBSim/models/FGExternalReactions.h   |  59 +++---
 src/FDM/JSBSim/models/FGGasCell.h             |   4 +-
 .../JSBSim/models/propulsion/FGElectric.cpp   |   3 +-
 src/FDM/JSBSim/models/propulsion/FGForce.cpp  |   6 +-
 src/FDM/JSBSim/models/propulsion/FGForce.h    |  17 +-
 src/FDM/JSBSim/models/propulsion/FGPiston.cpp |   3 +-
 src/FDM/JSBSim/models/propulsion/FGPiston.h   |   8 +-
 .../JSBSim/models/propulsion/FGPropeller.cpp  |   6 +-
 src/FDM/JSBSim/models/propulsion/FGRocket.cpp |   3 +-
 .../JSBSim/models/propulsion/FGThruster.cpp   |   4 +-
 .../JSBSim/models/propulsion/FGTurbine.cpp    |   3 +-
 .../JSBSim/models/propulsion/FGTurboProp.cpp  |   0
 18 files changed, 325 insertions(+), 213 deletions(-)
 mode change 100755 => 100644 src/FDM/JSBSim/math/FGFunction.cpp
 mode change 100755 => 100644 src/FDM/JSBSim/math/FGFunction.h
 mode change 100755 => 100644 src/FDM/JSBSim/models/propulsion/FGTurboProp.cpp

diff --git a/src/FDM/JSBSim/math/FGFunction.cpp b/src/FDM/JSBSim/math/FGFunction.cpp
old mode 100755
new mode 100644
diff --git a/src/FDM/JSBSim/math/FGFunction.h b/src/FDM/JSBSim/math/FGFunction.h
old mode 100755
new mode 100644
diff --git a/src/FDM/JSBSim/models/FGBuoyantForces.cpp b/src/FDM/JSBSim/models/FGBuoyantForces.cpp
index 4bdb68053..51ae27f01 100644
--- a/src/FDM/JSBSim/models/FGBuoyantForces.cpp
+++ b/src/FDM/JSBSim/models/FGBuoyantForces.cpp
@@ -38,16 +38,16 @@ INCLUDES
 
 #include <iostream>
 
+#include "FGFDMExec.h"
 #include "FGBuoyantForces.h"
 #include "FGMassBalance.h"
-#include "input_output/FGPropertyManager.h"
 #include "input_output/FGXMLElement.h"
 
 using namespace std;
 
 namespace JSBSim {
 
-IDENT(IdSrc,"$Id: FGBuoyantForces.cpp,v 1.30 2015/03/28 14:49:02 bcoconni Exp $");
+IDENT(IdSrc,"$Id: FGBuoyantForces.cpp,v 1.31 2017/06/03 19:49:20 bcoconni Exp $");
 IDENT(IdHdr,ID_BUOYANTFORCES);
 
 /*%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
diff --git a/src/FDM/JSBSim/models/FGExternalForce.cpp b/src/FDM/JSBSim/models/FGExternalForce.cpp
index 37dd60135..7c5aa894c 100644
--- a/src/FDM/JSBSim/models/FGExternalForce.cpp
+++ b/src/FDM/JSBSim/models/FGExternalForce.cpp
@@ -48,133 +48,162 @@
       </direction>
     </force>
 
+    <moment name="name" frame="BODY|LOCAL|WIND">
+
+      <function> ... </function>
+
+      <direction> <!-- optional for initial direction vector -->
+        <x> value </x>
+        <y> value </y>
+        <z> value </z>
+      </direction>
+    </force>
+
 </external_reactions>
 
 */
+#include <iostream>
 
+#include "FGFDMExec.h"
 #include "FGExternalForce.h"
 #include "input_output/FGXMLElement.h"
-#include <iostream>
+#include "math/FGPropertyValue.h"
+#include "math/FGFunction.h"
 
 using namespace std;
 
 namespace JSBSim {
 
-IDENT(IdSrc,"$Id: FGExternalForce.cpp,v 1.16 2014/12/18 09:56:05 andgi Exp $");
+IDENT(IdSrc,"$Id: FGExternalForce.cpp,v 1.22 2017/06/04 21:06:08 bcoconni Exp $");
 IDENT(IdHdr,ID_EXTERNALFORCE);
 
 //%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
 
-FGExternalForce::FGExternalForce(FGFDMExec *FDMExec, Element *el, int index)
-  : FGForce(FDMExec)
+FGPropertyVector3::FGPropertyVector3(FGPropertyManager* pm,
+                                     const std::string& baseName,
+                                     const std::string& xcmp,
+                                     const std::string& ycmp,
+                                     const std::string& zcmp)
 {
-  Element* location_element=0;
-  Element* direction_element=0;
-  Element* function_element=0;
-  string sFrame;
-  string BasePropertyName;
-  FGColumnVector3 location;
-  Magnitude_Function = 0;
-  magnitude = 0.0;
-  azimuth = 0.0;
-
-  FGPropertyManager* PropertyManager = fdmex->GetPropertyManager();
-  Name = el->GetAttributeValue("name");
-  BasePropertyName = "external_reactions/" + Name;
-
-  // The value sent to the sim through the external_forces/{force name}/magnitude
-  // property will be multiplied against the unit vector, which can come in
-  // initially in the direction vector. The frame in which the vector is defined
-  // is specified with the frame attribute. The vector is normalized to magnitude 1.
-
-  function_element = el->FindElement("function");
-  if (function_element) {
-    Magnitude_Function = new FGFunction(PropertyManager, function_element);
-  } else {
-    PropertyManager->Tie( BasePropertyName + "/magnitude",(FGExternalForce*)this, &FGExternalForce::GetMagnitude, &FGExternalForce::SetMagnitude);
-  }
+  data[0] = pm->CreatePropertyObject<double>(baseName + "/" + xcmp);
+  data[1] = pm->CreatePropertyObject<double>(baseName + "/" + ycmp);
+  data[2] = pm->CreatePropertyObject<double>(baseName + "/" + zcmp);
+}
 
+//%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
 
+FGParameter* FGExternalForce::bind(Element *el, FGPropertyManager* pm,
+                                   const string& magName, FGPropertyVector3& v)
+{
   // Set frame (from FGForce).
-  sFrame = el->GetAttributeValue("frame");
+  string sFrame = el->GetAttributeValue("frame");
   if (sFrame.empty()) {
-    cerr << "No frame specified for external force, \"" << Name << "\"." << endl;
-    cerr << "Frame set to Body" << endl;
+    cerr << el->ReadFrom()
+         << "No frame specified for external " << el->GetName() << ", \""
+         << Name << "\"." << endl
+         << "Frame set to Body" << endl;
     ttype = tNone;
   } else if (sFrame == "BODY") {
     ttype = tNone;
   } else if (sFrame == "LOCAL") {
     ttype = tLocalBody;
-    PropertyManager->Tie( BasePropertyName + "/azimuth", (FGExternalForce*)this, &FGExternalForce::GetAzimuth, &FGExternalForce::SetAzimuth);
   } else if (sFrame == "WIND") {
     ttype = tWindBody;
   } else {
-    cerr << "Invalid frame specified for external force, \"" << Name << "\"." << endl;
-    cerr << "Frame set to Body" << endl;
+    cerr << el->ReadFrom()
+         << "Invalid frame specified for external " << el->GetName() << ", \""
+         << Name << "\"." << endl
+         << "Frame set to Body" << endl;
     ttype = tNone;
   }
-  PropertyManager->Tie( BasePropertyName + "/x", (FGExternalForce*)this, &FGExternalForce::GetX, &FGExternalForce::SetX);
-  PropertyManager->Tie( BasePropertyName + "/y", (FGExternalForce*)this, &FGExternalForce::GetY, &FGExternalForce::SetY);
-  PropertyManager->Tie( BasePropertyName + "/z", (FGExternalForce*)this, &FGExternalForce::GetZ, &FGExternalForce::SetZ);
 
-  location_element = el->FindElement("location");
-  if (!location_element) {
-    cerr << "No location element specified in force object." << endl;
-  } else {
-    location = location_element->FindElementTripletConvertTo("IN");
-    SetLocation(location);
-  }
-  PropertyManager->Tie( BasePropertyName + "/location-x-in", (FGExternalForce*)this, &FGExternalForce::GetLocX, &FGExternalForce::SetLocX);
-  PropertyManager->Tie( BasePropertyName + "/location-y-in", (FGExternalForce*)this, &FGExternalForce::GetLocY, &FGExternalForce::SetLocY);
-  PropertyManager->Tie( BasePropertyName + "/location-z-in", (FGExternalForce*)this, &FGExternalForce::GetLocZ, &FGExternalForce::SetLocZ);
-
-  direction_element = el->FindElement("direction");
+  Element* direction_element = el->FindElement("direction");
   if (!direction_element) {
-    cerr << "No direction element specified in force object. Default is (0,0,0)." << endl;
+    cerr << el->ReadFrom()
+         << "No direction element specified in " << el->GetName()
+         << " object. Default is (0,0,0)." << endl;
   } else {
-    vDirection = direction_element->FindElementTripletConvertTo("IN");
-    vDirection.Normalize();
+    FGColumnVector3 direction = direction_element->FindElementTripletConvertTo("IN");
+    direction.Normalize();
+    v = direction;
   }
 
-  Debug(0);
+  // The value sent to the sim through the external_reactions/{force name}/magnitude
+  // property will be multiplied against the unit vector, which can come in
+  // initially in the direction vector. The frame in which the vector is defined
+  // is specified with the frame attribute. The vector is normalized to magnitude 1.
+
+  Element* function_element = el->FindElement("function");
+  if (function_element) {
+    return new FGFunction(pm, function_element);
+  } else {
+    FGPropertyNode* node = pm->GetNode(magName, true);
+    return new FGPropertyValue(node);
+  }
 }
 
 //%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
-// Copy constructor
 
-FGExternalForce::FGExternalForce(const FGExternalForce& extForce) : FGForce(extForce)
+void FGExternalForce::setForce(Element *el)
 {
-  magnitude = extForce.magnitude;
-  Frame = extForce.Frame;
-  vDirection = extForce.vDirection;
-  Name = extForce.Name;
+  FGPropertyManager* PropertyManager = fdmex->GetPropertyManager();
+  Name = el->GetAttributeValue("name");
+  string BasePropertyName = "external_reactions/" + Name;
+
+  forceDirection = FGPropertyVector3(PropertyManager, BasePropertyName,
+                                     "x", "y", "z");
+  forceMagnitude = bind(el, PropertyManager, BasePropertyName + "/magnitude",
+                        forceDirection);
+
+  Element* location_element = el->FindElement("location");
+  if (!location_element) {
+    cerr << el->ReadFrom()
+         << "No location element specified in force object." << endl;
+  } else {
+    FGColumnVector3 location = location_element->FindElementTripletConvertTo("IN");
+    SetLocation(location);
+  }
+  PropertyManager->Tie( BasePropertyName + "/location-x-in", (FGForce*)this,
+                        &FGForce::GetLocationX, &FGForce::SetLocationX);
+  PropertyManager->Tie( BasePropertyName + "/location-y-in", (FGForce*)this,
+                        &FGForce::GetLocationY, &FGForce::SetLocationY);
+  PropertyManager->Tie( BasePropertyName + "/location-z-in", (FGForce*)this,
+                        &FGForce::GetLocationZ, &FGForce::SetLocationZ);
 }
-  
+
+//%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
+
+void FGExternalForce::setMoment(Element *el)
+{
+  FGPropertyManager* PropertyManager = fdmex->GetPropertyManager();
+  Name = el->GetAttributeValue("name");
+  string BasePropertyName = "external_reactions/" + Name;
+
+  momentDirection = FGPropertyVector3(PropertyManager, BasePropertyName,
+                                      "l", "m", "n");
+  momentMagnitude = bind(el, PropertyManager, BasePropertyName + "/magnitude-lbsft",
+                         momentDirection);
+}
+
 //%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
 
 FGExternalForce::~FGExternalForce()
 {
-  delete Magnitude_Function;
+  delete forceMagnitude;
+  delete momentMagnitude;
   Debug(1);
 }
 
 //%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
 
-void FGExternalForce::SetMagnitude(double mag)
-{
-  magnitude = mag;
-  vFn = vDirection*mag;
-}
-
-//%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
-
 const FGColumnVector3& FGExternalForce::GetBodyForces(void)
 {
-  if (Magnitude_Function) {
-    double mag = Magnitude_Function->GetValue();
-    SetMagnitude(mag);
-  }
-  
+  if (forceMagnitude)
+    vFn = forceMagnitude->GetValue() * forceDirection;
+
+  if (momentMagnitude)
+    vMn = Transform() * (momentMagnitude->GetValue() * momentDirection);
+
   return FGForce::GetBodyForces();
 }
 
@@ -204,8 +233,21 @@ void FGExternalForce::Debug(int from)
   if (debug_lvl & 1) { // Standard console startup message output
     if (from == 0) { // Constructor
       cout << "    " << Name << endl;
-      cout << "    Frame: " << Frame << endl;
-      cout << "    Location: (" << vXYZn(eX) << ", " << vXYZn(eY) << ", " << vXYZn(eZ) << ")" << endl;
+      cout << "    Frame: ";
+      switch(ttype) {
+      case tNone:
+        cout << "BODY";
+        break;
+      case tLocalBody:
+        cout << "LOCAL";
+        break;
+      case tWindBody:
+        cout << "WIND";
+        break;
+      default:
+        cout << "ERROR/UNKNOWN";
+      }
+      cout << endl << "    Location: (" << vXYZn(eX) << ", " << vXYZn(eY) << ", " << vXYZn(eZ) << ")" << endl;
     }
   }
   if (debug_lvl & 2 ) { // Instantiation/Destruction notification
diff --git a/src/FDM/JSBSim/models/FGExternalForce.h b/src/FDM/JSBSim/models/FGExternalForce.h
index 0d7df5a59..81760543b 100644
--- a/src/FDM/JSBSim/models/FGExternalForce.h
+++ b/src/FDM/JSBSim/models/FGExternalForce.h
@@ -7,21 +7,21 @@
  ------------- Copyright (C) 2007  Jon S. Berndt (jon@jsbsim.org) -------------
 
  This program is free software; you can redistribute it and/or modify it under
- the terms of the GNU Lesser General Public License as published by the Free Software
- Foundation; either version 2 of the License, or (at your option) any later
- version.
+ the terms of the GNU Lesser 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 Lesser General Public License for more
  details.
 
- You should have received a copy of the GNU Lesser 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.
+ You should have received a copy of the GNU Lesser 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.
 
- Further information about the GNU Lesser General Public License can also be found on
- the world wide web at http://www.gnu.org.
+ Further information about the GNU Lesser General Public License can also be
+ found on the world wide web at http://www.gnu.org.
 
 
  HISTORY
@@ -40,18 +40,16 @@ INCLUDES
 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%*/
 
 #include <string>
-#include "FGFDMExec.h"
-#include "FGJSBBase.h"
+
 #include "models/propulsion/FGForce.h"
-#include "input_output/FGPropertyManager.h"
 #include "math/FGColumnVector3.h"
-#include "math/FGFunction.h"
+#include "simgear/props/propertyObject.hxx"
 
 /*%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
 DEFINITIONS
 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%*/
 
-#define ID_EXTERNALFORCE "$Id: FGExternalForce.h,v 1.13 2014/11/25 01:44:17 dpculp Exp $"
+#define ID_EXTERNALFORCE "$Id: FGExternalForce.h,v 1.19 2017/06/04 21:06:08 bcoconni Exp $"
 
 /*%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
 FORWARD DECLARATIONS
@@ -59,14 +57,18 @@ FORWARD DECLARATIONS
 
 namespace JSBSim {
 
+class FGParameter;
+class Element;
+class FGPropertyManager;
+
 /*%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
 CLASS DOCUMENTATION
 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%*/
 
-/** Encapsulates code that models an individual arbitrary force.
-    This class encapsulates an individual force applied at the specified
+/** Encapsulates code that models an individual arbitrary force, moment or a combination thereof.
+    This class encapsulates an individual reaction applied at the specified
     location on the vehicle, and oriented as specified in one of three frames:
-    
+
     - BODY frame is defined with the X axis positive forward, the Y axis
            positive out the right wing, and the Z axis completing the set
            positive downward out the belly of the aircraft.
@@ -80,14 +82,14 @@ CLASS DOCUMENTATION
            wind frame definition, which is rotated about the Y axis 180 degrees
            from this WIND frame.
 
-    Much of the substance of this class is located in the FGForce base class, from
-    which this class is derived.
-    
+    Much of the substance of this class is located in the FGForce base class,
+    from which this class is derived.
+
     Here is the XML definition of a force (optional items are in []):
-    
+
     @code
     <force name="name" frame="BODY | LOCAL | WIND">
-      
+
       [<function> ... </function>]
 
       <location unit="{IN | M}"> 
@@ -103,54 +105,124 @@ CLASS DOCUMENTATION
     </force>
     @endcode
 
+    The location of the force vector, in structural coordinates, can be set at
+    runtime through the following properties:
+
+    @code
+    external_reactions/{force name}/location-x-in
+    external_reactions/{force name}/location-y-in
+    external_reactions/{force name}/location-z-in
+    @endcode
+
+    The XML definition of a moment (optional items are in []) is a bit simpler
+    because you do not need to specify the location:
+
+    @code
+    <moment name="name" frame="BODY | LOCAL | WIND">
+
+      [<function> ... </function>]
+
+      [<direction> <!-- optional initial direction vector -->
+        <x> {number} </x>
+        <y> {number} </y>
+        <z> {number} </z>
+      </direction>]
+    </moment>
+    @endcode
+
     The initial direction can optionally be set by specifying a unit vector
-    in the chosen frame (body, local, or wind). The direction is specified
-    at runtime through setting any/all of the following properties:
-    
+    in the chosen frame (body, local, or wind).
+
+    As an example, a parachute can be defined oriented in the wind axis frame
+    so the drag always acts in the drag direction - opposite the positive X
+    axis. That does not include the effects of parachute oscillations, but
+    those could be handled in the calling application.
+
+    The force (or moment) direction is not actually required to be specified as
+    a unit vector, but prior to the force (or moment) vector being calculated,
+    the direction vector is normalized when initialized.
+
+    The force direction can be specified at runtime through setting any/all of
+    the following properties:
+
     @code
     external_reactions/{force name}/x
     external_reactions/{force name}/y
     external_reactions/{force name}/z
     @endcode
-    
-    As an example, a parachute can be defined oriented in the wind axis frame
-    so the drag always acts in the drag direction - opposite the positive X
-    axis. That does not include the effects of parachute oscillations, but
-    those could be handled in the calling application.
-     
-    The force direction is not actually required to be specified as a unit
-    vector, but prior to the force vector being calculated, the direction
-    vector is normalized.
 
-    The location of the force vector, in structural coordinates, can be set at
-    runtime through the following properties:
+    The moment direction can be specified at runtime through setting any/all of
+    the following properties:
 
     @code
-    external_reactions/{force name}/locx
-    external_reactions/{force name}/locy
-    external_reactions/{force name}/locz
+    external_reactions/{moment name}/l
+    external_reactions/{moment name}/m
+    external_reactions/{moment name}/n
+    @endcode
+
+    However in that case, the direction is no longer normalized.
+
+    When no <function> has been provided in the force definition, its magnitude
+    can be specified through the following property:
+
+    @code
+    external_reactions/{force name}/magnitude
+    @endcode
+
+    When no <function> has been provided in the moment definition, its magnitude
+    can be specified through the following property:
+
+    @code
+    external_reactions/{moment name}/magnitude-lbsft
     @endcode
-    
 */
 
 /*%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
 CLASS DECLARATION
 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%*/
 
+class FGPropertyVector3
+{
+public:
+  FGPropertyVector3(void) {}
+  FGPropertyVector3(FGPropertyManager* pm, const std::string& baseName,
+                    const std::string& xcmp, const std::string& ycmp,
+                    const std::string& zcmp);
+
+  FGPropertyVector3& operator=(const FGColumnVector3& v) {
+    data[0] = v(1);
+    data[1] = v(2);
+    data[2] = v(3);
+
+    return *this;
+  }
+
+  operator FGColumnVector3() const {
+    return FGColumnVector3(data[0], data[1], data[2]);
+  }
+
+  FGColumnVector3 operator*(double a) const {
+    return FGColumnVector3(a * data[0], a * data[1], a * data[2]);
+  }
+
+private:
+  SGPropObjDouble data[3];
+};
+
+inline FGColumnVector3 operator*(double a, const FGPropertyVector3& v) {
+  return v*a;
+}
+
 class FGExternalForce : public FGForce
 {
 public:
-  /** Constructor.
-      @param FDMExec pointer to the main executive class.
-  */
-  FGExternalForce(FGFDMExec *FDMExec);
-
   /** Constructor.
       @param FDMExec pointer to the main executive class.
       @param el pointer to the XML element defining an individual force.
-      @param index the position of this force object in the whole list.
   */
-  FGExternalForce(FGFDMExec *FDMExec, Element *el, int index);
+  FGExternalForce(FGFDMExec *FDMExec)
+    : FGForce(FDMExec), forceMagnitude(NULL), momentMagnitude(NULL)
+  { Debug(0); }
 
   /** Copy Constructor
       @param extForce a reference to an existing FGExternalForce object
@@ -160,35 +232,18 @@ public:
   /// Destructor
   ~FGExternalForce();
 
-  void SetMagnitude(double mag);
-  void SetAzimuth(double az) {azimuth = az;}
-
+  void setForce(Element* el);
+  void setMoment(Element* el);
   const FGColumnVector3& GetBodyForces(void);
-  double GetMagnitude(void) const {return magnitude;}
-  double GetAzimuth(void) const {return azimuth;}
-  double GetX(void) const {return vDirection(eX);}
-  double GetY(void) const {return vDirection(eY);}
-  double GetZ(void) const {return vDirection(eZ);}
-  void SetX(double x) {vDirection(eX) = x;}
-  void SetY(double y) {vDirection(eY) = y;}
-  void SetZ(double z) {vDirection(eZ) = z;}
-  double GetLocX(void) const {return vActingXYZn(eX);}
-  double GetLocY(void) const {return vActingXYZn(eY);}
-  double GetLocZ(void) const {return vActingXYZn(eZ);}
-  void SetLocX(double x) {vXYZn(eX) = x; vActingXYZn(eX) = x;}
-  void SetLocY(double y) {vXYZn(eY) = y; vActingXYZn(eY) = y;}
-  void SetLocZ(double z) {vXYZn(eZ) = z; vActingXYZn(eZ) = z;}  
-  
-private:
 
-  std::string Frame;
+private:
+  FGParameter* bind(Element* el, FGPropertyManager* pm,
+                    const std::string& baseName, FGPropertyVector3& v);
+
   std::string Name;
-  FGFunction* Magnitude_Function;
-  FGColumnVector3 vDirection;
-  double magnitude;
-  double azimuth;
+  FGParameter *forceMagnitude, *momentMagnitude;
+  FGPropertyVector3 forceDirection, momentDirection;
   void Debug(int from);
 };
 }
 #endif
-
diff --git a/src/FDM/JSBSim/models/FGExternalReactions.cpp b/src/FDM/JSBSim/models/FGExternalReactions.cpp
index 14489904f..50304959a 100644
--- a/src/FDM/JSBSim/models/FGExternalReactions.cpp
+++ b/src/FDM/JSBSim/models/FGExternalReactions.cpp
@@ -39,6 +39,7 @@ INCLUDES
 #include <iostream>
 #include <string>
 
+#include "FGExternalForce.h"
 #include "FGExternalReactions.h"
 #include "input_output/FGXMLElement.h"
 
@@ -54,7 +55,7 @@ DEFINITIONS
 GLOBAL DATA
 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%*/
 
-IDENT(IdSrc,"$Id: FGExternalReactions.cpp,v 1.19 2014/11/25 01:42:27 dpculp Exp $");
+IDENT(IdSrc,"$Id: FGExternalReactions.cpp,v 1.25 2017/06/04 21:06:08 bcoconni Exp $");
 IDENT(IdHdr,ID_EXTERNALREACTIONS);
 
 /*%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
@@ -63,8 +64,6 @@ CLASS IMPLEMENTATION
 
 FGExternalReactions::FGExternalReactions(FGFDMExec* fdmex) : FGModel(fdmex)
 {
-  NoneDefined = true;
-
   Debug(0);
 }
 
@@ -80,18 +79,25 @@ bool FGExternalReactions::Load(Element* el)
 
   // Parse force elements
 
-  int index=0;
   Element* force_element = el->FindElement("force");
   while (force_element) {
-    Forces.push_back( new FGExternalForce(FDMExec, force_element, index) );
-    NoneDefined = false;
-    index++; 
+    Forces.push_back(new FGExternalForce(FDMExec));
+    Forces.back()->setForce(force_element);
     force_element = el->FindNextElement("force");
   }
 
+  // Parse moment elements
+
+  Element* moment_element = el->FindElement("moment");
+  while (moment_element) {
+    Forces.push_back(new FGExternalForce(FDMExec));
+    Forces.back()->setMoment(moment_element);
+    moment_element = el->FindNextElement("moment");
+  }
+
   PostLoad(el, PropertyManager);
 
-  if (!NoneDefined) bind();
+  if (!Forces.empty()) bind();
 
   return true;
 }
@@ -101,7 +107,6 @@ bool FGExternalReactions::Load(Element* el)
 FGExternalReactions::~FGExternalReactions()
 {
   for (unsigned int i=0; i<Forces.size(); i++) delete Forces[i];
-  Forces.clear();
 
   Debug(1);
 }
@@ -124,7 +129,7 @@ bool FGExternalReactions::Run(bool Holding)
 {
   if (FGModel::Run(Holding)) return true;
   if (Holding) return false; // if paused don't execute
-  if (NoneDefined) return true;
+  if (Forces.empty()) return true;
 
   RunPreFunctions();
 
diff --git a/src/FDM/JSBSim/models/FGExternalReactions.h b/src/FDM/JSBSim/models/FGExternalReactions.h
index f5be3578f..50766967f 100644
--- a/src/FDM/JSBSim/models/FGExternalReactions.h
+++ b/src/FDM/JSBSim/models/FGExternalReactions.h
@@ -40,13 +40,13 @@ INCLUDES
 
 #include <vector>
 #include "FGModel.h"
-#include "FGExternalForce.h"
+#include "math/FGColumnVector3.h"
 
 /*%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
 DEFINITIONS
 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%*/
 
-#define ID_EXTERNALREACTIONS "$Id: FGExternalReactions.h,v 1.17 2015/02/27 20:36:47 bcoconni Exp $"
+#define ID_EXTERNALREACTIONS "$Id: FGExternalReactions.h,v 1.20 2017/06/04 21:06:08 bcoconni Exp $"
 
 /*%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
 FORWARD DECLARATIONS
@@ -55,21 +55,23 @@ FORWARD DECLARATIONS
 namespace JSBSim {
 
 class Element;
+class FGExternalForce;
 
 /*%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
 CLASS DOCUMENTATION
 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%*/
 
-/** Manages the external and/or arbitrary forces.
+/** Manages the external and/or arbitrary forces and moments.
+
     The external reactions capability in JSBSim really should be named
-    "arbitrary forces", because this feature can be used to model a wide
-    variety of forces that act on a vehicle. Some examples include: parachutes,
-    catapult, arresting hook, and tow line.
+    "arbitrary forces and moments", because this feature can be used to model a
+    wide variety of forces and moments that act on a vehicle. Some examples
+    include: parachutes, catapult, arresting hook, and tow line.
     
-    This class acts similarly to the other "manager classes" (FGPropulsion, 
-    FGFCS, FGGroundReactions, FGAerodynamics) because it manages collections
-    of constituent forces. The individual forces are implemented with the
-    FGExternalForce class.
+    This class acts similarly to the other "manager classes" (FGPropulsion,
+    FGFCS, FGGroundReactions, FGAerodynamics) because it manages collections of
+    constituent elements. The individual forces and moments are implemented with
+    the FGExternalForce class.
     
     The format of the <em>optional</em> external reactions section in the config
     file is as follows:
@@ -80,35 +82,42 @@ CLASS DOCUMENTATION
   <!-- Interface properties, a.k.a. property declarations -->
   <property> ... </property>
     
-  <force name="name" frame="BODY | LOCAL | WIND" unit="unit">
+  <force name="name" frame="BODY | LOCAL | WIND">
     ...
   </force>
+  <moment name="name" frame="BODY | LOCAL | WIND">
+    ...
+  </moment>
 
-  <!-- Additional force definitions may follow -->
-  <force name="name" frame="BODY | LOCAL | WIND" unit="unit">
+  <!-- Additional force and moment definitions may follow -->
+  <force name="name" frame="BODY | LOCAL | WIND">
     ...
   </force>
+  <moment name="name" frame="BODY | LOCAL | WIND">
+    ...
+  </moment>
 
 </external_reactions>
     @endcode
 
     See the FGExternalForce class for more information on the format of the
-    force specification itself.
+    force and moment specifications.
     
-    When force elements are encountered in the configuration file, a new instance
-    of the FGExternalForce class is created and a pointer to the class is pushed
-    onto the Forces vector.
+    When force or moment elements are encountered in the configuration file, a
+    new instance of the FGExternalForce class is created and a pointer to the
+    class is pushed onto the Forces vector.
     
-    This class is one of a few of the manager classes that allows properties
-    to be "declared". In code, these are represented by the
+    This class is one of a few of the manager classes that allows properties to
+    be "declared". In code, these are represented by the
     <em>interface_properties</em> vector. Properties that have not yet been
     created in an already parsed section of the configuration file and that are
-    used in the definition of an external force should be declared in the
-    external_reactions section because they will not be created automatically,
-    and so would cause an error, since the property cannot be found to exist.
+    used in the definition of an external force or moment should be declared in
+    the external_reactions section because they will not be created
+    automatically, and so would cause an error, since the property cannot be
+    found to exist.
         
-    See the FGExternalForce documentation for details on how forces are
-    actually calculated.
+    See the FGExternalForce documentation for details on how forces and moments
+    are actually calculated.
   */
 
 /*%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
@@ -167,8 +176,6 @@ private:
   FGColumnVector3 vTotalForces;
   FGColumnVector3 vTotalMoments;
 
-  bool NoneDefined;
-
   void bind(void);
   void Debug(int from);
 };
diff --git a/src/FDM/JSBSim/models/FGGasCell.h b/src/FDM/JSBSim/models/FGGasCell.h
index 1105c4f95..563525752 100644
--- a/src/FDM/JSBSim/models/FGGasCell.h
+++ b/src/FDM/JSBSim/models/FGGasCell.h
@@ -50,7 +50,7 @@ INCLUDES
 DEFINITIONS
 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%*/
 
-#define ID_GASCELL "$Id: FGGasCell.h,v 1.16 2015/03/28 14:49:02 bcoconni Exp $"
+#define ID_GASCELL "$Id: FGGasCell.h,v 1.17 2017/06/03 19:49:20 bcoconni Exp $"
 
 /*%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
 FORWARD DECLARATIONS
@@ -59,7 +59,7 @@ FORWARD DECLARATIONS
 namespace JSBSim {
 
 class FGBallonet;
-class Element;
+class FGMassBalance;
 
 /*%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
 CLASS DOCUMENTATION
diff --git a/src/FDM/JSBSim/models/propulsion/FGElectric.cpp b/src/FDM/JSBSim/models/propulsion/FGElectric.cpp
index 9273a97bc..ee7938291 100644
--- a/src/FDM/JSBSim/models/propulsion/FGElectric.cpp
+++ b/src/FDM/JSBSim/models/propulsion/FGElectric.cpp
@@ -42,6 +42,7 @@ INCLUDES
 #include <iostream>
 #include <sstream>
 
+#include "FGFDMExec.h"
 #include "FGElectric.h"
 #include "FGPropeller.h"
 #include "input_output/FGXMLElement.h"
@@ -50,7 +51,7 @@ using namespace std;
 
 namespace JSBSim {
 
-IDENT(IdSrc,"$Id: FGElectric.cpp,v 1.20 2015/09/27 09:54:21 bcoconni Exp $");
+IDENT(IdSrc,"$Id: FGElectric.cpp,v 1.21 2017/06/03 19:49:20 bcoconni Exp $");
 IDENT(IdHdr,ID_ELECTRIC);
 
 /*%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
diff --git a/src/FDM/JSBSim/models/propulsion/FGForce.cpp b/src/FDM/JSBSim/models/propulsion/FGForce.cpp
index a579f7773..d4e1b0395 100644
--- a/src/FDM/JSBSim/models/propulsion/FGForce.cpp
+++ b/src/FDM/JSBSim/models/propulsion/FGForce.cpp
@@ -53,7 +53,7 @@ using namespace std;
 
 namespace JSBSim {
 
-IDENT(IdSrc,"$Id: FGForce.cpp,v 1.19 2014/01/13 10:46:10 ehofman Exp $");
+IDENT(IdSrc,"$Id: FGForce.cpp,v 1.20 2017/05/26 12:25:40 bcoconni Exp $");
 IDENT(IdHdr,ID_FORCE);
 
 //%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
@@ -64,14 +64,12 @@ FGForce::FGForce(FGFDMExec *FDMExec) :
 {
   vFn.InitMatrix();
   vMn.InitMatrix();
-  vH.InitMatrix();
   vOrient.InitMatrix();
   vXYZn.InitMatrix();
   vActingXYZn.InitMatrix();
 
   vFb.InitMatrix();
   vM.InitMatrix();
-  vDXYZ.InitMatrix();
 
   mT.InitMatrix(1., 0., 0.,
                 0., 1., 0.,
@@ -97,7 +95,7 @@ const FGColumnVector3& FGForce::GetBodyForces(void)
   // needs to be done like this to convert from structural to body coords.
   // CG and RP values are in inches
 
-  vDXYZ = fdmex->GetMassBalance()->StructuralToBody(vActingXYZn);
+  FGColumnVector3 vDXYZ = fdmex->GetMassBalance()->StructuralToBody(vActingXYZn);
 
   vM = vMn + vDXYZ*vFb;
 
diff --git a/src/FDM/JSBSim/models/propulsion/FGForce.h b/src/FDM/JSBSim/models/propulsion/FGForce.h
index 2cd81c0e7..e432943f1 100644
--- a/src/FDM/JSBSim/models/propulsion/FGForce.h
+++ b/src/FDM/JSBSim/models/propulsion/FGForce.h
@@ -57,7 +57,6 @@ SENTRY
 INCLUDES
 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%*/
 
-#include "FGFDMExec.h"
 #include "FGJSBBase.h"
 #include "math/FGMatrix33.h"
 #include "math/FGColumnVector3.h"
@@ -66,7 +65,7 @@ INCLUDES
 DEFINITIONS
 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%*/
 
-#define ID_FORCE "$Id: FGForce.h,v 1.17 2012/04/01 17:05:51 bcoconni Exp $"
+#define ID_FORCE "$Id: FGForce.h,v 1.19 2017/06/03 19:49:20 bcoconni Exp $"
 
 /*%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
 FORWARD DECLARATIONS
@@ -74,6 +73,8 @@ FORWARD DECLARATIONS
 
 namespace JSBSim {
 
+class FGFDMExec;
+
 /*%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
 CLASS DOCUMENTATION
 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%*/
@@ -215,7 +216,7 @@ and vMn, the moments, can be made directly. Otherwise, the usage is similar.<br>
 <br><br></p>
 
     @author Tony Peden
-    @version $Id: FGForce.h,v 1.17 2012/04/01 17:05:51 bcoconni Exp $
+    @version $Id: FGForce.h,v 1.19 2017/06/03 19:49:20 bcoconni Exp $
 */
 
 /*%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
@@ -227,12 +228,8 @@ class FGForce : public FGJSBBase
 public:
   /// Constructor
   FGForce(FGFDMExec *FDMExec);
-  FGForce(const FGForce& force) {
-    vFn = force.vFn;
-    vXYZn = force.vXYZn;
-    ttype = force.ttype;
-    fdmex = force.fdmex;
-  }
+  FGForce(const FGForce& force);
+
   /// Destructor
   ~FGForce();
 
@@ -316,7 +313,6 @@ protected:
   FGFDMExec *fdmex;
   FGColumnVector3 vFn;
   FGColumnVector3 vMn;
-  FGColumnVector3 vH;
   FGColumnVector3 vOrient;
   TransformType ttype;
   FGColumnVector3 vXYZn;
@@ -326,7 +322,6 @@ protected:
 private:
   FGColumnVector3 vFb;
   FGColumnVector3 vM;
-  FGColumnVector3 vDXYZ;
 
   void Debug(int from);
 };
diff --git a/src/FDM/JSBSim/models/propulsion/FGPiston.cpp b/src/FDM/JSBSim/models/propulsion/FGPiston.cpp
index 2ec5c29a0..a61c2f5fd 100644
--- a/src/FDM/JSBSim/models/propulsion/FGPiston.cpp
+++ b/src/FDM/JSBSim/models/propulsion/FGPiston.cpp
@@ -43,6 +43,7 @@ INCLUDES
 #include <iostream>
 #include <sstream>
 
+#include "FGFDMExec.h"
 #include "FGPiston.h"
 #include "FGPropeller.h"
 #include "input_output/FGXMLElement.h"
@@ -51,7 +52,7 @@ using namespace std;
 
 namespace JSBSim {
 
-IDENT(IdSrc,"$Id: FGPiston.cpp,v 1.82 2016/01/02 17:42:53 bcoconni Exp $");
+IDENT(IdSrc,"$Id: FGPiston.cpp,v 1.84 2017/06/03 19:49:20 bcoconni Exp $");
 IDENT(IdHdr,ID_PISTON);
 
 /*%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
diff --git a/src/FDM/JSBSim/models/propulsion/FGPiston.h b/src/FDM/JSBSim/models/propulsion/FGPiston.h
index 97c6b7350..8c2668d3f 100644
--- a/src/FDM/JSBSim/models/propulsion/FGPiston.h
+++ b/src/FDM/JSBSim/models/propulsion/FGPiston.h
@@ -46,7 +46,7 @@ INCLUDES
 DEFINITIONS
 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%*/
 
-#define ID_PISTON "$Id: FGPiston.h,v 1.38 2016/01/02 17:42:53 bcoconni Exp $"
+#define ID_PISTON "$Id: FGPiston.h,v 1.39 2017/04/29 11:16:46 ehofman Exp $"
 #define FG_MAX_BOOST_SPEEDS 3
 
 /*%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
@@ -106,6 +106,10 @@ CLASS DOCUMENTATION
   <ratedrpm3> {number} </ratedrpm3>
   <ratedaltitude3 unit="{FT | M}"> {number} </ratedaltitude3>
   <takeoffboost unit="{INHG | PA | ATM}"> {number} </takeoffboost>
+  <oil-pressure-relief-valve-psi> {number} </oil-pressure-relief-valve=psi>
+  <design-oil-temp-degK>  {number} </design-oil-temp-degK>
+  <oil-pressure-rpm-max> {number} </oil-pressure-rpm-max>
+  <oil-viscosity-index> {number} </oil-viscosity-index>
 </piston_engine>
 @endcode
 
@@ -211,7 +215,7 @@ boostspeed they refer to:
     @author David Megginson (initial porting and additional code)
     @author Ron Jensen (additional engine code)
     @see Taylor, Charles Fayette, "The Internal Combustion Engine in Theory and Practice"
-    @version $Id: FGPiston.h,v 1.38 2016/01/02 17:42:53 bcoconni Exp $
+    @version $Id: FGPiston.h,v 1.39 2017/04/29 11:16:46 ehofman Exp $
   */
 
 /*%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
diff --git a/src/FDM/JSBSim/models/propulsion/FGPropeller.cpp b/src/FDM/JSBSim/models/propulsion/FGPropeller.cpp
index 50d9f8836..f2910efc2 100644
--- a/src/FDM/JSBSim/models/propulsion/FGPropeller.cpp
+++ b/src/FDM/JSBSim/models/propulsion/FGPropeller.cpp
@@ -38,6 +38,7 @@ INCLUDES
 #include <iostream>
 #include <sstream>
 
+#include "FGFDMExec.h"
 #include "FGPropeller.h"
 #include "input_output/FGXMLElement.h"
 
@@ -45,7 +46,7 @@ using namespace std;
 
 namespace JSBSim {
 
-IDENT(IdSrc,"$Id: FGPropeller.cpp,v 1.61 2017/03/22 21:27:47 bcoconni Exp $");
+IDENT(IdSrc,"$Id: FGPropeller.cpp,v 1.63 2017/06/03 19:49:20 bcoconni Exp $");
 IDENT(IdHdr,ID_PROPELLER);
 
 /*%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
@@ -146,7 +147,6 @@ FGPropeller::FGPropeller(FGFDMExec* exec, Element* prop_element, int num)
   Type = ttPropeller;
   RPM = 0;
   vTorque.InitMatrix();
-  vH.InitMatrix();
   D4 = Diameter*Diameter*Diameter*Diameter;
   D5 = D4*Diameter;
   Pitch = MinPitch;
@@ -273,7 +273,7 @@ double FGPropeller::Calculate(double EnginePower)
   // natural axis of the engine. The transform takes place in the base class
   // FGForce::GetBodyForces() function.
 
-  vH(eX) = Ixx*omega*Sense*Sense_multiplier;
+  FGColumnVector3 vH(Ixx*omega*Sense*Sense_multiplier, 0.0, 0.0);
 
   if (omega > 0.0) ExcessTorque = PowerAvailable / omega;
   else             ExcessTorque = PowerAvailable / 1.0;
diff --git a/src/FDM/JSBSim/models/propulsion/FGRocket.cpp b/src/FDM/JSBSim/models/propulsion/FGRocket.cpp
index 69f72d776..b2ca883f5 100644
--- a/src/FDM/JSBSim/models/propulsion/FGRocket.cpp
+++ b/src/FDM/JSBSim/models/propulsion/FGRocket.cpp
@@ -41,6 +41,7 @@ INCLUDES
 #include <iostream>
 #include <sstream>
 
+#include "FGFDMExec.h"
 #include "FGRocket.h"
 #include "FGThruster.h"
 #include "input_output/FGXMLElement.h"
@@ -49,7 +50,7 @@ using namespace std;
 
 namespace JSBSim {
 
-IDENT(IdSrc,"$Id: FGRocket.cpp,v 1.39 2015/09/27 09:54:21 bcoconni Exp $");
+IDENT(IdSrc,"$Id: FGRocket.cpp,v 1.40 2017/06/03 19:49:20 bcoconni Exp $");
 IDENT(IdHdr,ID_ROCKET);
 
 /*%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
diff --git a/src/FDM/JSBSim/models/propulsion/FGThruster.cpp b/src/FDM/JSBSim/models/propulsion/FGThruster.cpp
index b01cd6eec..1f4ddba75 100644
--- a/src/FDM/JSBSim/models/propulsion/FGThruster.cpp
+++ b/src/FDM/JSBSim/models/propulsion/FGThruster.cpp
@@ -38,6 +38,8 @@ INCLUDES
 #include <iostream>
 #include <sstream>
 
+#include "FGFDMExec.h"
+#include "input_output/FGPropertyManager.h"
 #include "FGThruster.h"
 #include "input_output/FGXMLElement.h"
 
@@ -45,7 +47,7 @@ using namespace std;
 
 namespace JSBSim {
 
-IDENT(IdSrc,"$Id: FGThruster.cpp,v 1.22 2015/09/27 10:03:53 bcoconni Exp $");
+IDENT(IdSrc,"$Id: FGThruster.cpp,v 1.23 2017/06/03 19:49:20 bcoconni Exp $");
 IDENT(IdHdr,ID_THRUSTER);
 
 /*%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
diff --git a/src/FDM/JSBSim/models/propulsion/FGTurbine.cpp b/src/FDM/JSBSim/models/propulsion/FGTurbine.cpp
index 8b4eeac3e..796ec02cf 100644
--- a/src/FDM/JSBSim/models/propulsion/FGTurbine.cpp
+++ b/src/FDM/JSBSim/models/propulsion/FGTurbine.cpp
@@ -42,6 +42,7 @@ INCLUDES
 #include <iostream>
 #include <sstream>
 
+#include "FGFDMExec.h"
 #include "math/FGFunction.h"
 #include "FGTurbine.h"
 #include "FGThruster.h"
@@ -51,7 +52,7 @@ using namespace std;
 
 namespace JSBSim {
 
-IDENT(IdSrc,"$Id: FGTurbine.cpp,v 1.48 2015/12/02 04:25:23 dpculp Exp $");
+IDENT(IdSrc,"$Id: FGTurbine.cpp,v 1.49 2017/06/03 19:49:20 bcoconni Exp $");
 IDENT(IdHdr,ID_TURBINE);
 
 /*%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
diff --git a/src/FDM/JSBSim/models/propulsion/FGTurboProp.cpp b/src/FDM/JSBSim/models/propulsion/FGTurboProp.cpp
old mode 100755
new mode 100644