#author("2025-09-11T11:22:14+09:00","default:guest","guest")
#author("2025-09-11T11:23:19+09:00","default:guest","guest")
*参照元 [#yae1b76a]
#backlinks

*説明 [#y6bdf0a8]
-パス: [[linux-5.15/mm/compaction.c]]

-FIXME: これは何?
--説明


**引数 [#cf2fa82f]
-struct zone *zone
--メモリゾーン。
--[[linux-5.15/zone]]
-int order
--オーダー
-unsigned int alloc_flags
--割当フラグ
-int highest_zoneidx
--この値以下のゾーンから割り当てる
-unsigned long wmark_target
--閾値、空きページ数や利用可能なページ数を指定する


**返り値 [#c61a2469]
-enum compact_result
--COMPACT_SKIPPED  - コンパクションするための空きページが足りない(のでコンパクションしない)
--COMPACT_SUCCESS  - コンパクションしなくても割当が成功する(のでコンパクションしない)
--COMPACT_CONTINUE - コンパクションすべき


**参考 [#fe7fb776]


*実装 [#a2bbec0c]

 static enum compact_result __compaction_suitable(struct zone *zone, int order,
 					unsigned int alloc_flags,
 					int highest_zoneidx,
 					unsigned long wmark_target)
 {
 	unsigned long watermark;
 
 	if (is_via_compact_memory(order))
 		return COMPACT_CONTINUE;
 
 	watermark = wmark_pages(zone, alloc_flags & ALLOC_WMARK_MASK);
 	/*
 	 * If watermarks for high-order allocation are already met, there
 	 * should be no need for compaction at all.
 	 */
 	if (zone_watermark_ok(zone, order, watermark, highest_zoneidx,
 								alloc_flags))
 		return COMPACT_SUCCESS;
 
-watermarkその1の判定
--判定の目的は「現時点でメモリ割当可能ならコンパクションしない」です。watermarkを超える空きページがあるので、コンパクションは不要と判断します。
-alloc_flags & ALLOC_WMARK_MASKの意味
--ALLOC_WMARK_MASK = 4 - 1 = 3で、alloc_flagsのビットフィールド0~1の値を取得します。値はstruct zoneの配列_watermarkの添字にします。
-値の意味はenum zone_watermarksと同じで下記の通り。
--0: min   = WMARK_MIN
--1: low   = WMARK_LOW
--2: high  = WMARK_HIGH
--3: 使わない
--[[linux-5.15/is_via_compact_memory()]]
--[[linux-5.15/wmark_pages()]]
--[[linux-5.15/zone_watermark_ok()]]

 	/*
 	 * Watermarks for order-0 must be met for compaction to be able to
 	 * isolate free pages for migration targets. This means that the
 	 * watermark and alloc_flags have to match, or be more pessimistic than
 	 * the check in __isolate_free_page(). We don't use the direct
 	 * compactor's alloc_flags, as they are not relevant for freepage
 	 * isolation. We however do use the direct compactor's highest_zoneidx
 	 * to skip over zones where lowmem reserves would prevent allocation
 	 * even if compaction succeeds.
 	 * For costly orders, we require low watermark instead of min for
 	 * compaction to proceed to increase its chances.
 	 * ALLOC_CMA is used, as pages in CMA pageblocks are considered
 	 * suitable migration targets
 	 */
 	watermark = (order > PAGE_ALLOC_COSTLY_ORDER) ?
 				low_wmark_pages(zone) : min_wmark_pages(zone);
 	watermark += compact_gap(order);
 	if (!__zone_watermark_ok(zone, 0, watermark, highest_zoneidx,
 						ALLOC_CMA, wmark_target))
 		return COMPACT_SKIPPED;
 
-watermarkその2の判定
--判定の目的は「空きページが足りないならコンパクションしない」です。コンパクションに必要な空きページが足りないので、コンパクションは不要と判断します。
--order 4以上: low watermarkを使います
--order 3以下: min watermarkを使います(PAGE_ALLOC_COSTLY_ORDER = 3)
--さらにcompact_gap() = (2 << order)を加算します(値の意味は後述(※))から、
--さらにcompact_gap() = (2 << order)を加算します(値の意味はcompact_gapのコメント参照)から、
--watermark2 = low or min watermark + (2 << order)
-引数ALLOC_CMAは割当てにCMAも使ってよいことを意味します。
-引数wmark_targetの値は呼び出し元を見ると、zone_page_state(zone, NR_FREE_PAGES)が指定されています。値は/proc/zoneinfoのpages freeで確認できます。
--[[linux-5.15/__zone_watermark_ok()]]
--[[linux-5.15/compact_gap()]]

 	return COMPACT_CONTINUE;
 }



*コメント [#v1674188]

トップ   編集 差分 履歴 添付 複製 名前変更 リロード   新規 一覧 検索 最終更新   ヘルプ   最終更新のRSS