Code:
/ Net / Net / 3.5.50727.3053 / DEVDIV / depot / DevDiv / releases / whidbey / netfxsp / ndp / fx / src / DataOracleClient / System / Data / OracleClient / OracleString.cs / 5 / OracleString.cs
//------------------------------------------------------------------------------ //// Copyright (c) Microsoft Corporation. All rights reserved. // //[....] //----------------------------------------------------------------------------- namespace System.Data.OracleClient { using System; using System.Data.SqlTypes; using System.Data.Common; using System.Diagnostics; using System.Globalization; using System.Runtime.CompilerServices; using System.Runtime.InteropServices; using System.Text; //--------------------------------------------------------------------- // OracleString // // This class implements support for Oracle's CHAR, VARCHAR, NCHAR, // NVARCHAR and LONG internal data types. While some of these data // types may be retrieved as multi-byte strings from Oracle there is // no particular benefit to leaving them as multi-byte because we // would be forced to re-implement the entire String class for // multi-byte strings to avoid constant conversions. // // For that reason, this type class should simply be a wrapper class // around the CLS String data type, with the appropriate internal // constructors to allow data values to be set from the data reader. // [StructLayout(LayoutKind.Sequential)] public struct OracleString : IComparable, INullable { private string _value; public static readonly OracleString Empty = new OracleString(false); public static readonly OracleString Null = new OracleString(true); // Construct from nothing -- the value will be null or empty private OracleString(bool isNull) { _value = (isNull) ? null : String.Empty; } public OracleString (string s) { _value = s; } // (internal) construct from a row/parameter binding internal OracleString( NativeBuffer buffer, int valueOffset, int lengthOffset, MetaType metaType, OracleConnection connection, // See MDAC #78258 for reason. bool boundAsUCS2, // See MDAC #78258 for reason. bool outputParameterBinding) { // oracle has inconsistent behavior for output parameters. _value = MarshalToString(buffer, valueOffset, lengthOffset, metaType, connection, boundAsUCS2, outputParameterBinding); } public bool IsNull { get { return (null == _value); } } public int Length { get { if (IsNull) { throw ADP.DataIsNull(); } return _value.Length; } } public string Value { get { if (IsNull) { throw ADP.DataIsNull(); } return _value; } } public char this[int index] { get { if (IsNull) { throw ADP.DataIsNull(); } return _value[index]; } } public int CompareTo (object obj) { if (obj.GetType() == typeof(OracleString)) { OracleString s = (OracleString)obj; // If both values are Null, consider them equal. // Otherwise, Null is less than anything. if (IsNull) { return s.IsNull ? 0 : -1; } if (s.IsNull) { return 1; } // Neither value is null, do the comparison. return CultureInfo.CurrentCulture.CompareInfo.Compare(_value, s._value); } throw ADP.WrongType(obj.GetType(), typeof(OracleString)); } public override bool Equals(object value) { if (value is OracleString) { return (this == (OracleString)value).Value; } else { return false; } } static internal int GetChars( NativeBuffer buffer, int valueOffset, int lengthOffset, MetaType metaType, OracleConnection connection, // See MDAC #78258 for reason. bool boundAsUCS2, // See MDAC #78258 for reason. int sourceOffset, char[] destinationBuffer, int destinationOffset, int charCount) { // This static method allows the GetChars type getter to do it's job // without having to marshal the entire value into managed space. bool mustRelease = false; RuntimeHelpers.PrepareConstrainedRegions(); try { buffer.DangerousAddRef(ref mustRelease); if (boundAsUCS2) { if (!metaType.IsLong) { //SQLBU:440832 -- using DangerousGetDataPtrWithBaseOffset instead of DangerousGetDataPtr Marshal.Copy(buffer.DangerousGetDataPtrWithBaseOffset(valueOffset + (ADP.CharSize * sourceOffset)), destinationBuffer, destinationOffset, charCount ); } else { // Long values are bound out-of-line, which means we have // to do this the hard way... NativeBuffer_LongColumnData.CopyOutOfLineChars(buffer.ReadIntPtr(valueOffset), sourceOffset, destinationBuffer, destinationOffset, charCount); } } else { // In the odd case that we don't have a Unicode value (see MDAC #78258 // for the reason) we have to do this the hard way -- get the full value, // then copy the data... string value = MarshalToString(buffer, valueOffset, lengthOffset, metaType, connection, boundAsUCS2, false); int valueLength = value.Length; int resultLength = (sourceOffset + charCount) > valueLength ? valueLength - sourceOffset : charCount; char[] result = value.ToCharArray(sourceOffset, resultLength); Buffer.BlockCopy(result, 0, destinationBuffer, (destinationOffset * ADP.CharSize), (resultLength * ADP.CharSize)); charCount = resultLength; } } finally { if (mustRelease) { buffer.DangerousRelease(); } } return charCount; } public override int GetHashCode() { return IsNull ? 0 : _value.GetHashCode(); } static internal int GetLength (NativeBuffer buffer, int lengthOffset, MetaType metaType) { // Get the length of the data bound int length; // Oracle only will write two bytes of length, but LONG data types // can exceed that amount; our piecewise callbacks will write a // full DWORD of length, so we need to get the full length for them, // but if we do that for all the other types, we'll be reading // un-initialized memory and bad things happen. if (metaType.IsLong) length = buffer.ReadInt32 (lengthOffset); else length = buffer.ReadInt16 (lengthOffset); GC.KeepAlive(buffer); return length; } static internal string MarshalToString( NativeBuffer buffer, int valueOffset, int lengthOffset, MetaType metaType, OracleConnection connection, bool boundAsUCS2, bool outputParameterBinding) { int valueLength = GetLength(buffer, lengthOffset, metaType); if (boundAsUCS2 && outputParameterBinding) { valueLength /= 2; } string result; bool isOutOfLine = metaType.IsLong && !outputParameterBinding; // Long column values are bound out-of-line IntPtr longBuffer = IntPtr.Zero; if (boundAsUCS2) { if (isOutOfLine) { byte[] temp = new byte[valueLength * ADP.CharSize]; NativeBuffer_LongColumnData.CopyOutOfLineBytes(buffer.ReadIntPtr(valueOffset), 0, temp, 0, valueLength * ADP.CharSize); result = System.Text.Encoding.Unicode.GetString(temp); } else { result = buffer.PtrToStringUni (valueOffset, valueLength); } } else { byte[] temp; if (isOutOfLine) { temp = new byte[valueLength]; NativeBuffer_LongColumnData.CopyOutOfLineBytes(buffer.ReadIntPtr(valueOffset), 0, temp, 0, valueLength); } else { temp = buffer.ReadBytes(valueOffset, valueLength); } result = connection.GetString (temp, metaType.UsesNationalCharacterSet); } GC.KeepAlive(buffer); return result; } static internal int MarshalToNative( object value, int offset, int size, NativeBuffer buffer, int bufferOffset, OCI.DATATYPE ociType, bool bindAsUCS2) { Encoding encoding = (bindAsUCS2) ? System.Text.Encoding.Unicode : System.Text.Encoding.UTF8; string from; string fromString; // Get the actual CLR String value from the object if ( value is OracleString ) from = ((OracleString)value)._value; else from = (string)value; // Pick out the substring they've asked for with offset and size if (0 == offset && 0 == size) fromString = from; else if (0 == size || (offset+size) > from.Length) fromString = from.Substring(offset); else fromString = from.Substring(offset,size); byte[] frombytes = encoding.GetBytes(fromString); int dataSize = frombytes.Length; int bytesWritten = dataSize; if (0 != dataSize) { int charCount = dataSize; if (bindAsUCS2) { Debug.Assert (0 == (dataSize & 0x1), "odd number of bytes in a Unicode string?"); charCount /= 2; // Need to adjust for number of UCS2 characters } if (OCI.DATATYPE.LONGVARCHAR == ociType) { buffer.WriteInt32 (bufferOffset, charCount); bufferOffset = checked((int)bufferOffset + 4) ; bytesWritten += 4; } else { // assert for size only if the data type is not LONG Debug.Assert (ociType == OCI.DATATYPE.LONG || ociType == OCI.DATATYPE.LONGVARCHAR || dataSize <= short.MaxValue, "invalid size for non-LONG data?"); } buffer.WriteBytes (bufferOffset, frombytes, 0, dataSize); } return bytesWritten; } public override string ToString() { if (IsNull) { return ADP.NullString; } return _value; } //////////////////////////////////////////////////////////////////////// //////////////////////////////////////////////////////////////////////// // // Operators // //////////////////////////////////////////////////////////////////////// //////////////////////////////////////////////////////////////////////// public static OracleString Concat(OracleString x, OracleString y) { // Alternative method for operator + return (x + y); } public static OracleBoolean Equals(OracleString x, OracleString y) { // Alternative method for operator == return (x == y); } public static OracleBoolean GreaterThan(OracleString x, OracleString y) { // Alternative method for operator > return (x > y); } public static OracleBoolean GreaterThanOrEqual(OracleString x, OracleString y) { // Alternative method for operator >= return (x >= y); } public static OracleBoolean LessThan(OracleString x, OracleString y) { // Alternative method for operator < return (x < y); } public static OracleBoolean LessThanOrEqual(OracleString x, OracleString y) { // Alternative method for operator <= return (x <= y); } public static OracleBoolean NotEquals(OracleString x, OracleString y) { // Alternative method for operator != return (x != y); } public static implicit operator OracleString(string s) { return new OracleString(s); } public static explicit operator String(OracleString x) { return x.Value; } public static OracleString operator+ (OracleString x, OracleString y) { if (x.IsNull || y.IsNull) { return Null; } OracleString result = new OracleString(x._value + y._value); return result; } public static OracleBoolean operator== (OracleString x, OracleString y) { return (x.IsNull || y.IsNull) ? OracleBoolean.Null : new OracleBoolean(x.CompareTo(y) == 0); } public static OracleBoolean operator> (OracleString x, OracleString y) { return (x.IsNull || y.IsNull) ? OracleBoolean.Null : new OracleBoolean(x.CompareTo(y) > 0); } public static OracleBoolean operator>= (OracleString x, OracleString y) { return (x.IsNull || y.IsNull) ? OracleBoolean.Null : new OracleBoolean(x.CompareTo(y) >= 0); } public static OracleBoolean operator< (OracleString x, OracleString y) { return (x.IsNull || y.IsNull) ? OracleBoolean.Null : new OracleBoolean(x.CompareTo(y) < 0); } public static OracleBoolean operator<= (OracleString x, OracleString y) { return (x.IsNull || y.IsNull) ? OracleBoolean.Null : new OracleBoolean(x.CompareTo(y) <= 0); } public static OracleBoolean operator!= (OracleString x, OracleString y) { return (x.IsNull || y.IsNull) ? OracleBoolean.Null : new OracleBoolean(x.CompareTo(y) != 0); } } } // File provided for Reference Use Only by Microsoft Corporation (c) 2007. //------------------------------------------------------------------------------ //// Copyright (c) Microsoft Corporation. All rights reserved. // //[....] //----------------------------------------------------------------------------- namespace System.Data.OracleClient { using System; using System.Data.SqlTypes; using System.Data.Common; using System.Diagnostics; using System.Globalization; using System.Runtime.CompilerServices; using System.Runtime.InteropServices; using System.Text; //--------------------------------------------------------------------- // OracleString // // This class implements support for Oracle's CHAR, VARCHAR, NCHAR, // NVARCHAR and LONG internal data types. While some of these data // types may be retrieved as multi-byte strings from Oracle there is // no particular benefit to leaving them as multi-byte because we // would be forced to re-implement the entire String class for // multi-byte strings to avoid constant conversions. // // For that reason, this type class should simply be a wrapper class // around the CLS String data type, with the appropriate internal // constructors to allow data values to be set from the data reader. // [StructLayout(LayoutKind.Sequential)] public struct OracleString : IComparable, INullable { private string _value; public static readonly OracleString Empty = new OracleString(false); public static readonly OracleString Null = new OracleString(true); // Construct from nothing -- the value will be null or empty private OracleString(bool isNull) { _value = (isNull) ? null : String.Empty; } public OracleString (string s) { _value = s; } // (internal) construct from a row/parameter binding internal OracleString( NativeBuffer buffer, int valueOffset, int lengthOffset, MetaType metaType, OracleConnection connection, // See MDAC #78258 for reason. bool boundAsUCS2, // See MDAC #78258 for reason. bool outputParameterBinding) { // oracle has inconsistent behavior for output parameters. _value = MarshalToString(buffer, valueOffset, lengthOffset, metaType, connection, boundAsUCS2, outputParameterBinding); } public bool IsNull { get { return (null == _value); } } public int Length { get { if (IsNull) { throw ADP.DataIsNull(); } return _value.Length; } } public string Value { get { if (IsNull) { throw ADP.DataIsNull(); } return _value; } } public char this[int index] { get { if (IsNull) { throw ADP.DataIsNull(); } return _value[index]; } } public int CompareTo (object obj) { if (obj.GetType() == typeof(OracleString)) { OracleString s = (OracleString)obj; // If both values are Null, consider them equal. // Otherwise, Null is less than anything. if (IsNull) { return s.IsNull ? 0 : -1; } if (s.IsNull) { return 1; } // Neither value is null, do the comparison. return CultureInfo.CurrentCulture.CompareInfo.Compare(_value, s._value); } throw ADP.WrongType(obj.GetType(), typeof(OracleString)); } public override bool Equals(object value) { if (value is OracleString) { return (this == (OracleString)value).Value; } else { return false; } } static internal int GetChars( NativeBuffer buffer, int valueOffset, int lengthOffset, MetaType metaType, OracleConnection connection, // See MDAC #78258 for reason. bool boundAsUCS2, // See MDAC #78258 for reason. int sourceOffset, char[] destinationBuffer, int destinationOffset, int charCount) { // This static method allows the GetChars type getter to do it's job // without having to marshal the entire value into managed space. bool mustRelease = false; RuntimeHelpers.PrepareConstrainedRegions(); try { buffer.DangerousAddRef(ref mustRelease); if (boundAsUCS2) { if (!metaType.IsLong) { //SQLBU:440832 -- using DangerousGetDataPtrWithBaseOffset instead of DangerousGetDataPtr Marshal.Copy(buffer.DangerousGetDataPtrWithBaseOffset(valueOffset + (ADP.CharSize * sourceOffset)), destinationBuffer, destinationOffset, charCount ); } else { // Long values are bound out-of-line, which means we have // to do this the hard way... NativeBuffer_LongColumnData.CopyOutOfLineChars(buffer.ReadIntPtr(valueOffset), sourceOffset, destinationBuffer, destinationOffset, charCount); } } else { // In the odd case that we don't have a Unicode value (see MDAC #78258 // for the reason) we have to do this the hard way -- get the full value, // then copy the data... string value = MarshalToString(buffer, valueOffset, lengthOffset, metaType, connection, boundAsUCS2, false); int valueLength = value.Length; int resultLength = (sourceOffset + charCount) > valueLength ? valueLength - sourceOffset : charCount; char[] result = value.ToCharArray(sourceOffset, resultLength); Buffer.BlockCopy(result, 0, destinationBuffer, (destinationOffset * ADP.CharSize), (resultLength * ADP.CharSize)); charCount = resultLength; } } finally { if (mustRelease) { buffer.DangerousRelease(); } } return charCount; } public override int GetHashCode() { return IsNull ? 0 : _value.GetHashCode(); } static internal int GetLength (NativeBuffer buffer, int lengthOffset, MetaType metaType) { // Get the length of the data bound int length; // Oracle only will write two bytes of length, but LONG data types // can exceed that amount; our piecewise callbacks will write a // full DWORD of length, so we need to get the full length for them, // but if we do that for all the other types, we'll be reading // un-initialized memory and bad things happen. if (metaType.IsLong) length = buffer.ReadInt32 (lengthOffset); else length = buffer.ReadInt16 (lengthOffset); GC.KeepAlive(buffer); return length; } static internal string MarshalToString( NativeBuffer buffer, int valueOffset, int lengthOffset, MetaType metaType, OracleConnection connection, bool boundAsUCS2, bool outputParameterBinding) { int valueLength = GetLength(buffer, lengthOffset, metaType); if (boundAsUCS2 && outputParameterBinding) { valueLength /= 2; } string result; bool isOutOfLine = metaType.IsLong && !outputParameterBinding; // Long column values are bound out-of-line IntPtr longBuffer = IntPtr.Zero; if (boundAsUCS2) { if (isOutOfLine) { byte[] temp = new byte[valueLength * ADP.CharSize]; NativeBuffer_LongColumnData.CopyOutOfLineBytes(buffer.ReadIntPtr(valueOffset), 0, temp, 0, valueLength * ADP.CharSize); result = System.Text.Encoding.Unicode.GetString(temp); } else { result = buffer.PtrToStringUni (valueOffset, valueLength); } } else { byte[] temp; if (isOutOfLine) { temp = new byte[valueLength]; NativeBuffer_LongColumnData.CopyOutOfLineBytes(buffer.ReadIntPtr(valueOffset), 0, temp, 0, valueLength); } else { temp = buffer.ReadBytes(valueOffset, valueLength); } result = connection.GetString (temp, metaType.UsesNationalCharacterSet); } GC.KeepAlive(buffer); return result; } static internal int MarshalToNative( object value, int offset, int size, NativeBuffer buffer, int bufferOffset, OCI.DATATYPE ociType, bool bindAsUCS2) { Encoding encoding = (bindAsUCS2) ? System.Text.Encoding.Unicode : System.Text.Encoding.UTF8; string from; string fromString; // Get the actual CLR String value from the object if ( value is OracleString ) from = ((OracleString)value)._value; else from = (string)value; // Pick out the substring they've asked for with offset and size if (0 == offset && 0 == size) fromString = from; else if (0 == size || (offset+size) > from.Length) fromString = from.Substring(offset); else fromString = from.Substring(offset,size); byte[] frombytes = encoding.GetBytes(fromString); int dataSize = frombytes.Length; int bytesWritten = dataSize; if (0 != dataSize) { int charCount = dataSize; if (bindAsUCS2) { Debug.Assert (0 == (dataSize & 0x1), "odd number of bytes in a Unicode string?"); charCount /= 2; // Need to adjust for number of UCS2 characters } if (OCI.DATATYPE.LONGVARCHAR == ociType) { buffer.WriteInt32 (bufferOffset, charCount); bufferOffset = checked((int)bufferOffset + 4) ; bytesWritten += 4; } else { // assert for size only if the data type is not LONG Debug.Assert (ociType == OCI.DATATYPE.LONG || ociType == OCI.DATATYPE.LONGVARCHAR || dataSize <= short.MaxValue, "invalid size for non-LONG data?"); } buffer.WriteBytes (bufferOffset, frombytes, 0, dataSize); } return bytesWritten; } public override string ToString() { if (IsNull) { return ADP.NullString; } return _value; } //////////////////////////////////////////////////////////////////////// //////////////////////////////////////////////////////////////////////// // // Operators // //////////////////////////////////////////////////////////////////////// //////////////////////////////////////////////////////////////////////// public static OracleString Concat(OracleString x, OracleString y) { // Alternative method for operator + return (x + y); } public static OracleBoolean Equals(OracleString x, OracleString y) { // Alternative method for operator == return (x == y); } public static OracleBoolean GreaterThan(OracleString x, OracleString y) { // Alternative method for operator > return (x > y); } public static OracleBoolean GreaterThanOrEqual(OracleString x, OracleString y) { // Alternative method for operator >= return (x >= y); } public static OracleBoolean LessThan(OracleString x, OracleString y) { // Alternative method for operator < return (x < y); } public static OracleBoolean LessThanOrEqual(OracleString x, OracleString y) { // Alternative method for operator <= return (x <= y); } public static OracleBoolean NotEquals(OracleString x, OracleString y) { // Alternative method for operator != return (x != y); } public static implicit operator OracleString(string s) { return new OracleString(s); } public static explicit operator String(OracleString x) { return x.Value; } public static OracleString operator+ (OracleString x, OracleString y) { if (x.IsNull || y.IsNull) { return Null; } OracleString result = new OracleString(x._value + y._value); return result; } public static OracleBoolean operator== (OracleString x, OracleString y) { return (x.IsNull || y.IsNull) ? OracleBoolean.Null : new OracleBoolean(x.CompareTo(y) == 0); } public static OracleBoolean operator> (OracleString x, OracleString y) { return (x.IsNull || y.IsNull) ? OracleBoolean.Null : new OracleBoolean(x.CompareTo(y) > 0); } public static OracleBoolean operator>= (OracleString x, OracleString y) { return (x.IsNull || y.IsNull) ? OracleBoolean.Null : new OracleBoolean(x.CompareTo(y) >= 0); } public static OracleBoolean operator< (OracleString x, OracleString y) { return (x.IsNull || y.IsNull) ? OracleBoolean.Null : new OracleBoolean(x.CompareTo(y) < 0); } public static OracleBoolean operator<= (OracleString x, OracleString y) { return (x.IsNull || y.IsNull) ? OracleBoolean.Null : new OracleBoolean(x.CompareTo(y) <= 0); } public static OracleBoolean operator!= (OracleString x, OracleString y) { return (x.IsNull || y.IsNull) ? OracleBoolean.Null : new OracleBoolean(x.CompareTo(y) != 0); } } } // File provided for Reference Use Only by Microsoft Corporation (c) 2007.
Link Menu

