From 139a0862ab8ff62a60ec75759b3581af690289ee Mon Sep 17 00:00:00 2001 From: Federico Barresi Date: Thu, 27 Aug 2020 16:12:45 +0200 Subject: [PATCH] Refactor of S7 utilities - fix #18 - New overloaded extension methods signatures for SetBitAt - Removed not necessary casting to short for GetIntAt - Added overloads for S7 `Time_Of_Day` functions - Added more tests - made old methods obsolete --- CHANGELOG.md | 15 +++++++- Sharp7.Tests/TestUtilities.cs | 15 ++++++++ Sharp7/S7.cs | 72 +++++++++++++++++++++++++++++++++-- 3 files changed, 97 insertions(+), 5 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 6c57723..d7d3445 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,7 +1,20 @@ # Change Log All notable changed to this project will be documented in this file. -## [1.1.71] - 08.2020 +## [1.1.xx] - ETA 09.2020 +### Added +### Changed +- CHANGELOG.md + +### Fixed +- [#18](https://github.com/fbarresi/Sharp7/issues/18) + - New overloaded extension method signatures for SetBitAt + - Removed not necessary casting to short for GetIntAt + - Added overloads for S7 `Time_Of_Day` functions + - Added more tests + - made old methods obsolete + +## [1.1.71] - 14.08.2020 ### Added - CHANGELOG.md ### Changed diff --git a/Sharp7.Tests/TestUtilities.cs b/Sharp7.Tests/TestUtilities.cs index 5b11071..5aff84c 100644 --- a/Sharp7.Tests/TestUtilities.cs +++ b/Sharp7.Tests/TestUtilities.cs @@ -28,6 +28,11 @@ namespace Sharp7.Tests S7.SetBitAt(ref buffer, 0, 1, true); buffer.ShouldBe(new byte[] {3, 2, 3, 4}); } + [Fact] public void TestSetBitAtAsExtensionMethod() { + var buffer = new byte[] {1,2,3,4}; + buffer.SetBitAt(0, 1, true); + buffer.ShouldBe(new byte[] {3, 2, 3, 4}); + } //unsigned @@ -254,6 +259,8 @@ namespace Sharp7.Tests public void TestGetTODAt(byte[] buffer, int milliseconds) { S7.GetTODAt(buffer, 0).ShouldBe(new DateTime(0).AddMilliseconds(milliseconds)); + S7.GetTODAsDateTimeAt(buffer, 0).ShouldBe(new DateTime(0).AddMilliseconds(milliseconds)); + S7.GetTODAsTimeSpanAt(buffer, 0).ShouldBe(TimeSpan.FromMilliseconds(milliseconds)); } [Theory] @@ -263,12 +270,17 @@ namespace Sharp7.Tests var buffer = new byte[4]; S7.SetTODAt(buffer, 0, new DateTime(0).AddMilliseconds(milliseconds)); buffer.ShouldBe(expected); + buffer = new byte[4]; + S7.SetTODAt(buffer, 0, TimeSpan.FromMilliseconds(milliseconds)); + buffer.ShouldBe(expected); } [Theory] [InlineData(new byte[] { 0, 0, 0, 0,0,0,0,200 }, 2)] public void TestGetLTODAt(byte[] buffer, int ticks) { S7.GetLTODAt(buffer, 0).ShouldBe(new DateTime(ticks)); + S7.GetLTODAsDateTimeAt(buffer, 0).ShouldBe(new DateTime(ticks)); + S7.GetLTODAsTimeSpanAt(buffer, 0).ShouldBe(TimeSpan.FromTicks(ticks)); } [Theory] @@ -278,6 +290,9 @@ namespace Sharp7.Tests var buffer = new byte[8]; S7.SetLTODAt(buffer, 0, new DateTime(ticks)); buffer.ShouldBe(expected); + buffer = new byte[8]; + S7.SetLTODAt(buffer, 0, TimeSpan.FromTicks(ticks)); + buffer.ShouldBe(expected); } [Theory] diff --git a/Sharp7/S7.cs b/Sharp7/S7.cs index f774c2d..6b91a32 100644 --- a/Sharp7/S7.cs +++ b/Sharp7/S7.cs @@ -49,16 +49,34 @@ namespace Sharp7 return (buffer[pos] & Mask[bit]) != 0; } + [Obsolete("Use SetBitAt as extension method")] public static void SetBitAt(ref byte[] buffer, int pos, int bit, bool value) + { + buffer.SetBitAt(pos, bit, value); + } + + public static void SetBitAt(this byte[] buffer, int pos, int bit, bool value) { byte[] Mask = {0x01, 0x02, 0x04, 0x08, 0x10, 0x20, 0x40, 0x80}; - if (bit < 0) bit = 0; - if (bit > 7) bit = 7; + if (bit < 0) + { + bit = 0; + } + + if (bit > 7) + { + bit = 7; + } if (value) + { buffer[pos] = (byte) (buffer[pos] | Mask[bit]); + } else + { buffer[pos] = (byte) (buffer[pos] & ~Mask[bit]); + } + } #endregion @@ -87,7 +105,7 @@ namespace Sharp7 public static int GetIntAt(this byte[] buffer, int pos) { - return (short) ((buffer[pos] << 8) | buffer[pos + 1]); + return (buffer[pos] << 8) | buffer[pos + 1]; } public static void SetIntAt(this byte[] buffer, int pos, Int16 value) @@ -430,13 +448,19 @@ namespace Sharp7 #region Get/Set TOD (S7 TIME_OF_DAY) + [Obsolete("Use GetTODAsDateTimeAt or GetTODAsTimeSpanAt instead")] public static DateTime GetTODAt(this byte[] buffer, int pos) + { + return buffer.GetTODAsDateTimeAt(pos); + } + + public static DateTime GetTODAsDateTimeAt(this byte[] buffer, int pos) { try { return new DateTime(0).AddMilliseconds(buffer.GetDIntAt(pos)); } - catch (System.ArgumentOutOfRangeException) + catch (ArgumentOutOfRangeException) { return new DateTime(0); } @@ -447,12 +471,35 @@ namespace Sharp7 TimeSpan Time = value.TimeOfDay; SetDIntAt(buffer, pos, (Int32) Math.Round(Time.TotalMilliseconds)); } + + public static TimeSpan GetTODAsTimeSpanAt(this byte[] buffer, int pos) + { + try + { + return TimeSpan.FromMilliseconds(buffer.GetDIntAt(pos)); + } + catch (ArgumentOutOfRangeException) + { + return TimeSpan.Zero; + } + } + + public static void SetTODAt(this byte[] buffer, int pos, TimeSpan value) + { + SetDIntAt(buffer, pos, (Int32) Math.Round(value.TotalMilliseconds)); + } #endregion #region Get/Set LTOD (S7 1500 LONG TIME_OF_DAY) + [Obsolete("Use GetLTODAsDateTimeAt or GetLTODAsTimeSpanAt instead")] public static DateTime GetLTODAt(this byte[] buffer, int pos) + { + return buffer.GetLTODAsDateTimeAt(pos); + } + + public static DateTime GetLTODAsDateTimeAt(this byte[] buffer, int pos) { // .NET Tick = 100 ns, S71500 Tick = 1 ns try @@ -471,6 +518,23 @@ namespace Sharp7 SetLIntAt(buffer, pos, (Int64) Time.Ticks * 100); } + public static TimeSpan GetLTODAsTimeSpanAt(this byte[] buffer, int pos) + { + try + { + return TimeSpan.FromTicks(Math.Abs(GetLIntAt(buffer, pos) / 100)); + } + catch (System.ArgumentOutOfRangeException) + { + return TimeSpan.Zero; + } + } + + public static void SetLTODAt(this byte[] buffer, int pos, TimeSpan value) + { + SetLIntAt(buffer, pos, (Int64) value.Ticks * 100); + } + #endregion #region GET/SET LDT (S7 1500 Long Date and Time)