Edit

Microsoft ODBC Driver for SQL Server

Download ODBC driver

ODBC is the primary native data access API for applications written in C and C++ for SQL Server. The Microsoft ODBC Driver for SQL Server connects to SQL Server, Azure SQL Database, Azure SQL Managed Instance, Azure Synapse Analytics, and SQL database in Microsoft Fabric. For the database versions each driver release supports, see SQL version compatibility.

Other languages that can use ODBC include COBOL, Perl, PHP, and Python. ODBC is widely used in data integration scenarios, and the Microsoft Drivers for PHP for SQL Server are built on this driver.

The sqlcmd and bcp utilities work with this driver, but they install separately: the mssql-tools18 package on Linux and macOS, and the Microsoft Command Line Utilities on Windows. Use sqlcmd to run Transact-SQL (T-SQL) statements, system procedures, and script files. Use bcp to bulk copy data between an instance of SQL Server and a data file, in either direction.

Choose your starting point

Production baseline for Azure SQL

Use this snippet as a starting point for a production-oriented Azure SQL connection. It loads the server name and database name from application configuration, authenticates with a managed identity so that no secret appears in the connection string, and enables Tabular Data Stream (TDS) 8.0 encryption with full certificate validation. It sets a per-attempt login timeout, and retries transient failures with exponential backoff and jitter.

The C++ snippet in this article omits includes, handle allocation, and the logging helper for brevity.

std::wstring BuildConnectionString(const wchar_t* server, const wchar_t* database) {
    std::wstring cs = L"Driver={ODBC Driver 18 for SQL Server}";
    cs += L";Server=tcp:"; cs += server; cs += L",1433";
    cs += L";Database="; cs += database;
    cs += L";Authentication=ActiveDirectoryMsi";   // managed identity, no stored secret
    cs += L";Encrypt=strict";                      // TDS 8.0 with certificate validation
    cs += L";ConnectRetryCount=3";                 // idle connection resiliency, not initial connect
    cs += L";ConnectRetryInterval=10";
    return cs;
}

// Transient fault codes documented for Azure SQL, plus the resource governance
// codes. Network termination and timeout errors (64, 233, 258, 10053, 10054,
// 10060) are retried a bounded number of times, which is the documented
// guidance for them. 258 is the code the driver reports for a connect timeout.
// 10053 and 10054 can also mean the encryption handshake failed rather than a
// plain network reset, so read the error text before assuming a network fault.
bool IsTransient(SQLINTEGER nativeError) {
    switch (nativeError) {
        case 615: case 926: case 4060: case 4221:
        case 10928: case 10929: case 10936:
        case 40197: case 40501: case 40613:
        case 42108: case 42109:
        case 49918: case 49919: case 49920:
        case 40020: case 40143: case 40166: case 40540:   // failover subcodes
        case 64: case 233: case 258:
        case 10053: case 10054: case 10060:
            return true;
        default:
            return false;
    }
}

// Retries only errors that a new connection can clear, with exponential backoff
// plus jitter so that concurrent clients don't retry in lockstep.
SQLRETURN ConnectWithRetry(SQLHDBC hDbc, const std::wstring& connectionString, int maxAttempts) {
    SQLRETURN rc = SQL_ERROR;
    for (int attempt = 1; attempt <= maxAttempts; ++attempt) {
        // Set the per-attempt connect timeout through the connection attribute.
        // This works on every driver version, so the sample doesn't depend on
        // which connection string keywords a given release accepts.
        SQLSetConnectAttrW(hDbc, SQL_ATTR_LOGIN_TIMEOUT,
                           reinterpret_cast<SQLPOINTER>(static_cast<SQLLEN>(30)), 0);

        rc = SQLDriverConnectW(hDbc, nullptr,
                               const_cast<SQLWCHAR*>(reinterpret_cast<const SQLWCHAR*>(connectionString.c_str())),
                               SQL_NTS, nullptr, 0, nullptr, SQL_DRIVER_NOPROMPT);
        if (SQL_SUCCEEDED(rc)) {
            Log("INFO", "connected on attempt %d/%d", attempt, maxAttempts);
            return rc;
        }

        // Walks the diagnostic records and returns the first record that carries
        // a real SQL Server error number. Microsoft Entra failures report several
        // driver-specific records first, whose native error is 0.
        SQLINTEGER native = LogDiagnostics(SQL_HANDLE_DBC, hDbc, "connect");
        if (attempt == maxAttempts || !IsTransient(native)) return rc;

        // Cap the backoff at 64 seconds. This also keeps the shift in range
        // when a caller passes a large maxAttempts.
        int shift = (attempt - 1 < 6) ? attempt - 1 : 6;
        DWORD delayMs = (1UL << shift) * 1000UL + (DWORD)(GetTickCount64() % 500);
        Log("WARN", "retrying in %lu ms (attempt %d/%d)", delayMs, attempt + 1, maxAttempts);
        Sleep(delayMs);
    }
    return rc;
}

ConnectRetryCount and ConnectRetryInterval enable idle connection resiliency, which transparently restores a connection that dropped while idle. They don't retry the initial connect, which is why this snippet also implements application-level retry. Keep both.

ODBC reports diagnostics through SQLGetDiagRec rather than the return code alone, so classify failures before retrying. An authentication or configuration error then fails immediately instead of consuming the whole retry budget.

