Skip to content

Add vector(float16) support - #4501

Draft
apoorvdeshmukh wants to merge 4 commits into
mainfrom
dev/ad/vector-float16-support
Draft

Add vector(float16) support#4501
apoorvdeshmukh wants to merge 4 commits into
mainfrom
dev/ad/vector-float16-support

Conversation

@apoorvdeshmukh

@apoorvdeshmukh apoorvdeshmukh commented Aug 4, 2026

Copy link
Copy Markdown
Contributor

Adds support for the float16 base type of the vector data type, by advertising version 2 of the VECTORSUPPORT feature extension. A vector(N, float16) column is now exchanged in its native binary form rather than as a varchar(max) JSON string.

Opened as a draft: this is an integration branch. The four commits are independently buildable and can be split into separate PRs on request.

Representation

.NET .NET Framework
Default SqlVector<Half> string (JSON)
Typed read GetSqlVector<Half> exact, or GetSqlVector<float> widened GetSqlVector<float> widened
Write SqlVector<Half> SqlVector<float>, JSON string, or SqlBulkCopy

System.Half does not exist on .NET Framework, so a float16 column is reported as a string there, matching how it is already presented when the server does not negotiate float16 support. GetSqlVector<float> widens the elements, which is exact. .NET Framework decodes binary16 itself, as no BCL package supplies System.Half for net462; on .NET the same methods delegate to BitConverter.

SqlVector<T> keeps its shipped contract: T alone determines the base type written to the wire. Conversion between base types is left to the server, except for SqlBulkCopy, which states the destination's base type in the INSERT BULK statement and so must convert the payload itself.

Behaviour changes

  • Reading a vector(N, float16) column no longer returns varchar(max). String read paths still work, but the text changes from the server's scientific notation ([1.0000000e+000,2.0000000e+000]) to a compact JSON array ([1,2]). Both parse to the same values. This is the same transition float32 columns made when vector support was added in 6.1, so the two base types now render identically.
  • On .NET, GetFieldType, GetValue and the column type of a filled DataTable change from string to SqlVector<Half>; casting GetValue directly to string now throws InvalidCastException.
  • SqlVector<T>.ToString() now returns the values as a JSON array rather than the type name, which also affects existing SqlVector<float> callers.
  • float16 is server-side preview-gated (PREVIEW_FEATURES = ON), so applications which have not enabled it are unaffected.

Also included

A vector column's base type and dimension count are now available from the column schema as ["VectorBaseType"] and ["VectorDimensions"], via DbColumn's virtual indexer, so no new public API. This is a v1 gap affecting float32 today: the dimension count previously required hardcoding (ColumnSize - 8) / 4. The vector type is also registered in the DataTypes schema collection, where it was missing.

Validation

Verified against SQL Server 18.0.258.0.

Suite net9.0 net462
Vector manual tests 206/206 136/136
Unit tests 1067/1067 1102/1102

The binary16 codec is validated bit-exactly against System.Half across all 65,536 patterns and a strided sweep of the single precision range. It is compiled on every framework so that the .NET Framework path is the one under test.

Existing Float16VectorTypeBackwardCompatibilityTests pass unchanged. CI has no float16-capable server, so those tests will skip.

Commits

Commit Contents Depends on
9a935eb Vector column metadata
8fc82cb binary16 codec (internal)
dad19a3 float16 support 8fc82cb
734a90a Docs and sample dad19a3

The third cannot be split further: advertising version 2 without the reader, parameter and bulk copy wiring would leave float16 columns arriving natively with nothing able to interpret them.

Note for the TVP work

WriteSmiTypeInfo has no Vector case in main; TVP support for vectors is on the unmerged dev/ad/tvp-json-vector. This change neither breaks nor covers that path. When the TVP branch lands it must write the base type into the TVP column metadata scale byte, as WriteParameterMetadata does.

Checklist

  • Tests added or updated
  • Public API changes documented
  • Breaking changes assessed — see Behaviour changes above
  • Release note entry for the next 7.1 preview

apoorvdeshmukh and others added 4 commits August 4, 2026 23:50
A vector column's base type and number of dimensions were already available
from the column schema, but only as a numeric scale and a column size which
the caller had to decode. They are now surfaced under their own names, so
that applications inspecting result set metadata do not have to know that
encoding.

Also registers the vector type in the DataTypes schema collection, where it
was missing.

