.. | .. |
---|
11 | 11 | #include <linux/flex_proportions.h> |
---|
12 | 12 | #include <linux/backing-dev-defs.h> |
---|
13 | 13 | #include <linux/blk_types.h> |
---|
| 14 | +#include <linux/blk-cgroup.h> |
---|
14 | 15 | |
---|
15 | 16 | struct bio; |
---|
16 | 17 | |
---|
.. | .. |
---|
68 | 69 | unsigned for_reclaim:1; /* Invoked from the page allocator */ |
---|
69 | 70 | unsigned range_cyclic:1; /* range_start is cyclic */ |
---|
70 | 71 | unsigned for_sync:1; /* sync(2) WB_SYNC_ALL writeback */ |
---|
| 72 | + |
---|
| 73 | + /* |
---|
| 74 | + * When writeback IOs are bounced through async layers, only the |
---|
| 75 | + * initial synchronous phase should be accounted towards inode |
---|
| 76 | + * cgroup ownership arbitration to avoid confusion. Later stages |
---|
| 77 | + * can set the following flag to disable the accounting. |
---|
| 78 | + */ |
---|
| 79 | + unsigned no_cgroup_owner:1; |
---|
| 80 | + |
---|
| 81 | + unsigned punt_to_cgroup:1; /* cgrp punting, see __REQ_CGROUP_PUNT */ |
---|
| 82 | + |
---|
71 | 83 | #ifdef CONFIG_CGROUP_WRITEBACK |
---|
72 | 84 | struct bdi_writeback *wb; /* wb this writeback is issued under */ |
---|
73 | 85 | struct inode *inode; /* inode being written out */ |
---|
.. | .. |
---|
84 | 96 | |
---|
85 | 97 | static inline int wbc_to_write_flags(struct writeback_control *wbc) |
---|
86 | 98 | { |
---|
87 | | - if (wbc->sync_mode == WB_SYNC_ALL) |
---|
88 | | - return REQ_SYNC; |
---|
89 | | - else if (wbc->for_kupdate || wbc->for_background) |
---|
90 | | - return REQ_BACKGROUND; |
---|
| 99 | + int flags = 0; |
---|
91 | 100 | |
---|
92 | | - return 0; |
---|
| 101 | + if (wbc->punt_to_cgroup) |
---|
| 102 | + flags = REQ_CGROUP_PUNT; |
---|
| 103 | + |
---|
| 104 | + if (wbc->sync_mode == WB_SYNC_ALL) |
---|
| 105 | + flags |= REQ_SYNC; |
---|
| 106 | + else if (wbc->for_kupdate || wbc->for_background) |
---|
| 107 | + flags |= REQ_BACKGROUND; |
---|
| 108 | + |
---|
| 109 | + return flags; |
---|
| 110 | +} |
---|
| 111 | + |
---|
| 112 | +static inline struct cgroup_subsys_state * |
---|
| 113 | +wbc_blkcg_css(struct writeback_control *wbc) |
---|
| 114 | +{ |
---|
| 115 | +#ifdef CONFIG_CGROUP_WRITEBACK |
---|
| 116 | + if (wbc->wb) |
---|
| 117 | + return wbc->wb->blkcg_css; |
---|
| 118 | +#endif |
---|
| 119 | + return blkcg_root_css; |
---|
93 | 120 | } |
---|
94 | 121 | |
---|
95 | 122 | /* |
---|
.. | .. |
---|
170 | 197 | void wakeup_flusher_threads_bdi(struct backing_dev_info *bdi, |
---|
171 | 198 | enum wb_reason reason); |
---|
172 | 199 | void inode_wait_for_writeback(struct inode *inode); |
---|
| 200 | +void inode_io_list_del(struct inode *inode); |
---|
173 | 201 | |
---|
174 | 202 | /* writeback.h requires fs.h; it, too, is not included from here. */ |
---|
175 | 203 | static inline void wait_on_inode(struct inode *inode) |
---|
.. | .. |
---|
188 | 216 | struct inode *inode) |
---|
189 | 217 | __releases(&inode->i_lock); |
---|
190 | 218 | void wbc_detach_inode(struct writeback_control *wbc); |
---|
191 | | -void wbc_account_io(struct writeback_control *wbc, struct page *page, |
---|
192 | | - size_t bytes); |
---|
| 219 | +void wbc_account_cgroup_owner(struct writeback_control *wbc, struct page *page, |
---|
| 220 | + size_t bytes); |
---|
| 221 | +int cgroup_writeback_by_id(u64 bdi_id, int memcg_id, unsigned long nr_pages, |
---|
| 222 | + enum wb_reason reason, struct wb_completion *done); |
---|
193 | 223 | void cgroup_writeback_umount(void); |
---|
194 | 224 | |
---|
195 | 225 | /** |
---|
.. | .. |
---|
246 | 276 | * |
---|
247 | 277 | * @bio is a part of the writeback in progress controlled by @wbc. Perform |
---|
248 | 278 | * writeback specific initialization. This is used to apply the cgroup |
---|
249 | | - * writeback context. |
---|
| 279 | + * writeback context. Must be called after the bio has been associated with |
---|
| 280 | + * a device. |
---|
250 | 281 | */ |
---|
251 | 282 | static inline void wbc_init_bio(struct writeback_control *wbc, struct bio *bio) |
---|
252 | 283 | { |
---|
.. | .. |
---|
257 | 288 | * regular writeback instead of writing things out itself. |
---|
258 | 289 | */ |
---|
259 | 290 | if (wbc->wb) |
---|
260 | | - bio_associate_blkcg(bio, wbc->wb->blkcg_css); |
---|
| 291 | + bio_associate_blkg_from_css(bio, wbc->wb->blkcg_css); |
---|
261 | 292 | } |
---|
262 | 293 | |
---|
263 | 294 | #else /* CONFIG_CGROUP_WRITEBACK */ |
---|
.. | .. |
---|
290 | 321 | { |
---|
291 | 322 | } |
---|
292 | 323 | |
---|
293 | | -static inline void wbc_account_io(struct writeback_control *wbc, |
---|
294 | | - struct page *page, size_t bytes) |
---|
| 324 | +static inline void wbc_account_cgroup_owner(struct writeback_control *wbc, |
---|
| 325 | + struct page *page, size_t bytes) |
---|
295 | 326 | { |
---|
296 | 327 | } |
---|
297 | 328 | |
---|
.. | .. |
---|
332 | 363 | extern int block_dump; |
---|
333 | 364 | extern int laptop_mode; |
---|
334 | 365 | |
---|
335 | | -extern int dirty_background_ratio_handler(struct ctl_table *table, int write, |
---|
336 | | - void __user *buffer, size_t *lenp, |
---|
337 | | - loff_t *ppos); |
---|
338 | | -extern int dirty_background_bytes_handler(struct ctl_table *table, int write, |
---|
339 | | - void __user *buffer, size_t *lenp, |
---|
340 | | - loff_t *ppos); |
---|
341 | | -extern int dirty_ratio_handler(struct ctl_table *table, int write, |
---|
342 | | - void __user *buffer, size_t *lenp, |
---|
343 | | - loff_t *ppos); |
---|
344 | | -extern int dirty_bytes_handler(struct ctl_table *table, int write, |
---|
345 | | - void __user *buffer, size_t *lenp, |
---|
346 | | - loff_t *ppos); |
---|
| 366 | +int dirty_background_ratio_handler(struct ctl_table *table, int write, |
---|
| 367 | + void *buffer, size_t *lenp, loff_t *ppos); |
---|
| 368 | +int dirty_background_bytes_handler(struct ctl_table *table, int write, |
---|
| 369 | + void *buffer, size_t *lenp, loff_t *ppos); |
---|
| 370 | +int dirty_ratio_handler(struct ctl_table *table, int write, |
---|
| 371 | + void *buffer, size_t *lenp, loff_t *ppos); |
---|
| 372 | +int dirty_bytes_handler(struct ctl_table *table, int write, |
---|
| 373 | + void *buffer, size_t *lenp, loff_t *ppos); |
---|
347 | 374 | int dirtytime_interval_handler(struct ctl_table *table, int write, |
---|
348 | | - void __user *buffer, size_t *lenp, loff_t *ppos); |
---|
349 | | - |
---|
350 | | -struct ctl_table; |
---|
351 | | -int dirty_writeback_centisecs_handler(struct ctl_table *, int, |
---|
352 | | - void __user *, size_t *, loff_t *); |
---|
| 375 | + void *buffer, size_t *lenp, loff_t *ppos); |
---|
| 376 | +int dirty_writeback_centisecs_handler(struct ctl_table *table, int write, |
---|
| 377 | + void *buffer, size_t *lenp, loff_t *ppos); |
---|
353 | 378 | |
---|
354 | 379 | void global_dirty_limits(unsigned long *pbackground, unsigned long *pdirty); |
---|
355 | 380 | unsigned long wb_calc_thresh(struct bdi_writeback *wb, unsigned long thresh); |
---|