From 40978ba56697503256b388597c216f608b76b74e Mon Sep 17 00:00:00 2001 From: Davoud Date: Wed, 14 Jun 2023 13:36:22 -0700 Subject: [PATCH 1/2] Improve TdsParser --- .../src/Microsoft/Data/SqlClient/TdsParser.cs | 177 ++++++++-------- .../src/Microsoft/Data/SqlClient/TdsParser.cs | 198 ++++++++++-------- 2 files changed, 202 insertions(+), 173 deletions(-) diff --git a/src/Microsoft.Data.SqlClient/netcore/src/Microsoft/Data/SqlClient/TdsParser.cs b/src/Microsoft.Data.SqlClient/netcore/src/Microsoft/Data/SqlClient/TdsParser.cs index c83587ab4c..32a559a855 100644 --- a/src/Microsoft.Data.SqlClient/netcore/src/Microsoft/Data/SqlClient/TdsParser.cs +++ b/src/Microsoft.Data.SqlClient/netcore/src/Microsoft/Data/SqlClient/TdsParser.cs @@ -8159,43 +8159,54 @@ internal void TdsLogin(SqlLogin rec, TdsEnums.FeatureExtension requestedFeatures } int feOffset = length; + // calculate and reserve the required bytes for the featureEx + length = ApplyFeatureExData(requestedFeatures, recoverySessionData, fedAuthFeatureExtensionData, useFeatureExt, length); + + WriteLoginData(rec, + requestedFeatures, + recoverySessionData, + fedAuthFeatureExtensionData, + encrypt, + encryptedPassword, + encryptedChangePassword, + encryptedPasswordLengthInBytes, + encryptedChangePasswordLengthInBytes, + useFeatureExt, + userName, + length, + feOffset, + clientInterfaceName, + outSSPIBuff, + outSSPILength); - if (useFeatureExt) + if (rentedSSPIBuff != null) { - if ((requestedFeatures & TdsEnums.FeatureExtension.SessionRecovery) != 0) - { - length += WriteSessionRecoveryFeatureRequest(recoverySessionData, false); - } - if ((requestedFeatures & TdsEnums.FeatureExtension.FedAuth) != 0) - { - Debug.Assert(fedAuthFeatureExtensionData != null, "fedAuthFeatureExtensionData should not null."); - length += WriteFedAuthFeatureRequest(fedAuthFeatureExtensionData, write: false); - } - if ((requestedFeatures & TdsEnums.FeatureExtension.Tce) != 0) - { - length += WriteTceFeatureRequest(false); - } - if ((requestedFeatures & TdsEnums.FeatureExtension.GlobalTransactions) != 0) - { - length += WriteGlobalTransactionsFeatureRequest(false); - } - if ((requestedFeatures & TdsEnums.FeatureExtension.DataClassification) != 0) - { - length += WriteDataClassificationFeatureRequest(false); - } - if ((requestedFeatures & TdsEnums.FeatureExtension.UTF8Support) != 0) - { - length += WriteUTF8SupportFeatureRequest(false); - } - - if ((requestedFeatures & TdsEnums.FeatureExtension.SQLDNSCaching) != 0) - { - length += WriteSQLDNSCachingFeatureRequest(false); - } - - length++; // for terminator + ArrayPool.Shared.Return(rentedSSPIBuff, clearArray: true); } + _physicalStateObj.WritePacket(TdsEnums.HARDFLUSH); + _physicalStateObj.ResetSecurePasswordsInformation(); + _physicalStateObj.HasPendingData = true; + _physicalStateObj._messageStatus = 0; + }// tdsLogin + + private void WriteLoginData(SqlLogin rec, + TdsEnums.FeatureExtension requestedFeatures, + SessionData recoverySessionData, + FederatedAuthenticationFeatureExtensionData fedAuthFeatureExtensionData, + SqlConnectionEncryptOption encrypt, + byte[] encryptedPassword, + byte[] encryptedChangePassword, + int encryptedPasswordLengthInBytes, + int encryptedChangePasswordLengthInBytes, + bool useFeatureExt, + string userName, + int length, + int featureExOffset, + string clientInterfaceName, + byte[] outSSPIBuff, + uint outSSPILength) + { try { WriteInt(length, _physicalStateObj); @@ -8409,7 +8420,7 @@ internal void TdsLogin(SqlLogin rec, TdsEnums.FeatureExtension requestedFeatures SqlClientEventSource.Log.TryTraceEvent(" Sending federated authentication feature request"); } - WriteInt(feOffset, _physicalStateObj); + WriteInt(featureExOffset, _physicalStateObj); } WriteString(clientInterfaceName, _physicalStateObj); @@ -8433,42 +8444,7 @@ internal void TdsLogin(SqlLogin rec, TdsEnums.FeatureExtension requestedFeatures } } - if (useFeatureExt) - { - if ((requestedFeatures & TdsEnums.FeatureExtension.SessionRecovery) != 0) - { - WriteSessionRecoveryFeatureRequest(recoverySessionData, true); - } - if ((requestedFeatures & TdsEnums.FeatureExtension.FedAuth) != 0) - { - SqlClientEventSource.Log.TryTraceEvent(" Sending federated authentication feature request"); - Debug.Assert(fedAuthFeatureExtensionData != null, "fedAuthFeatureExtensionData should not null."); - WriteFedAuthFeatureRequest(fedAuthFeatureExtensionData, write: true); - } - if ((requestedFeatures & TdsEnums.FeatureExtension.Tce) != 0) - { - WriteTceFeatureRequest(true); - } - if ((requestedFeatures & TdsEnums.FeatureExtension.GlobalTransactions) != 0) - { - WriteGlobalTransactionsFeatureRequest(true); - } - if ((requestedFeatures & TdsEnums.FeatureExtension.DataClassification) != 0) - { - WriteDataClassificationFeatureRequest(true); - } - if ((requestedFeatures & TdsEnums.FeatureExtension.UTF8Support) != 0) - { - WriteUTF8SupportFeatureRequest(true); - } - - if ((requestedFeatures & TdsEnums.FeatureExtension.SQLDNSCaching) != 0) - { - WriteSQLDNSCachingFeatureRequest(true); - } - - _physicalStateObj.WriteByte(0xFF); // terminator - } + ApplyFeatureExData(requestedFeatures, recoverySessionData, fedAuthFeatureExtensionData, useFeatureExt, length, true); } catch (Exception e) { @@ -8481,17 +8457,58 @@ internal void TdsLogin(SqlLogin rec, TdsEnums.FeatureExtension requestedFeatures throw; } + } - if (rentedSSPIBuff != null) + private int ApplyFeatureExData(TdsEnums.FeatureExtension requestedFeatures, + SessionData recoverySessionData, + FederatedAuthenticationFeatureExtensionData fedAuthFeatureExtensionData, + bool useFeatureExt, + int length, + bool write = false) + { + if (useFeatureExt) { - ArrayPool.Shared.Return(rentedSSPIBuff, clearArray: true); + if ((requestedFeatures & TdsEnums.FeatureExtension.SessionRecovery) != 0) + { + length += WriteSessionRecoveryFeatureRequest(recoverySessionData, write); + } + if ((requestedFeatures & TdsEnums.FeatureExtension.FedAuth) != 0) + { + SqlClientEventSource.Log.TryTraceEvent(" Sending federated authentication feature request & wirte = {0}", write); + Debug.Assert(fedAuthFeatureExtensionData != null, "fedAuthFeatureExtensionData should not null."); + length += WriteFedAuthFeatureRequest(fedAuthFeatureExtensionData, write: write); + } + if ((requestedFeatures & TdsEnums.FeatureExtension.Tce) != 0) + { + length += WriteTceFeatureRequest(write); + } + if ((requestedFeatures & TdsEnums.FeatureExtension.GlobalTransactions) != 0) + { + length += WriteGlobalTransactionsFeatureRequest(write); + } + if ((requestedFeatures & TdsEnums.FeatureExtension.DataClassification) != 0) + { + length += WriteDataClassificationFeatureRequest(write); + } + if ((requestedFeatures & TdsEnums.FeatureExtension.UTF8Support) != 0) + { + length += WriteUTF8SupportFeatureRequest(write); + } + + if ((requestedFeatures & TdsEnums.FeatureExtension.SQLDNSCaching) != 0) + { + length += WriteSQLDNSCachingFeatureRequest(write); + } + + length++; // for terminator + if (write) + { + _physicalStateObj.WriteByte(0xFF); // terminator + } } - _physicalStateObj.WritePacket(TdsEnums.HARDFLUSH); - _physicalStateObj.ResetSecurePasswordsInformation(); - _physicalStateObj.HasPendingData = true; - _physicalStateObj._messageStatus = 0; - }// tdsLogin + return length; + } /// /// Send the access token to the server. @@ -8524,12 +8541,6 @@ internal void SendFedAuthToken(SqlFedAuthToken fedAuthToken) } private void SSPIData(byte[] receivedBuff, uint receivedLength, ref byte[] sendBuff, ref uint sendLength) - { - SNISSPIData(receivedBuff, receivedLength, ref sendBuff, ref sendLength); - } - - - private void SNISSPIData(byte[] receivedBuff, uint receivedLength, ref byte[] sendBuff, ref uint sendLength) { if (TdsParserStateObjectFactory.UseManagedSNI) { diff --git a/src/Microsoft.Data.SqlClient/netfx/src/Microsoft/Data/SqlClient/TdsParser.cs b/src/Microsoft.Data.SqlClient/netfx/src/Microsoft/Data/SqlClient/TdsParser.cs index c407e1c6e9..d340be58c9 100644 --- a/src/Microsoft.Data.SqlClient/netfx/src/Microsoft/Data/SqlClient/TdsParser.cs +++ b/src/Microsoft.Data.SqlClient/netfx/src/Microsoft/Data/SqlClient/TdsParser.cs @@ -8992,7 +8992,7 @@ internal void TdsLogin(SqlLogin rec, Debug.Assert(SniContext.Snix_Login == _physicalStateObj.SniContext, $"Unexpected SniContext. Expecting Snix_Login, actual value is '{_physicalStateObj.SniContext}'"); _physicalStateObj.SniContext = SniContext.Snix_LoginSspi; SSPIData(null, 0, outSSPIBuff, ref outSSPILength); - if (outSSPILength > Int32.MaxValue) + if (outSSPILength > int.MaxValue) { throw SQL.InvalidSSPIPacketSize(); // SqlBu 332503 } @@ -9000,56 +9000,74 @@ internal void TdsLogin(SqlLogin rec, checked { - length += (Int32)outSSPILength; + length += (int)outSSPILength; } } } int feOffset = length; + // calculate and reserve the required bytes for the featureEx + length = ApplyFeatureExData(requestedFeatures, recoverySessionData, fedAuthFeatureExtensionData, useFeatureExt, length); + + WriteLoginData(rec, + requestedFeatures, + recoverySessionData, + fedAuthFeatureExtensionData, + encrypt, + encryptedPassword, + encryptedChangePassword, + encryptedPasswordLengthInBytes, + encryptedChangePasswordLengthInBytes, + useFeatureExt, + userName, + length, + feOffset, + clientInterfaceName, + outSSPIBuff, + outSSPILength); - if (useFeatureExt) + _physicalStateObj.WritePacket(TdsEnums.HARDFLUSH); + _physicalStateObj.ResetSecurePasswordsInfomation(); // Password information is needed only from Login process; done with writing login packet and should clear information + _physicalStateObj._pendingData = true; + _physicalStateObj._messageStatus = 0; + + // Remvove CTAIP Provider after login record is sent. + // + if (originalNetworkAddressInfo != null) { - checked + UInt32 error = SNINativeMethodWrapper.SNIRemoveProvider(_physicalStateObj.Handle, SNINativeMethodWrapper.ProviderEnum.CTAIP_PROV); + if (error != TdsEnums.SNI_SUCCESS) { - if ((requestedFeatures & TdsEnums.FeatureExtension.SessionRecovery) != 0) - { - length += WriteSessionRecoveryFeatureRequest(recoverySessionData, false); - }; - if ((requestedFeatures & TdsEnums.FeatureExtension.FedAuth) != 0) - { - Debug.Assert(fedAuthFeatureExtensionData != null, "fedAuthFeatureExtensionData should not null."); - length += WriteFedAuthFeatureRequest(fedAuthFeatureExtensionData, write: false); - } - if ((requestedFeatures & TdsEnums.FeatureExtension.Tce) != 0) - { - length += WriteTceFeatureRequest(false); - } - if ((requestedFeatures & TdsEnums.FeatureExtension.GlobalTransactions) != 0) - { - length += WriteGlobalTransactionsFeatureRequest(false); - } - if ((requestedFeatures & TdsEnums.FeatureExtension.AzureSQLSupport) != 0) - { - length += WriteAzureSQLSupportFeatureRequest(false); - } - if ((requestedFeatures & TdsEnums.FeatureExtension.DataClassification) != 0) - { - length += WriteDataClassificationFeatureRequest(false); - } - if ((requestedFeatures & TdsEnums.FeatureExtension.UTF8Support) != 0) - { - length += WriteUTF8SupportFeatureRequest(false); - } - - if ((requestedFeatures & TdsEnums.FeatureExtension.SQLDNSCaching) != 0) - { - length += WriteSQLDNSCachingFeatureRequest(false); - } + _physicalStateObj.AddError(ProcessSNIError(_physicalStateObj)); + ThrowExceptionAndWarning(_physicalStateObj); + } - length++; // for terminator + try + { } // EmptyTry/Finally to avoid FXCop violation + finally + { + _physicalStateObj.ClearAllWritePackets(); } } + }// tdsLogin + private void WriteLoginData(SqlLogin rec, + TdsEnums.FeatureExtension requestedFeatures, + SessionData recoverySessionData, + FederatedAuthenticationFeatureExtensionData fedAuthFeatureExtensionData, + SqlConnectionEncryptOption encrypt, + byte[] encryptedPassword, + byte[] encryptedChangePassword, + int encryptedPasswordLengthInBytes, + int encryptedChangePasswordLengthInBytes, + bool useFeatureExt, + string userName, + int length, + int featureExOffset, + string clientInterfaceName, + byte[] outSSPIBuff, + uint outSSPILength) + { try { WriteInt(length, _physicalStateObj); @@ -9265,7 +9283,12 @@ internal void TdsLogin(SqlLogin rec, // write ibFeatureExtLong if (useFeatureExt) { - WriteInt(feOffset, _physicalStateObj); + if ((requestedFeatures & TdsEnums.FeatureExtension.FedAuth) != 0) + { + SqlClientEventSource.Log.TryTraceEvent(" Sending federated authentication feature request"); + } + + WriteInt(featureExOffset, _physicalStateObj); } WriteString(clientInterfaceName, _physicalStateObj); @@ -9292,84 +9315,79 @@ internal void TdsLogin(SqlLogin rec, } } - if (useFeatureExt) + ApplyFeatureExData(requestedFeatures, recoverySessionData, fedAuthFeatureExtensionData, useFeatureExt, length, true); + } // try + catch (Exception e) + { + // UNDONE - should not be catching all exceptions!!! + if (ADP.IsCatchableExceptionType(e)) + { + // be sure to wipe out our buffer if we started sending stuff + _physicalStateObj.ResetPacketCounters(); + _physicalStateObj.ResetBuffer(); + } + + throw; + } + } + + private int ApplyFeatureExData(TdsEnums.FeatureExtension requestedFeatures, + SessionData recoverySessionData, + FederatedAuthenticationFeatureExtensionData fedAuthFeatureExtensionData, + bool useFeatureExt, + int length, + bool write = false) + { + if (useFeatureExt) + { + checked { if ((requestedFeatures & TdsEnums.FeatureExtension.SessionRecovery) != 0) { - WriteSessionRecoveryFeatureRequest(recoverySessionData, true); + length += WriteSessionRecoveryFeatureRequest(recoverySessionData, write); }; if ((requestedFeatures & TdsEnums.FeatureExtension.FedAuth) != 0) { - SqlClientEventSource.Log.TryTraceEvent(" Sending federated authentication feature request"); + SqlClientEventSource.Log.TryTraceEvent(" Sending federated authentication feature request & wirte = {0}", write); Debug.Assert(fedAuthFeatureExtensionData != null, "fedAuthFeatureExtensionData should not null."); - WriteFedAuthFeatureRequest(fedAuthFeatureExtensionData, write: true); - }; + length += WriteFedAuthFeatureRequest(fedAuthFeatureExtensionData, write: write); + } if ((requestedFeatures & TdsEnums.FeatureExtension.Tce) != 0) { - WriteTceFeatureRequest(true); - }; + length += WriteTceFeatureRequest(write); + } if ((requestedFeatures & TdsEnums.FeatureExtension.GlobalTransactions) != 0) { - WriteGlobalTransactionsFeatureRequest(true); - }; + length += WriteGlobalTransactionsFeatureRequest(write); + } if ((requestedFeatures & TdsEnums.FeatureExtension.AzureSQLSupport) != 0) { - WriteAzureSQLSupportFeatureRequest(true); + length += WriteAzureSQLSupportFeatureRequest(write); } if ((requestedFeatures & TdsEnums.FeatureExtension.DataClassification) != 0) { - WriteDataClassificationFeatureRequest(true); + length += WriteDataClassificationFeatureRequest(write); } if ((requestedFeatures & TdsEnums.FeatureExtension.UTF8Support) != 0) { - WriteUTF8SupportFeatureRequest(true); + length += WriteUTF8SupportFeatureRequest(write); } if ((requestedFeatures & TdsEnums.FeatureExtension.SQLDNSCaching) != 0) { - WriteSQLDNSCachingFeatureRequest(true); + length += WriteSQLDNSCachingFeatureRequest(write); } - _physicalStateObj.WriteByte(0xFF); // terminator - } - } // try - catch (Exception e) - { - // UNDONE - should not be catching all exceptions!!! - if (ADP.IsCatchableExceptionType(e)) - { - // be sure to wipe out our buffer if we started sending stuff - _physicalStateObj.ResetPacketCounters(); - _physicalStateObj.ResetBuffer(); + length++; // for terminator + if (write) + { + _physicalStateObj.WriteByte(0xFF); // terminator + } } - - throw; } - _physicalStateObj.WritePacket(TdsEnums.HARDFLUSH); - _physicalStateObj.ResetSecurePasswordsInfomation(); // Password information is needed only from Login process; done with writing login packet and should clear information - _physicalStateObj._pendingData = true; - _physicalStateObj._messageStatus = 0; - - // Remvove CTAIP Provider after login record is sent. - // - if (originalNetworkAddressInfo != null) - { - UInt32 error = SNINativeMethodWrapper.SNIRemoveProvider(_physicalStateObj.Handle, SNINativeMethodWrapper.ProviderEnum.CTAIP_PROV); - if (error != TdsEnums.SNI_SUCCESS) - { - _physicalStateObj.AddError(ProcessSNIError(_physicalStateObj)); - ThrowExceptionAndWarning(_physicalStateObj); - } - - try - { } // EmptyTry/Finally to avoid FXCop violation - finally - { - _physicalStateObj.ClearAllWritePackets(); - } - } - }// tdsLogin + return length; + } /// /// Send the access token to the server. From bafc8ae7da8cdd790dc2a261b3038ef0d48397fe Mon Sep 17 00:00:00 2001 From: Davoud Date: Fri, 23 Jun 2023 11:06:32 -0700 Subject: [PATCH 2/2] cleanup --- .../netcore/src/Common/Common.Tests.sln | 25 ----- .../Common/src/System/PasteArguments.Unix.cs | 28 ------ .../src/System/PasteArguments.Windows.cs | 66 ------------- .../src/Common/src/System/PasteArguments.cs | 99 ------------------- .../Collections/DictionaryExtensions.cs | 20 ---- ....Data.SqlClient.ManualTesting.Tests.csproj | 4 - .../SQL/Common/InternalConnectionWrapper.cs | 16 +++ 7 files changed, 16 insertions(+), 242 deletions(-) delete mode 100644 src/Microsoft.Data.SqlClient/netcore/src/Common/Common.Tests.sln delete mode 100644 src/Microsoft.Data.SqlClient/netcore/src/Common/src/System/PasteArguments.Unix.cs delete mode 100644 src/Microsoft.Data.SqlClient/netcore/src/Common/src/System/PasteArguments.Windows.cs delete mode 100644 src/Microsoft.Data.SqlClient/netcore/src/Common/src/System/PasteArguments.cs delete mode 100644 src/Microsoft.Data.SqlClient/netcore/src/Common/tests/System/Collections/DictionaryExtensions.cs diff --git a/src/Microsoft.Data.SqlClient/netcore/src/Common/Common.Tests.sln b/src/Microsoft.Data.SqlClient/netcore/src/Common/Common.Tests.sln deleted file mode 100644 index febf1b4227..0000000000 --- a/src/Microsoft.Data.SqlClient/netcore/src/Common/Common.Tests.sln +++ /dev/null @@ -1,25 +0,0 @@ - -Microsoft Visual Studio Solution File, Format Version 12.00 -# Visual Studio 15 -VisualStudioVersion = 15.0.26430.13 -MinimumVisualStudioVersion = 10.0.40219.1 -Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "Common.Tests", "tests\Common.Tests.csproj", "{C72FD34C-539A-4447-9796-62A229571199}" -EndProject -Global - GlobalSection(SolutionConfigurationPlatforms) = preSolution - Debug|Any CPU = Debug|Any CPU - Release|Any CPU = Release|Any CPU - EndGlobalSection - GlobalSection(ProjectConfigurationPlatforms) = postSolution - {C72FD34C-539A-4447-9796-62A229571199}.Debug|Any CPU.ActiveCfg = netcoreapp-Windows_NT-Debug|Any CPU - {C72FD34C-539A-4447-9796-62A229571199}.Debug|Any CPU.Build.0 = netcoreapp-Windows_NT-Debug|Any CPU - {C72FD34C-539A-4447-9796-62A229571199}.Release|Any CPU.ActiveCfg = netcoreapp-Windows_NT-Release|Any CPU - {C72FD34C-539A-4447-9796-62A229571199}.Release|Any CPU.Build.0 = netcoreapp-Windows_NT-Release|Any CPU - EndGlobalSection - GlobalSection(SolutionProperties) = preSolution - HideSolutionNode = FALSE - EndGlobalSection - GlobalSection(ExtensibilityGlobals) = postSolution - SolutionGuid = {5E554AE7-CBC2-4C34-9FEA-1A6250CE5D3F} - EndGlobalSection -EndGlobal diff --git a/src/Microsoft.Data.SqlClient/netcore/src/Common/src/System/PasteArguments.Unix.cs b/src/Microsoft.Data.SqlClient/netcore/src/Common/src/System/PasteArguments.Unix.cs deleted file mode 100644 index 1a4d92850f..0000000000 --- a/src/Microsoft.Data.SqlClient/netcore/src/Common/src/System/PasteArguments.Unix.cs +++ /dev/null @@ -1,28 +0,0 @@ -// Licensed to the .NET Foundation under one or more agreements. -// The .NET Foundation licenses this file to you under the MIT license. -// See the LICENSE file in the project root for more information. - -using System.Collections.Generic; -using System.Runtime.CompilerServices; -using System.Text; - -namespace System -{ - internal static partial class PasteArguments - { - /// - /// Repastes a set of arguments into a linear string that parses back into the originals under pre- or post-2008 VC parsing rules. - /// On Unix: the rules for parsing the executable name (argv[0]) are ignored. - /// - internal static string Paste(IEnumerable arguments, bool pasteFirstArgumentUsingArgV0Rules) - { - var stringBuilder = new StringBuilder(); - foreach (string argument in arguments) - { - AppendArgument(stringBuilder, argument); - } - return stringBuilder.ToString(); - } - - } -} diff --git a/src/Microsoft.Data.SqlClient/netcore/src/Common/src/System/PasteArguments.Windows.cs b/src/Microsoft.Data.SqlClient/netcore/src/Common/src/System/PasteArguments.Windows.cs deleted file mode 100644 index 1e8cfdbaf7..0000000000 --- a/src/Microsoft.Data.SqlClient/netcore/src/Common/src/System/PasteArguments.Windows.cs +++ /dev/null @@ -1,66 +0,0 @@ -// Licensed to the .NET Foundation under one or more agreements. -// The .NET Foundation licenses this file to you under the MIT license. -// See the LICENSE file in the project root for more information. - -using System.Collections.Generic; -using System.Runtime.CompilerServices; -using System.Text; - -namespace System -{ - internal static partial class PasteArguments - { - /// - /// Repastes a set of arguments into a linear string that parses back into the originals under pre- or post-2008 VC parsing rules. - /// The rules for parsing the executable name (argv[0]) are special, so you must indicate whether the first argument actually is argv[0]. - /// - internal static string Paste(IEnumerable arguments, bool pasteFirstArgumentUsingArgV0Rules) - { - var stringBuilder = new StringBuilder(); - - foreach (string argument in arguments) - { - if (pasteFirstArgumentUsingArgV0Rules) - { - pasteFirstArgumentUsingArgV0Rules = false; - - // Special rules for argv[0] - // - Backslash is a normal character. - // - Quotes used to include whitespace characters. - // - Parsing ends at first whitespace outside quoted region. - // - No way to get a literal quote past the parser. - - bool hasWhitespace = false; - foreach (char c in argument) - { - if (c == Quote) - { - throw new ApplicationException("The argv[0] argument cannot include a double quote."); - } - if (char.IsWhiteSpace(c)) - { - hasWhitespace = true; - } - } - if (argument.Length == 0 || hasWhitespace) - { - stringBuilder.Append(Quote); - stringBuilder.Append(argument); - stringBuilder.Append(Quote); - } - else - { - stringBuilder.Append(argument); - } - } - else - { - AppendArgument(stringBuilder, argument); - } - } - - return stringBuilder.ToString(); - } - - } -} diff --git a/src/Microsoft.Data.SqlClient/netcore/src/Common/src/System/PasteArguments.cs b/src/Microsoft.Data.SqlClient/netcore/src/Common/src/System/PasteArguments.cs deleted file mode 100644 index c088fd4eb7..0000000000 --- a/src/Microsoft.Data.SqlClient/netcore/src/Common/src/System/PasteArguments.cs +++ /dev/null @@ -1,99 +0,0 @@ -// Licensed to the .NET Foundation under one or more agreements. -// The .NET Foundation licenses this file to you under the MIT license. -// See the LICENSE file in the project root for more information. - -using System.Text; - -namespace System -{ - internal static partial class PasteArguments - { - internal static void AppendArgument(StringBuilder stringBuilder, string argument) - { - if (stringBuilder.Length != 0) - { - stringBuilder.Append(' '); - } - - // Parsing rules for non-argv[0] arguments: - // - Backslash is a normal character except followed by a quote. - // - 2N backslashes followed by a quote ==> N literal backslashes followed by unescaped quote - // - 2N+1 backslashes followed by a quote ==> N literal backslashes followed by a literal quote - // - Parsing stops at first whitespace outside of quoted region. - // - (post 2008 rule): A closing quote followed by another quote ==> literal quote, and parsing remains in quoting mode. - if (argument.Length != 0 && ContainsNoWhitespaceOrQuotes(argument)) - { - // Simple case - no quoting or changes needed. - stringBuilder.Append(argument); - } - else - { - stringBuilder.Append(Quote); - int idx = 0; - while (idx < argument.Length) - { - char c = argument[idx++]; - if (c == Backslash) - { - int numBackSlash = 1; - while (idx < argument.Length && argument[idx] == Backslash) - { - idx++; - numBackSlash++; - } - - if (idx == argument.Length) - { - // We'll emit an end quote after this so must double the number of backslashes. - stringBuilder.Append(Backslash, numBackSlash * 2); - } - else if (argument[idx] == Quote) - { - // Backslashes will be followed by a quote. Must double the number of backslashes. - stringBuilder.Append(Backslash, numBackSlash * 2 + 1); - stringBuilder.Append(Quote); - idx++; - } - else - { - // Backslash will not be followed by a quote, so emit as normal characters. - stringBuilder.Append(Backslash, numBackSlash); - } - - continue; - } - - if (c == Quote) - { - // Escape the quote so it appears as a literal. This also guarantees that we won't end up generating a closing quote followed - // by another quote (which parses differently pre-2008 vs. post-2008.) - stringBuilder.Append(Backslash); - stringBuilder.Append(Quote); - continue; - } - - stringBuilder.Append(c); - } - - stringBuilder.Append(Quote); - } - } - - private static bool ContainsNoWhitespaceOrQuotes(string s) - { - for (int i = 0; i < s.Length; i++) - { - char c = s[i]; - if (char.IsWhiteSpace(c) || c == Quote) - { - return false; - } - } - - return true; - } - - private const char Quote = '\"'; - private const char Backslash = '\\'; - } -} diff --git a/src/Microsoft.Data.SqlClient/netcore/src/Common/tests/System/Collections/DictionaryExtensions.cs b/src/Microsoft.Data.SqlClient/netcore/src/Common/tests/System/Collections/DictionaryExtensions.cs deleted file mode 100644 index 8840a7ed22..0000000000 --- a/src/Microsoft.Data.SqlClient/netcore/src/Common/tests/System/Collections/DictionaryExtensions.cs +++ /dev/null @@ -1,20 +0,0 @@ -// Licensed to the .NET Foundation under one or more agreements. -// The .NET Foundation licenses this file to you under the MIT license. -// See the LICENSE file in the project root for more information. - -namespace System.Collections.Generic -{ - internal static class DictionaryExtensions - { - public static bool TryAdd(this IDictionary dict, TKey key, TValue value) - { - if (!dict.ContainsKey(key)) - { - dict.Add(key, value); - return true; - } - - return false; - } - } -} diff --git a/src/Microsoft.Data.SqlClient/tests/ManualTests/Microsoft.Data.SqlClient.ManualTesting.Tests.csproj b/src/Microsoft.Data.SqlClient/tests/ManualTests/Microsoft.Data.SqlClient.ManualTesting.Tests.csproj index 84d74244a5..c7187391ac 100644 --- a/src/Microsoft.Data.SqlClient/tests/ManualTests/Microsoft.Data.SqlClient.ManualTesting.Tests.csproj +++ b/src/Microsoft.Data.SqlClient/tests/ManualTests/Microsoft.Data.SqlClient.ManualTesting.Tests.csproj @@ -10,7 +10,6 @@ win-$(Platform) $(DefineConstants);NETCOREAPP $(DefineConstants);NETFRAMEWORK - $(DefineConstants);NET50_OR_LATER $(ObjFolder)$(Configuration).$(Platform).$(AssemblyName) $(BinFolder)$(Configuration).$(Platform).$(AssemblyName) @@ -278,9 +277,6 @@ - - Common\System\Collections\DictionaryExtensions.cs - diff --git a/src/Microsoft.Data.SqlClient/tests/ManualTests/SQL/Common/InternalConnectionWrapper.cs b/src/Microsoft.Data.SqlClient/tests/ManualTests/SQL/Common/InternalConnectionWrapper.cs index 38c62d69e9..7a49860f45 100644 --- a/src/Microsoft.Data.SqlClient/tests/ManualTests/SQL/Common/InternalConnectionWrapper.cs +++ b/src/Microsoft.Data.SqlClient/tests/ManualTests/SQL/Common/InternalConnectionWrapper.cs @@ -10,6 +10,22 @@ namespace Microsoft.Data.SqlClient.ManualTesting.Tests { +#if NETFRAMEWORK + internal static class DictionaryExtensions + { + public static bool TryAdd(this IDictionary dict, TKey key, TValue value) + { + if (!dict.ContainsKey(key)) + { + dict.Add(key, value); + return true; + } + + return false; + } + } +#endif + public class InternalConnectionWrapper { private static Dictionary s_killByTSqlConnectionStrings = new Dictionary();