For more information about each part of this configuration, see:

For the catalog of Azure SQL transient errors, see transient fault error codes.

Key features

  • Cross-platform: The same API on Windows, Linux, and macOS.
  • Microsoft Entra ID authentication: Passwordless connections with managed identity, service principal, interactive, and integrated flows.
  • Strict encryption: TDS 8.0 connections with full certificate validation in version 18 and later versions.
  • Always Encrypted: Client-side encryption for sensitive columns, with support for custom keystore providers.
  • Connection resiliency: Transparent restoration of a connection that dropped while idle.
  • High availability: Availability group listener support with MultiSubnetFailover.
  • Data classification: Sensitivity metadata for classified columns.
  • Vector data type: Native support for the vector type.
  • Distributed transactions: XA transaction support through the Microsoft Distributed Transaction Coordinator (MSDTC).
  • Companion tools: sqlcmd and bcp, installed separately.

Get started

Article Description
Download ODBC Driver for SQL Server Installer and package downloads for every supported driver version, on all three platforms.
Connect to and query a database with C++ A complete C++ sample that connects, runs a query, and reads results, so you can confirm your setup end to end.
Support lifecycle Which driver versions are still supported, and the date each one leaves support.
Major version differences What breaks when you move from version 17 to version 18, starting with the encryption default change.

Install the driver

Article Description
System requirements, installation, and driver files (Windows) Supported Windows versions, the installer command line for silent deployment, and where each driver file lands on disk.
System requirements (Linux and macOS) Which Linux distributions and macOS releases each driver version supports, plus SQL Server version compatibility.
Install the ODBC driver on Linux Package manager steps for Alpine, Debian, Red Hat, SUSE, Ubuntu, and Azure Linux, plus offline installation and the driver file locations.
Install the ODBC driver on macOS Homebrew tap and formula steps for macOS, including how to install version 18, 17, or 13.1.
Install the unixODBC driver manager (Linux and macOS) Install or upgrade unixODBC, the driver manager that loads the ODBC driver on Linux and macOS.

Configure and connect

Article Description
DSN and connection string keywords and attributes The full catalog of connection string keywords, DSN entries, and SQLSetConnectAttr attributes, with accepted values for each.
Connection string keywords and data source names (Linux and macOS) How odbc.ini and odbcinst.ini define a DSN on Linux and macOS, plus the TLS and TCP keep-alive settings specific to those platforms.
ODBC Data Source Administrator DSN (Windows) Every option on the Windows DSN wizard pages, for when you configure a data source through the UI instead of a connection string.
Driver-aware connection pooling (Windows) Which connection string keywords and attributes put a connection in its own pool, and which ones cost an extra round trip to reset.

Authenticate and secure

Article Description
Use Microsoft Entra ID with the ODBC driver Every Authentication keyword value, from managed identity and service principal to interactive and integrated, with the setup each one needs.
Use Always Encrypted with the ODBC driver Encrypt sensitive columns in the client process so plaintext never reaches the server, with the driver's API summary and its documented limitations.
Data classification Read the sensitivity labels the server attaches to classified columns, so your application can enforce its own data protection policy.
Use integrated authentication (Linux and macOS) Configure Kerberos so a Linux or macOS client can connect with Windows credentials instead of a SQL Server login.

High availability and resiliency

Article Description
Connection resiliency How ConnectRetryCount and ConnectRetryInterval restore a connection when the server drops it while idle, and the IMCxx errors the driver returns when recovery isn't possible.
High availability and disaster recovery Connect through an availability group listener and use MultiSubnetFailover so failover doesn't stall on a subnet timeout.
Use transparent network IP resolution How the legacy TransparentNetworkIPResolution fallback orders connection attempts across multiple IP addresses, and why MultiSubnetFailover supersedes it.

Work with data

Article Description
Vector data type Bind, send, and retrieve the vector type, including its native C representation and bulk copy support.
Use XA transactions with DTC Enlist SQL Server in a distributed transaction through the Microsoft Distributed Transaction Coordinator on Windows, Linux, or macOS.
Programming guidelines (Linux and macOS) Which features the driver supports on Linux and macOS, which it doesn't, and how character set and OpenSSL handling differ from Windows.

Diagnose and troubleshoot

Article Description
Connection encryption troubleshooting Fix the certificate and encryption errors that version 18 surfaces because it encrypts by default.
Data access tracing (Linux and macOS) Turn on driver tracing and capture a log file when you need to see the calls your application actually makes.
Known issues (Linux and macOS) Confirmed defects and their workarounds. Check here before you file a support case.
Frequently asked questions (Linux and macOS) Short answers to the questions that come up most often about the driver on Linux and macOS.

Release notes and bug fixes

Article Description
Release notes for Windows New features, behavior changes, and fixes in each Windows driver release.
Release notes for Linux and macOS New features, behavior changes, and fixes in each Linux and macOS driver release.
Release notes for the SQL Server tools Changes to the sqlcmd and bcp utilities, which install separately from the driver on Linux and macOS.

Reference

Article Description
ODBC driver on Windows A version-by-version summary of what the driver supports on Windows, and an index of the Windows-specific articles.
Features of the ODBC driver on Windows Which release introduced each Windows feature, plus the behavior changes that came with it.