Understanding SQL Server’s High Memory Usage: What You Need to Know
“Why is SQL Server memory usage high?” If you haven’t been asked this question, you haven’t supported SQL Server long enough.
I’ve encountered managers, systems administrators, and developers who’ve wondered this. Simply put, data reads are much faster in RAM than from disks. RAM latency is typically measured in nanoseconds. By contrast, disk latency is measured in milliseconds.
It’s not uncommon to find dedicated SQL Server machines with 90% of memory allocated to the sqlservr.exe process (another reason to use dedicated SQL Server machines, but that’s for another post).
Let’s take a high-level look at how SQL Server uses memory so the next time you’re asked why memory usage is so high, you’ll be able to respond and explain why this is typically ok.
Buffer Pool (Cache)
This is the largest memory area used for caching data and index pages. SQL Server keeps data in memory to minimize expensive disk I/O operations. Many things can affect how long pages are kept in the cache, but we won’t cover those here. When you adjust SQL Server’s max memory setting, you’re telling SQL Server how much memory it can use for the Buffer Pool (this affects other types of memory allocations as well, but the Buffer Pool is the largest consumer).
If you’ve adjusted max memory but still see that the sqlservr.exe process is consuming more, it’s because SQL Server has additional memory requirements unaffected by this setting. See “SQL Server might commit memory over the max memory setting” for some reasons why you may be experiencing this.
Plan Cache
The plan cache stores execution plans to avoid the cost of recompiling queries. You see, when SQL Server compiles a query, it must perform several steps:
- Parse the query.
- Bind it by resolving objects (tables, columns, etc) referenced in the query to ensure they exist. Validate data types, perform implicit conversions (try to avoid these if possible), and ensure logical operators in the query are bound to database objects to ensure it can actually execute.
- Next, the optimizer takes the parsed query and attempts to generate the most efficient execution plan (the keyword here is attempts). This is a critical step.
- Next, the plan is finalized and converted into a format SQL Server can execute.
- Then, the plan is stored in the plan cache for future reuse, provided the same query is executed.
Just like with the Buffer Pool, various things can affect plan reuse or force a query to be recompiled. Again, I won’t go too far into that today.
The max memory setting influences the plan cache size and is managed dynamically within this allocation. For a more in-depth understanding of SQL Server’s plan cache limits and memory management, see Erin Stellato’s blog post on SQLskills.
Worker Threads and Connections
SQL Server needs memory to manage worker threads and connections. These are critical components of its query execution engine.
Worker threads are responsible for executing tasks in SQL Server (running queries, handling requests, and performing background tasks). Each thread needs a certain amount of memory to function. These can be adjusted through the max worker threads configuration setting. I can’t recall a time I’ve ever needed to change this setting. If you find yourself thinking you need to change the default, check out Brent Ozar’s post here.
Each client’s connection to SQL Server requires memory to handle communication and processing.
- Connection Context – Session settings, Query and command states, etc.
If you want to take a deep dive into threads, review Microsoft’s Thread and Tasks Architecture Guide.
Memory for Internal Processes
SQL Server performs various operations during query execution and other activities. It needs memory to do that.
- Locking
- Sorting
- Hash Joins
- Temporary Objects (that don’t spill over to tempdb)
In-memory OLTP (Memory-Optimized Tables)
This feature was introduced in SQL Server 2014 and designed for high-performance transactions. It can consume large amounts of memory; you should plan carefully before using this feature. See here for more information on managing memory allocated to these objects using SQL Server’s Resource Governor.
In Conclusion
High memory usage in SQL Server is not a problem—it’s a feature that improves performance by reducing reliance on slower disk operations.
Ready to Optimize Your SQL Server?
Discover how The SERO Group can take the guesswork out of SQL Server management. Schedule a no-obligation discovery call today!