1
2
3
4
5#ifndef PAGE_FLAGS_H
6#define PAGE_FLAGS_H
7
8#include <linux/types.h>
9#ifndef __GENERATING_BOUNDS_H
10#include <linux/mm_types.h>
11#include <generated/bounds.h>
12#endif
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72enum pageflags {
73 PG_locked,
74 PG_error,
75 PG_referenced,
76 PG_uptodate,
77 PG_dirty,
78 PG_lru,
79 PG_active,
80 PG_slab,
81 PG_owner_priv_1,
82 PG_arch_1,
83 PG_reserved,
84 PG_private,
85 PG_private_2,
86 PG_writeback,
87#ifdef CONFIG_PAGEFLAGS_EXTENDED
88 PG_head,
89 PG_tail,
90#else
91 PG_compound,
92#endif
93 PG_swapcache,
94 PG_mappedtodisk,
95 PG_reclaim,
96 PG_swapbacked,
97 PG_unevictable,
98#ifdef CONFIG_MMU
99 PG_mlocked,
100#endif
101#ifdef CONFIG_ARCH_USES_PG_UNCACHED
102 PG_uncached,
103#endif
104#ifdef CONFIG_MEMORY_FAILURE
105 PG_hwpoison,
106#endif
107#ifdef CONFIG_TRANSPARENT_HUGEPAGE
108 PG_compound_lock,
109#endif
110 __NR_PAGEFLAGS,
111
112
113 PG_checked = PG_owner_priv_1,
114
115
116
117
118
119 PG_fscache = PG_private_2,
120
121
122 PG_pinned = PG_owner_priv_1,
123 PG_savepinned = PG_dirty,
124
125
126 PG_slob_free = PG_private,
127};
128
129#ifndef __GENERATING_BOUNDS_H
130
131
132
133
134#define TESTPAGEFLAG(uname, lname) \
135static inline int Page##uname(const struct page *page) \
136 { return test_bit(PG_##lname, &page->flags); }
137
138#define SETPAGEFLAG(uname, lname) \
139static inline void SetPage##uname(struct page *page) \
140 { set_bit(PG_##lname, &page->flags); }
141
142#define CLEARPAGEFLAG(uname, lname) \
143static inline void ClearPage##uname(struct page *page) \
144 { clear_bit(PG_##lname, &page->flags); }
145
146#define __SETPAGEFLAG(uname, lname) \
147static inline void __SetPage##uname(struct page *page) \
148 { __set_bit(PG_##lname, &page->flags); }
149
150#define __CLEARPAGEFLAG(uname, lname) \
151static inline void __ClearPage##uname(struct page *page) \
152 { __clear_bit(PG_##lname, &page->flags); }
153
154#define TESTSETFLAG(uname, lname) \
155static inline int TestSetPage##uname(struct page *page) \
156 { return test_and_set_bit(PG_##lname, &page->flags); }
157
158#define TESTCLEARFLAG(uname, lname) \
159static inline int TestClearPage##uname(struct page *page) \
160 { return test_and_clear_bit(PG_##lname, &page->flags); }
161
162#define __TESTCLEARFLAG(uname, lname) \
163static inline int __TestClearPage##uname(struct page *page) \
164 { return __test_and_clear_bit(PG_##lname, &page->flags); }
165
166#define PAGEFLAG(uname, lname) TESTPAGEFLAG(uname, lname) \
167 SETPAGEFLAG(uname, lname) CLEARPAGEFLAG(uname, lname)
168
169#define __PAGEFLAG(uname, lname) TESTPAGEFLAG(uname, lname) \
170 __SETPAGEFLAG(uname, lname) __CLEARPAGEFLAG(uname, lname)
171
172#define PAGEFLAG_FALSE(uname) \
173static inline int Page##uname(const struct page *page) \
174 { return 0; }
175
176#define TESTSCFLAG(uname, lname) \
177 TESTSETFLAG(uname, lname) TESTCLEARFLAG(uname, lname)
178
179#define SETPAGEFLAG_NOOP(uname) \
180static inline void SetPage##uname(struct page *page) { }
181
182#define CLEARPAGEFLAG_NOOP(uname) \
183static inline void ClearPage##uname(struct page *page) { }
184
185#define __CLEARPAGEFLAG_NOOP(uname) \
186static inline void __ClearPage##uname(struct page *page) { }
187
188#define TESTCLEARFLAG_FALSE(uname) \
189static inline int TestClearPage##uname(struct page *page) { return 0; }
190
191#define __TESTCLEARFLAG_FALSE(uname) \
192static inline int __TestClearPage##uname(struct page *page) { return 0; }
193
194struct page;
195
196TESTPAGEFLAG(Locked, locked)
197PAGEFLAG(Error, error) TESTCLEARFLAG(Error, error)
198PAGEFLAG(Referenced, referenced) TESTCLEARFLAG(Referenced, referenced)
199PAGEFLAG(Dirty, dirty) TESTSCFLAG(Dirty, dirty) __CLEARPAGEFLAG(Dirty, dirty)
200PAGEFLAG(LRU, lru) __CLEARPAGEFLAG(LRU, lru)
201PAGEFLAG(Active, active) __CLEARPAGEFLAG(Active, active)
202 TESTCLEARFLAG(Active, active)
203__PAGEFLAG(Slab, slab)
204PAGEFLAG(Checked, checked)
205PAGEFLAG(Pinned, pinned) TESTSCFLAG(Pinned, pinned)
206PAGEFLAG(SavePinned, savepinned);
207PAGEFLAG(Reserved, reserved) __CLEARPAGEFLAG(Reserved, reserved)
208PAGEFLAG(SwapBacked, swapbacked) __CLEARPAGEFLAG(SwapBacked, swapbacked)
209
210__PAGEFLAG(SlobFree, slob_free)
211
212
213
214
215
216
217PAGEFLAG(Private, private) __SETPAGEFLAG(Private, private)
218 __CLEARPAGEFLAG(Private, private)
219PAGEFLAG(Private2, private_2) TESTSCFLAG(Private2, private_2)
220PAGEFLAG(OwnerPriv1, owner_priv_1) TESTCLEARFLAG(OwnerPriv1, owner_priv_1)
221
222
223
224
225
226TESTPAGEFLAG(Writeback, writeback) TESTSCFLAG(Writeback, writeback)
227PAGEFLAG(MappedToDisk, mappedtodisk)
228
229
230PAGEFLAG(Reclaim, reclaim) TESTCLEARFLAG(Reclaim, reclaim)
231PAGEFLAG(Readahead, reclaim)
232
233#ifdef CONFIG_HIGHMEM
234
235
236
237
238#define PageHighMem(__p) is_highmem(page_zone(__p))
239#else
240PAGEFLAG_FALSE(HighMem)
241#endif
242
243#ifdef CONFIG_SWAP
244PAGEFLAG(SwapCache, swapcache)
245#else
246PAGEFLAG_FALSE(SwapCache)
247 SETPAGEFLAG_NOOP(SwapCache) CLEARPAGEFLAG_NOOP(SwapCache)
248#endif
249
250PAGEFLAG(Unevictable, unevictable) __CLEARPAGEFLAG(Unevictable, unevictable)
251 TESTCLEARFLAG(Unevictable, unevictable)
252
253#ifdef CONFIG_MMU
254PAGEFLAG(Mlocked, mlocked) __CLEARPAGEFLAG(Mlocked, mlocked)
255 TESTSCFLAG(Mlocked, mlocked) __TESTCLEARFLAG(Mlocked, mlocked)
256#else
257PAGEFLAG_FALSE(Mlocked) SETPAGEFLAG_NOOP(Mlocked)
258 TESTCLEARFLAG_FALSE(Mlocked) __TESTCLEARFLAG_FALSE(Mlocked)
259#endif
260
261#ifdef CONFIG_ARCH_USES_PG_UNCACHED
262PAGEFLAG(Uncached, uncached)
263#else
264PAGEFLAG_FALSE(Uncached)
265#endif
266
267#ifdef CONFIG_MEMORY_FAILURE
268PAGEFLAG(HWPoison, hwpoison)
269TESTSCFLAG(HWPoison, hwpoison)
270#define __PG_HWPOISON (1UL << PG_hwpoison)
271#else
272PAGEFLAG_FALSE(HWPoison)
273#define __PG_HWPOISON 0
274#endif
275
276u64 stable_page_flags(struct page *page);
277
278static inline int PageUptodate(struct page *page)
279{
280 int ret = test_bit(PG_uptodate, &(page)->flags);
281
282
283
284
285
286
287
288
289
290 if (ret)
291 smp_rmb();
292
293 return ret;
294}
295
296static inline void __SetPageUptodate(struct page *page)
297{
298 smp_wmb();
299 __set_bit(PG_uptodate, &(page)->flags);
300}
301
302static inline void SetPageUptodate(struct page *page)
303{
304#ifdef CONFIG_S390
305 if (!test_and_set_bit(PG_uptodate, &page->flags))
306 page_set_storage_key(page_to_phys(page), PAGE_DEFAULT_KEY, 0);
307#else
308
309
310
311
312
313
314
315
316 smp_wmb();
317 set_bit(PG_uptodate, &(page)->flags);
318#endif
319}
320
321CLEARPAGEFLAG(Uptodate, uptodate)
322
323extern void cancel_dirty_page(struct page *page, unsigned int account_size);
324
325int test_clear_page_writeback(struct page *page);
326int test_set_page_writeback(struct page *page);
327
328static inline void set_page_writeback(struct page *page)
329{
330 test_set_page_writeback(page);
331}
332
333#ifdef CONFIG_PAGEFLAGS_EXTENDED
334
335
336
337
338
339
340__PAGEFLAG(Head, head) CLEARPAGEFLAG(Head, head)
341__PAGEFLAG(Tail, tail)
342
343static inline int PageCompound(struct page *page)
344{
345 return page->flags & ((1L << PG_head) | (1L << PG_tail));
346
347}
348#ifdef CONFIG_TRANSPARENT_HUGEPAGE
349static inline void ClearPageCompound(struct page *page)
350{
351 BUG_ON(!PageHead(page));
352 ClearPageHead(page);
353}
354#endif
355#else
356
357
358
359
360
361
362TESTPAGEFLAG(Compound, compound)
363__PAGEFLAG(Head, compound)
364
365
366
367
368
369
370
371
372
373
374
375#define PG_head_tail_mask ((1L << PG_compound) | (1L << PG_reclaim))
376
377static inline int PageTail(struct page *page)
378{
379 return ((page->flags & PG_head_tail_mask) == PG_head_tail_mask);
380}
381
382static inline void __SetPageTail(struct page *page)
383{
384 page->flags |= PG_head_tail_mask;
385}
386
387static inline void __ClearPageTail(struct page *page)
388{
389 page->flags &= ~PG_head_tail_mask;
390}
391
392#ifdef CONFIG_TRANSPARENT_HUGEPAGE
393static inline void ClearPageCompound(struct page *page)
394{
395 BUG_ON((page->flags & PG_head_tail_mask) != (1 << PG_compound));
396 clear_bit(PG_compound, &page->flags);
397}
398#endif
399
400#endif
401
402#ifdef CONFIG_TRANSPARENT_HUGEPAGE
403
404
405
406
407
408
409
410
411static inline int PageTransHuge(struct page *page)
412{
413 VM_BUG_ON(PageTail(page));
414 return PageHead(page);
415}
416
417static inline int PageTransCompound(struct page *page)
418{
419 return PageCompound(page);
420}
421
422#else
423
424static inline int PageTransHuge(struct page *page)
425{
426 return 0;
427}
428
429static inline int PageTransCompound(struct page *page)
430{
431 return 0;
432}
433#endif
434
435#ifdef CONFIG_MMU
436#define __PG_MLOCKED (1 << PG_mlocked)
437#else
438#define __PG_MLOCKED 0
439#endif
440
441#ifdef CONFIG_TRANSPARENT_HUGEPAGE
442#define __PG_COMPOUND_LOCK (1 << PG_compound_lock)
443#else
444#define __PG_COMPOUND_LOCK 0
445#endif
446
447
448
449
450
451#define PAGE_FLAGS_CHECK_AT_FREE \
452 (1 << PG_lru | 1 << PG_locked | \
453 1 << PG_private | 1 << PG_private_2 | \
454 1 << PG_writeback | 1 << PG_reserved | \
455 1 << PG_slab | 1 << PG_swapcache | 1 << PG_active | \
456 1 << PG_unevictable | __PG_MLOCKED | __PG_HWPOISON | \
457 __PG_COMPOUND_LOCK)
458
459
460
461
462
463
464#define PAGE_FLAGS_CHECK_AT_PREP ((1 << NR_PAGEFLAGS) - 1)
465
466#define PAGE_FLAGS_PRIVATE \
467 (1 << PG_private | 1 << PG_private_2)
468
469
470
471
472
473
474
475static inline int page_has_private(struct page *page)
476{
477 return !!(page->flags & PAGE_FLAGS_PRIVATE);
478}
479
480#endif
481
482#endif
483