Co-authored-by: Copilot App <223556219+Copilot@users.noreply.github.com>
Copilot-Session: e17ed782-c576-4cb7-9b4b-7ad286d7a7d0
SQL Server transports vector(N, float16) elements as raw binary16 values.
System.Half is only available on .NET, so the conversion is implemented
manually for .NET Framework.

The manual implementation is compiled for every target framework rather than
only for .NET Framework, so that it can be validated exhaustively against
System.Half on .NET while remaining the code path .NET Framework actually
uses. It is verified against every binary16 bit pattern, a strided sweep of
the single precision range, and the rounding, subnormal, overflow and
underflow boundaries.

Co-authored-by: Copilot App <223556219+Copilot@users.noreply.github.com>
Copilot-Session: e17ed782-c576-4cb7-9b4b-7ad286d7a7d0
Advertises version 2 of the VECTORSUPPORT feature extension, so that a
vector(N, float16) column is exchanged in its native binary form rather than
as a varchar(max) JSON string.

On .NET such a column is surfaced as SqlVector<Half>. .NET Framework has no
System.Half, so it is reported as a string there, matching how it is already
presented when the server does not negotiate float16 support. Callers on
either framework can explicitly request a strongly typed value via
GetSqlVector<float>, which widens the elements without loss.

SqlVector<T> continues to derive the base type written to the wire from T
alone. Conversion between base types is left to the server, which performs it
for parameters. Bulk copy is the exception: it declares the destination's base
type in the INSERT BULK statement, so a payload using a different base type is
rejected as a column length error rather than converted, and is rewritten by
the driver first. That conversion runs after coercion, because the payload
coercion produces uses the source value's own base type: a JSON string always
yields float32, which is how a float16 column reads back where System.Half is
unavailable.

SqlVector<T>.ToString() now returns the vector's values as a JSON array rather
than the type name.

Co-authored-by: Copilot App <223556219+Copilot@users.noreply.github.com>
Copilot-Session: e17ed782-c576-4cb7-9b4b-7ad286d7a7d0
Describes the base types a vector column can have, how they map to
SqlVector<T>, and how a float16 column is read and written on .NET Framework,
where System.Half does not exist. Also documents the vector feature extension
versions and the column metadata properties.

Adds a sample covering both frameworks, reading a float16 column as an exact,
widened or JSON value, inspecting a column's base type and dimensions, and
converting between base types.

Co-authored-by: Copilot App <223556219+Copilot@users.noreply.github.com>
Copilot-Session: e17ed782-c576-4cb7-9b4b-7ad286d7a7d0
Copilot AI review requested due to automatic review settings August 4, 2026 18:24
@github-project-automation github-project-automation Bot moved this to To triage in SqlClient Board Aug 4, 2026

Copilot AI left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pull request overview

Adds end-to-end support for SQL Server vector(N, float16) by negotiating VECTORSUPPORT feature extension version 2, introducing an IEEE-754 binary16 codec, and wiring float16 handling through SqlVector<T> read/write paths (including bulk copy), with accompanying docs and tests.

Changes:

  • Negotiate vector feature extension v2 and track negotiated vector capability version (float32/float16) on the connection.
  • Add float16 vector support across SqlVector<T>, SqlDataReader, SqlBuffer, SqlParameter, SqlCommand, and SqlBulkCopy, including payload conversion for bulk copy.
  • Add unit/manual tests plus docs/snippets/sample updates; expose vector base type + dimensions via DbColumn indexer and register vector in the DataTypes schema collection.

Reviewed changes

Copilot reviewed 23 out of 23 changed files in this pull request and generated 2 comments.

