private void WriteSmiParameter(SqlParameter param, int paramIndex, bool sendDefault, TdsParserStateObject stateObj) { // // Determine Metadata // ParameterPeekAheadValue peekAhead; MSS.SmiParameterMetaData metaData = param.MetaDataForSmi(out peekAhead); if (!_isKatmai) { MetaType mt = MetaType.GetMetaTypeFromSqlDbType(metaData.SqlDbType, metaData.IsMultiValued); throw ADP.VersionDoesNotSupportDataType(mt.TypeName); } // // Determine value to send // object value; MSS.ExtendedClrTypeCode typeCode; // if we have an output or default param, set the value to null so we do not send it across to the server if (sendDefault) { // Value for TVP default is empty list, not NULL if (SqlDbType.Structured == metaData.SqlDbType && metaData.IsMultiValued) { value = s_tvpEmptyValue; typeCode = MSS.ExtendedClrTypeCode.IEnumerableOfSqlDataRecord; } else { // Need to send null value for default value = null; typeCode = MSS.ExtendedClrTypeCode.DBNull; } } else if (param.Direction == ParameterDirection.Output) { bool isCLRType = param.ParamaterIsSqlType; // We have to forward the TYPE info, we need to know what type we are returning. Once we null the paramater we will no longer be able to distinguish what type were seeing. param.Value = null; value = null; typeCode = MSS.ExtendedClrTypeCode.DBNull; param.ParamaterIsSqlType = isCLRType; } else { value = param.GetCoercedValue(); typeCode = MSS.MetaDataUtilsSmi.DetermineExtendedTypeCodeForUseWithSqlDbType(metaData.SqlDbType, metaData.IsMultiValued, value); } // // Write parameter metadata // WriteSmiParameterMetaData(metaData, sendDefault, stateObj); // // Now write the value // TdsParameterSetter paramSetter = new TdsParameterSetter(stateObj, metaData); MSS.ValueUtilsSmi.SetCompatibleValueV200( new MSS.SmiEventSink_Default(), // TDS Errors/events dealt with at lower level for now, just need an object for processing paramSetter, 0, // ordinal. TdsParameterSetter only handles one parameter at a time metaData, value, typeCode, param.Offset, 0 < param.Size ? param.Size : -1, peekAhead); }
private void WriteSmiParameter(SqlParameter param, int paramIndex, bool sendDefault, TdsParserStateObject stateObj) { object coercedValue; ExtendedClrTypeCode iEnumerableOfSqlDataRecord; ParameterPeekAheadValue value2; SmiParameterMetaData metaData = param.MetaDataForSmi(out value2); if (!this._isKatmai) { throw ADP.VersionDoesNotSupportDataType(MetaType.GetMetaTypeFromSqlDbType(metaData.SqlDbType, metaData.IsMultiValued).TypeName); } if (sendDefault) { if ((SqlDbType.Structured == metaData.SqlDbType) && metaData.IsMultiValued) { coercedValue = __tvpEmptyValue; iEnumerableOfSqlDataRecord = ExtendedClrTypeCode.IEnumerableOfSqlDataRecord; } else { coercedValue = null; iEnumerableOfSqlDataRecord = ExtendedClrTypeCode.DBNull; } } else if (param.Direction == ParameterDirection.Output) { bool paramaterIsSqlType = param.ParamaterIsSqlType; param.Value = null; coercedValue = null; iEnumerableOfSqlDataRecord = ExtendedClrTypeCode.DBNull; param.ParamaterIsSqlType = paramaterIsSqlType; } else { coercedValue = param.GetCoercedValue(); iEnumerableOfSqlDataRecord = MetaDataUtilsSmi.DetermineExtendedTypeCodeForUseWithSqlDbType(metaData.SqlDbType, metaData.IsMultiValued, coercedValue, null, 210L); } if (Bid.AdvancedOn) { Bid.Trace("<sc.TdsParser.WriteSmiParameter|ADV> %d#, Sending parameter '%ls', default flag=%d, metadata:\n", this.ObjectID, param.ParameterName, sendDefault ? 1 : 0); Bid.PutStr(metaData.TraceString(3)); Bid.Trace("\n"); } this.WriteSmiParameterMetaData(metaData, sendDefault, stateObj); TdsParameterSetter setters = new TdsParameterSetter(stateObj, metaData); ValueUtilsSmi.SetCompatibleValueV200(new SmiEventSink_Default(), setters, 0, metaData, coercedValue, iEnumerableOfSqlDataRecord, param.Offset, (0 < param.Size) ? param.Size : -1, value2); }