This book is available now!
Buy at Amazon US or
Buy at Amazon UK
- HttpServerUtilityBase.cs
- MailHeaderInfo.cs
- Int16Converter.cs
- NonSerializedAttribute.cs
- WebUtil.cs
- DiagnosticEventProvider.cs
- DataGridViewMethods.cs
- HtmlInputImage.cs
- XmlReaderDelegator.cs
- CompiledIdentityConstraint.cs
- IsolatedStorageFileStream.cs
- HTMLTagNameToTypeMapper.cs
- HybridDictionary.cs
- XmlDataLoader.cs
- CancellationHandler.cs
- Attributes.cs
- WebPageTraceListener.cs
- FactoryMaker.cs
- SqlDeflator.cs
- Drawing.cs
- OrderByBuilder.cs
- PickBranchDesigner.xaml.cs
- BigInt.cs
- Helper.cs
- XmlQuerySequence.cs
- ReliableMessagingVersion.cs
- SingleSelectRootGridEntry.cs
- LinkUtilities.cs
- MachineSettingsSection.cs
- SystemWebSectionGroup.cs
- SqlAliaser.cs
- DataPagerFieldItem.cs
- BinHexEncoder.cs
- AnnotationComponentChooser.cs
- HTMLTextWriter.cs
- DispatchRuntime.cs
- TextElementEnumerator.cs
- HostedImpersonationContext.cs
- DocumentXmlWriter.cs
- DataChangedEventManager.cs
- SineEase.cs
- SessionState.cs
- FormDesigner.cs
- SemanticResolver.cs
- SBCSCodePageEncoding.cs
- Behavior.cs
- KeyValueSerializer.cs
- Operators.cs
- ItemDragEvent.cs
- DataControlFieldCell.cs
- MatrixValueSerializer.cs
- ConfigUtil.cs
- Internal.cs
- Timer.cs
- AssemblyUtil.cs
- EdgeProfileValidation.cs
- Mutex.cs
- InstancePersistenceCommandException.cs
- HtmlMeta.cs
- HandlerBase.cs
- XmlRawWriter.cs
- ColumnCollectionEditor.cs
- DiagnosticTrace.cs
- InvalidProgramException.cs
- BidPrivateBase.cs
- SchemaHelper.cs
- PrePrepareMethodAttribute.cs
- DoubleCollectionValueSerializer.cs
- ExtenderProvidedPropertyAttribute.cs
- PeerHopCountAttribute.cs
- GZipDecoder.cs
- RouteValueDictionary.cs
- ReachDocumentSequenceSerializerAsync.cs
- GZipDecoder.cs
- BulletedList.cs
- SortFieldComparer.cs
- ControllableStoryboardAction.cs
- RuntimeUtils.cs
- CookielessHelper.cs
- ContentElement.cs
- __ConsoleStream.cs
- ChangeProcessor.cs
- ExpressionNode.cs
- FileFormatException.cs
- ConsumerConnectionPoint.cs
- BooleanAnimationBase.cs
- UnsignedPublishLicense.cs
- PreProcessor.cs
- ApplicationHost.cs
- BitmapEffectDrawingContextWalker.cs
- StylusPointProperties.cs
- WebPartEditVerb.cs
- Soap.cs
- ParagraphResult.cs
- XsltInput.cs
- SynchronizedDispatch.cs
- Constants.cs
- WorkflowRuntimeSection.cs
- CLRBindingWorker.cs
- XmlSerializationReader.cs