// UDTs and null variants come back via return value, all else is via targetBuffer.
// implements SqlClient 2.0-compatible output parameter semantics
internal static object GetOutputParameterV3Smi(
SmiEventSink_Default sink, // event sink for errors
ITypedGettersV3 getters, // getters interface to grab value from
int ordinal, // parameter within getters
SmiMetaData metaData, // Getter's type for this ordinal
SmiContext context, // used to obtain scratch streams
SqlBuffer targetBuffer // destination
) {
object result = null; // Workaround for UDT hack in non-Smi code paths.
if ( IsDBNull_Unchecked( sink, getters, ordinal ) ) {
GetNullOutputParameterSmi(metaData, targetBuffer, ref result);
}
else {
switch( metaData.SqlDbType )
{
case SqlDbType.BigInt:
targetBuffer.Int64 = GetInt64_Unchecked( sink, getters, ordinal );
break;
case SqlDbType.Binary:
case SqlDbType.Image:
case SqlDbType.Timestamp:
case SqlDbType.VarBinary:
targetBuffer.SqlBinary = GetSqlBinary_Unchecked( sink, getters, ordinal );
break;
case SqlDbType.Bit:
targetBuffer.Boolean = GetBoolean_Unchecked( sink, getters, ordinal );
break;
case SqlDbType.NChar:
case SqlDbType.NText:
case SqlDbType.NVarChar:
case SqlDbType.Char:
case SqlDbType.VarChar:
case SqlDbType.Text:
targetBuffer.SetToString( GetString_Unchecked( sink, getters, ordinal ) );
break;
case SqlDbType.DateTime:
case SqlDbType.SmallDateTime: {
SqlDateTime dt = new SqlDateTime( GetDateTime_Unchecked( sink, getters, ordinal ) );
targetBuffer.SetToDateTime( dt.DayTicks, dt.TimeTicks );
break;
}
case SqlDbType.Decimal: {
SqlDecimal dec = GetSqlDecimal_Unchecked( sink, getters, ordinal );
targetBuffer.SetToDecimal( dec.Precision, dec.Scale, dec.IsPositive, dec.Data );
break;
}
case SqlDbType.Float:
targetBuffer.Double = GetDouble_Unchecked( sink, getters, ordinal );
break;
case SqlDbType.Int:
targetBuffer.Int32 = GetInt32_Unchecked( sink, getters, ordinal );
break;
case SqlDbType.Money:
case SqlDbType.SmallMoney:
targetBuffer.SetToMoney( GetInt64_Unchecked( sink, getters, ordinal) );
break;
case SqlDbType.Real:
targetBuffer.Single = GetSingle_Unchecked( sink, getters, ordinal );
break;
case SqlDbType.UniqueIdentifier:
targetBuffer.SqlGuid = new SqlGuid( GetGuid_Unchecked( sink, getters, ordinal ) );
break;
case SqlDbType.SmallInt:
targetBuffer.Int16 = GetInt16_Unchecked( sink, getters, ordinal );
break;
case SqlDbType.TinyInt:
targetBuffer.Byte = GetByte_Unchecked( sink, getters, ordinal );
break;
case SqlDbType.Variant:
// For variants, recur using the current value's sqldbtype
metaData = getters.GetVariantType( sink, ordinal );
sink.ProcessMessagesAndThrow();
Debug.Assert( SqlDbType.Variant != metaData.SqlDbType, "Variant-within-variant not supposed to be possible!" );
GetOutputParameterV3Smi( sink, getters, ordinal, metaData, context, targetBuffer );
break;
case SqlDbType.Udt:
result = GetUdt_LengthChecked( sink, getters, ordinal, metaData );
break;
case SqlDbType.Xml:
targetBuffer.SqlXml = GetSqlXml_Unchecked( sink, getters, ordinal, null );
break;
default:
Debug.Assert( false, "Unexpected SqlDbType" );
break;
}
}
return result;
}