案件の概要
社内のメーリングリストに「SQL Serverプロセスがメモリリークしていて、調査を助けてほしい。」というメールがとんできました。よく読んでみると、どうやら、過去に私が担当したことのあるお客様の環境のようです。私がお手伝いしたのはSQL Server 2000からSQL Server 2005へのアップグレードプロジェクトでしたが、つい数カ月前にその環境をSQL Server 2012へアップグレードしたとのこと。そして、最近になってSQL Serverプロセスのメモリ - private bytes - が右肩上がりに増えていることに気がついたらしいのです。
private bytesが右肩上がりに増えるということは…
さて、SQL Server プロセスのprivate bytesが右肩上がりに増えると、なぜSQL Serverがリークしているということになるのでしょう?お客様は、SQL Serverのサービスアカウントにlock pages in memory特権を与えて、AWEモデル*1を使用していましたが、working setを見てもAWEのようなnonpageable memoryはカウントされないからでしょうか?でも、working setとprivate bytesは別物です。
*1 SQL Serverのメモリモデルは、Conventional (既定), AWE, Large Pageの3つがあります。
実は、「private bytesが右肩上がりに増える」という情報だけでは、リークしているかどうかはわかりません。Windows Server 2012以降、AWEのメモリはprivate bytesとして確認できるようになっていますし、private bytesとしてカウントされるメモリは、スレッドスタックやプログラムコードなども含まれるからです。例えば、SQL Serverのスレッドは必要に応じて作成されますし、Large Pageモデルでない限りSQL Serverは必要に応じて徐々にメモリを確保します。つまり、右肩上がりに増えていきます。
というわけで、SQL Serverがメモリリークしているかどうかは、どれくらいの割合でメモリが増えているのか?とか、OSはどのバージョンを使用しているのか?とか、これだけではないですけど、いろいろな情報を総合的に考えてメモリリークしていそうだな、という結論に至ります。
少し話がずれましたが、担当者からのヘルプメールには、お客様はWindows Server 2008 R2を使用していて、private bytesが数か月にわたって30GBにも膨れ上がっていることが記載されており、「こりゃリークしとるな。」と思える状況だということがわかりました。