internal static Udt ReadUdtMetadata(this TdsPackageReader reader) => new Udt { DatabaseName = reader.ReadString(reader.ReadByte()), SchemaName = reader.ReadString(reader.ReadByte()), TypeName = reader.ReadString(reader.ReadByte()), AssemblyQualifiedName = reader.ReadString(reader.ReadUInt16()) };
internal static long EnvSqlTransaction(this TdsPackageReader reader) { var newTransactionId = 0L; if (reader.ReadByte() == 8) { newTransactionId = reader.ReadInt64(); } if (reader.ReadByte() == 8) { reader.ReadInt64(); } return(newTransactionId); }
public static XmlSchema?ReadXmlSchema(this TdsPackageReader reader) { var schemaPresent = reader.ReadByte(); if ((schemaPresent & 1) != 0) { return new XmlSchema { CollectionDatabase = reader.ReadString(reader.ReadByte()), CollectionOwningSchema = reader.ReadString(reader.ReadByte()), CollectionName = reader.ReadString(reader.ReadUInt16()) } } ; return(null); }
public static MultiPartTableName?ReadMultiPartTableName(this TdsPackageReader reader) { // Find out how many parts in the TDS stream var nParts = reader.ReadByte(); if (nParts == 0) { return(null); } var mpt = new MultiPartTableName(); if (nParts == 4) { mpt.ServerName = reader.ReadString(reader.ReadUInt16()); } if (nParts >= 3) { mpt.CatalogName = reader.ReadString(reader.ReadUInt16()); } if (nParts >= 2) { mpt.SchemaName = reader.ReadString(reader.ReadUInt16()); } mpt.TableName = reader.ReadString(reader.ReadUInt16()); return(mpt); }
public static int ReadTdsTypeLen(this TdsPackageReader reader, int len) => len == 0 ? 0 : len == 1 ? reader.ReadByte() : len == 2 ? reader.ReadUInt16() : reader.ReadInt32();
internal static void EnvCharset(this TdsPackageReader reader) { var newValue = reader.ReadString(reader.ReadByte()); var oldValue = reader.ReadString(reader.ReadByte()); // we copied this behavior directly from luxor - see charset envchange // section from sqlctokn.c if (newValue == TdsEnums.DEFAULT_ENGLISH_CODE_PAGE_STRING) { reader.CurrentSession.DefaultCodePage = TdsEnums.DEFAULT_ENGLISH_CODE_PAGE_VALUE; reader.CurrentSession.DefaultEncoding = Encoding.GetEncoding(reader.CurrentSession.DefaultCodePage); return; } var stringCodePage = newValue.Substring(TdsEnums.CHARSET_CODE_PAGE_OFFSET); reader.CurrentSession.DefaultCodePage = int.Parse(stringCodePage, NumberStyles.Integer, CultureInfo.InvariantCulture); reader.CurrentSession.DefaultEncoding = Encoding.GetEncoding(reader.CurrentSession.DefaultCodePage); }
internal static void EnvCollation(this TdsPackageReader reader) { var newLength = reader.ReadByte(); if (newLength == 5) { var collation = reader.ReadCollation(); var codepage = collation.GetCodePage(); reader.CurrentSession.DefaultCollation = collation; reader.CurrentSession.DefaultEncoding = reader.CurrentSession.GetEncodingFromCache(codepage); } var oldLength = reader.ReadByte(); if (oldLength == 5) { var oldCollation = reader.ReadCollation(); } }
public static void SqlErrorAndInfo(this TdsPackageReader reader, byte token, int tokenLength) { var start = reader.GetReadPos(); var error = new SqlInfoAndError { Number = reader.ReadInt32(), State = reader.ReadByte(), Class = reader.ReadByte(), Message = reader.ReadString(reader.ReadUInt16()), Server = reader.ReadString(reader.ReadByte()), Procedure = reader.ReadString(reader.ReadByte()) }; var current = reader.GetReadPos(); error.LineNumber = tokenLength - (current - start) > 2 ? reader.ReadInt32() : reader.ReadInt16(); if (error.Class >= TdsEnums.MIN_ERROR_CLASS) { throw new Exception(error.Message); } reader.CurrentSession.Errors.Add(error); }
private static void ReadMetadata(TdsPackageReader reader, ColumnMetadata col) { // read user type - 4 bytes Yukon, 2 backwards reader.ReadUInt32(); // read the 2 flags and set appropriate flags in structure col.Flag1 = reader.ReadByte(); col.Flag2 = reader.ReadByte(); var tdsType = col.TdsType = reader.ReadByte(); var tmp = col.MetaType = TdsMetaType.TdsTypes[tdsType]; col.IsPlp = tmp.IsPlp; col.IsTextOrImage = tmp.IsTextOrImage; var length = ReadTdsTypeLen(reader, tmp.LenBytes); if (length == TdsEnums.SQL_USHORTVARMAXLEN && tmp.LenBytes == 2) { col.IsPlp = true; } if (tdsType == TdsEnums.SQLUDT) { reader.ReadUdtMetadata(); } if (tdsType == TdsEnums.SQLXMLTYPE) { ReadXmlSchema(reader); } if (tmp.HasPrecision) { reader.ReadByte(); } if (tmp.HasScale) { col.Scale = reader.ReadByte(); } if (tmp.HasCollation) { col.Encoding = GetEncodingFromCollation(reader); } if (col.TdsType == TdsEnums.SQLTEXT || col.TdsType == TdsEnums.SQLNTEXT || col.TdsType == TdsEnums.SQLIMAGE) { ReadMultiPartTableName(reader); } col.Column = reader.ReadString(reader.ReadByte()); }
// read feature ID public static void FeatureExtAck(this TdsPackageReader reader) { while (true) { var featureId = reader.ReadByte(); if (featureId == TdsEnums.FEATUREEXT_TERMINATOR) { break; } var dataLen = reader.ReadUInt32(); var data = reader.GetBytes(checked ((int)dataLen)); if (dataLen > 0) { OnFeatureExtAck(featureId, data); } } }
public static SqlServerInfo LoginAck(this TdsPackageReader reader) { var sqlServerInfo = new SqlServerInfo(); // read past interface type and version reader.ReadByte(); var b = reader.GetBytes(TdsEnums.VERSION_SIZE); var tdsVersion = (uint)((((((b[0] << 8) | b[1]) << 8) | b[2]) << 8) | b[3]); // bytes are in motorola order (high byte first) var majorMinor = tdsVersion & 0xff00ffff; var increment = (tdsVersion >> 16) & 0xff; // Server responds: // 0x07000000 -> Sphinx // Notice server response format is different for bwd compat // 0x07010000 -> Shiloh RTM // Notice server response format is different for bwd compat // 0x71000001 -> Shiloh SP1 // 0x72090002 -> Yukon RTM // 0x730B0003 -> Katmai RTM // 0x74000004 -> DENALI RTM // information provided by S. Ashwin switch (majorMinor) { case (TdsEnums.YUKON_MAJOR << 24) | TdsEnums.YUKON_RTM_MINOR when increment == TdsEnums.YUKON_INCREMENT: sqlServerInfo.IsYukon = true; break; case (TdsEnums.KATMAI_MAJOR << 24) | TdsEnums.KATMAI_MINOR when increment == TdsEnums.KATMAI_INCREMENT: sqlServerInfo.IsYukon = true; sqlServerInfo.IsKatmaiOrNewer = true; break; case (TdsEnums.DENALI_MAJOR << 24) | TdsEnums.DENALI_MINOR when increment == TdsEnums.DENALI_INCREMENT: sqlServerInfo.IsYukon = true; sqlServerInfo.IsKatmaiOrNewer = true; sqlServerInfo.IsDenali = true; break; default: throw SQL.InvalidTdsVersion(); } //isYukon is always true otherwise we send an exception var len = reader.ReadByte(); sqlServerInfo.Name = reader.ReadUnicodeChars(len * 2); sqlServerInfo.MajorVersion = reader.ReadByte(); sqlServerInfo.MinorVersion = reader.ReadByte(); sqlServerInfo.BuildNum = (short)((reader.ReadByte() << 8) + reader.ReadByte()); return(sqlServerInfo); }
public static void EnvChange(this TdsPackageReader reader, int tokenLength, Action <int> transactionAction) { // There could be multiple environment change messages following this token. var processedLength = 0; var startpos = reader.GetReadPos(); while (tokenLength > processedLength) { var type = reader.ReadByte(); switch (type) { case TdsEnums.ENV_DATABASE: case TdsEnums.ENV_LANG: reader.EnvLanguage(); break; case TdsEnums.ENV_CHARSET: reader.EnvCharset(); break; case TdsEnums.ENV_PACKETSIZE: reader.EnvPackageSize(); break; case TdsEnums.ENV_LOCALEID: throw new NotImplementedException(); case TdsEnums.ENV_COMPFLAGS: throw new NotImplementedException(); case TdsEnums.ENV_COLLATION: reader.EnvCollation(); break; case TdsEnums.ENV_BEGINTRAN: case TdsEnums.ENV_COMMITTRAN: case TdsEnums.ENV_ROLLBACKTRAN: case TdsEnums.ENV_ENLISTDTC: case TdsEnums.ENV_DEFECTDTC: case TdsEnums.ENV_TRANSACTIONENDED: if (transactionAction == null) { reader.EnvSqlTransaction(); } else { transactionAction(type); } break; case TdsEnums.ENV_LOGSHIPNODE: throw new NotImplementedException(); case TdsEnums.ENV_PROMOTETRANSACTION: throw new NotImplementedException(); case TdsEnums.ENV_TRANSACTIONMANAGERADDRESS: case TdsEnums.ENV_SPRESETCONNECTIONACK: throw new NotImplementedException(); case TdsEnums.ENV_USERINSTANCE: throw new NotImplementedException(); case TdsEnums.ENV_ROUTING: throw new NotImplementedException(); default: Debug.Assert(false, "Unknown environment change token: " + type); break; } processedLength = reader.GetReadPos() - startpos; } }
public static void EnvPackageSize(this TdsPackageReader tdsPackageReader) { var newValue = tdsPackageReader.ReadString(tdsPackageReader.ReadByte()); var oldValue = tdsPackageReader.ReadString(tdsPackageReader.ReadByte()); var packetSize = int.Parse(newValue, NumberStyles.Integer, CultureInfo.InvariantCulture); }
public static void ParseSessionState(this TdsPackageReader reader, int length) { var sdata = reader.CurrentSession.CurrentSessionData; if (length < 5) { throw SQL.ParsingError(); } var seqNum = reader.ReadUInt32(); if (seqNum == uint.MaxValue) { reader.CurrentSession.DoNotPoolThisConnection = true; } var status = reader.ReadByte(); if (status > 1) { throw SQL.ParsingError(); } var recoverable = status != 0; length -= 5; while (length > 0) { var stateId = reader.ReadByte(); var stateLenByte = reader.ReadByte(); var stateLen = stateLenByte < 0xFF ? stateLenByte : reader.ReadInt32(); byte[] buffer = null; lock (sdata.Delta) { if (sdata.Delta[stateId] == null) { buffer = new byte[stateLen]; sdata.Delta[stateId] = new SessionStateRecord { Version = seqNum, DataLength = stateLen, Data = buffer, Recoverable = recoverable }; sdata.DeltaDirty = true; if (!recoverable) { checked { sdata.UnrecoverableStatesCount++; } } } else { if (sdata.Delta[stateId].Version <= seqNum) { var sv = sdata.Delta[stateId]; sv.Version = seqNum; sv.DataLength = stateLen; if (sv.Recoverable != recoverable) { if (recoverable) { Debug.Assert(sdata.UnrecoverableStatesCount > 0, "Unrecoverable states count >0"); sdata.UnrecoverableStatesCount--; } else { checked { sdata.UnrecoverableStatesCount++; } } sv.Recoverable = recoverable; } buffer = sv.Data; if (buffer.Length < stateLen) { buffer = new byte[stateLen]; sv.Data = buffer; } } } } if (buffer != null) { reader.ReadByteArray(buffer, 0, stateLen); } else { reader.GetBytes(stateLen); } length -= stateLenByte < 0xFF ? 2 + stateLen : 6 + stateLen; } }
private static MetadataBulkCopy ReadMetadata(TdsPackageReader reader) { var col = new MetadataBulkCopy(); // read user type - 4 bytes Yukon, 2 backwards reader.ReadUInt32(); // read the 2 flags and set appropriate flags in structure col.Flag1 = reader.ReadByte(); col.Flag2 = reader.ReadByte(); var tdsType = reader.ReadByte(); col.TdsType = tdsType; var tmp = col.MetaType = TdsMetaType.TdsTypes[tdsType]; col.IsPlp = tmp.IsPlp; col.IsTextOrImage = tmp.IsTextOrImage; var length = col.Length = reader.ReadTdsTypeLen(tmp.LenBytes); if (length == TdsEnums.SQL_USHORTVARMAXLEN && tmp.LenBytes == 2) { col.IsPlp = true; } if (tdsType == TdsEnums.SQLUDT) { reader.ReadUdtMetadata(); } if (tdsType == TdsEnums.SQLXMLTYPE) { reader.ReadXmlSchema(); } if (tmp.HasPrecision) { col.Precision = reader.ReadByte(); } if (tmp.HasScale) { col.Scale = reader.ReadByte(); } if (tmp.HasCollation) { col.Collation = reader.ReadCollation(); col.Encoding = reader.CurrentSession.GetEncodingFromCache(col.Collation.GetCodePage()); } if (col.IsTextOrImage) { col.PartTableName = reader.ReadMultiPartTableName(); } //bulkcopy typeCorrection if (tdsType == TdsEnums.SQLXMLTYPE) { col.TdsType = TdsEnums.SQLNVARCHAR; col.Length = TdsEnums.SQL_USHORTVARMAXLEN; col.Collation = new SqlCollations(); } if (tdsType == TdsEnums.SQLUDT) { col.TdsType = TdsEnums.SQLBIGVARBINARY; col.Length = TdsEnums.SQL_USHORTVARMAXLEN; } col.Column = reader.ReadString(reader.ReadByte()); return(col); }
internal static void EnvLanguage(this TdsPackageReader tdsPackageReader) { var newValue = tdsPackageReader.ReadString(tdsPackageReader.ReadByte()); var oldValue = tdsPackageReader.ReadString(tdsPackageReader.ReadByte()); }