Show a summary per file
File Description
src/Microsoft.Data.SqlClient/tests/UnitTests/SimulatedServerTests/ConnectionTests.cs Updates simulated negotiation tests for vector feature extension v2.
src/Microsoft.Data.SqlClient/tests/UnitTests/Microsoft/Data/SqlTypes/SqlVectorTest.cs Adds float16 construction/rendering tests and payload conversion tests.
src/Microsoft.Data.SqlClient/tests/UnitTests/Microsoft/Data/SqlTypes/Float16ConverterTest.cs New unit tests validating binary16 codec (incl. exhaustive bit-pattern validation on .NET).
src/Microsoft.Data.SqlClient/tests/ManualTests/SQL/VectorTest/VectorFloat16BehaviourTests.cs Manual tests for float16-specific behaviors (read/write/cross-base-type/bulk copy).
src/Microsoft.Data.SqlClient/tests/ManualTests/SQL/VectorTest/VectorColumnMetadataTests.cs Manual tests for vector column metadata + schema collection registration.
src/Microsoft.Data.SqlClient/tests/ManualTests/SQL/VectorTest/NativeVectorFloat16Tests.cs Manual typed tests for SqlVector<Half> on .NET.
src/Microsoft.Data.SqlClient/src/Microsoft/Data/SqlTypes/SqlVector.cs Implements float16 support in SqlVector<T>, adds JSON ToString(), payload widening/conversion helpers.
src/Microsoft.Data.SqlClient/src/Microsoft/Data/SqlClient/TdsEnums.cs Adds vector version constants and sets max supported vector version to float16 (v2).
src/Microsoft.Data.SqlClient/src/Microsoft/Data/SqlClient/SqlParameter.cs Handles float16 vector return/coercion paths (Half on .NET, widening on netfx).
src/Microsoft.Data.SqlClient/src/Microsoft/Data/SqlClient/SqlMetaDataFactory.DataTypes.cs Registers vector in GetSchema("DataTypes").
src/Microsoft.Data.SqlClient/src/Microsoft/Data/SqlClient/SqlEnums.cs Adds float16 vector element type and element-size mapping; meta type inference includes SqlVector<Half> on .NET.
src/Microsoft.Data.SqlClient/src/Microsoft/Data/SqlClient/SqlDbColumn.cs Exposes VectorBaseType/VectorDimensions via DbColumn indexer.
src/Microsoft.Data.SqlClient/src/Microsoft/Data/SqlClient/SqlDataReader.cs Adds float16 field-type mapping and broadens GetSqlVector<T> to allow Half on .NET.
src/Microsoft.Data.SqlClient/src/Microsoft/Data/SqlClient/SqlCommand.cs Emits (N, float16) parameter declaration when needed (keeps float32 declaration unchanged).
src/Microsoft.Data.SqlClient/src/Microsoft/Data/SqlClient/SqlBulkCopy.cs Emits float16 vector type in INSERT BULK declaration and converts payload base type to match destination.
src/Microsoft.Data.SqlClient/src/Microsoft/Data/SqlClient/SqlBuffer.cs Centralizes float16 vector rendering/value-shaping across frameworks.
src/Microsoft.Data.SqlClient/src/Microsoft/Data/SqlClient/Connection/SqlConnectionInternal.cs Records negotiated vector feature version on FEATUREEXTACK.
src/Microsoft.Data.SqlClient/src/Microsoft/Data/SqlClient/Connection/ConnectionCapabilities.cs Replaces bool flag with VectorVersion and derived float32/float16 capability properties.
src/Microsoft.Data.SqlClient/src/Microsoft/Data/Common/Float16Converter.cs New internal binary16<->binary32 conversion implementation.
src/Microsoft.Data.SqlClient/ref/Microsoft.Data.SqlTypes.cs Updates reference surface to include SqlVector<T>.ToString() override.
doc/snippets/Microsoft.Data.SqlTypes/SqlVector.xml Documents float16 support, size constraints, and ToString() JSON rendering.
doc/samples/SqlVectorFloat16Example.cs New sample demonstrating float16 vectors (insert/read/metadata).
.github/instructions/features.instructions.md Updates repo feature reference docs for float16 vector base type and negotiation versions.
Suppressed comments (1)

src/Microsoft.Data.SqlClient/src/Microsoft/Data/SqlTypes/SqlVector.cs:420

  • ConvertPayloadElementType doesn’t validate the vector header magic/version bytes before using the length and element type fields. This can cause non-vector payloads to be converted (or to fail later with less appropriate exceptions). Validate VecHeaderMagicNo/VecVersionNo up front, consistent with GetCountsOrThrow.
        if (tdsBytes.Length < TdsEnums.VECTOR_HEADER_SIZE)
        {
            throw ADP.InvalidVectorHeader();
        }

Comment on lines +1726 to +1729
// The payload is converted directly rather than through a strongly typed vector,
// so that .NET Framework, which has no System.Half, can also write to float16
// destinations.
return SqlTypes.SqlVector<float>.ConvertPayloadElementType(payload, destinationElementType);
Comment on lines +151 to +154
if (tdsBytes.Length < TdsEnums.VECTOR_HEADER_SIZE)
{
throw ADP.InvalidVectorHeader();
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

Status: To triage

Development

Successfully merging this pull request may close these issues.

2 participants