diff --git a/VectoCore/Models/Connector/Ports/ITnPort.cs b/VectoCore/Models/Connector/Ports/ITnPort.cs
index f3df1dd0c8f1a4d839150851878c5068618e3450..0d6ddba5b82b143d8d717d83c0dac6d754e51f96 100644
--- a/VectoCore/Models/Connector/Ports/ITnPort.cs
+++ b/VectoCore/Models/Connector/Ports/ITnPort.cs
@@ -26,6 +26,6 @@ namespace TUGraz.VectoCore.Models.Connector.Ports
         /// <param name="dt">[s]</param>
         /// <param name="torque">[Nm]</param>
         /// <param name="angularVelocity">[rad/s]</param>
-        IResponse Request(TimeSpan absTime, TimeSpan dt, NewtonMeter torque, RadianPerSecond angularVelocity);
+        IResponse Request(TimeSpan absTime, TimeSpan dt, NewtonMeter torque, PerSecond angularVelocity);
     }
 }
\ No newline at end of file
diff --git a/VectoCore/Models/Simulation/Cockpit/IEngineCockpit.cs b/VectoCore/Models/Simulation/Cockpit/IEngineCockpit.cs
index e1844efc5802e3a74f000371116d53f1dcd0b502..52b57d8e718cae9a2553c4058d93250ae8100d58 100644
--- a/VectoCore/Models/Simulation/Cockpit/IEngineCockpit.cs
+++ b/VectoCore/Models/Simulation/Cockpit/IEngineCockpit.cs
@@ -10,6 +10,6 @@ namespace TUGraz.VectoCore.Models.Simulation.Cockpit
         /// <summary>
         /// [rad/s] The current engine speed.
         /// </summary>
-        RadianPerSecond EngineSpeed();
+        PerSecond EngineSpeed();
     }
 }
\ No newline at end of file
diff --git a/VectoCore/Models/Simulation/Impl/VehicleContainer.cs b/VectoCore/Models/Simulation/Impl/VehicleContainer.cs
index c1de88ce572721a10032d879c1f97f1ce32d63b0..dfa97107416ce81cbb05c1bcdd477385b5aa37a7 100644
--- a/VectoCore/Models/Simulation/Impl/VehicleContainer.cs
+++ b/VectoCore/Models/Simulation/Impl/VehicleContainer.cs
@@ -29,7 +29,7 @@ namespace TUGraz.VectoCore.Models.Simulation.Impl
 
         #region IEngineCockpit
 
