From 63cbe25f95082ce345198ed311daa5ab0382c1b5 Mon Sep 17 00:00:00 2001 From: Kevin Hahn Date: Wed, 31 Jul 2024 10:56:51 +0700 Subject: [PATCH 1/3] change target framework from netstandard1.6 to netstandard2.0 and remove related conditional compilation. Should fix issues where a library is compiled against netstandard2.0 but the consumer is a net8.0 project which results in the runtime error: Could not load type 'Icu.SortKey' from assembly 'icu.net' --- source/Directory.Build.props | 2 +- source/icu.net.tests/SetUpFixture.cs | 2 +- source/icu.net/Collation/Collator.cs | 11 +- source/icu.net/Collation/RuleBasedCollator.cs | 7 +- source/icu.net/Locale.cs | 5 +- source/icu.net/Platform.cs | 14 +- source/icu.net/SafeEnumeratorHandle.cs | 6 +- source/icu.net/SortKey.cs | 140 ------------------ source/icu.net/icu.net.csproj | 18 --- 9 files changed, 7 insertions(+), 198 deletions(-) delete mode 100644 source/icu.net/SortKey.cs diff --git a/source/Directory.Build.props b/source/Directory.Build.props index 6936c43b..898fbf31 100644 --- a/source/Directory.Build.props +++ b/source/Directory.Build.props @@ -1,6 +1,6 @@ - net40;net451;netstandard1.6;net8.0 + net40;net451;netstandard2.0;net8.0 netstandard $(MSBuildThisFileDirectory)\..\output\$(Configuration) $(MSBuildThisFileDirectory)\..\output diff --git a/source/icu.net.tests/SetUpFixture.cs b/source/icu.net.tests/SetUpFixture.cs index f160ee93..f7771138 100644 --- a/source/icu.net.tests/SetUpFixture.cs +++ b/source/icu.net.tests/SetUpFixture.cs @@ -16,7 +16,7 @@ private static bool IsWindows { // See Icu.Platform. Unfortunately that's internal, so we can't use it. -#if !NETSTANDARD1_6 && !NET +#if NETFRAMEWORK // See http://www.mono-project.com/docs/faq/technical/#how-to-detect-the-execution-platform switch ((int)Environment.OSVersion.Platform) { diff --git a/source/icu.net/Collation/Collator.cs b/source/icu.net/Collation/Collator.cs index 5f27ef08..8817e1e6 100644 --- a/source/icu.net/Collation/Collator.cs +++ b/source/icu.net/Collation/Collator.cs @@ -14,10 +14,7 @@ namespace Icu.Collation /// You use this class to build searching and sorting routines for natural /// language text. /// - public abstract class Collator : IComparer, IDisposable -#if FEATURE_ICLONEABLE - , ICloneable -#endif + public abstract class Collator : IComparer, IDisposable, ICloneable { /// /// Gets or sets the minimum strength that will be used in comparison @@ -194,18 +191,13 @@ static public SortKey CreateSortKey(string originalString, byte[] keyData, int k var options = CompareOptions.None; -#if NETSTANDARD1_6 - var sortKey = new SortKey(CultureInfo.InvariantCulture.Name, originalString, options, keyData); -#else var sortKey = CultureInfo.InvariantCulture.CompareInfo.GetSortKey(string.Empty, options); SetInternalOriginalStringField(sortKey, originalString); SetInternalKeyDataField(sortKey, keyData, keyDataLength); -#endif return sortKey; } -#if !NETSTANDARD1_6 private static void SetInternalKeyDataField(SortKey sortKey, byte[] keyData, int keyDataLength) { var keyDataCopy = new byte[keyDataLength]; @@ -275,7 +267,6 @@ private static bool IsRunningOnMono() { return Type.GetType("Mono.Runtime") != null; } -#endif /// /// Simple class to allow passing collation error info back to the caller of CheckRules. diff --git a/source/icu.net/Collation/RuleBasedCollator.cs b/source/icu.net/Collation/RuleBasedCollator.cs index 9d56158b..488c9cdf 100644 --- a/source/icu.net/Collation/RuleBasedCollator.cs +++ b/source/icu.net/Collation/RuleBasedCollator.cs @@ -3,12 +3,9 @@ using System; using System.Collections.Generic; using System.Runtime.InteropServices; -#if NETSTANDARD1_6 -using Icu; -#else using System.Globalization; using System.Runtime.ConstrainedExecution; -#endif + namespace Icu.Collation { @@ -30,9 +27,7 @@ public SafeRuleBasedCollatorHandle() : /// true if the handle is released successfully; otherwise, in the event of a catastrophic failure, false. /// In this case, it generates a ReleaseHandleFailed Managed Debugging Assistant. /// -#if !NETSTANDARD1_6 && !NET [ReliabilityContract(Consistency.WillNotCorruptState, Cer.Success)] -#endif protected override bool ReleaseHandle() { try diff --git a/source/icu.net/Locale.cs b/source/icu.net/Locale.cs index 916eeeb0..43e9309c 100644 --- a/source/icu.net/Locale.cs +++ b/source/icu.net/Locale.cs @@ -11,10 +11,7 @@ namespace Icu /// /// A Locale object represents a specific geographical, political, or cultural region. /// - public class Locale -#if FEATURE_ICLONEABLE - : ICloneable -#endif + public class Locale : ICloneable { /// /// Construct a default locale object, a Locale for the default locale ID diff --git a/source/icu.net/Platform.cs b/source/icu.net/Platform.cs index 9cd08a9e..240b3d48 100644 --- a/source/icu.net/Platform.cs +++ b/source/icu.net/Platform.cs @@ -29,19 +29,7 @@ internal static class Platform public const string x64 = nameof(x64); public const string x86 = nameof(x86); - public static string ProcessArchitecture - { - get { - -#if NET || NETSTANDARD - // Workaround described here since the API does not exist: - // https://github.com/dotnet/corefx/issues/999#issuecomment-75907756 - return IntPtr.Size == 4 ? x86 : x64; -#else - return Environment.Is64BitProcess ? x64 : x86; -#endif - } - } + public static string ProcessArchitecture => Environment.Is64BitProcess ? x64 : x86; public static OperatingSystemType OperatingSystem { diff --git a/source/icu.net/SafeEnumeratorHandle.cs b/source/icu.net/SafeEnumeratorHandle.cs index 5522de4b..f4489f08 100644 --- a/source/icu.net/SafeEnumeratorHandle.cs +++ b/source/icu.net/SafeEnumeratorHandle.cs @@ -2,10 +2,8 @@ // This software is licensed under the MIT license (http://opensource.org/licenses/MIT) using System; using System.Runtime.InteropServices; - -#if !NETSTANDARD1_6 using System.Runtime.ConstrainedExecution; -#endif + namespace Icu { @@ -23,9 +21,7 @@ public SafeEnumeratorHandle() : base(IntPtr.Zero, true) /// failure, false. In this case, it generates a ReleaseHandleFailed Managed Debugging /// Assistant. /// -#if !NETSTANDARD1_6 && !NET [ReliabilityContract(Consistency.WillNotCorruptState, Cer.Success)] -#endif protected override bool ReleaseHandle() { NativeMethods.uenum_close(handle); diff --git a/source/icu.net/SortKey.cs b/source/icu.net/SortKey.cs deleted file mode 100644 index 04a1f9dd..00000000 --- a/source/icu.net/SortKey.cs +++ /dev/null @@ -1,140 +0,0 @@ -// Copyright (c) 2013 SIL International -// This software is licensed under the MIT license (http://opensource.org/licenses/MIT) -using System; -using System.Globalization; - -namespace Icu -{ - /// - /// Replacement for System.Globalization.SortKey, which does not exist in - /// .NET Standard 1.5. Will be brought back in .NET Standard 2.0. - /// See https://github.com/dotnet/corefx/issues/10065 for more information. - /// - public class SortKey - { - private readonly string localeName; - private readonly CompareOptions options; - private readonly byte[] m_KeyData; - private readonly string m_String; - - internal SortKey(string localeName, string str, CompareOptions options, byte[] keyData) - { - var copy = new byte[keyData.Length]; - keyData.CopyTo(copy, 0); - - this.m_KeyData = copy; - this.localeName = localeName; - this.options = options; - this.m_String = str; - } - - /// - /// Gets the byte array representing the current System.Globalization.SortKey object. - /// - public virtual byte[] KeyData - { - get - { - var copy = new byte[m_KeyData.Length]; - m_KeyData.CopyTo(copy, 0); - - return copy; - } - } - - /// - /// Gets the original string used to create the current System.Globalization.SortKey - /// object. - /// - public virtual string OriginalString { get { return m_String; } } - - /// - /// Compares two sort keys. - /// - /// The first sort key to compare. - /// The second sort key to compare. - /// A signed integer that indicates the relationship between sortkey1 and sortkey2. - /// Value - /// Condition Less than zero: sortkey1 is less than sortkey2. - /// Zero : sortkey1 is equal to sortkey2. - /// Greater than zero : sortkey1 is greater than sortkey2. - /// - public static int Compare(SortKey sortkey1, SortKey sortkey2) - { - if (sortkey1 == null || sortkey2 == null) - { - throw new ArgumentNullException("A value is required to compare both values"); - } - - var keyData1 = sortkey1.KeyData; - var keyData2 = sortkey2.KeyData; - - if (keyData1.Length == 0) - { - return keyData2.Length == 0 ? 0 : -1; - } - - if (keyData2.Length == 0) - { - return keyData1.Length == 0 ? 0 : 1; - } - - var length = Math.Min(keyData1.Length, keyData2.Length); - - for (int i = 0; i < length; i++) - { - var value = keyData1[i]; - var value2 = keyData2[i]; - - if (value > value2) - { - return 1; - } - - if (value < value2) - { - return -1; - } - } - - return 0; - } - - /// - /// Determines whether the specified object is equal to the current - /// System.Globalization.SortKey object. - /// - /// The object to compare with the current - /// System.Globalization.SortKey object. - /// true if the value parameter is equal to the current - /// System.Globalization.SortKey object; otherwise, false. - public override bool Equals(object value) - { - var obj = value as SortKey; - - if (obj == null) - return false; - - return Compare(this, obj) == 0; - } - - /// - /// Serves as a hash function for the current System.Globalization.SortKey object - /// that is suitable for hashing algorithms and data structures such as a hash table. - /// - /// A hash code for the current System.Globalization.SortKey object. - public override int GetHashCode() - { - return CompareInfo.GetCompareInfo(localeName).GetHashCode(m_String, options); - } - - /// - /// Returns a string that represents the current System.Globalization.SortKey object. - /// - /// A string that represents the current System.Globalization.SortKey object. - public override string ToString() - { - return $"SortKey - {localeName}, {options}, {OriginalString}"; - } - } -} diff --git a/source/icu.net/icu.net.csproj b/source/icu.net/icu.net.csproj index d06d3517..cdedd08e 100644 --- a/source/icu.net/icu.net.csproj +++ b/source/icu.net/icu.net.csproj @@ -5,35 +5,17 @@ icu.net is a C# Wrapper around ICU4C README.md - - - $(DefineConstants);FEATURE_ICLONEABLE - - - - - - - - - - - - - - - From 33e10521861cf86c2b156786d9c70b8921716eda Mon Sep 17 00:00:00 2001 From: Kevin Hahn Date: Thu, 1 Aug 2024 08:25:47 +0700 Subject: [PATCH 2/3] wrap ReliabilityContract in conditional compilation on .NET Framework --- source/icu.net/Collation/RuleBasedCollator.cs | 2 ++ source/icu.net/SafeEnumeratorHandle.cs | 2 ++ 2 files changed, 4 insertions(+) diff --git a/source/icu.net/Collation/RuleBasedCollator.cs b/source/icu.net/Collation/RuleBasedCollator.cs index 488c9cdf..65ab6c17 100644 --- a/source/icu.net/Collation/RuleBasedCollator.cs +++ b/source/icu.net/Collation/RuleBasedCollator.cs @@ -27,7 +27,9 @@ public SafeRuleBasedCollatorHandle() : /// true if the handle is released successfully; otherwise, in the event of a catastrophic failure, false. /// In this case, it generates a ReleaseHandleFailed Managed Debugging Assistant. /// +#if NETFRAMEWORK [ReliabilityContract(Consistency.WillNotCorruptState, Cer.Success)] +#endif protected override bool ReleaseHandle() { try diff --git a/source/icu.net/SafeEnumeratorHandle.cs b/source/icu.net/SafeEnumeratorHandle.cs index f4489f08..a152e935 100644 --- a/source/icu.net/SafeEnumeratorHandle.cs +++ b/source/icu.net/SafeEnumeratorHandle.cs @@ -21,7 +21,9 @@ public SafeEnumeratorHandle() : base(IntPtr.Zero, true) /// failure, false. In this case, it generates a ReleaseHandleFailed Managed Debugging /// Assistant. /// +#if NETFRAMEWORK [ReliabilityContract(Consistency.WillNotCorruptState, Cer.Success)] +#endif protected override bool ReleaseHandle() { NativeMethods.uenum_close(handle); From 876d228a14268d1ffd4e5a2ed215b2426aecd64b Mon Sep 17 00:00:00 2001 From: Kevin Hahn Date: Thu, 1 Aug 2024 08:31:33 +0700 Subject: [PATCH 3/3] update changelog --- CHANGELOG.md | 14 ++++++++++++++ 1 file changed, 14 insertions(+) diff --git a/CHANGELOG.md b/CHANGELOG.md index c5f52777..e15e6ff7 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -16,6 +16,20 @@ and this project adheres to [Semantic Versioning](http://semver.org/). ## [Unreleased] +### Breaking + +- Removed support for [netstandard1.6](https://learn.microsoft.com/en-us/dotnet/standard/net-standard?tabs=net-standard-1-6#select-net-standard-version) +- Removed Icu.SortKey class which was only in the netstandard1.6 version of the dll + +### Added + +- Added support for netstandard2.0 + +### Fixed + +- Fixed a bug when using a library compiled against icu-dotnet netstandard1.6, when your project referenced a different version of icu-dotnet + + ## [2.10.0] - 2024-06-17 ### Added