自己レスです。
※10カ月近くほったらかしでした。申し訳ないです。
質問時と若干環境が変わり、sessionStateをDBステート<sessionState mode="SQLServer"に切り替えました。
但しDBステートに変えても、同様のエラーが出ていました。
試行錯誤の結果、多重ですが以下の対策を施しました。
①Boot.iniに/3GBスイッチを適用。
②巨大なDataTableはSessionオブジェクトに入れるのを止め、DB上に自前の該当DataTable用テーブルを作り、セッションと同じように、アクセス時にデータを読み込み(SELECT)、Page.Unload時にデータをテーブルに書き出す(BULK)仕組みを作成。
③IISのアプリケーションプールのメモリリサイクル量を仮想800MB、使用700MBを上限とした。
④IISのWebガーデンをCPU個分増やした。
⑤web.config(グローバル/ローカル共に)から不要なアセンブリを削除。
導入理由と効果についてですが
①の対策
メモリの使用上限をアップ。
以前の2倍ぐらいのデータ量までOutOfMemoryExceptionは出なくなりました。
②の対策
直接原因であるStringBuilder発のエラーを避けるための緊急処置。
以前の4倍のデータ量ではOutOfMemoryExceptionで出なくなりました。(4倍以上は試していません)
意外なことに処理速度も30%ぐらい向上しました。
※セッションを利用しないと同義ですが…
③の対策
直接対策というよりメモリ確保量が多くなり、危険な状態のワーカープロセスをサクサク終了するためです。
OutOfMemoryExceptionの発生頻度が9/10~1/2ぐらいになりました。
④の対策
危険な状態のワーカープロセスの利用頻度を下げられるのでは?と思い導入。
OutOfMemoryExceptionの発生頻度が3/4~1/2ぐらいになりました。
⑤の対策
一部のHPアセンブリが多いとOutOfMemoryExceptionが発生しやすいと書かれていたので導入。
効果は不明です。
印象的には②が最も効果的でした。
上記の対策が効いたのか、ここ数カ月OutOfMemoryExceptionは発生していません。
なお、.NETFramework自体にもOutOfMemoryExceptionが発生する不具合があったので、以下のパッチも導入予定です。
⑥.NETFramework2.0 SP1