-        public RadianPerSecond EngineSpeed()
+        public PerSecond EngineSpeed()
         {
             if (_engine == null) {
                 throw new VectoException("no engine available!");
diff --git a/VectoCore/Models/SimulationComponent/Data/CombustionEngineData.cs b/VectoCore/Models/SimulationComponent/Data/CombustionEngineData.cs
index 0b7def405135caeb627585e41dcde7ffe9c5bed4..954e88b367d921828278c720988c8edb835a1f2f 100644
--- a/VectoCore/Models/SimulationComponent/Data/CombustionEngineData.cs
+++ b/VectoCore/Models/SimulationComponent/Data/CombustionEngineData.cs
@@ -75,7 +75,7 @@ namespace TUGraz.VectoCore.Models.SimulationComponent.Data
         /// <summary>
         ///     [rad/s]
         /// </summary>
-        public RadianPerSecond IdleSpeed
+        public PerSecond IdleSpeed
         {
             get { return _data.Body.IdleSpeed.RPMtoRad(); }
             protected set { _data.Body.IdleSpeed = (double) value.ConvertTo().Rounds.Per.Minute; }
diff --git a/VectoCore/Models/SimulationComponent/Data/DrivingCycleData.cs b/VectoCore/Models/SimulationComponent/Data/DrivingCycleData.cs
index 056f46fde552ec3d6e6cb83851745af54fc1dc89..a1e4032d5a4a9070912bc18e1267e7841a2506b1 100644
--- a/VectoCore/Models/SimulationComponent/Data/DrivingCycleData.cs
+++ b/VectoCore/Models/SimulationComponent/Data/DrivingCycleData.cs
@@ -178,7 +178,7 @@ namespace TUGraz.VectoCore.Models.SimulationComponent.Data
             ///     [rad/s]	If "n" is defined VECTO uses that instead of the
             ///     calculated engine speed value.
             /// </summary>
-            public RadianPerSecond EngineSpeed { get; set; }
+            public PerSecond EngineSpeed { get; set; }
 
             /// <summary>
             ///     [-]	Gear input. Overwrites the gear shift model.
@@ -249,7 +249,7 @@ namespace TUGraz.VectoCore.Models.SimulationComponent.Data
                     AdditionalAuxPowerDemand =
                         row.ParseDoubleOrGetDefault(Fields.AdditionalAuxPowerDemand).SI().Kilo.Watt.Cast<Watt>(),
                     EngineSpeed =
-                        row.ParseDoubleOrGetDefault(Fields.EngineSpeed).SI().Rounds.Per.Minute.Cast<RadianPerSecond>(),
+                        row.ParseDoubleOrGetDefault(Fields.EngineSpeed).SI().Rounds.Per.Minute.Cast<PerSecond>(),
                     Gear = row.ParseDoubleOrGetDefault(Fields.Gear),
                     AirSpeedRelativeToVehicle =
                         row.ParseDoubleOrGetDefault(Fields.AirSpeedRelativeToVehicle)
@@ -311,7 +311,7 @@ namespace TUGraz.VectoCore.Models.SimulationComponent.Data
                         row.ParseDoubleOrGetDefault(Fields.AdditionalAuxPowerDemand).SI().Kilo.Watt.Cast<Watt>(),
                     Gear = row.ParseDoubleOrGetDefault(Fields.Gear),
                     EngineSpeed =
-                        row.ParseDoubleOrGetDefault(Fields.EngineSpeed).SI().Rounds.Per.Minute.Cast<RadianPerSecond>(),
+                        row.ParseDoubleOrGetDefault(Fields.EngineSpeed).SI().Rounds.Per.Minute.Cast<PerSecond>(),
                     AirSpeedRelativeToVehicle =
                         row.ParseDoubleOrGetDefault(Fields.AirSpeedRelativeToVehicle)
                             .SI()
@@ -365,7 +365,7 @@ namespace TUGraz.VectoCore.Models.SimulationComponent.Data
                 foreach (DataRow row in table.Rows) {
                     var entry = new DrivingCycleEntry {
                         EngineSpeed =
-                            row.ParseDoubleOrGetDefault(Fields.EngineSpeed).SI().Rounds.Per.Minute.Cast<RadianPerSecond>(),
+                            row.ParseDoubleOrGetDefault(Fields.EngineSpeed).SI().Rounds.Per.Minute.Cast<PerSecond>(),
                         AdditionalAuxPowerDemand =
                             row.ParseDoubleOrGetDefault(Fields.AdditionalAuxPowerDemand).SI().Kilo.Watt.Cast<Watt>(),
                         AuxiliarySupplyPower = AuxSupplyPowerReader.Read(row)
diff --git a/VectoCore/Models/SimulationComponent/Data/Engine/FuelConsumptionMap.cs b/VectoCore/Models/SimulationComponent/Data/Engine/FuelConsumptionMap.cs
index cf39c70c9908d34f8237f2da12d26dc1e5181b65..f1ef8218c1b7f94cb5820c1446974730e96d65ab 100644
--- a/VectoCore/Models/SimulationComponent/Data/Engine/FuelConsumptionMap.cs
+++ b/VectoCore/Models/SimulationComponent/Data/Engine/FuelConsumptionMap.cs
@@ -26,7 +26,7 @@ namespace TUGraz.VectoCore.Models.SimulationComponent.Data.Engine
                     try {
                         var entry = new FuelConsumptionEntry {
                             EngineSpeed =
-                                row.ParseDouble(Fields.EngineSpeed).SI().Rounds.Per.Minute.Cast<RadianPerSecond>(),
+                                row.ParseDouble(Fields.EngineSpeed).SI().Rounds.Per.Minute.Cast<PerSecond>(),
                             Torque = row.ParseDouble(Fields.Torque).SI<NewtonMeter>(),
                             FuelConsumption =
                                 row.ParseDouble(Fields.FuelConsumption).SI().Gramm.Per.Hour.ConvertTo().Kilo.Gramm.Per.Second
@@ -61,7 +61,7 @@ namespace TUGraz.VectoCore.Models.SimulationComponent.Data.Engine
         /// <param name="engineSpeed">[rad/sec]</param>
         /// <param name="torque">[Nm]</param>
         /// <returns>[kg/s]</returns>
-        public SI GetFuelConsumption(NewtonMeter torque, RadianPerSecond engineSpeed)
+        public SI GetFuelConsumption(NewtonMeter torque, PerSecond engineSpeed)
         {
             // delauney map needs is initialised with rpm, therefore the engineSpeed has to be converted.
             return
@@ -93,7 +93,7 @@ namespace TUGraz.VectoCore.Models.SimulationComponent.Data.Engine
             /// <summary>
             ///     engine speed [rad/s]
             /// </summary>
-            public RadianPerSecond EngineSpeed { get; set; }
+            public PerSecond EngineSpeed { get; set; }
 
             /// <summary>
             ///     Torque [Nm]
diff --git a/VectoCore/Models/SimulationComponent/Data/Engine/FullLoadCurve.cs b/VectoCore/Models/SimulationComponent/Data/Engine/FullLoadCurve.cs
index c78dd738df4dac7cb84255575b81fc82884fb326..23817dfd7f9340ae61192d9c270148cdf9076587 100644
--- a/VectoCore/Models/SimulationComponent/Data/Engine/FullLoadCurve.cs
+++ b/VectoCore/Models/SimulationComponent/Data/Engine/FullLoadCurve.cs
@@ -9,267 +9,268 @@ using TUGraz.VectoCore.Utils;
 
 namespace TUGraz.VectoCore.Models.SimulationComponent.Data.Engine
 {
-    /// <summary>
-    /// Represents the Full load curve.
-    /// </summary>
-    public class FullLoadCurve : SimulationComponentData
-    {
-        [JsonProperty] private List<FullLoadCurveEntry> _entries;
-
-        public static FullLoadCurve ReadFromFile(string fileName)
-        {
-            var data = VectoCSVFile.Read(fileName);
-
-            //todo Contract.Requires<VectoException>(data.Columns.Count != 4, "FullLoadCurve Data File must consist of 4 columns.");
-            if (data.Columns.Count != 4) {
-                throw new VectoException("FullLoadCurve Data File must consist of 4 columns.");
-            }
-
-            //todo Contract.Requires<VectoException>(data.Rows.Count < 2, "FullLoadCurve must consist of at least two lines with numeric values (below file header)");
-            if (data.Rows.Count < 2) {
-                throw new VectoException(
-                    "FullLoadCurve must consist of at least two lines with numeric values (below file header)");
-            }
-
-            List<FullLoadCurveEntry> entries;
-            if (HeaderIsValid(data.Columns)) {
-                entries = CreateFromColumnNames(data);
-            } else {
-                var log = LogManager.GetLogger<FullLoadCurve>();
-                log.WarnFormat(
-                    "FullLoadCurve: Header Line is not valid. Expected: '{0}, {1}, {2}, {3}', Got: '{4}'. Falling back to column index.",
-                    Fields.EngineSpeed, Fields.TorqueFullLoad, Fields.TorqueDrag, Fields.PT1,
-                    string.Join(", ", data.Columns.Cast<DataColumn>().Select(c => c.ColumnName).Reverse()));
-
-                entries = CreateFromColumnIndizes(data);
-            }
-
-            return new FullLoadCurve { _entries = entries };
-        }
-
-        private static bool HeaderIsValid(DataColumnCollection columns)
-        {
-            Contract.Requires(columns != null);
-            return columns.Contains(Fields.EngineSpeed)
-                   && columns.Contains(Fields.TorqueDrag)
-                   && columns.Contains(Fields.TorqueFullLoad)
-                   && columns.Contains(Fields.PT1);
-        }
-
-        private static List<FullLoadCurveEntry> CreateFromColumnNames(DataTable data)
-        {
-            Contract.Requires(data != null);
-            return (from DataRow row in data.Rows
-                select new FullLoadCurveEntry {
-                    EngineSpeed = row.ParseDouble(Fields.EngineSpeed).RPMtoRad(),
-                    TorqueFullLoad = row.ParseDouble(Fields.TorqueFullLoad).SI<NewtonMeter>(),
-                    TorqueDrag = row.ParseDouble(Fields.TorqueDrag).SI<NewtonMeter>(),
-                    PT1 = row.ParseDouble(Fields.PT1).SI<Second>()
-                }).ToList();
-        }
-
-        private static List<FullLoadCurveEntry> CreateFromColumnIndizes(DataTable data)
-        {
-            Contract.Requires(data != null);
-            return (from DataRow row in data.Rows
-                select new FullLoadCurveEntry {
-                    EngineSpeed = row.ParseDouble(0).RPMtoRad(),
-                    TorqueFullLoad = row.ParseDouble(1).SI<NewtonMeter>(),
-                    TorqueDrag = row.ParseDouble(2).SI<NewtonMeter>(),
-                    PT1 = row.ParseDouble(3).SI<Second>()
-                }).ToList();
-        }
-
-        /// <summary>
-        ///     [rad/s] => [Nm]
-        /// </summary>
-        /// <param name="angularFrequency">[rad/s]</param>
-        /// <returns>[Nm]</returns>
-        public NewtonMeter FullLoadStationaryTorque(RadianPerSecond angularFrequency)
-        {
-            var idx = FindIndex(angularFrequency);
-            return VectoMath.Interpolate((double) _entries[idx - 1].EngineSpeed, (double) _entries[idx].EngineSpeed,
-                (double) _entries[idx - 1].TorqueFullLoad, (double) _entries[idx].TorqueFullLoad,
-                (double) angularFrequency).SI<NewtonMeter>();
-        }
-
-        /// <summary>
-        ///     [rad/s] => [W]
-        /// </summary>
-        /// <param name="angularFrequency">[rad/s]</param>
-        /// <returns>[W]</returns>
-        public Watt FullLoadStationaryPower(RadianPerSecond angularFrequency)
-        {
-            return Formulas.TorqueToPower(FullLoadStationaryTorque(angularFrequency), angularFrequency);
-        }
-
-        /// <summary>
-        ///     [rad/s] => [Nm]
-        /// </summary>
-        /// <param name="angularFrequency">[rad/s]</param>
-        /// <returns>[Nm]</returns>
-        public NewtonMeter DragLoadStationaryTorque(RadianPerSecond angularFrequency)
-        {
-            var idx = FindIndex(angularFrequency);
-            return VectoMath.Interpolate((double) _entries[idx - 1].EngineSpeed, (double) _entries[idx].EngineSpeed,
-                (double) _entries[idx - 1].TorqueDrag, (double) _entries[idx].TorqueDrag,
-                (double) angularFrequency).SI<NewtonMeter>();
-        }
-
-        /// <summary>
-        ///     [rad/s] => [W].
-        /// </summary>
-        /// <param name="angularFrequency">[rad/s]</param>
-        /// <returns>[W]</returns>
-        public Watt DragLoadStationaryPower(RadianPerSecond angularFrequency)
-        {
-            Contract.Requires(angularFrequency.HasEqualUnit(new SI().Radian.Per.Second));
-            Contract.Ensures(Contract.Result<SI>().HasEqualUnit(new SI().Watt));
-
-            return Formulas.TorqueToPower(DragLoadStationaryTorque(angularFrequency), angularFrequency);
-        }
-
-        /// <summary>
-        ///     [rad/s] => [-]
-        /// </summary>
-        /// <param name="angularFrequency">[rad/s]</param>
-        /// <returns>[-]</returns>
-        public double PT1(SI angularFrequency)
-        {
-            Contract.Requires(angularFrequency.HasEqualUnit(new SI().Radian.Per.Second));
-            Contract.Ensures(Contract.Result<SI>().HasEqualUnit(new SI()));
-
-            var idx = FindIndex(angularFrequency);
-            return VectoMath.Interpolate((double) _entries[idx - 1].EngineSpeed, (double) _entries[idx].EngineSpeed,
-                (double) _entries[idx - 1].PT1, (double) _entries[idx].PT1,
-                (double) angularFrequency);
-        }
-
-        /// <summary>
-        ///     [rad/s] => index. Get item index for engineSpeed.
-        /// </summary>
-        /// <param name="engineSpeed">[rad/s]</param>
-        /// <returns>index</returns>
-        protected int FindIndex(SI engineSpeed)
-        {
-            Contract.Requires(engineSpeed.HasEqualUnit(new SI().Radian.Per.Second));
-
-            int idx;
-            if (engineSpeed < _entries[0].EngineSpeed) {
-                Log.ErrorFormat("requested rpm below minimum rpm in FLD curve - extrapolating. n: {0}, rpm_min: {1}",
-                    engineSpeed.ConvertTo().Rounds.Per.Minute, _entries[0].EngineSpeed.ConvertTo().Rounds.Per.Minute);
-                idx = 1;
-            } else {
-                idx = _entries.FindIndex(x => x.EngineSpeed > engineSpeed);
-            }
-            if (idx <= 0) {
-                idx = engineSpeed > _entries[0].EngineSpeed ? _entries.Count - 1 : 1;
-            }
-            return idx;
-        }
-
-        private static class Fields
-        {
-            /// <summary>
-            ///     [rpm] engine speed
-            /// </summary>
-            public const string EngineSpeed = "engine speed";
-
-            /// <summary>
-            ///     [Nm] full load torque
-            /// </summary>
-            public const string TorqueFullLoad = "full load torque";
-
-            /// <summary>
-            ///     [Nm] motoring torque
-            /// </summary>
-            public const string TorqueDrag = "motoring torque";
-
-            /// <summary>
-            ///     [s] time constant
-            /// </summary>
-            public const string PT1 = "PT1";
-        }
-
-        private class FullLoadCurveEntry
-        {
-            /// <summary>
-            ///     [rad/s] engine speed
-            /// </summary>
-            public RadianPerSecond EngineSpeed { get; set; }
-
-            /// <summary>
-            ///     [Nm] full load torque
-            /// </summary>
-            public NewtonMeter TorqueFullLoad { get; set; }
-
-            /// <summary>
-            ///     [Nm] motoring torque
-            /// </summary>
-            public NewtonMeter TorqueDrag { get; set; }
-
-            /// <summary>
-            ///     [s] PT1 time constant
-            /// </summary>
-            public Second PT1 { get; set; }
-
-            #region Equality members
-
-            protected bool Equals(FullLoadCurveEntry other)
-            {
-                Contract.Requires(other != null);
-                return EngineSpeed.Equals(other.EngineSpeed)
-                       && TorqueFullLoad.Equals(other.TorqueFullLoad)
-                       && TorqueDrag.Equals(other.TorqueDrag)
-                       && PT1.Equals(other.PT1);
-            }
-
-            public override bool Equals(object obj)
-            {
-                if (ReferenceEquals(null, obj)) {
-                    return false;
-                }
-                if (ReferenceEquals(this, obj)) {
-                    return true;
-                }
-                return obj.GetType() == GetType() && Equals((FullLoadCurveEntry) obj);
-            }
-
-            public override int GetHashCode()
-            {
-                var hashCode = EngineSpeed.GetHashCode();
-                hashCode = (hashCode * 397) ^ TorqueFullLoad.GetHashCode();
-                hashCode = (hashCode * 397) ^ TorqueDrag.GetHashCode();
-                hashCode = (hashCode * 397) ^ PT1.GetHashCode();
-                return hashCode;
-            }
-
-            #endregion
-        }
-
-        #region Equality members
-
-        protected bool Equals(FullLoadCurve other)
-        {
-            return _entries.SequenceEqual(other._entries);
-        }
-
-        public override bool Equals(object obj)
-        {
-            if (ReferenceEquals(null, obj)) {
-                return false;
-            }
-            if (ReferenceEquals(this, obj)) {
-                return true;
-            }
-            return obj.GetType() == GetType() && Equals((FullLoadCurve) obj);
-        }
-
-        public override int GetHashCode()
-        {
-            return (_entries != null ? _entries.GetHashCode() : 0);
-        }
-
-        #endregion
-    }
+	/// <summary>
+	/// Represents the Full load curve.
+	/// </summary>
+	public class FullLoadCurve : SimulationComponentData
+	{
+		[JsonProperty] private List<FullLoadCurveEntry> _entries;
+
+		public static FullLoadCurve ReadFromFile(string fileName)
+		{
+			var data = VectoCSVFile.Read(fileName);
+
+			//todo Contract.Requires<VectoException>(data.Columns.Count != 4, "FullLoadCurve Data File must consist of 4 columns.");
+			if (data.Columns.Count != 4) {
+				throw new VectoException("FullLoadCurve Data File must consist of 4 columns.");
+			}
+
+			//todo Contract.Requires<VectoException>(data.Rows.Count < 2, "FullLoadCurve must consist of at least two lines with numeric values (below file header)");
+			if (data.Rows.Count < 2) {
+				throw new VectoException(
+					"FullLoadCurve must consist of at least two lines with numeric values (below file header)");
+			}
+
+			List<FullLoadCurveEntry> entries;
+			if (HeaderIsValid(data.Columns)) {
+				entries = CreateFromColumnNames(data);
+			} else {
+				var log = LogManager.GetLogger<FullLoadCurve>();
+				log.WarnFormat(
+					"FullLoadCurve: Header Line is not valid. Expected: '{0}, {1}, {2}, {3}', Got: '{4}'. Falling back to column index.",
+					Fields.EngineSpeed, Fields.TorqueFullLoad, Fields.TorqueDrag, Fields.PT1,
+					string.Join(", ", data.Columns.Cast<DataColumn>().Select(c => c.ColumnName).Reverse()));
+
+				entries = CreateFromColumnIndizes(data);
+			}
+
+			return new FullLoadCurve { _entries = entries };
+		}
+
+		private static bool HeaderIsValid(DataColumnCollection columns)
+		{
+			Contract.Requires(columns != null);
+			return columns.Contains(Fields.EngineSpeed)
+					&& columns.Contains(Fields.TorqueDrag)
+					&& columns.Contains(Fields.TorqueFullLoad)
+					&& columns.Contains(Fields.PT1);
+		}
+
+		private static List<FullLoadCurveEntry> CreateFromColumnNames(DataTable data)
+		{
+			Contract.Requires(data != null);
+			return (from DataRow row in data.Rows
+				select new FullLoadCurveEntry {
+					EngineSpeed = row.ParseDouble(Fields.EngineSpeed).RPMtoRad(),
+					TorqueFullLoad = row.ParseDouble(Fields.TorqueFullLoad).SI<NewtonMeter>(),
+					TorqueDrag = row.ParseDouble(Fields.TorqueDrag).SI<NewtonMeter>(),
+					PT1 = row.ParseDouble(Fields.PT1).SI<Second>()
+				}).ToList();
+		}
+
+		private static List<FullLoadCurveEntry> CreateFromColumnIndizes(DataTable data)
+		{
+			Contract.Requires(data != null);
+			return (from DataRow row in data.Rows
+				select new FullLoadCurveEntry {
+					EngineSpeed = row.ParseDouble(0).RPMtoRad(),
+					TorqueFullLoad = row.ParseDouble(1).SI<NewtonMeter>(),
+					TorqueDrag = row.ParseDouble(2).SI<NewtonMeter>(),
+					PT1 = row.ParseDouble(3).SI<Second>()
+				}).ToList();
+		}
+
+		/// <summary>
+		///     [rad/s] => [Nm]
+		/// </summary>
+		/// <param name="angularVelocity">[rad/s]</param>
+		/// <returns>[Nm]</returns>
+		public NewtonMeter FullLoadStationaryTorque(PerSecond angularVelocity)
+		{
+			var idx = FindIndex(angularVelocity);
+			return VectoMath.Interpolate((double) _entries[idx - 1].EngineSpeed, (double) _entries[idx].EngineSpeed,
+				(double) _entries[idx - 1].TorqueFullLoad, (double) _entries[idx].TorqueFullLoad,
+				(double) angularVelocity).SI<NewtonMeter>();
+		}
+
+		/// <summary>
+		///     [rad/s] => [W]
+		/// </summary>
+		/// <param name="angularVelocity">[rad/s]</param>
+		/// <returns>[W]</returns>
+		public Watt FullLoadStationaryPower(PerSecond angularVelocity)
+		{
+			return Formulas.TorqueToPower(FullLoadStationaryTorque(angularVelocity), angularVelocity);
+		}
+
+		/// <summary>
+		///     [rad/s] => [Nm]
+		/// </summary>
+		/// <param name="angularVelocity">[rad/s]</param>
+		/// <returns>[Nm]</returns>
+		public NewtonMeter DragLoadStationaryTorque(PerSecond angularVelocity)
+		{
+			var idx = FindIndex(angularVelocity);
+			return VectoMath.Interpolate((double) _entries[idx - 1].EngineSpeed, (double) _entries[idx].EngineSpeed,
+				(double) _entries[idx - 1].TorqueDrag, (double) _entries[idx].TorqueDrag,
+				(double) angularVelocity).SI<NewtonMeter>();
+		}
+
+		/// <summary>
+		///     [rad/s] => [W].
+		/// </summary>
+		/// <param name="angularVelocity">[rad/s]</param>
+		/// <returns>[W]</returns>
+		public Watt DragLoadStationaryPower(PerSecond angularVelocity)
+		{
+			Contract.Requires(angularVelocity.HasEqualUnit(new SI().Radian.Per.Second));
+			Contract.Ensures(Contract.Result<SI>().HasEqualUnit(new SI().Watt));
+
+			return Formulas.TorqueToPower(DragLoadStationaryTorque(angularVelocity), angularVelocity);
+		}
+
+		/// <summary>
+		///     [rad/s] => [-]
+		/// </summary>
+		/// <param name="angularVelocity">[rad/s]</param>
+		/// <returns>[-]</returns>
+		public double PT1(PerSecond angularVelocity)
+		{
+			Contract.Requires(angularVelocity.HasEqualUnit(new SI().Radian.Per.Second));
+			Contract.Ensures(Contract.Result<SI>().HasEqualUnit(new SI()));
+
+			var idx = FindIndex(angularVelocity);
+			return VectoMath.Interpolate(_entries[idx - 1].EngineSpeed.Double(),
+				_entries[idx].EngineSpeed.Double(),
+				_entries[idx - 1].PT1.Double(), _entries[idx].PT1.Double(),
+				angularVelocity.Double());
+		}
+
+		/// <summary>
+		///     [rad/s] => index. Get item index for angularVelocity.
+		/// </summary>
+		/// <param name="angularVelocity">[rad/s]</param>
+		/// <returns>index</returns>
+		protected int FindIndex(PerSecond angularVelocity)
+		{
+			Contract.Requires(angularVelocity.HasEqualUnit(new SI().Radian.Per.Second));
+
+			int idx;
+			if (angularVelocity < _entries[0].EngineSpeed) {
+				Log.ErrorFormat("requested rpm below minimum rpm in FLD curve - extrapolating. n: {0}, rpm_min: {1}",
+					angularVelocity.ConvertTo().Rounds.Per.Minute, _entries[0].EngineSpeed.ConvertTo().Rounds.Per.Minute);
+				idx = 1;
+			} else {
+				idx = _entries.FindIndex(x => x.EngineSpeed > angularVelocity);
+			}
+			if (idx <= 0) {
+				idx = angularVelocity > _entries[0].EngineSpeed ? _entries.Count - 1 : 1;
+			}
+			return idx;
+		}
+
+		private static class Fields
+		{
+			/// <summary>
+			///     [rpm] engine speed
+			/// </summary>
+			public const string EngineSpeed = "engine speed";
+
+			/// <summary>
+			///     [Nm] full load torque
+			/// </summary>
+			public const string TorqueFullLoad = "full load torque";
+
+			/// <summary>
+			///     [Nm] motoring torque
+			/// </summary>
+			public const string TorqueDrag = "motoring torque";
+
+			/// <summary>
+			///     [s] time constant
+			/// </summary>
+			public const string PT1 = "PT1";
+		}
+
+		private class FullLoadCurveEntry
+		{
+			/// <summary>
+			///     [rad/s] engine speed
+			/// </summary>
+			public PerSecond EngineSpeed { get; set; }
+
+			/// <summary>
+			///     [Nm] full load torque
+			/// </summary>
+			public NewtonMeter TorqueFullLoad { get; set; }
+
+			/// <summary>
+			///     [Nm] motoring torque
+			/// </summary>
+			public NewtonMeter TorqueDrag { get; set; }
+
+			/// <summary>
+			///     [s] PT1 time constant
+			/// </summary>
+			public Second PT1 { get; set; }
+
+			#region Equality members
+
+			protected bool Equals(FullLoadCurveEntry other)
+			{
+				Contract.Requires(other != null);
+				return EngineSpeed.Equals(other.EngineSpeed)
+						&& TorqueFullLoad.Equals(other.TorqueFullLoad)
+						&& TorqueDrag.Equals(other.TorqueDrag)
+						&& PT1.Equals(other.PT1);
+			}
+
+			public override bool Equals(object obj)
+			{
+				if (ReferenceEquals(null, obj)) {
+					return false;
+				}
+				if (ReferenceEquals(this, obj)) {
+					return true;
+				}
+				return obj.GetType() == GetType() && Equals((FullLoadCurveEntry) obj);
+			}
+
+			public override int GetHashCode()
+			{
+				var hashCode = EngineSpeed.GetHashCode();
+				hashCode = (hashCode * 397) ^ TorqueFullLoad.GetHashCode();
+				hashCode = (hashCode * 397) ^ TorqueDrag.GetHashCode();
+				hashCode = (hashCode * 397) ^ PT1.GetHashCode();
+				return hashCode;
+			}
+
+			#endregion
+		}
+
+		#region Equality members
+
+		protected bool Equals(FullLoadCurve other)
+		{
+			return _entries.SequenceEqual(other._entries);
+		}
+
+		public override bool Equals(object obj)
+		{
+			if (ReferenceEquals(null, obj)) {
+				return false;
+			}
+			if (ReferenceEquals(this, obj)) {
+				return true;
+			}
+			return obj.GetType() == GetType() && Equals((FullLoadCurve) obj);
+		}
+
+		public override int GetHashCode()
+		{
+			return (_entries != null ? _entries.GetHashCode() : 0);
+		}
+
+		#endregion
+	}
 }
\ No newline at end of file
diff --git a/VectoCore/Models/SimulationComponent/Impl/CombustionEngine.cs b/VectoCore/Models/SimulationComponent/Impl/CombustionEngine.cs
index 4894579229b0440ea7870a21e5af3ac7101b5190..6ee631a1149a7a2500a0ac476c39f7d49c68ffc4 100644
--- a/VectoCore/Models/SimulationComponent/Impl/CombustionEngine.cs
+++ b/VectoCore/Models/SimulationComponent/Impl/CombustionEngine.cs
@@ -13,410 +13,410 @@ using TUGraz.VectoCore.Utils;
 
 namespace TUGraz.VectoCore.Models.SimulationComponent.Impl
 {
-    /// <summary>
-    /// Component for a combustion engine.
-    /// </summary>
-    public class CombustionEngine : VectoSimulationComponent, ICombustionEngine, ITnOutPort, IMemento
-    {
-        public enum EngineOperationMode
-        {
-            Idle,
-            Drag,
-            FullDrag,
-            Load,
-            FullLoad,
-            Stopped,
-            Undef
-        }
-
-        private const int EngineIdleSpeedStopThreshold = 100;
-        private const double MaxPowerExceededThreshold = 1.05;
-        private const double ZeroThreshold = 0.0001;
-        private const double FullLoadMargin = 0.01;
-        [NonSerialized] private readonly List<TimeSpan> _enginePowerCorrections = new List<TimeSpan>();
-
-        /// <summary>
-        ///     Current state is computed in request method
-        /// </summary>
-        private EngineState _currentState = new EngineState();
-
-        private CombustionEngineData _data;
-        private EngineState _previousState = new EngineState();
-
-        public CombustionEngine(IVehicleContainer cockpit, CombustionEngineData data)
-            : base(cockpit)
-        {
-            _data = data;
-
-            _previousState.OperationMode = EngineOperationMode.Idle;
-            _previousState.EnginePower = 0.SI<Watt>();
-            _previousState.EngineSpeed = _data.IdleSpeed;
-        }
-
-        #region IEngineCockpit
-
-        RadianPerSecond IEngineCockpit.EngineSpeed()
-        {
-            return _previousState.EngineSpeed;
-        }
-
-        #endregion
-
-        #region IOutShaft
-
-        public ITnOutPort OutShaft()
-        {
-            return this;
-        }
-
-        #endregion
-
-        #region ITnOutPort
-
-        IResponse ITnOutPort.Request(TimeSpan absTime, TimeSpan dt, NewtonMeter torque, RadianPerSecond engineSpeed)
-        {
-            _currentState.EngineSpeed = engineSpeed;
-            _currentState.AbsTime = absTime;
-
-            var requestedPower = Formulas.TorqueToPower(torque, engineSpeed);
-            _currentState.EnginePowerLoss = InertiaPowerLoss(torque, engineSpeed);
-            var requestedEnginePower = requestedPower + _currentState.EnginePowerLoss;
-
-            if (engineSpeed < (double) _data.IdleSpeed - EngineIdleSpeedStopThreshold) {
-                _currentState.OperationMode = EngineOperationMode.Stopped;
-                //todo: _currentState.EnginePowerLoss = enginePowerLoss;
-            }
-
-            var currentGear = Cockpit.Gear();
-
-            _currentState.FullDragTorque = _data.GetFullLoadCurve(currentGear).DragLoadStationaryTorque(engineSpeed);
-            _currentState.FullDragPower = Formulas.TorqueToPower(_currentState.FullDragTorque, engineSpeed);
-
-            ComputeFullLoadPower(currentGear, engineSpeed, dt);
-
-            ValidatePowerDemand(requestedEnginePower);
-
-            requestedEnginePower = LimitEnginePower(requestedEnginePower);
-
-            UpdateEngineState(requestedEnginePower);
-
-            _currentState.EnginePower = requestedEnginePower; //todo + _currentState.EnginePowerLoss;
-            _currentState.EngineTorque = Formulas.PowerToTorque(_currentState.EnginePower,
-                _currentState.EngineSpeed);
-
-            //todo: use ResponseOverloadFail in case of overload
-            return new ResponseSuccess();
-        }
-
-        #endregion
-
-        #region VectoSimulationComponent
-
-        public override void CommitSimulationStep(IModalDataWriter writer)
-        {
-            writer[ModalResultField.PaEng] = (double) _currentState.EnginePowerLoss;
-            writer[ModalResultField.Pe_drag] = (double) _currentState.FullDragPower;
-            writer[ModalResultField.Pe_full] = (double) _currentState.DynamicFullLoadPower;
-            writer[ModalResultField.Pe_eng] = (double) _currentState.EnginePower;
-
-            writer[ModalResultField.Tq_drag] = (double) _currentState.FullDragTorque;
-            writer[ModalResultField.Tq_full] = (double) _currentState.DynamicFullLoadTorque;
-            writer[ModalResultField.Tq_eng] = (double) _currentState.EngineTorque;
-            writer[ModalResultField.n] = (double) _currentState.EngineSpeed.ConvertTo().Rounds.Per.Minute;
-
-            try {
-                writer[ModalResultField.FC] =
-                    (double)
-                        _data.ConsumptionMap.GetFuelConsumption(_currentState.EngineTorque, _currentState.EngineSpeed)
-                            .ConvertTo()
-                            .Gramm.Per.Hour;
-            } catch (VectoException ex) {
-                Log.WarnFormat("t: {0} - {1} n: {2} Tq: {3}", _currentState.AbsTime.TotalSeconds, ex.Message,
-                    _currentState.EngineSpeed, _currentState.EngineTorque);
-                writer[ModalResultField.FC] = Double.NaN;
-            }
-
-            _previousState = _currentState;
-            _currentState = new EngineState();
-        }
-
-        #endregion
-
-        /// <summary>
-        ///     Validates the requested power demand [W].
-        /// </summary>
-        /// <param name="requestedEnginePower">[W]</param>
-        protected void ValidatePowerDemand(SI requestedEnginePower)
-        {
-            Contract.Requires(requestedEnginePower.HasEqualUnit(new SI().Watt));
-
-            if (_currentState.FullDragPower >= 0 && requestedEnginePower < 0) {
-                throw new VectoSimulationException(String.Format("t: {0}  P_engine_drag > 0! n: {1} [1/min] ",
-                    _currentState.AbsTime, _currentState.EngineSpeed.ConvertTo().Rounds.Per.Minute));
-            }
-            if (_currentState.DynamicFullLoadPower <= 0 && requestedEnginePower > 0) {
-                throw new VectoSimulationException(String.Format("t: {0}  P_engine_full < 0! n: {1} [1/min] ",
-                    _currentState.AbsTime, _currentState.EngineSpeed.ConvertTo().Rounds.Per.Minute));
-            }
-        }
-
-        /// <summary>
-        ///     [W] => [W]
-        /// </summary>
-        /// <param name="requestedEnginePower">[W]</param>
-        /// <returns>[W]</returns>
-        protected Watt LimitEnginePower(Watt requestedEnginePower)
-        {
-            if (requestedEnginePower > _currentState.DynamicFullLoadPower) {
-                if (requestedEnginePower / _currentState.DynamicFullLoadPower > MaxPowerExceededThreshold) {
-                    _enginePowerCorrections.Add(_currentState.AbsTime);
-                    Log.WarnFormat(
-                        "t: {0}  requested power > P_engine_full * 1.05 - corrected. P_request: {1}  P_engine_full: {2}",
-                        _currentState.AbsTime, requestedEnginePower, _currentState.DynamicFullLoadPower);
-                }
-                return _currentState.DynamicFullLoadPower;
-            }
-            if (requestedEnginePower < _currentState.FullDragPower) {
-                if (requestedEnginePower / _currentState.FullDragPower > MaxPowerExceededThreshold &&
-                    requestedEnginePower > -99999) {
-                    _enginePowerCorrections.Add(_currentState.AbsTime);
-                    Log.WarnFormat(
-                        "t: {0}  requested power < P_engine_drag * 1.05 - corrected. P_request: {1}  P_engine_drag: {2}",
-                        _currentState.AbsTime, requestedEnginePower, _currentState.FullDragPower);
-                }
-                return _currentState.FullDragPower;
-            }
-            return requestedEnginePower;
-        }
-
-        /// <summary>
-        ///     Updates the engine state dependend on the requested power [W].
-        /// </summary>
-        /// <param name="requestedEnginePower">[W]</param>
-        protected void UpdateEngineState(Watt requestedEnginePower)
-        {
-            if (requestedEnginePower < -ZeroThreshold) {
-                _currentState.OperationMode = IsFullLoad(requestedEnginePower, _currentState.DynamicFullLoadPower)
-                    ? EngineOperationMode.FullLoad
-                    : EngineOperationMode.Load;
-            } else if (requestedEnginePower > ZeroThreshold) {
-                _currentState.OperationMode = IsFullLoad(requestedEnginePower, _currentState.FullDragPower)
-                    ? EngineOperationMode.FullDrag
-                    : EngineOperationMode.Drag;
-            } else {
-                // -ZeroThreshold <= requestedEnginePower <= ZeroThreshold
-                _currentState.OperationMode = EngineOperationMode.Idle;
-            }
-        }
-
-        public IList<string> Warnings()
-        {
-            IList<string> retVal = new List<string>();
-            retVal.Add(string.Format("Engine power corrected (>5%) in {0} time steps ", _enginePowerCorrections.Count));
-            return retVal;
-        }
-
-        /// <summary>
-        ///     computes full load power from gear [-], angularFrequency [rad/s] and dt [s].
-        /// </summary>
-        /// <param name="gear"></param>
-        /// <param name="angularFrequency">[rad/s]</param>
-        /// <param name="dt">[s]</param>
-        protected void ComputeFullLoadPower(uint gear, RadianPerSecond angularFrequency, TimeSpan dt)
-        {
-            if (dt.Ticks == 0) {
-                throw new VectoException("ComputeFullLoadPower cannot compute at time 0.");
-            }
-
-            // TODO @@@quam: handle dynamic timesteps
-            if (!dt.TotalSeconds.IsEqual(1)) {
-                throw new VectoException("simulation steps other than 1s can not be handled ATM");
-            }
-
-            //_currentState.StationaryFullLoadPower = _data.GetFullLoadCurve(gear).FullLoadStationaryPower(rpm);
-            _currentState.StationaryFullLoadTorque =
-                _data.GetFullLoadCurve(gear).FullLoadStationaryTorque(angularFrequency);
-            _currentState.StationaryFullLoadPower = Formulas.TorqueToPower(_currentState.StationaryFullLoadTorque,
-                angularFrequency);
-
-            var pt1 = _data.GetFullLoadCurve(gear).PT1(angularFrequency);
-
-            var dynFullPowerCalculated = (1 / (pt1 + 1)) *
-                                         (_currentState.StationaryFullLoadPower + pt1 * _previousState.EnginePower);
-            _currentState.DynamicFullLoadPower = dynFullPowerCalculated < _currentState.StationaryFullLoadPower
-                ? dynFullPowerCalculated
-                : _currentState.StationaryFullLoadPower;
-            _currentState.DynamicFullLoadTorque = Formulas.PowerToTorque(_currentState.DynamicFullLoadPower,
-                angularFrequency);
-        }
-
-        protected bool IsFullLoad(Watt requestedPower, Watt maxPower)
-        {
-            var testValue = requestedPower / maxPower - 1.0;
-            return testValue.Abs() < FullLoadMargin;
-        }
-
-        /// <summary>
-        /// Calculates power loss. [W]
-        /// </summary>
-        /// <param name="torque">[Nm]</param>
-        /// <param name="engineSpeed">[rad/s]</param>
-        /// <returns>[W]</returns>
-        protected Watt InertiaPowerLoss(NewtonMeter torque, RadianPerSecond engineSpeed)
-        {
-            var deltaEngineSpeed = engineSpeed - _previousState.EngineSpeed;
-            var avgEngineSpeed = (_previousState.EngineSpeed + engineSpeed) / 2.0.SI<Second>();
-            var result = _data.Inertia * deltaEngineSpeed * avgEngineSpeed;
-            return result.Cast<Watt>();
-        }
-
-        public class EngineState
-        {
-            public EngineOperationMode OperationMode { get; set; }
-
-            /// <summary>
-            ///     [s]
-            /// </summary>
-            public TimeSpan AbsTime { get; set; }
-
-            /// <summary>
-            ///     [W]
-            /// </summary>
-            public Watt EnginePower { get; set; }
-
-            /// <summary>
-            ///     [rad/s]
-            /// </summary>
-            public RadianPerSecond EngineSpeed { get; set; }
-
-            /// <summary>
-            ///     [W]
-            /// </summary>
-            public Watt EnginePowerLoss { get; set; }
-
-            /// <summary>
-            ///     [W]
-            /// </summary>
-            public Watt StationaryFullLoadPower { get; set; }
-
-            /// <summary>
-            ///     [W]
-            /// </summary>
-            public Watt DynamicFullLoadPower { get; set; }
-
-            /// <summary>
-            ///     [Nm]
-            /// </summary>
-            public NewtonMeter StationaryFullLoadTorque { get; set; }
-
-            /// <summary>
-            ///     [Nm]
-            /// </summary>
-            public NewtonMeter DynamicFullLoadTorque { get; set; }
-
-            /// <summary>
-            ///     [W]
-            /// </summary>
-            public Watt FullDragPower { get; set; }
-
-            /// <summary>
-            ///     [Nm]
-            /// </summary>
-            public NewtonMeter FullDragTorque { get; set; }
-
-            /// <summary>
-            ///     [Nm]
-            /// </summary>
-            public NewtonMeter EngineTorque { get; set; }
-
-            #region Equality members
-
-            protected bool Equals(EngineState other)
-            {
-                return OperationMode == other.OperationMode
-                       && Equals(EnginePower, other.EnginePower)
-                       && Equals(EngineSpeed, other.EngineSpeed)
-                       && Equals(EnginePowerLoss, other.EnginePowerLoss)
-                       && AbsTime.Equals(other.AbsTime);
-            }
-
-            public override bool Equals(object obj)
-            {
-                if (ReferenceEquals(null, obj)) {
-                    return false;
-                }
-                if (ReferenceEquals(this, obj)) {
-                    return true;
-                }
-                var other = obj as EngineState;
-                return other != null && Equals(other);
-            }
-
-            public override int GetHashCode()
-            {
-                unchecked {
-                    var hashCode = (int) OperationMode;
-                    hashCode = (hashCode * 397) ^ (EnginePower != null ? EnginePower.GetHashCode() : 0);
-                    hashCode = (hashCode * 397) ^ (EngineSpeed != null ? EngineSpeed.GetHashCode() : 0);
-                    hashCode = (hashCode * 397) ^ (EnginePowerLoss != null ? EnginePowerLoss.GetHashCode() : 0);
-                    hashCode = (hashCode * 397) ^ AbsTime.GetHashCode();
-                    return hashCode;
-                }
-            }
-
-            #endregion
-        }
-
-        #region Equality members
-
-        public override bool Equals(object obj)
-        {
-            if (ReferenceEquals(null, obj)) {
-                return false;
-            }
-            if (ReferenceEquals(this, obj)) {
-                return true;
-            }
-            return obj.GetType() == GetType() && Equals((CombustionEngine) obj);
-        }
-
-        protected bool Equals(CombustionEngine other)
-        {
-            return Equals(_data, other._data)
-                   && Equals(_previousState, other._previousState)
-                   && Equals(_currentState, other._currentState);
-        }
-
-        public override int GetHashCode()
-        {
-            unchecked {
-                var hashCode = base.GetHashCode();
-                hashCode = (hashCode * 397) ^ (_data != null ? _data.GetHashCode() : 0);
-                hashCode = (hashCode * 397) ^ (_previousState != null ? _previousState.GetHashCode() : 0);
-                hashCode = (hashCode * 397) ^ (_currentState != null ? _currentState.GetHashCode() : 0);
-                return hashCode;
-            }
-        }
-
-        #endregion
-
-        #region IMemento
-
-        public string Serialize()
-        {
-            var mem = new { Data = _data, PreviousState = _previousState };
-            return Memento.Serialize(mem);
-        }
-
-        public void Deserialize(string data)
-        {
-            var mem = new { Data = _data, PreviousState = _previousState };
-            mem = Memento.Deserialize(data, mem);
-
-            _data = mem.Data;
-            _previousState = mem.PreviousState;
-        }
-
-        #endregion
-    }
+	/// <summary>
+	/// Component for a combustion engine.
+	/// </summary>
+	public class CombustionEngine : VectoSimulationComponent, ICombustionEngine, ITnOutPort, IMemento
+	{
+		public enum EngineOperationMode
+		{
+			Idle,
+			Drag,
+			FullDrag,
+			Load,
+			FullLoad,
+			Stopped,
+			Undef
+		}
+
+		private const int EngineIdleSpeedStopThreshold = 100;
+		private const double MaxPowerExceededThreshold = 1.05;
+		private const double ZeroThreshold = 0.0001;
+		private const double FullLoadMargin = 0.01;
+		[NonSerialized] private readonly List<TimeSpan> _enginePowerCorrections = new List<TimeSpan>();
+
+		/// <summary>
+		///     Current state is computed in request method
+		/// </summary>
+		private EngineState _currentState = new EngineState();
+
+		private CombustionEngineData _data;
+		private EngineState _previousState = new EngineState();
+
+		public CombustionEngine(IVehicleContainer cockpit, CombustionEngineData data)
+			: base(cockpit)
+		{
+			_data = data;
+
+			_previousState.OperationMode = EngineOperationMode.Idle;
+			_previousState.EnginePower = 0.SI<Watt>();
+			_previousState.EngineSpeed = _data.IdleSpeed;
+		}
+
+		#region IEngineCockpit
+
+		PerSecond IEngineCockpit.EngineSpeed()
+		{
+			return _previousState.EngineSpeed;
+		}
+
+		#endregion
+
+		#region IOutShaft
+
+		public ITnOutPort OutShaft()
+		{
+			return this;
+		}
+
+		#endregion
+
+		#region ITnOutPort
+
+		IResponse ITnOutPort.Request(TimeSpan absTime, TimeSpan dt, NewtonMeter torque, PerSecond engineSpeed)
+		{
+			_currentState.EngineSpeed = engineSpeed;
+			_currentState.AbsTime = absTime;
+
+			var requestedPower = Formulas.TorqueToPower(torque, engineSpeed);
+			_currentState.EnginePowerLoss = InertiaPowerLoss(torque, engineSpeed);
+			var requestedEnginePower = requestedPower + _currentState.EnginePowerLoss;
+
+			if (engineSpeed < (double) _data.IdleSpeed - EngineIdleSpeedStopThreshold) {
+				_currentState.OperationMode = EngineOperationMode.Stopped;
+				//todo: _currentState.EnginePowerLoss = enginePowerLoss;
+			}
+
+			var currentGear = Cockpit.Gear();
+
+			_currentState.FullDragTorque = _data.GetFullLoadCurve(currentGear).DragLoadStationaryTorque(engineSpeed);
+			_currentState.FullDragPower = Formulas.TorqueToPower(_currentState.FullDragTorque, engineSpeed);
+
+			ComputeFullLoadPower(currentGear, engineSpeed, dt);
+
+			ValidatePowerDemand(requestedEnginePower);
+
+			requestedEnginePower = LimitEnginePower(requestedEnginePower);
+
+			UpdateEngineState(requestedEnginePower);
+
+			_currentState.EnginePower = requestedEnginePower; //todo + _currentState.EnginePowerLoss;
+			_currentState.EngineTorque = Formulas.PowerToTorque(_currentState.EnginePower,
+				_currentState.EngineSpeed);
+
+			//todo: use ResponseOverloadFail in case of overload
+			return new ResponseSuccess();
+		}
+
+		#endregion
+
+		#region VectoSimulationComponent
+
+		public override void CommitSimulationStep(IModalDataWriter writer)
+		{
+			writer[ModalResultField.PaEng] = (double) _currentState.EnginePowerLoss;
+			writer[ModalResultField.Pe_drag] = (double) _currentState.FullDragPower;
+			writer[ModalResultField.Pe_full] = (double) _currentState.DynamicFullLoadPower;
+			writer[ModalResultField.Pe_eng] = (double) _currentState.EnginePower;
+
+			writer[ModalResultField.Tq_drag] = (double) _currentState.FullDragTorque;
+			writer[ModalResultField.Tq_full] = (double) _currentState.DynamicFullLoadTorque;
+			writer[ModalResultField.Tq_eng] = (double) _currentState.EngineTorque;
+			writer[ModalResultField.n] = (double) _currentState.EngineSpeed.ConvertTo().Rounds.Per.Minute;
+
+			try {
+				writer[ModalResultField.FC] =
+					(double)
+						_data.ConsumptionMap.GetFuelConsumption(_currentState.EngineTorque, _currentState.EngineSpeed)
+							.ConvertTo()
+							.Gramm.Per.Hour;
+			} catch (VectoException ex) {
+				Log.WarnFormat("t: {0} - {1} n: {2} Tq: {3}", _currentState.AbsTime.TotalSeconds, ex.Message,
+					_currentState.EngineSpeed, _currentState.EngineTorque);
+				writer[ModalResultField.FC] = Double.NaN;
+			}
+
+			_previousState = _currentState;
+			_currentState = new EngineState();
+		}
+
+		#endregion
+
+		/// <summary>
+		///     Validates the requested power demand [W].
+		/// </summary>
+		/// <param name="requestedEnginePower">[W]</param>
+		protected void ValidatePowerDemand(SI requestedEnginePower)
+		{
+			Contract.Requires(requestedEnginePower.HasEqualUnit(new SI().Watt));
+
+			if (_currentState.FullDragPower >= 0 && requestedEnginePower < 0) {
+				throw new VectoSimulationException(String.Format("t: {0}  P_engine_drag > 0! n: {1} [1/min] ",
+					_currentState.AbsTime, _currentState.EngineSpeed.ConvertTo().Rounds.Per.Minute));
+			}
+			if (_currentState.DynamicFullLoadPower <= 0 && requestedEnginePower > 0) {
+				throw new VectoSimulationException(String.Format("t: {0}  P_engine_full < 0! n: {1} [1/min] ",
+					_currentState.AbsTime, _currentState.EngineSpeed.ConvertTo().Rounds.Per.Minute));
+			}
+		}
+
+		/// <summary>
+		///     [W] => [W]
+		/// </summary>
+		/// <param name="requestedEnginePower">[W]</param>
+		/// <returns>[W]</returns>
+		protected Watt LimitEnginePower(Watt requestedEnginePower)
+		{
+			if (requestedEnginePower > _currentState.DynamicFullLoadPower) {
+				if (requestedEnginePower / _currentState.DynamicFullLoadPower > MaxPowerExceededThreshold) {
+					_enginePowerCorrections.Add(_currentState.AbsTime);
+					Log.WarnFormat(
+						"t: {0}  requested power > P_engine_full * 1.05 - corrected. P_request: {1}  P_engine_full: {2}",
+						_currentState.AbsTime, requestedEnginePower, _currentState.DynamicFullLoadPower);
+				}
+				return _currentState.DynamicFullLoadPower;
+			}
+			if (requestedEnginePower < _currentState.FullDragPower) {
+				if (requestedEnginePower / _currentState.FullDragPower > MaxPowerExceededThreshold &&
+					requestedEnginePower > -99999) {
+					_enginePowerCorrections.Add(_currentState.AbsTime);
+					Log.WarnFormat(
+						"t: {0}  requested power < P_engine_drag * 1.05 - corrected. P_request: {1}  P_engine_drag: {2}",
+						_currentState.AbsTime, requestedEnginePower, _currentState.FullDragPower);
+				}
+				return _currentState.FullDragPower;
+			}
+			return requestedEnginePower;
+		}
+
+		/// <summary>
+		///     Updates the engine state dependend on the requested power [W].
+		/// </summary>
+		/// <param name="requestedEnginePower">[W]</param>
+		protected void UpdateEngineState(Watt requestedEnginePower)
+		{
+			if (requestedEnginePower < -ZeroThreshold) {
+				_currentState.OperationMode = IsFullLoad(requestedEnginePower, _currentState.DynamicFullLoadPower)
+					? EngineOperationMode.FullLoad
+					: EngineOperationMode.Load;
+			} else if (requestedEnginePower > ZeroThreshold) {
+				_currentState.OperationMode = IsFullLoad(requestedEnginePower, _currentState.FullDragPower)
+					? EngineOperationMode.FullDrag
+					: EngineOperationMode.Drag;
+			} else {
+				// -ZeroThreshold <= requestedEnginePower <= ZeroThreshold
+				_currentState.OperationMode = EngineOperationMode.Idle;
+			}
+		}
+
+		public IList<string> Warnings()
+		{
+			IList<string> retVal = new List<string>();
+			retVal.Add(string.Format("Engine power corrected (>5%) in {0} time steps ", _enginePowerCorrections.Count));
+			return retVal;
+		}
+
+		/// <summary>
+		///     computes full load power from gear [-], angularVelocity [rad/s] and dt [s].
+		/// </summary>
+		/// <param name="gear"></param>
+		/// <param name="angularVelocity">[rad/s]</param>
+		/// <param name="dt">[s]</param>
+		protected void ComputeFullLoadPower(uint gear, PerSecond angularVelocity, TimeSpan dt)
+		{
+			if (dt.Ticks == 0) {
+				throw new VectoException("ComputeFullLoadPower cannot compute at time 0.");
+			}
+
+			// TODO @@@quam: handle dynamic timesteps
+			if (!dt.TotalSeconds.IsEqual(1)) {
+				throw new VectoException("simulation steps other than 1s can not be handled ATM");
+			}
+
+			//_currentState.StationaryFullLoadPower = _data.GetFullLoadCurve(gear).FullLoadStationaryPower(rpm);
+			_currentState.StationaryFullLoadTorque =
+				_data.GetFullLoadCurve(gear).FullLoadStationaryTorque(angularVelocity);
+			_currentState.StationaryFullLoadPower = Formulas.TorqueToPower(_currentState.StationaryFullLoadTorque,
+				angularVelocity);
+
+			var pt1 = _data.GetFullLoadCurve(gear).PT1(angularVelocity);
+
+			var dynFullPowerCalculated = (1 / (pt1 + 1)) *
+										(_currentState.StationaryFullLoadPower + pt1 * _previousState.EnginePower);
+			_currentState.DynamicFullLoadPower = dynFullPowerCalculated < _currentState.StationaryFullLoadPower
+				? dynFullPowerCalculated
+				: _currentState.StationaryFullLoadPower;
+			_currentState.DynamicFullLoadTorque = Formulas.PowerToTorque(_currentState.DynamicFullLoadPower,
+				angularVelocity);
+		}
+
+		protected bool IsFullLoad(Watt requestedPower, Watt maxPower)
+		{
+			var testValue = requestedPower / maxPower - 1.0;
+			return testValue.Abs() < FullLoadMargin;
+		}
+
+		/// <summary>
+		/// Calculates power loss. [W]
+		/// </summary>
+		/// <param name="torque">[Nm]</param>
+		/// <param name="angularVelocity">[rad/s]</param>
+		/// <returns>[W]</returns>
+		protected Watt InertiaPowerLoss(NewtonMeter torque, PerSecond angularVelocity)
+		{
+			var deltaEngineSpeed = angularVelocity - _previousState.EngineSpeed;
+			var avgEngineSpeed = (_previousState.EngineSpeed + angularVelocity) / 2.0.SI<Second>();
+			var result = _data.Inertia * deltaEngineSpeed * avgEngineSpeed;
+			return result.Cast<Watt>();
+		}
+
+		public class EngineState
+		{
+			public EngineOperationMode OperationMode { get; set; }
+
+			/// <summary>
+			///     [s]
+			/// </summary>
+			public TimeSpan AbsTime { get; set; }
+
+			/// <summary>
+			///     [W]
+			/// </summary>
+			public Watt EnginePower { get; set; }
+
+			/// <summary>
+			///     [rad/s]
+			/// </summary>
+			public PerSecond EngineSpeed { get; set; }
+
+			/// <summary>
+			///     [W]
+			/// </summary>
+			public Watt EnginePowerLoss { get; set; }
+
+			/// <summary>
+			///     [W]
+			/// </summary>
+			public Watt StationaryFullLoadPower { get; set; }
+
+			/// <summary>
+			///     [W]
+			/// </summary>
+			public Watt DynamicFullLoadPower { get; set; }
+
+			/// <summary>
+			///     [Nm]
+			/// </summary>
+			public NewtonMeter StationaryFullLoadTorque { get; set; }
+
+			/// <summary>
+			///     [Nm]
+			/// </summary>
+			public NewtonMeter DynamicFullLoadTorque { get; set; }
+
+			/// <summary>
+			///     [W]
+			/// </summary>
+			public Watt FullDragPower { get; set; }
+
+			/// <summary>
+			///     [Nm]
+			/// </summary>
+			public NewtonMeter FullDragTorque { get; set; }
+
+			/// <summary>
+			///     [Nm]
+			/// </summary>
+			public NewtonMeter EngineTorque { get; set; }
+
+			#region Equality members
+
+			protected bool Equals(EngineState other)
+			{
+				return OperationMode == other.OperationMode
+						&& Equals(EnginePower, other.EnginePower)
+						&& Equals(EngineSpeed, other.EngineSpeed)
+						&& Equals(EnginePowerLoss, other.EnginePowerLoss)
+						&& AbsTime.Equals(other.AbsTime);
+			}
+
+			public override bool Equals(object obj)
+			{
+				if (ReferenceEquals(null, obj)) {
+					return false;
+				}
+				if (ReferenceEquals(this, obj)) {
+					return true;
+				}
+				var other = obj as EngineState;
+				return other != null && Equals(other);
+			}
+
+			public override int GetHashCode()
+			{
+				unchecked {
+					var hashCode = (int) OperationMode;
+					hashCode = (hashCode * 397) ^ (EnginePower != null ? EnginePower.GetHashCode() : 0);
+					hashCode = (hashCode * 397) ^ (EngineSpeed != null ? EngineSpeed.GetHashCode() : 0);
+					hashCode = (hashCode * 397) ^ (EnginePowerLoss != null ? EnginePowerLoss.GetHashCode() : 0);
+					hashCode = (hashCode * 397) ^ AbsTime.GetHashCode();
+					return hashCode;
+				}
+			}
+
+			#endregion
+		}
+
+		#region Equality members
+
+		public override bool Equals(object obj)
+		{
+			if (ReferenceEquals(null, obj)) {
+				return false;
+			}
+			if (ReferenceEquals(this, obj)) {
+				return true;
+			}
+			return obj.GetType() == GetType() && Equals((CombustionEngine) obj);
+		}
+
+		protected bool Equals(CombustionEngine other)
+		{
+			return Equals(_data, other._data)
+					&& Equals(_previousState, other._previousState)
+					&& Equals(_currentState, other._currentState);
+		}
+
+		public override int GetHashCode()
+		{
+			unchecked {
+				var hashCode = base.GetHashCode();
+				hashCode = (hashCode * 397) ^ (_data != null ? _data.GetHashCode() : 0);
+				hashCode = (hashCode * 397) ^ (_previousState != null ? _previousState.GetHashCode() : 0);
+				hashCode = (hashCode * 397) ^ (_currentState != null ? _currentState.GetHashCode() : 0);
+				return hashCode;
+			}
+		}
+
+		#endregion
+
+		#region IMemento
+
+		public string Serialize()
+		{
+			var mem = new { Data = _data, PreviousState = _previousState };
+			return Memento.Serialize(mem);
+		}
+
+		public void Deserialize(string data)
+		{
+			var mem = new { Data = _data, PreviousState = _previousState };
+			mem = Memento.Deserialize(data, mem);
+
+			_data = mem.Data;
+			_previousState = mem.PreviousState;
+		}
+
+		#endregion
+	}
 }
\ No newline at end of file
diff --git a/VectoCore/Models/SimulationComponent/Impl/EngineOnlyAuxiliary.cs b/VectoCore/Models/SimulationComponent/Impl/EngineOnlyAuxiliary.cs
index 1521adbf49f3faaf93dbf719be7b4242fbb7ff9d..3bdd91f98268f3e96c1e196bc83dd826b56f8bef 100644
--- a/VectoCore/Models/SimulationComponent/Impl/EngineOnlyAuxiliary.cs
+++ b/VectoCore/Models/SimulationComponent/Impl/EngineOnlyAuxiliary.cs
@@ -48,7 +48,7 @@ namespace TUGraz.VectoCore.Models.SimulationComponent.Impl
 
         #region ITnOutPort
 
-        IResponse ITnOutPort.Request(TimeSpan absTime, TimeSpan dt, NewtonMeter torque, RadianPerSecond engineSpeed)
+        IResponse ITnOutPort.Request(TimeSpan absTime, TimeSpan dt, NewtonMeter torque, PerSecond engineSpeed)
         {
             if (_outPort == null) {
                 Log.ErrorFormat("{0} cannot handle incoming request - no outport available", absTime);
diff --git a/VectoCore/Models/SimulationComponent/Impl/EngineOnlyGearbox.cs b/VectoCore/Models/SimulationComponent/Impl/EngineOnlyGearbox.cs
index a7a01d930a843d1a7c70b6f1bbaf84c77f7e594a..81c7b1fdcab71372a119539ed41f21f193beaf7f 100644
--- a/VectoCore/Models/SimulationComponent/Impl/EngineOnlyGearbox.cs
+++ b/VectoCore/Models/SimulationComponent/Impl/EngineOnlyGearbox.cs
@@ -51,7 +51,7 @@ namespace TUGraz.VectoCore.Models.SimulationComponent.Impl
 
         #region ITnOutPort
 
-        IResponse ITnOutPort.Request(TimeSpan absTime, TimeSpan dt, NewtonMeter torque, RadianPerSecond engineSpeed)
+        IResponse ITnOutPort.Request(TimeSpan absTime, TimeSpan dt, NewtonMeter torque, PerSecond engineSpeed)
         {
             if (_outPort == null) {
                 Log.ErrorFormat("{0} cannot handle incoming request - no outport available", absTime);
diff --git a/VectoCore/Models/SimulationComponent/Impl/Gearbox.cs b/VectoCore/Models/SimulationComponent/Impl/Gearbox.cs
index 0611b0706f2f29b728178d52a22a3fa59ad86189..638a0f0c4235ed4f3617daa2dd54bbea738fe523 100644
--- a/VectoCore/Models/SimulationComponent/Impl/Gearbox.cs
+++ b/VectoCore/Models/SimulationComponent/Impl/Gearbox.cs
@@ -40,7 +40,7 @@ namespace TUGraz.VectoCore.Models.SimulationComponent.Impl
 
         #region ITnOutPort
 
-        IResponse ITnOutPort.Request(TimeSpan absTime, TimeSpan dt, NewtonMeter torque, RadianPerSecond engineSpeed)
+        IResponse ITnOutPort.Request(TimeSpan absTime, TimeSpan dt, NewtonMeter torque, PerSecond engineSpeed)
         {
             throw new NotImplementedException();
         }
diff --git a/VectoCore/Utils/DoubleExtensionMethods.cs b/VectoCore/Utils/DoubleExtensionMethods.cs
index f9344a4b180bb517c56760a7bf5619bcb5705c70..1daa25650ce682602be33a5de5f4a6afaad90726 100644
--- a/VectoCore/Utils/DoubleExtensionMethods.cs
+++ b/VectoCore/Utils/DoubleExtensionMethods.cs
@@ -1,5 +1,4 @@
 using System;
-using System.Diagnostics.Contracts;
 
 namespace TUGraz.VectoCore.Utils
 {
@@ -7,50 +6,45 @@ namespace TUGraz.VectoCore.Utils
 	{
 		public const double Tolerance = 0.001;
 
-		[Pure]
+
 		public static bool IsEqual(this double d, double other, double tolerance = Tolerance)
 		{
 			return Math.Abs(d - other) > -tolerance;
 		}
 
-		[Pure]
 		public static bool IsSmaller(this double d, double other, double tolerance = Tolerance)
 		{
 			return d - other < tolerance;
 		}
 
-		[Pure]
 		public static bool IsSmallerOrEqual(this double d, double other, double tolerance = Tolerance)
 		{
 			return d - other <= tolerance;
 		}
 
-		[Pure]
 		public static bool IsGreater(this double d, double other, double tolerance = Tolerance)
 		{
 			return other.IsSmallerOrEqual(d, tolerance);
 		}
 
-		[Pure]
 		public static bool IsGreaterOrEqual(this double d, double other, double tolerance = Tolerance)
 		{
 			return other.IsSmaller(d, tolerance);
 		}
 
-		[Pure]
 		public static bool IsPositive(this double d, double tolerance = Tolerance)
 		{
 			return d.IsGreaterOrEqual(0.0, tolerance);
 		}
 
 		/// <summary>
-		/// Converts the double-value from rounds per minute to the SI Unit RadianPerSecond
+		/// Converts the double-value from rounds per minute to the SI Unit PerSecond
 		/// </summary>
 		/// <param name="d"></param>
 		/// <returns></returns>
-		public static RadianPerSecond RPMtoRad(this double d)
+		public static PerSecond RPMtoRad(this double d)
 		{
-			return d.SI().Rounds.Per.Minute.ConvertTo().Radian.Per.Second.Cast<RadianPerSecond>();
+			return d.SI().Rounds.Per.Minute.ConvertTo().Radian.Per.Second.Cast<PerSecond>();
 		}
 
 		/// <summary>
@@ -65,9 +59,9 @@ namespace TUGraz.VectoCore.Utils
 		/// <summary>
 		/// Gets the special SI class of the number.
 		/// </summary>
-		public static T SI<T>(this double d) where T : SIBase<T>
+		public static T SI<T>(this double d) where T : SIBase<T>, new()
 		{
-			return (T) Activator.CreateInstance(typeof (T), d);
+			return SIBase<T>.Create(d);
 		}
 	}
 }
\ No newline at end of file
diff --git a/VectoCore/Utils/Formulas.cs b/VectoCore/Utils/Formulas.cs
index 2548cd6d5a20870db1e54a68a36d2a8a4de110f0..1dfe96caaef92dd32107f51052b42accfe10d2dc 100644
--- a/VectoCore/Utils/Formulas.cs
+++ b/VectoCore/Utils/Formulas.cs
@@ -6,22 +6,22 @@ namespace TUGraz.VectoCore.Utils
 		///     [Nm], [rad/s] => [W]. Calculates the power from torque and angular velocity.
 		/// </summary>
 		/// <param name="torque">[Nm]</param>
-		/// <param name="angularFrequency">[rad/s]</param>
+		/// <param name="angularVelocity">[rad/s]</param>
 		/// <returns>power [W]</returns>
-		public static Watt TorqueToPower(NewtonMeter torque, RadianPerSecond angularFrequency)
+		public static Watt TorqueToPower(NewtonMeter torque, PerSecond angularVelocity)
 		{
-			return torque * angularFrequency;
+			return torque * angularVelocity;
 		}
 
 		/// <summary>
 		///     [W], [rad/s] => [Nm]. Calculates the torque from power and angular velocity.
 		/// </summary>
 		/// <param name="power">[W]</param>
-		/// <param name="angularFrequency">[rad/s]</param>
+		/// <param name="angularVelocity">[rad/s]</param>
 		/// <returns>torque [Nm]</returns>
-		public static NewtonMeter PowerToTorque(Watt power, RadianPerSecond angularFrequency)
+		public static NewtonMeter PowerToTorque(Watt power, PerSecond angularVelocity)
 		{
-			return power / angularFrequency;
+			return power / angularVelocity;
 		}
 	}
 }
\ No newline at end of file
diff --git a/VectoCore/Utils/IntExtensionMethods.cs b/VectoCore/Utils/IntExtensionMethods.cs
index 489b3b86fa07a5819fc8f2e5d791632e8e8003c8..0075574fbf4b245c924c328da76a9b59cec7f012 100644
--- a/VectoCore/Utils/IntExtensionMethods.cs
+++ b/VectoCore/Utils/IntExtensionMethods.cs
@@ -6,13 +6,13 @@ namespace TUGraz.VectoCore.Utils
 	public static class IntExtensionMethods
 	{
 		/// <summary>
-		/// Converts the value from rounds per minute to the SI Unit RadianPerSecond
+		/// Converts the value from rounds per minute to the SI Unit PerSecond
 		/// </summary>
 		/// <param name="d"></param>
 		/// <returns></returns>
-		public static RadianPerSecond RPMtoRad(this double d)
+		public static PerSecond RPMtoRad(this int d)
 		{
-			return d.SI().Rounds.Per.Minute.ConvertTo().Radian.Per.Second.Cast<RadianPerSecond>();
+			return d.SI().Rounds.Per.Minute.ConvertTo().Radian.Per.Second.Cast<PerSecond>();
 		}
 
 		/// <summary>
@@ -30,9 +30,9 @@ namespace TUGraz.VectoCore.Utils
 		/// </summary>
 		/// <param name="d"></param>
 		/// <returns></returns>
-		public static T SI<T>(this int d) where T : SIBase<T>
+		public static T SI<T>(this int d) where T : SIBase<T>, new()
 		{
-			return (T) Activator.CreateInstance(typeof (T), d);
+			return SIBase<T>.Create(d);
 		}
 	}
 }
\ No newline at end of file
diff --git a/VectoCore/Utils/SI.cs b/VectoCore/Utils/SI.cs
index 34bd0cc54a862da1387a4afffccd9bd84086a0c3..1e29afeb4c497eb566e36e40f5b0635fe6413e9b 100644
--- a/VectoCore/Utils/SI.cs
+++ b/VectoCore/Utils/SI.cs
@@ -2,6 +2,7 @@ using System;
 using System.Collections.Generic;
 using System.Diagnostics;
 using System.Diagnostics.Contracts;
+using System.Dynamic;
 using System.Linq;
 using System.Runtime.Serialization;
 using TUGraz.VectoCore.Exceptions;
@@ -10,56 +11,72 @@ namespace TUGraz.VectoCore.Utils
 {
 	public class MeterPerSecond : SIBase<MeterPerSecond>
 	{
-		public MeterPerSecond(double val = 0) : base(val, new SI().Meter.Per.Second) {}
-	}
-
-	public class Radian : SIBase<Radian>
-	{
-		public Radian(double val = 0) : base(val, new SI().Radian) {}
+		public MeterPerSecond() : this(0) {}
+		protected MeterPerSecond(double val) : base(val, new SI().Meter.Per.Second) {}
 	}
 
 	public class Second : SIBase<Second>
 	{
-		public Second(double val = 0) : base(val, new SI().Second) {}
+		public Second() : this(0) {}
+		protected Second(double val) : base(val, new SI().Second) {}
 	}
 
 	public class Watt : SIBase<Watt>
 	{
-		public Watt(double val = 0) : base(val, new SI().Watt) {}
+		public Watt() : this(0) {}
+		protected Watt(double val) : base(val, new SI().Watt) {}
 
-		public static RadianPerSecond operator /(Watt watt, NewtonMeter newtonMeter)
+		public static PerSecond operator /(Watt watt, NewtonMeter newtonMeter)
 		{
-			return ((watt as SI) / newtonMeter).Cast<RadianPerSecond>();
+			return ((watt as SI) / newtonMeter).Cast<PerSecond>();
 		}
 
-		public static NewtonMeter operator /(Watt watt, RadianPerSecond radianPerSecond)
+		public static NewtonMeter operator /(Watt watt, PerSecond perSecond)
 		{
-			return ((watt as SI) / radianPerSecond).Cast<NewtonMeter>();
+			return ((watt as SI) / perSecond).Cast<NewtonMeter>();
 		}
 	}
 
-	public class RadianPerSecond : SIBase<RadianPerSecond>
+	public class PerSecond : SIBase<PerSecond>
 	{
-		public RadianPerSecond(double val = 0) : base(val, new SI().Radian.Per.Second) {}
-
-		public static Watt operator *(RadianPerSecond radianPerSecond, NewtonMeter newtonMeter)
-		{
-			return ((radianPerSecond as SI) * newtonMeter).Cast<Watt>();
-		}
+		public PerSecond() : this(0) {}
+		protected PerSecond(double val) : base(val, new SI().Radian.Per.Second) {}
 	}
 
 	public class RoundsPerMinute : SIBase<RoundsPerMinute>
 	{
-		public RoundsPerMinute(double val = 0) : base(val, new SI().Rounds.Per.Minute) {}
+		public RoundsPerMinute() : this(0) {}
+		protected RoundsPerMinute(double val) : base(val, new SI().Rounds.Per.Minute) {}
+	}
+
+
+	public class Newton : SIBase<Newton>
+	{
+		protected Newton(double val) : base(val, new SI().Newton) {}
+
+		public Newton() : this(0) {}
+	}
+
+	public class Radian : SIBase<Radian>
+	{
+		public Radian() : this(0) {}
+
+		public Radian(double val) : base(val, new SI().Radian) {}
 	}
 
 	public class NewtonMeter : SIBase<NewtonMeter>
 	{
-		public NewtonMeter(double val = 0) : base(val, new SI().Newton.Meter) {}
+		public NewtonMeter() : this(0) {}
+		protected NewtonMeter(double val) : base(val, new SI().Newton.Meter) {}
 
-		public static Watt operator *(NewtonMeter newtonMeter, RadianPerSecond radianPerSecond)
+		public static Watt operator *(NewtonMeter newtonMeter, PerSecond perSecond)
 		{
-			return ((newtonMeter as SI) * radianPerSecond).Cast<Watt>();
+			return ((newtonMeter as SI) * perSecond).Cast<Watt>();
+		}
+
+		public static Watt operator *(PerSecond perSecond, NewtonMeter newtonMeter)
+		{
+			return ((perSecond as SI) * newtonMeter).Cast<Watt>();
 		}
 
 		public static Second operator /(NewtonMeter newtonMeter, Watt watt)
@@ -68,14 +85,16 @@ namespace TUGraz.VectoCore.Utils
 		}
 	}
 
-	public class Newton : SIBase<Newton>
-	{
-		public Newton(double val = 0) : base(val, new SI().Newton) {}
-	}
 
-	public abstract class SIBase<T> : SI where T : SIBase<T>
+	public abstract class SIBase<T> : SI where T : SIBase<T>, new()
 	{
-		protected SIBase(double val = 0) : base(val) {}
+		public static T Create(double val)
+		{
+			return new T { Val = val };
+		}
+
+		protected SIBase() {}
+		protected SIBase(double val) : base(val) {}
 		protected SIBase(double val, SI unit) : base(val, unit) {}
 
 		#region Operators
@@ -153,16 +172,15 @@ namespace TUGraz.VectoCore.Utils
 		#endregion
 	}
 
-
 	[DataContract]
-	public class SI
+	public class SI : IComparable
 	{
 		[DataMember] protected readonly string[] Denominator;
 		[DataMember] protected readonly int Exponent;
 		[DataMember] protected readonly string[] Numerator;
 		[DataMember] protected readonly bool Reciproc;
 		[DataMember] protected readonly bool Reverse;
-		[DataMember] protected readonly double Val;
+		[DataMember] protected double Val;
 
 		public SI(double val = 0.0)
 		{
@@ -278,9 +296,12 @@ namespace TUGraz.VectoCore.Utils
 		/// </summary>
 		/// <typeparam name="T"></typeparam>
 		/// <returns></returns>
-		public T Cast<T>() where T : SIBase<T>
+		public T Cast<T>() where T : SIBase<T>, new()
 		{
-			var t = (T) Activator.CreateInstance(typeof (T), Val);
+			var t = SIBase<T>.Create(Val);
+			if (!HasEqualUnit(t)) {
+				throw new VectoException(string.Format("SI Unit Conversion failed: From {0} to {1}", this, t));
+			}
 			Contract.Assert(HasEqualUnit(t), string.Format("SI Unit Conversion failed: From {0} to {1}", this, t));
 			return t;
 		}
@@ -427,12 +448,12 @@ namespace TUGraz.VectoCore.Utils
 		[DebuggerHidden]
 		public SI Radian
 		{
-			get { return new SI(this, fromUnit: "rad", toUnit: "rad"); }
+			get { return new SI(this); }
 		}
 
 		public SI GradientPercent
 		{
-			get { return new SI(this, factor: Math.Atan(Val) / Val, fromUnit: "%", toUnit: "rad"); }
+			get { return new SI(this, factor: Math.Atan(Val) / Val, fromUnit: "%", toUnit: ""); }
 		}
 
 		/// <summary>
@@ -441,7 +462,7 @@ namespace TUGraz.VectoCore.Utils
 		[DebuggerHidden]
 		public SI Rounds
 		{
-			get { return new SI(this, 2 * Math.PI, toUnit: "rad"); }
+			get { return new SI(this, 2 * Math.PI); }
 		}
 
 		/// <summary>
@@ -701,6 +722,16 @@ namespace TUGraz.VectoCore.Utils
 			}
 		}
 
+		int IComparable.CompareTo(object obj)
+		{
+			var si = (obj as SI);
+			if (si == null || this > si) {
+				return 1;
+			}
+
+			return this < si ? -1 : 0;
+		}
+
 		public static bool operator ==(SI left, SI right)
 		{
 			return Equals(left, right);
diff --git a/VectoCore/Utils/VectoMath.cs b/VectoCore/Utils/VectoMath.cs
index b000e637a67e80dc6b43205f0170da2a310d8a04..71a8fb44a3a0e8bc681175a8b94db1da1f51ac87 100644
--- a/VectoCore/Utils/VectoMath.cs
+++ b/VectoCore/Utils/VectoMath.cs
@@ -11,19 +11,25 @@ namespace TUGraz.VectoCore.Utils
 			return (xint - x1) * (y2 - y1) / (x2 - x1) + y1;
 		}
 
-		public static T Abs<T>(T si) where T : SIBase<T>
+		public static SI Abs(SI si)
 		{
-			return (T) si.Abs();
+			return si.Abs();
 		}
 
-		public static T Min<T>(T c1, T c2) where T : SIBase<T>
+
+		public static T Abs<T>(T si) where T : SIBase<T>, new()
+		{
+			return si.Abs().Cast<T>();
+		}
+
+		public static T Min<T>(T c1, T c2) where T : IComparable
 		{
-			return c1 <= c2 ? c1 : c2;
+			return c1.CompareTo(c2) <= 0 ? c1 : c2;
 		}
 
-		public static T Max<T>(T c1, T c2) where T : SIBase<T>
+		public static T Max<T>(T c1, T c2) where T : IComparable
 		{
-			return c1 >= c2 ? c1 : c2;
+			return c1.CompareTo(c2) >= 0 ? c1 : c2;
 		}
 	}
 }
\ No newline at end of file
diff --git a/VectoCoreTest/Models/Simulation/DrivingCycleTests.cs b/VectoCoreTest/Models/Simulation/DrivingCycleTests.cs
index eee3b16b6b6b9d9d1bdf570aa92078ed4de97217..35d4f7f444d6702a42e9ce00314e7fd64c073b71 100644
--- a/VectoCoreTest/Models/Simulation/DrivingCycleTests.cs
+++ b/VectoCoreTest/Models/Simulation/DrivingCycleTests.cs
@@ -10,91 +10,91 @@ using TUGraz.VectoCore.Utils;
 
 namespace TUGraz.VectoCore.Tests.Models.Simulation
 {
-    [TestClass]
-    public class DrivingCycleTests
-    {
-        [TestMethod]
-        public void TestEngineOnly()
-        {
-            var container = new VehicleContainer();
+	[TestClass]
+	public class DrivingCycleTests
+	{
+		[TestMethod]
+		public void TestEngineOnly()
+		{
+			var container = new VehicleContainer();
 
-            var cycleData = DrivingCycleData.ReadFromFileEngineOnly(@"TestData\Cycles\Coach Engine Only.vdri");
-            var cycle = new EngineOnlyDrivingCycle(container, cycleData);
+			var cycleData = DrivingCycleData.ReadFromFileEngineOnly(@"TestData\Cycles\Coach Engine Only.vdri");
+			var cycle = new EngineOnlyDrivingCycle(container, cycleData);
 
-            var outPort = new MockTnOutPort();
-            var inPort = cycle.InShaft();
-            var cycleOut = cycle.OutPort();
+			var outPort = new MockTnOutPort();
+			var inPort = cycle.InShaft();
+			var cycleOut = cycle.OutPort();
 
-            inPort.Connect(outPort);
+			inPort.Connect(outPort);
 
-            var absTime = new TimeSpan();
-            var dt = TimeSpan.FromSeconds(1);
+			var absTime = new TimeSpan();
+			var dt = TimeSpan.FromSeconds(1);
 
-            var response = cycleOut.Request(absTime, dt);
-            Assert.IsInstanceOfType(response, typeof (ResponseSuccess));
+			var response = cycleOut.Request(absTime, dt);
+			Assert.IsInstanceOfType(response, typeof (ResponseSuccess));
 
-            var dataWriter = new TestModalDataWriter();
-            container.CommitSimulationStep(dataWriter);
+			var dataWriter = new TestModalDataWriter();
+			container.CommitSimulationStep(dataWriter);
 
-            Assert.AreEqual(absTime, outPort.AbsTime);
-            Assert.AreEqual(dt, outPort.Dt);
-            Assert.AreEqual(600.0.RPMtoRad(), outPort.AngularFrequency);
-            Assert.AreEqual(0.SI<NewtonMeter>(), outPort.Torque);
-        }
+			Assert.AreEqual(absTime, outPort.AbsTime);
+			Assert.AreEqual(dt, outPort.Dt);
+			Assert.AreEqual(600.0.RPMtoRad(), outPort.AngularVelocity);
+			Assert.AreEqual(0.SI<NewtonMeter>(), outPort.Torque);
+		}
 
-        [TestMethod]
-        public void Test_TimeBased_FirstCycle()
-        {
-            var container = new VehicleContainer();
+		[TestMethod]
+		public void Test_TimeBased_FirstCycle()
+		{
+			var container = new VehicleContainer();
 
-            var cycleData = DrivingCycleData.ReadFromFileTimeBased(@"TestData\Cycles\Coach time based.vdri");
-            var cycle = new TimeBasedDrivingCycle(container, cycleData);
+			var cycleData = DrivingCycleData.ReadFromFileTimeBased(@"TestData\Cycles\Coach time based.vdri");
+			var cycle = new TimeBasedDrivingCycle(container, cycleData);
 
-            var outPort = new MockDriverDemandOutPort();
+			var outPort = new MockDriverDemandOutPort();
 
-            var inPort = cycle.InPort();
-            var cycleOut = cycle.OutPort();
+			var inPort = cycle.InPort();
+			var cycleOut = cycle.OutPort();
 
-            inPort.Connect(outPort);
+			inPort.Connect(outPort);
 
-            var absTime = new TimeSpan();
-            var dt = TimeSpan.FromSeconds(1);
+			var absTime = new TimeSpan();
+			var dt = TimeSpan.FromSeconds(1);
 
-            var response = cycleOut.Request(absTime, dt);
-            Assert.IsInstanceOfType(response, typeof (ResponseSuccess));
+			var response = cycleOut.Request(absTime, dt);
+			Assert.IsInstanceOfType(response, typeof (ResponseSuccess));
 
-            Assert.AreEqual(absTime, outPort.AbsTime);
-            Assert.AreEqual(dt, outPort.Dt);
-            Assert.AreEqual(0.0.SI<MeterPerSecond>(), outPort.Velocity);
-            Assert.AreEqual((-0.020237973).SI().GradientPercent.Cast<Radian>(), outPort.Gradient);
-        }
+			Assert.AreEqual(absTime, outPort.AbsTime);
+			Assert.AreEqual(dt, outPort.Dt);
+			Assert.AreEqual(0.0.SI<MeterPerSecond>(), outPort.Velocity);
+			Assert.AreEqual((-0.020237973).SI().GradientPercent.Cast<Radian>(), outPort.Gradient);
+		}
 
-        [TestMethod]
-        public void Test_TimeBased_TimeFieldMissing()
-        {
-            var container = new VehicleContainer();
+		[TestMethod]
+		public void Test_TimeBased_TimeFieldMissing()
+		{
+			var container = new VehicleContainer();
 
-            var cycleData = DrivingCycleData.ReadFromFileTimeBased(@"TestData\Cycles\Cycle time field missing.vdri");
-            var cycle = new TimeBasedDrivingCycle(container, cycleData);
+			var cycleData = DrivingCycleData.ReadFromFileTimeBased(@"TestData\Cycles\Cycle time field missing.vdri");
+			var cycle = new TimeBasedDrivingCycle(container, cycleData);
 
-            var outPort = new MockDriverDemandOutPort();
+			var outPort = new MockDriverDemandOutPort();
 
-            var inPort = cycle.InPort();
-            var cycleOut = cycle.OutPort();
+			var inPort = cycle.InPort();
+			var cycleOut = cycle.OutPort();
 
-            inPort.Connect(outPort);
+			inPort.Connect(outPort);
 
-            var dataWriter = new TestModalDataWriter();
-            var absTime = new TimeSpan();
-            var dt = TimeSpan.FromSeconds(1);
+			var dataWriter = new TestModalDataWriter();
+			var absTime = new TimeSpan();
+			var dt = TimeSpan.FromSeconds(1);
 
-            while (cycleOut.Request(absTime, dt) is ResponseSuccess) {
-                Assert.AreEqual(absTime, outPort.AbsTime);
-                Assert.AreEqual(dt, outPort.Dt);
-                container.CommitSimulationStep(dataWriter);
+			while (cycleOut.Request(absTime, dt) is ResponseSuccess) {
+				Assert.AreEqual(absTime, outPort.AbsTime);
+				Assert.AreEqual(dt, outPort.Dt);
+				container.CommitSimulationStep(dataWriter);
 
-                absTime += dt;
-            }
-        }
-    }
+				absTime += dt;
+			}
+		}
+	}
 }
\ No newline at end of file
diff --git a/VectoCoreTest/Models/SimulationComponent/CombustionEngineTest.cs b/VectoCoreTest/Models/SimulationComponent/CombustionEngineTest.cs
index 9ba69f9cdf8ea0d23c3826618a656bc0c731252b..dd0e4772335baa21345738d91082a6de59a9d8d9 100644
--- a/VectoCoreTest/Models/SimulationComponent/CombustionEngineTest.cs
+++ b/VectoCoreTest/Models/SimulationComponent/CombustionEngineTest.cs
@@ -65,7 +65,7 @@ namespace TUGraz.VectoCore.Tests.Models.SimulationComponent
 			var absTime = new TimeSpan(seconds: 0, minutes: 0, hours: 0);
 			var dt = new TimeSpan(seconds: 1, minutes: 0, hours: 0);
 
-			var torque = new NewtonMeter();
+			var torque = 0.SI<NewtonMeter>();
 			var engineSpeed = 600.0.RPMtoRad();
 			var dataWriter = new TestModalDataWriter();
 
diff --git a/VectoCoreTest/Models/SimulationComponent/MockPorts.cs b/VectoCoreTest/Models/SimulationComponent/MockPorts.cs
index 46bd7188f3a2b00464b48a1c29a02e387a710530..d0f5b37d5036f6495ec5591da8cf7b89e8a1c5a6 100644
--- a/VectoCoreTest/Models/SimulationComponent/MockPorts.cs
+++ b/VectoCoreTest/Models/SimulationComponent/MockPorts.cs
@@ -6,41 +6,41 @@ using TUGraz.VectoCore.Utils;
 
 namespace TUGraz.VectoCore.Tests.Models.SimulationComponent
 {
-    public class MockTnOutPort : ITnOutPort
-    {
-        public TimeSpan AbsTime { get; set; }
-        public TimeSpan Dt { get; set; }
-        public NewtonMeter Torque { get; set; }
-        public RadianPerSecond AngularFrequency { get; set; }
+	public class MockTnOutPort : ITnOutPort
+	{
+		public TimeSpan AbsTime { get; set; }
+		public TimeSpan Dt { get; set; }
+		public NewtonMeter Torque { get; set; }
+		public PerSecond AngularVelocity { get; set; }
 
-        public IResponse Request(TimeSpan absTime, TimeSpan dt, NewtonMeter torque, RadianPerSecond angularFrequency)
-        {
-            AbsTime = absTime;
-            Dt = dt;
-            Torque = torque;
-            AngularFrequency = angularFrequency;
-            LogManager.GetLogger(GetType()).DebugFormat("Request: absTime: {0}, dt: {1}, torque: {3}, engineSpeed: {4}",
-                absTime, dt, torque, angularFrequency);
-            return new ResponseSuccess();
-        }
-    }
+		public IResponse Request(TimeSpan absTime, TimeSpan dt, NewtonMeter torque, PerSecond angularVelocity)
+		{
+			AbsTime = absTime;
+			Dt = dt;
+			Torque = torque;
+			AngularVelocity = angularVelocity;
+			LogManager.GetLogger(GetType()).DebugFormat("Request: absTime: {0}, dt: {1}, torque: {3}, engineSpeed: {4}",
+				absTime, dt, torque, angularVelocity);
+			return new ResponseSuccess();
+		}
+	}
 
-    public class MockDriverDemandOutPort : IDriverDemandOutPort
-    {
-        public TimeSpan AbsTime { get; set; }
-        public TimeSpan Dt { get; set; }
-        public MeterPerSecond Velocity { get; set; }
-        public Radian Gradient { get; set; }
+	public class MockDriverDemandOutPort : IDriverDemandOutPort
+	{
+		public TimeSpan AbsTime { get; set; }
+		public TimeSpan Dt { get; set; }
+		public MeterPerSecond Velocity { get; set; }
+		public Radian Gradient { get; set; }
 
-        public IResponse Request(TimeSpan absTime, TimeSpan dt, MeterPerSecond velocity, Radian gradient)
-        {
-            AbsTime = absTime;
-            Dt = dt;
-            Velocity = velocity;
-            Gradient = gradient;
-            LogManager.GetLogger(GetType()).DebugFormat("Request: absTime: {0}, dt: {1}, velocity: {3}, gradient: {4}",
-                absTime, dt, velocity, gradient);
-            return new ResponseSuccess();
-        }
-    }
+		public IResponse Request(TimeSpan absTime, TimeSpan dt, MeterPerSecond velocity, Radian gradient)
+		{
+			AbsTime = absTime;
+			Dt = dt;
+			Velocity = velocity;
+			Gradient = gradient;
+			LogManager.GetLogger(GetType()).DebugFormat("Request: absTime: {0}, dt: {1}, velocity: {3}, gradient: {4}",
+				absTime, dt, velocity, gradient);
+			return new ResponseSuccess();
+		}
+	}
 }
\ No newline at end of file
diff --git a/VectoCoreTest/Models/SimulationComponentData/FullLoadCurveTest.cs b/VectoCoreTest/Models/SimulationComponentData/FullLoadCurveTest.cs
index 7f0de7ba188499ef119b8e5b93fa57dfff8ba21a..ccf538dc5bb6b319518905b68208073c59924226 100644
--- a/VectoCoreTest/Models/SimulationComponentData/FullLoadCurveTest.cs
+++ b/VectoCoreTest/Models/SimulationComponentData/FullLoadCurveTest.cs
@@ -94,7 +94,7 @@ namespace TUGraz.VectoCore.Tests.Models.SimulationComponentData
 		public void Test_FileRead_NoHeader()
 		{
 			var curve = FullLoadCurve.ReadFromFile(@"TestData\Components\FullLoadCurve no header.vfld");
-			var result = curve.FullLoadStationaryTorque(1.SI<RadianPerSecond>());
+			var result = curve.FullLoadStationaryTorque(1.SI<PerSecond>());
 			Assert.AreNotEqual((double) result, 0.0);
 		}
 
diff --git a/VectoCoreTest/Utils/DoubleExtensionMethodTest.cs b/VectoCoreTest/Utils/DoubleExtensionMethodTest.cs
new file mode 100644
index 0000000000000000000000000000000000000000..21d802107dedb390e230f7ed1e36d8b7e2d2525e
--- /dev/null
+++ b/VectoCoreTest/Utils/DoubleExtensionMethodTest.cs
@@ -0,0 +1,29 @@
+using System;
+using Microsoft.VisualStudio.TestTools.UnitTesting;
+using TUGraz.VectoCore.Utils;
+
+namespace TUGraz.VectoCore.Tests.Utils
+{
+	[TestClass]
+	public class DoubleExtensionMethodTest
+	{
+		[TestMethod]
+		public void DoubleExtensions_SI_Test()
+		{
+			var val = 600.0.RPMtoRad();
+			Assert.AreEqual(600 / 60 * 2 * Math.PI, val.Double());
+
+			Assert.IsTrue(0.0.SI<PerSecond>().HasEqualUnit(val));
+
+			var val2 = 1200.0.SI().Rounds.Per.Minute.ConvertTo().Radian.Per.Second.Cast<PerSecond>();
+			val = val * 2;
+			Assert.AreEqual(val, val2);
+
+			val2 = val2 / 2;
+			val = val / 2;
+			Assert.AreEqual(val, val2);
+			Assert.AreEqual(600.SI().Rounds.Per.Minute.Cast<PerSecond>(), val2);
+			Assert.AreEqual(600.SI().Rounds.Per.Minute.Cast<PerSecond>().Double(), val2.Double());
+		}
+	}
+}
\ No newline at end of file
diff --git a/VectoCoreTest/Utils/SITest.cs b/VectoCoreTest/Utils/SITest.cs
index f14296368771e870f3426150a79ad36f87f7a3bd..8f989c45390a273c599cc07243fc82d4786901b3 100644
--- a/VectoCoreTest/Utils/SITest.cs
+++ b/VectoCoreTest/Utils/SITest.cs
@@ -1,4 +1,5 @@
 using System;
+using System.Diagnostics.CodeAnalysis;
 using Microsoft.VisualStudio.TestTools.UnitTesting;
 using TUGraz.VectoCore.Utils;
 
@@ -21,7 +22,7 @@ namespace TUGraz.VectoCore.Tests.Utils
 		public void TestSI()
 		{
 			var si = new SI();
-			Assert.AreEqual(0.0, (double) si);
+			Assert.AreEqual(0.0, si.Double());
 			Assert.AreEqual("0 [-]", si.ToString());
 			Assert.IsTrue(si.HasEqualUnit(new SI()));
 
@@ -29,7 +30,7 @@ namespace TUGraz.VectoCore.Tests.Utils
 			Assert.AreEqual("5 [W]", si2.ToString());
 
 			var si3 = 2.SI().Radian.Per.Second;
-			Assert.AreEqual("2 [rad/s]", si3.ToString());
+			Assert.AreEqual("2 [1/s]", si3.ToString());
 
 			var si4 = si2 * si3;
 			Assert.AreEqual("10 [W/s]", si4.ToString());
@@ -38,15 +39,15 @@ namespace TUGraz.VectoCore.Tests.Utils
 
 
 			var kg = 5.0.SI().Kilo.Gramm;
-			Assert.AreEqual(5.0, (double) kg);
+			Assert.AreEqual(5.0, kg.Double());
 			Assert.AreEqual("5 [kg]", kg.ToString());
 
 			kg = kg.ConvertTo().Kilo.Gramm.Value();
-			Assert.AreEqual(5.0, (double) kg);
+			Assert.AreEqual(5.0, kg.Double());
 			Assert.AreEqual("5 [kg]", kg.ToString());
 
 			kg = kg.ConvertTo().Gramm.Value();
-			Assert.AreEqual(5000, (double) kg);
+			Assert.AreEqual(5000, kg.Double());
 			Assert.AreEqual("5000 [g]", kg.ToString());
 
 			var x = 5.SI();
@@ -64,5 +65,35 @@ namespace TUGraz.VectoCore.Tests.Utils
 			var y = 2.SI();
 			Assert.AreEqual((2 * 5).SI(), y * x);
 		}
+
+		[TestMethod]
+		[SuppressMessage("ReSharper", "SuggestVarOrType_SimpleTypes")]
+		public void SITests_Addition_Subtraction()
+		{
+			var v1 = 600.SI<NewtonMeter>();
+			var v2 = 455.SI<NewtonMeter>();
+			NewtonMeter v3 = v1 + v2;
+
+			NewtonMeter v4 = v1 - v2;
+
+			var v5 = v1 * v2;
+			Assert.IsTrue(v5.HasEqualUnit(0.SI().Square.Newton.Meter));
+			Assert.AreEqual(v1.Double() * v2.Double(), v5.Double());
+
+			var v6 = v1 / v2;
+			Assert.IsTrue(v6.HasEqualUnit(0.SI()));
+			Assert.AreEqual(v1.Double() / v2.Double(), v6.Double());
+
+			var t = 10.SI<NewtonMeter>();
+			var angVelo = 5.SI<PerSecond>();
+
+			Watt w = t * angVelo;
+			Watt w1 = angVelo * t;
+
+			NewtonMeter t1 = w / angVelo;
+
+			PerSecond angVelo1 = w / t;
+			Second sec = t / w;
+		}
 	}
 }
\ No newline at end of file
diff --git a/VectoCoreTest/Utils/VectoMathTest.cs b/VectoCoreTest/Utils/VectoMathTest.cs
new file mode 100644
index 0000000000000000000000000000000000000000..2c163c8e67055adf5aba109fb75ee29ec58e5c41
--- /dev/null
+++ b/VectoCoreTest/Utils/VectoMathTest.cs
@@ -0,0 +1,37 @@
+using Microsoft.VisualStudio.TestTools.UnitTesting;
+using TUGraz.VectoCore.Utils;
+
+namespace TUGraz.VectoCore.Tests.Utils
+{
+	[TestClass]
+	public class VectoMathTest
+	{
+		[TestMethod]
+		public void VectoMath_Min()
+		{
+			var smaller = 0.SI();
+			var bigger = 5.SI();
+			var negative = -10.SI();
+			var positive = 10.SI();
+			Assert.AreEqual(smaller, VectoMath.Min(smaller, bigger));
+
+			Assert.AreEqual(bigger, VectoMath.Max(smaller, bigger));
+
+			Assert.AreEqual(positive, VectoMath.Abs(negative));
+			Assert.AreEqual(positive, VectoMath.Abs(positive));
+
+
+			var smallerWatt = 0.SI<Watt>();
+			var biggerWatt = 5.SI<Watt>();
+			var negativeWatt = -10.SI<Watt>();
+			var positiveWatt = 10.SI<Watt>();
+			Assert.AreEqual(smallerWatt, VectoMath.Min(smallerWatt, biggerWatt));
+
+			Assert.AreEqual(biggerWatt, VectoMath.Max(smallerWatt, biggerWatt));
+
+
+			Assert.AreEqual(positiveWatt, VectoMath.Abs(negativeWatt));
+			Assert.AreEqual(positiveWatt, VectoMath.Abs(positiveWatt));
+		}
+	}
+}
\ No newline at end of file
diff --git a/VectoCoreTest/VectoCoreTest.csproj b/VectoCoreTest/VectoCoreTest.csproj
index 1d6412df1d2f694efb63bbd900b0c89461604ef6..ed4d8f934625633628f7390b38ab1221e5a17596 100644
--- a/VectoCoreTest/VectoCoreTest.csproj
+++ b/VectoCoreTest/VectoCoreTest.csproj
@@ -86,6 +86,8 @@
     <Compile Include="Utils\SITest.cs" />
     <Compile Include="Utils\DelauneyMapTest.cs" />
     <Compile Include="Utils\TestModalDataWriter.cs" />
+    <Compile Include="Utils\DoubleExtensionMethodTest.cs" />
+    <Compile Include="Utils\VectoMathTest.cs" />
   </ItemGroup>
   <ItemGroup>
     <ProjectReference Include="..\VectoCore\VectoCore.csproj">