1b411b363SPhilipp Reisner /* 2b411b363SPhilipp Reisner drbd_int.h 3b411b363SPhilipp Reisner 4b411b363SPhilipp Reisner This file is part of DRBD by Philipp Reisner and Lars Ellenberg. 5b411b363SPhilipp Reisner 6b411b363SPhilipp Reisner Copyright (C) 2001-2008, LINBIT Information Technologies GmbH. 7b411b363SPhilipp Reisner Copyright (C) 1999-2008, Philipp Reisner <philipp.reisner@linbit.com>. 8b411b363SPhilipp Reisner Copyright (C) 2002-2008, Lars Ellenberg <lars.ellenberg@linbit.com>. 9b411b363SPhilipp Reisner 10b411b363SPhilipp Reisner drbd is free software; you can redistribute it and/or modify 11b411b363SPhilipp Reisner it under the terms of the GNU General Public License as published by 12b411b363SPhilipp Reisner the Free Software Foundation; either version 2, or (at your option) 13b411b363SPhilipp Reisner any later version. 14b411b363SPhilipp Reisner 15b411b363SPhilipp Reisner drbd is distributed in the hope that it will be useful, 16b411b363SPhilipp Reisner but WITHOUT ANY WARRANTY; without even the implied warranty of 17b411b363SPhilipp Reisner MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 18b411b363SPhilipp Reisner GNU General Public License for more details. 19b411b363SPhilipp Reisner 20b411b363SPhilipp Reisner You should have received a copy of the GNU General Public License 21b411b363SPhilipp Reisner along with drbd; see the file COPYING. If not, write to 22b411b363SPhilipp Reisner the Free Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA. 23b411b363SPhilipp Reisner 24b411b363SPhilipp Reisner */ 25b411b363SPhilipp Reisner 26b411b363SPhilipp Reisner #ifndef _DRBD_INT_H 27b411b363SPhilipp Reisner #define _DRBD_INT_H 28b411b363SPhilipp Reisner 299534d671SHerbert Xu #include <crypto/hash.h> 30b411b363SPhilipp Reisner #include <linux/compiler.h> 31b411b363SPhilipp Reisner #include <linux/types.h> 32b411b363SPhilipp Reisner #include <linux/list.h> 333f07c014SIngo Molnar #include <linux/sched/signal.h> 34b411b363SPhilipp Reisner #include <linux/bitops.h> 35b411b363SPhilipp Reisner #include <linux/slab.h> 36132cc538SRandy Dunlap #include <linux/ratelimit.h> 37b411b363SPhilipp Reisner #include <linux/tcp.h> 38b411b363SPhilipp Reisner #include <linux/mutex.h> 39b411b363SPhilipp Reisner #include <linux/major.h> 40b411b363SPhilipp Reisner #include <linux/blkdev.h> 4166114cadSTejun Heo #include <linux/backing-dev.h> 42b411b363SPhilipp Reisner #include <linux/genhd.h> 43062e879cSPhilipp Reisner #include <linux/idr.h> 449d5059c9SLuis de Bethencourt #include <linux/dynamic_debug.h> 45b411b363SPhilipp Reisner #include <net/tcp.h> 46b411b363SPhilipp Reisner #include <linux/lru_cache.h> 4770c71606SPaul Gortmaker #include <linux/prefetch.h> 483b98c0c2SLars Ellenberg #include <linux/drbd_genl_api.h> 49b8907339SPhilipp Reisner #include <linux/drbd.h> 50d9f65229SAndreas Gruenbacher #include "drbd_strings.h" 51b8907339SPhilipp Reisner #include "drbd_state.h" 52a3603a6eSAndreas Gruenbacher #include "drbd_protocol.h" 53b411b363SPhilipp Reisner 54b411b363SPhilipp Reisner #ifdef __CHECKER__ 55b411b363SPhilipp Reisner # define __protected_by(x) __attribute__((require_context(x,1,999,"rdwr"))) 56b411b363SPhilipp Reisner # define __protected_read_by(x) __attribute__((require_context(x,1,999,"read"))) 57b411b363SPhilipp Reisner # define __protected_write_by(x) __attribute__((require_context(x,1,999,"write"))) 58b411b363SPhilipp Reisner # define __must_hold(x) __attribute__((context(x,1,1), require_context(x,1,999,"call"))) 59b411b363SPhilipp Reisner #else 60b411b363SPhilipp Reisner # define __protected_by(x) 61b411b363SPhilipp Reisner # define __protected_read_by(x) 62b411b363SPhilipp Reisner # define __protected_write_by(x) 63b411b363SPhilipp Reisner # define __must_hold(x) 64b411b363SPhilipp Reisner #endif 65b411b363SPhilipp Reisner 66b411b363SPhilipp Reisner /* module parameter, defined in drbd_main.c */ 67b411b363SPhilipp Reisner extern unsigned int minor_count; 6890ab5ee9SRusty Russell extern bool disable_sendpage; 6990ab5ee9SRusty Russell extern bool allow_oos; 70b30ab791SAndreas Gruenbacher void tl_abort_disk_io(struct drbd_device *device); 71b411b363SPhilipp Reisner 72b411b363SPhilipp Reisner #ifdef CONFIG_DRBD_FAULT_INJECTION 73b411b363SPhilipp Reisner extern int enable_faults; 74b411b363SPhilipp Reisner extern int fault_rate; 75b411b363SPhilipp Reisner extern int fault_devs; 76b411b363SPhilipp Reisner #endif 77b411b363SPhilipp Reisner 78b411b363SPhilipp Reisner extern char usermode_helper[]; 79b411b363SPhilipp Reisner 80b411b363SPhilipp Reisner 81b411b363SPhilipp Reisner /* This is used to stop/restart our threads. 82b411b363SPhilipp Reisner * Cannot use SIGTERM nor SIGKILL, since these 83b411b363SPhilipp Reisner * are sent out by init on runlevel changes 84b411b363SPhilipp Reisner * I choose SIGHUP for now. 85b411b363SPhilipp Reisner */ 86b411b363SPhilipp Reisner #define DRBD_SIGKILL SIGHUP 87b411b363SPhilipp Reisner 88b411b363SPhilipp Reisner #define ID_IN_SYNC (4711ULL) 89b411b363SPhilipp Reisner #define ID_OUT_OF_SYNC (4712ULL) 90b411b363SPhilipp Reisner #define ID_SYNCER (-1ULL) 91579b57edSAndreas Gruenbacher 924a23f264SPhilipp Reisner #define UUID_NEW_BM_OFFSET ((u64)0x0001000000000000ULL) 93b411b363SPhilipp Reisner 9454761697SAndreas Gruenbacher struct drbd_device; 95bde89a9eSAndreas Gruenbacher struct drbd_connection; 96b411b363SPhilipp Reisner 973b52beffSAndreas Gruenbacher #define __drbd_printk_device(level, device, fmt, args...) \ 983b52beffSAndreas Gruenbacher dev_printk(level, disk_to_dev((device)->vdisk), fmt, ## args) 993b52beffSAndreas Gruenbacher #define __drbd_printk_peer_device(level, peer_device, fmt, args...) \ 1003b52beffSAndreas Gruenbacher dev_printk(level, disk_to_dev((peer_device)->device->vdisk), fmt, ## args) 1013b52beffSAndreas Gruenbacher #define __drbd_printk_resource(level, resource, fmt, args...) \ 1023b52beffSAndreas Gruenbacher printk(level "drbd %s: " fmt, (resource)->name, ## args) 1033b52beffSAndreas Gruenbacher #define __drbd_printk_connection(level, connection, fmt, args...) \ 1043b52beffSAndreas Gruenbacher printk(level "drbd %s: " fmt, (connection)->resource->name, ## args) 105b411b363SPhilipp Reisner 1063b52beffSAndreas Gruenbacher void drbd_printk_with_wrong_object_type(void); 1073b52beffSAndreas Gruenbacher 1083b52beffSAndreas Gruenbacher #define __drbd_printk_if_same_type(obj, type, func, level, fmt, args...) \ 1093b52beffSAndreas Gruenbacher (__builtin_types_compatible_p(typeof(obj), type) || \ 1103b52beffSAndreas Gruenbacher __builtin_types_compatible_p(typeof(obj), const type)), \ 1113b52beffSAndreas Gruenbacher func(level, (const type)(obj), fmt, ## args) 1123b52beffSAndreas Gruenbacher 1133b52beffSAndreas Gruenbacher #define drbd_printk(level, obj, fmt, args...) \ 1143b52beffSAndreas Gruenbacher __builtin_choose_expr( \ 1153b52beffSAndreas Gruenbacher __drbd_printk_if_same_type(obj, struct drbd_device *, \ 1163b52beffSAndreas Gruenbacher __drbd_printk_device, level, fmt, ## args), \ 1173b52beffSAndreas Gruenbacher __builtin_choose_expr( \ 1183b52beffSAndreas Gruenbacher __drbd_printk_if_same_type(obj, struct drbd_resource *, \ 1193b52beffSAndreas Gruenbacher __drbd_printk_resource, level, fmt, ## args), \ 1203b52beffSAndreas Gruenbacher __builtin_choose_expr( \ 1213b52beffSAndreas Gruenbacher __drbd_printk_if_same_type(obj, struct drbd_connection *, \ 1223b52beffSAndreas Gruenbacher __drbd_printk_connection, level, fmt, ## args), \ 1233b52beffSAndreas Gruenbacher __builtin_choose_expr( \ 1243b52beffSAndreas Gruenbacher __drbd_printk_if_same_type(obj, struct drbd_peer_device *, \ 1253b52beffSAndreas Gruenbacher __drbd_printk_peer_device, level, fmt, ## args), \ 1263b52beffSAndreas Gruenbacher drbd_printk_with_wrong_object_type())))) 1273b52beffSAndreas Gruenbacher 1283b52beffSAndreas Gruenbacher #define drbd_dbg(obj, fmt, args...) \ 1293b52beffSAndreas Gruenbacher drbd_printk(KERN_DEBUG, obj, fmt, ## args) 1303b52beffSAndreas Gruenbacher #define drbd_alert(obj, fmt, args...) \ 1313b52beffSAndreas Gruenbacher drbd_printk(KERN_ALERT, obj, fmt, ## args) 1323b52beffSAndreas Gruenbacher #define drbd_err(obj, fmt, args...) \ 1333b52beffSAndreas Gruenbacher drbd_printk(KERN_ERR, obj, fmt, ## args) 1343b52beffSAndreas Gruenbacher #define drbd_warn(obj, fmt, args...) \ 1353b52beffSAndreas Gruenbacher drbd_printk(KERN_WARNING, obj, fmt, ## args) 1363b52beffSAndreas Gruenbacher #define drbd_info(obj, fmt, args...) \ 1373b52beffSAndreas Gruenbacher drbd_printk(KERN_INFO, obj, fmt, ## args) 1383b52beffSAndreas Gruenbacher #define drbd_emerg(obj, fmt, args...) \ 1393b52beffSAndreas Gruenbacher drbd_printk(KERN_EMERG, obj, fmt, ## args) 140d0180171SAndreas Gruenbacher 141d0180171SAndreas Gruenbacher #define dynamic_drbd_dbg(device, fmt, args...) \ 142d0180171SAndreas Gruenbacher dynamic_dev_dbg(disk_to_dev(device->vdisk), fmt, ## args) 143b411b363SPhilipp Reisner 1440b0ba1efSAndreas Gruenbacher #define D_ASSERT(device, exp) do { \ 1450b0ba1efSAndreas Gruenbacher if (!(exp)) \ 1460b0ba1efSAndreas Gruenbacher drbd_err(device, "ASSERT( " #exp " ) in %s:%d\n", __FILE__, __LINE__); \ 1470b0ba1efSAndreas Gruenbacher } while (0) 148b411b363SPhilipp Reisner 149841ce241SAndreas Gruenbacher /** 150841ce241SAndreas Gruenbacher * expect - Make an assertion 151841ce241SAndreas Gruenbacher * 152841ce241SAndreas Gruenbacher * Unlike the assert macro, this macro returns a boolean result. 153841ce241SAndreas Gruenbacher */ 154841ce241SAndreas Gruenbacher #define expect(exp) ({ \ 155841ce241SAndreas Gruenbacher bool _bool = (exp); \ 156841ce241SAndreas Gruenbacher if (!_bool) \ 157d0180171SAndreas Gruenbacher drbd_err(device, "ASSERTION %s FAILED in %s\n", \ 158841ce241SAndreas Gruenbacher #exp, __func__); \ 159841ce241SAndreas Gruenbacher _bool; \ 160841ce241SAndreas Gruenbacher }) 161b411b363SPhilipp Reisner 162b411b363SPhilipp Reisner /* Defines to control fault insertion */ 163b411b363SPhilipp Reisner enum { 164b411b363SPhilipp Reisner DRBD_FAULT_MD_WR = 0, /* meta data write */ 165b411b363SPhilipp Reisner DRBD_FAULT_MD_RD = 1, /* read */ 166b411b363SPhilipp Reisner DRBD_FAULT_RS_WR = 2, /* resync */ 167b411b363SPhilipp Reisner DRBD_FAULT_RS_RD = 3, 168b411b363SPhilipp Reisner DRBD_FAULT_DT_WR = 4, /* data */ 169b411b363SPhilipp Reisner DRBD_FAULT_DT_RD = 5, 170b411b363SPhilipp Reisner DRBD_FAULT_DT_RA = 6, /* data read ahead */ 171b411b363SPhilipp Reisner DRBD_FAULT_BM_ALLOC = 7, /* bitmap allocation */ 172b411b363SPhilipp Reisner DRBD_FAULT_AL_EE = 8, /* alloc ee */ 1736b4388acSPhilipp Reisner DRBD_FAULT_RECEIVE = 9, /* Changes some bytes upon receiving a [rs]data block */ 174b411b363SPhilipp Reisner 175b411b363SPhilipp Reisner DRBD_FAULT_MAX, 176b411b363SPhilipp Reisner }; 177b411b363SPhilipp Reisner 178b411b363SPhilipp Reisner extern unsigned int 179b30ab791SAndreas Gruenbacher _drbd_insert_fault(struct drbd_device *device, unsigned int type); 1800cf9d27eSAndreas Gruenbacher 181b411b363SPhilipp Reisner static inline int 182b30ab791SAndreas Gruenbacher drbd_insert_fault(struct drbd_device *device, unsigned int type) { 1830cf9d27eSAndreas Gruenbacher #ifdef CONFIG_DRBD_FAULT_INJECTION 184b411b363SPhilipp Reisner return fault_rate && 185b411b363SPhilipp Reisner (enable_faults & (1<<type)) && 186b30ab791SAndreas Gruenbacher _drbd_insert_fault(device, type); 187b411b363SPhilipp Reisner #else 1880cf9d27eSAndreas Gruenbacher return 0; 189b411b363SPhilipp Reisner #endif 1900cf9d27eSAndreas Gruenbacher } 191b411b363SPhilipp Reisner 192b411b363SPhilipp Reisner /* integer division, round _UP_ to the next integer */ 193b411b363SPhilipp Reisner #define div_ceil(A, B) ((A)/(B) + ((A)%(B) ? 1 : 0)) 194b411b363SPhilipp Reisner /* usual integer division */ 195b411b363SPhilipp Reisner #define div_floor(A, B) ((A)/(B)) 196b411b363SPhilipp Reisner 197b411b363SPhilipp Reisner extern struct ratelimit_state drbd_ratelimit_state; 19805a10ec7SAndreas Gruenbacher extern struct idr drbd_devices; /* RCU, updates: genl_lock() */ 19977c556f6SAndreas Gruenbacher extern struct list_head drbd_resources; /* RCU, updates: genl_lock() */ 200b411b363SPhilipp Reisner 201d8763023SAndreas Gruenbacher extern const char *cmdname(enum drbd_packet cmd); 202b411b363SPhilipp Reisner 203b411b363SPhilipp Reisner /* for sending/receiving the bitmap, 204b411b363SPhilipp Reisner * possibly in some encoding scheme */ 205b411b363SPhilipp Reisner struct bm_xfer_ctx { 206b411b363SPhilipp Reisner /* "const" 207b411b363SPhilipp Reisner * stores total bits and long words 208b411b363SPhilipp Reisner * of the bitmap, so we don't need to 209b411b363SPhilipp Reisner * call the accessor functions over and again. */ 210b411b363SPhilipp Reisner unsigned long bm_bits; 211b411b363SPhilipp Reisner unsigned long bm_words; 212b411b363SPhilipp Reisner /* during xfer, current position within the bitmap */ 213b411b363SPhilipp Reisner unsigned long bit_offset; 214b411b363SPhilipp Reisner unsigned long word_offset; 215b411b363SPhilipp Reisner 216b411b363SPhilipp Reisner /* statistics; index: (h->command == P_BITMAP) */ 217b411b363SPhilipp Reisner unsigned packets[2]; 218b411b363SPhilipp Reisner unsigned bytes[2]; 219b411b363SPhilipp Reisner }; 220b411b363SPhilipp Reisner 221b30ab791SAndreas Gruenbacher extern void INFO_bm_xfer_stats(struct drbd_device *device, 222b411b363SPhilipp Reisner const char *direction, struct bm_xfer_ctx *c); 223b411b363SPhilipp Reisner 224b411b363SPhilipp Reisner static inline void bm_xfer_ctx_bit_to_word_offset(struct bm_xfer_ctx *c) 225b411b363SPhilipp Reisner { 226b411b363SPhilipp Reisner /* word_offset counts "native long words" (32 or 64 bit), 227b411b363SPhilipp Reisner * aligned at 64 bit. 228b411b363SPhilipp Reisner * Encoded packet may end at an unaligned bit offset. 229b411b363SPhilipp Reisner * In case a fallback clear text packet is transmitted in 230b411b363SPhilipp Reisner * between, we adjust this offset back to the last 64bit 231b411b363SPhilipp Reisner * aligned "native long word", which makes coding and decoding 232b411b363SPhilipp Reisner * the plain text bitmap much more convenient. */ 233b411b363SPhilipp Reisner #if BITS_PER_LONG == 64 234b411b363SPhilipp Reisner c->word_offset = c->bit_offset >> 6; 235b411b363SPhilipp Reisner #elif BITS_PER_LONG == 32 236b411b363SPhilipp Reisner c->word_offset = c->bit_offset >> 5; 237b411b363SPhilipp Reisner c->word_offset &= ~(1UL); 238b411b363SPhilipp Reisner #else 239b411b363SPhilipp Reisner # error "unsupported BITS_PER_LONG" 240b411b363SPhilipp Reisner #endif 241b411b363SPhilipp Reisner } 242b411b363SPhilipp Reisner 243bde89a9eSAndreas Gruenbacher extern unsigned int drbd_header_size(struct drbd_connection *connection); 244b411b363SPhilipp Reisner 245b411b363SPhilipp Reisner /**********************************************************************/ 246b411b363SPhilipp Reisner enum drbd_thread_state { 247e77a0a5cSAndreas Gruenbacher NONE, 248e77a0a5cSAndreas Gruenbacher RUNNING, 249e77a0a5cSAndreas Gruenbacher EXITING, 250e77a0a5cSAndreas Gruenbacher RESTARTING 251b411b363SPhilipp Reisner }; 252b411b363SPhilipp Reisner 253b411b363SPhilipp Reisner struct drbd_thread { 254b411b363SPhilipp Reisner spinlock_t t_lock; 255b411b363SPhilipp Reisner struct task_struct *task; 256b411b363SPhilipp Reisner struct completion stop; 257b411b363SPhilipp Reisner enum drbd_thread_state t_state; 258b411b363SPhilipp Reisner int (*function) (struct drbd_thread *); 2592457b6d5SAndreas Gruenbacher struct drbd_resource *resource; 260bde89a9eSAndreas Gruenbacher struct drbd_connection *connection; 261b411b363SPhilipp Reisner int reset_cpu_mask; 262c60b0251SAndreas Gruenbacher const char *name; 263b411b363SPhilipp Reisner }; 264b411b363SPhilipp Reisner 265b411b363SPhilipp Reisner static inline enum drbd_thread_state get_t_state(struct drbd_thread *thi) 266b411b363SPhilipp Reisner { 267b411b363SPhilipp Reisner /* THINK testing the t_state seems to be uncritical in all cases 268b411b363SPhilipp Reisner * (but thread_{start,stop}), so we can read it *without* the lock. 269b411b363SPhilipp Reisner * --lge */ 270b411b363SPhilipp Reisner 271b411b363SPhilipp Reisner smp_rmb(); 272b411b363SPhilipp Reisner return thi->t_state; 273b411b363SPhilipp Reisner } 274b411b363SPhilipp Reisner 275b411b363SPhilipp Reisner struct drbd_work { 276b411b363SPhilipp Reisner struct list_head list; 277309a8348SAndreas Gruenbacher int (*cb)(struct drbd_work *, int cancel); 27800d56944SPhilipp Reisner }; 27984b8c06bSAndreas Gruenbacher 28084b8c06bSAndreas Gruenbacher struct drbd_device_work { 28184b8c06bSAndreas Gruenbacher struct drbd_work w; 28284b8c06bSAndreas Gruenbacher struct drbd_device *device; 283b411b363SPhilipp Reisner }; 284b411b363SPhilipp Reisner 285ace652acSAndreas Gruenbacher #include "drbd_interval.h" 286ace652acSAndreas Gruenbacher 28754761697SAndreas Gruenbacher extern int drbd_wait_misc(struct drbd_device *, struct drbd_interval *); 2887be8da07SAndreas Gruenbacher 28928bc3b8cSAndreas Gruenbacher extern void lock_all_resources(void); 29028bc3b8cSAndreas Gruenbacher extern void unlock_all_resources(void); 29128bc3b8cSAndreas Gruenbacher 292b411b363SPhilipp Reisner struct drbd_request { 293b411b363SPhilipp Reisner struct drbd_work w; 29484b8c06bSAndreas Gruenbacher struct drbd_device *device; 295b411b363SPhilipp Reisner 296b411b363SPhilipp Reisner /* if local IO is not allowed, will be NULL. 297b411b363SPhilipp Reisner * if local IO _is_ allowed, holds the locally submitted bio clone, 298b411b363SPhilipp Reisner * or, after local IO completion, the ERR_PTR(error). 299fcefa62eSAndreas Gruenbacher * see drbd_request_endio(). */ 300b411b363SPhilipp Reisner struct bio *private_bio; 301b411b363SPhilipp Reisner 302ace652acSAndreas Gruenbacher struct drbd_interval i; 303b411b363SPhilipp Reisner 304b6dd1a89SLars Ellenberg /* epoch: used to check on "completion" whether this req was in 305b411b363SPhilipp Reisner * the current epoch, and we therefore have to close it, 306b6dd1a89SLars Ellenberg * causing a p_barrier packet to be send, starting a new epoch. 307b6dd1a89SLars Ellenberg * 308b6dd1a89SLars Ellenberg * This corresponds to "barrier" in struct p_barrier[_ack], 309b6dd1a89SLars Ellenberg * and to "barrier_nr" in struct drbd_epoch (and various 310b6dd1a89SLars Ellenberg * comments/function parameters/local variable names). 311b411b363SPhilipp Reisner */ 312b6dd1a89SLars Ellenberg unsigned int epoch; 313b411b363SPhilipp Reisner 314b411b363SPhilipp Reisner struct list_head tl_requests; /* ring list in the transfer log */ 315b411b363SPhilipp Reisner struct bio *master_bio; /* master bio pointer */ 316e5f891b2SLars Ellenberg 317844a6ae7SLars Ellenberg /* see struct drbd_device */ 318844a6ae7SLars Ellenberg struct list_head req_pending_master_completion; 319844a6ae7SLars Ellenberg struct list_head req_pending_local; 320844a6ae7SLars Ellenberg 321e5f891b2SLars Ellenberg /* for generic IO accounting */ 322e5f891b2SLars Ellenberg unsigned long start_jif; 323e5f891b2SLars Ellenberg 324e5f891b2SLars Ellenberg /* for DRBD internal statistics */ 325e5f891b2SLars Ellenberg 326e5f891b2SLars Ellenberg /* Minimal set of time stamps to determine if we wait for activity log 327e5f891b2SLars Ellenberg * transactions, local disk or peer. 32 bit "jiffies" are good enough, 328e5f891b2SLars Ellenberg * we don't expect a DRBD request to be stalled for several month. 329e5f891b2SLars Ellenberg */ 330e5f891b2SLars Ellenberg 331e5f891b2SLars Ellenberg /* before actual request processing */ 332e5f891b2SLars Ellenberg unsigned long in_actlog_jif; 333e5f891b2SLars Ellenberg 334e5f891b2SLars Ellenberg /* local disk */ 335e5f891b2SLars Ellenberg unsigned long pre_submit_jif; 336e5f891b2SLars Ellenberg 337e5f891b2SLars Ellenberg /* per connection */ 338e5f891b2SLars Ellenberg unsigned long pre_send_jif; 339e5f891b2SLars Ellenberg unsigned long acked_jif; 340e5f891b2SLars Ellenberg unsigned long net_done_jif; 341e5f891b2SLars Ellenberg 342e5f891b2SLars Ellenberg /* Possibly even more detail to track each phase: 343e5f891b2SLars Ellenberg * master_completion_jif 344e5f891b2SLars Ellenberg * how long did it take to complete the master bio 345e5f891b2SLars Ellenberg * (application visible latency) 346e5f891b2SLars Ellenberg * allocated_jif 347e5f891b2SLars Ellenberg * how long the master bio was blocked until we finally allocated 348e5f891b2SLars Ellenberg * a tracking struct 349e5f891b2SLars Ellenberg * in_actlog_jif 350e5f891b2SLars Ellenberg * how long did we wait for activity log transactions 351e5f891b2SLars Ellenberg * 352e5f891b2SLars Ellenberg * net_queued_jif 353e5f891b2SLars Ellenberg * when did we finally queue it for sending 354e5f891b2SLars Ellenberg * pre_send_jif 355e5f891b2SLars Ellenberg * when did we start sending it 356e5f891b2SLars Ellenberg * post_send_jif 357e5f891b2SLars Ellenberg * how long did we block in the network stack trying to send it 358e5f891b2SLars Ellenberg * acked_jif 359e5f891b2SLars Ellenberg * when did we receive (or fake, in protocol A) a remote ACK 360e5f891b2SLars Ellenberg * net_done_jif 361e5f891b2SLars Ellenberg * when did we receive final acknowledgement (P_BARRIER_ACK), 362e5f891b2SLars Ellenberg * or decide, e.g. on connection loss, that we do no longer expect 363e5f891b2SLars Ellenberg * anything from this peer for this request. 364e5f891b2SLars Ellenberg * 365e5f891b2SLars Ellenberg * pre_submit_jif 366e5f891b2SLars Ellenberg * post_sub_jif 367e5f891b2SLars Ellenberg * when did we start submiting to the lower level device, 368e5f891b2SLars Ellenberg * and how long did we block in that submit function 369e5f891b2SLars Ellenberg * local_completion_jif 370e5f891b2SLars Ellenberg * how long did it take the lower level device to complete this request 371e5f891b2SLars Ellenberg */ 372e5f891b2SLars Ellenberg 373b406777eSLars Ellenberg 374b406777eSLars Ellenberg /* once it hits 0, we may complete the master_bio */ 375b406777eSLars Ellenberg atomic_t completion_ref; 376b406777eSLars Ellenberg /* once it hits 0, we may destroy this drbd_request object */ 377b406777eSLars Ellenberg struct kref kref; 378a0d856dfSLars Ellenberg 379a0d856dfSLars Ellenberg unsigned rq_state; /* see comments above _req_mod() */ 380b411b363SPhilipp Reisner }; 381b411b363SPhilipp Reisner 382b411b363SPhilipp Reisner struct drbd_epoch { 383bde89a9eSAndreas Gruenbacher struct drbd_connection *connection; 384b411b363SPhilipp Reisner struct list_head list; 385b411b363SPhilipp Reisner unsigned int barrier_nr; 386b411b363SPhilipp Reisner atomic_t epoch_size; /* increased on every request added. */ 387b411b363SPhilipp Reisner atomic_t active; /* increased on every req. added, and dec on every finished. */ 388b411b363SPhilipp Reisner unsigned long flags; 389b411b363SPhilipp Reisner }; 390b411b363SPhilipp Reisner 391de0b2e69SRashika Kheria /* Prototype declaration of function defined in drbd_receiver.c */ 392de0b2e69SRashika Kheria int drbdd_init(struct drbd_thread *); 393de0b2e69SRashika Kheria int drbd_asender(struct drbd_thread *); 394de0b2e69SRashika Kheria 395b411b363SPhilipp Reisner /* drbd_epoch flag bits */ 396b411b363SPhilipp Reisner enum { 397b411b363SPhilipp Reisner DE_HAVE_BARRIER_NUMBER, 398b411b363SPhilipp Reisner }; 399b411b363SPhilipp Reisner 400b411b363SPhilipp Reisner enum epoch_event { 401b411b363SPhilipp Reisner EV_PUT, 402b411b363SPhilipp Reisner EV_GOT_BARRIER_NR, 403b411b363SPhilipp Reisner EV_BECAME_LAST, 404b411b363SPhilipp Reisner EV_CLEANUP = 32, /* used as flag */ 405b411b363SPhilipp Reisner }; 406b411b363SPhilipp Reisner 407b411b363SPhilipp Reisner struct digest_info { 408b411b363SPhilipp Reisner int digest_size; 409b411b363SPhilipp Reisner void *digest; 410b411b363SPhilipp Reisner }; 411b411b363SPhilipp Reisner 412f6ffca9fSAndreas Gruenbacher struct drbd_peer_request { 413a8cd15baSAndreas Gruenbacher struct drbd_work w; 414a8cd15baSAndreas Gruenbacher struct drbd_peer_device *peer_device; 41585719573SPhilipp Reisner struct drbd_epoch *epoch; /* for writes */ 41645bb912bSLars Ellenberg struct page *pages; 41745bb912bSLars Ellenberg atomic_t pending_bios; 418010f6e67SAndreas Gruenbacher struct drbd_interval i; 41945bb912bSLars Ellenberg /* see comments on ee flag bits below */ 42045bb912bSLars Ellenberg unsigned long flags; 42121ae5d7fSLars Ellenberg unsigned long submit_jif; 42285719573SPhilipp Reisner union { 42345bb912bSLars Ellenberg u64 block_id; 42485719573SPhilipp Reisner struct digest_info *digest; 42585719573SPhilipp Reisner }; 42645bb912bSLars Ellenberg }; 42745bb912bSLars Ellenberg 42845bb912bSLars Ellenberg /* ee flag bits. 42945bb912bSLars Ellenberg * While corresponding bios are in flight, the only modification will be 43045bb912bSLars Ellenberg * set_bit WAS_ERROR, which has to be atomic. 43145bb912bSLars Ellenberg * If no bios are in flight yet, or all have been completed, 43245bb912bSLars Ellenberg * non-atomic modification to ee->flags is ok. 43345bb912bSLars Ellenberg */ 434b411b363SPhilipp Reisner enum { 435b411b363SPhilipp Reisner __EE_CALL_AL_COMPLETE_IO, 436b411b363SPhilipp Reisner __EE_MAY_SET_IN_SYNC, 43745bb912bSLars Ellenberg 438a0fb3c47SLars Ellenberg /* is this a TRIM aka REQ_DISCARD? */ 439a0fb3c47SLars Ellenberg __EE_IS_TRIM, 440a0fb3c47SLars Ellenberg 44145bb912bSLars Ellenberg /* In case a barrier failed, 44245bb912bSLars Ellenberg * we need to resubmit without the barrier flag. */ 44345bb912bSLars Ellenberg __EE_RESUBMITTED, 44445bb912bSLars Ellenberg 4456c852becSAndreas Gruenbacher /* we may have several bios per peer request. 44645bb912bSLars Ellenberg * if any of those fail, we set this flag atomically 44745bb912bSLars Ellenberg * from the endio callback */ 44845bb912bSLars Ellenberg __EE_WAS_ERROR, 449c36c3cedSLars Ellenberg 450c36c3cedSLars Ellenberg /* This ee has a pointer to a digest instead of a block id */ 451c36c3cedSLars Ellenberg __EE_HAS_DIGEST, 4527be8da07SAndreas Gruenbacher 4537be8da07SAndreas Gruenbacher /* Conflicting local requests need to be restarted after this request */ 4547be8da07SAndreas Gruenbacher __EE_RESTART_REQUESTS, 455303d1448SPhilipp Reisner 456303d1448SPhilipp Reisner /* The peer wants a write ACK for this (wire proto C) */ 457303d1448SPhilipp Reisner __EE_SEND_WRITE_ACK, 458302bdeaeSPhilipp Reisner 459302bdeaeSPhilipp Reisner /* Is set when net_conf had two_primaries set while creating this peer_req */ 460302bdeaeSPhilipp Reisner __EE_IN_INTERVAL_TREE, 46121ae5d7fSLars Ellenberg 46221ae5d7fSLars Ellenberg /* for debugfs: */ 46321ae5d7fSLars Ellenberg /* has this been submitted, or does it still wait for something else? */ 46421ae5d7fSLars Ellenberg __EE_SUBMITTED, 46521ae5d7fSLars Ellenberg 46621ae5d7fSLars Ellenberg /* this is/was a write request */ 46721ae5d7fSLars Ellenberg __EE_WRITE, 46821ae5d7fSLars Ellenberg 4699104d31aSLars Ellenberg /* this is/was a write same request */ 4709104d31aSLars Ellenberg __EE_WRITE_SAME, 4719104d31aSLars Ellenberg 47221ae5d7fSLars Ellenberg /* this originates from application on peer 47321ae5d7fSLars Ellenberg * (not some resync or verify or other DRBD internal request) */ 47421ae5d7fSLars Ellenberg __EE_APPLICATION, 475700ca8c0SPhilipp Reisner 476700ca8c0SPhilipp Reisner /* If it contains only 0 bytes, send back P_RS_DEALLOCATED */ 477700ca8c0SPhilipp Reisner __EE_RS_THIN_REQ, 478b411b363SPhilipp Reisner }; 479b411b363SPhilipp Reisner #define EE_CALL_AL_COMPLETE_IO (1<<__EE_CALL_AL_COMPLETE_IO) 480b411b363SPhilipp Reisner #define EE_MAY_SET_IN_SYNC (1<<__EE_MAY_SET_IN_SYNC) 481a0fb3c47SLars Ellenberg #define EE_IS_TRIM (1<<__EE_IS_TRIM) 48245bb912bSLars Ellenberg #define EE_RESUBMITTED (1<<__EE_RESUBMITTED) 48345bb912bSLars Ellenberg #define EE_WAS_ERROR (1<<__EE_WAS_ERROR) 484c36c3cedSLars Ellenberg #define EE_HAS_DIGEST (1<<__EE_HAS_DIGEST) 4857be8da07SAndreas Gruenbacher #define EE_RESTART_REQUESTS (1<<__EE_RESTART_REQUESTS) 486303d1448SPhilipp Reisner #define EE_SEND_WRITE_ACK (1<<__EE_SEND_WRITE_ACK) 487302bdeaeSPhilipp Reisner #define EE_IN_INTERVAL_TREE (1<<__EE_IN_INTERVAL_TREE) 48821ae5d7fSLars Ellenberg #define EE_SUBMITTED (1<<__EE_SUBMITTED) 48921ae5d7fSLars Ellenberg #define EE_WRITE (1<<__EE_WRITE) 4909104d31aSLars Ellenberg #define EE_WRITE_SAME (1<<__EE_WRITE_SAME) 49121ae5d7fSLars Ellenberg #define EE_APPLICATION (1<<__EE_APPLICATION) 492700ca8c0SPhilipp Reisner #define EE_RS_THIN_REQ (1<<__EE_RS_THIN_REQ) 493b411b363SPhilipp Reisner 494b30ab791SAndreas Gruenbacher /* flag bits per device */ 495b411b363SPhilipp Reisner enum { 496b411b363SPhilipp Reisner UNPLUG_REMOTE, /* sending a "UnplugRemote" could help */ 497b411b363SPhilipp Reisner MD_DIRTY, /* current uuids and flags not yet on disk */ 498b411b363SPhilipp Reisner USE_DEGR_WFC_T, /* degr-wfc-timeout instead of wfc-timeout. */ 499b411b363SPhilipp Reisner CL_ST_CHG_SUCCESS, 500b411b363SPhilipp Reisner CL_ST_CHG_FAIL, 501b411b363SPhilipp Reisner CRASHED_PRIMARY, /* This node was a crashed primary. 502b411b363SPhilipp Reisner * Gets cleared when the state.conn 503b411b363SPhilipp Reisner * goes into C_CONNECTED state. */ 504b411b363SPhilipp Reisner CONSIDER_RESYNC, 505b411b363SPhilipp Reisner 506a8a4e51eSPhilipp Reisner MD_NO_FUA, /* Users wants us to not use FUA/FLUSH on meta data dev */ 5075ab7d2c0SLars Ellenberg 508b411b363SPhilipp Reisner BITMAP_IO, /* suspend application io; 509b411b363SPhilipp Reisner once no more io in flight, start bitmap io */ 510b411b363SPhilipp Reisner BITMAP_IO_QUEUED, /* Started bitmap IO */ 511a2a3c74fSLars Ellenberg WAS_IO_ERROR, /* Local disk failed, returned IO error */ 512a2a3c74fSLars Ellenberg WAS_READ_ERROR, /* Local disk READ failed (set additionally to the above) */ 513383606e0SLars Ellenberg FORCE_DETACH, /* Force-detach from local disk, aborting any pending local IO */ 514b411b363SPhilipp Reisner RESYNC_AFTER_NEG, /* Resync after online grow after the attach&negotiate finished. */ 515b411b363SPhilipp Reisner RESIZE_PENDING, /* Size change detected locally, waiting for the response from 516b411b363SPhilipp Reisner * the peer, if it changed there as well. */ 51743a5182cSPhilipp Reisner NEW_CUR_UUID, /* Create new current UUID when thawing IO */ 5180778286aSPhilipp Reisner AL_SUSPENDED, /* Activity logging is currently suspended. */ 519370a43e7SPhilipp Reisner AHEAD_TO_SYNC_SOURCE, /* Ahead -> SyncSource queued */ 520e64a3294SPhilipp Reisner B_RS_H_DONE, /* Before resync handler done (already executed) */ 52108b165baSPhilipp Reisner DISCARD_MY_DATA, /* discard_my_data flag per volume */ 522380207d0SPhilipp Reisner READ_BALANCE_RR, 523e334f550SLars Ellenberg 524f418815fSLars Ellenberg FLUSH_PENDING, /* if set, device->flush_jif is when we submitted that flush 525f418815fSLars Ellenberg * from drbd_flush_after_epoch() */ 526f418815fSLars Ellenberg 527e334f550SLars Ellenberg /* cleared only after backing device related structures have been destroyed. */ 528e334f550SLars Ellenberg GOING_DISKLESS, /* Disk is being detached, because of io-error, or admin request. */ 529e334f550SLars Ellenberg 530e334f550SLars Ellenberg /* to be used in drbd_device_post_work() */ 531e334f550SLars Ellenberg GO_DISKLESS, /* tell worker to schedule cleanup before detach */ 532e334f550SLars Ellenberg DESTROY_DISK, /* tell worker to close backing devices and destroy related structures. */ 533ac0acb9eSLars Ellenberg MD_SYNC, /* tell worker to call drbd_md_sync() */ 534ac0acb9eSLars Ellenberg RS_START, /* tell worker to start resync/OV */ 535e334f550SLars Ellenberg RS_PROGRESS, /* tell worker that resync made significant progress */ 536e334f550SLars Ellenberg RS_DONE, /* tell worker that resync is done */ 537b411b363SPhilipp Reisner }; 538b411b363SPhilipp Reisner 53954761697SAndreas Gruenbacher struct drbd_bitmap; /* opaque for drbd_device */ 540b411b363SPhilipp Reisner 54120ceb2b2SLars Ellenberg /* definition of bits in bm_flags to be used in drbd_bm_lock 54220ceb2b2SLars Ellenberg * and drbd_bitmap_io and friends. */ 54320ceb2b2SLars Ellenberg enum bm_flag { 54420ceb2b2SLars Ellenberg /* currently locked for bulk operation */ 5450e8488adSLars Ellenberg BM_LOCKED_MASK = 0xf, 54620ceb2b2SLars Ellenberg 54720ceb2b2SLars Ellenberg /* in detail, that is: */ 54820ceb2b2SLars Ellenberg BM_DONT_CLEAR = 0x1, 54920ceb2b2SLars Ellenberg BM_DONT_SET = 0x2, 55020ceb2b2SLars Ellenberg BM_DONT_TEST = 0x4, 55120ceb2b2SLars Ellenberg 5520e8488adSLars Ellenberg /* so we can mark it locked for bulk operation, 5530e8488adSLars Ellenberg * and still allow all non-bulk operations */ 5540e8488adSLars Ellenberg BM_IS_LOCKED = 0x8, 5550e8488adSLars Ellenberg 55620ceb2b2SLars Ellenberg /* (test bit, count bit) allowed (common case) */ 5570e8488adSLars Ellenberg BM_LOCKED_TEST_ALLOWED = BM_DONT_CLEAR | BM_DONT_SET | BM_IS_LOCKED, 55820ceb2b2SLars Ellenberg 55920ceb2b2SLars Ellenberg /* testing bits, as well as setting new bits allowed, but clearing bits 56020ceb2b2SLars Ellenberg * would be unexpected. Used during bitmap receive. Setting new bits 56120ceb2b2SLars Ellenberg * requires sending of "out-of-sync" information, though. */ 5620e8488adSLars Ellenberg BM_LOCKED_SET_ALLOWED = BM_DONT_CLEAR | BM_IS_LOCKED, 56320ceb2b2SLars Ellenberg 5640e8488adSLars Ellenberg /* for drbd_bm_write_copy_pages, everything is allowed, 5650e8488adSLars Ellenberg * only concurrent bulk operations are locked out. */ 5660e8488adSLars Ellenberg BM_LOCKED_CHANGE_ALLOWED = BM_IS_LOCKED, 56720ceb2b2SLars Ellenberg }; 56820ceb2b2SLars Ellenberg 569b411b363SPhilipp Reisner struct drbd_work_queue { 570b411b363SPhilipp Reisner struct list_head q; 571b411b363SPhilipp Reisner spinlock_t q_lock; /* to protect the list. */ 5728c0785a5SLars Ellenberg wait_queue_head_t q_wait; 573b411b363SPhilipp Reisner }; 574b411b363SPhilipp Reisner 575b411b363SPhilipp Reisner struct drbd_socket { 576b411b363SPhilipp Reisner struct mutex mutex; 577b411b363SPhilipp Reisner struct socket *socket; 578b411b363SPhilipp Reisner /* this way we get our 579b411b363SPhilipp Reisner * send/receive buffers off the stack */ 5805a87d920SAndreas Gruenbacher void *sbuf; 581e6ef8a5cSAndreas Gruenbacher void *rbuf; 582b411b363SPhilipp Reisner }; 583b411b363SPhilipp Reisner 584b411b363SPhilipp Reisner struct drbd_md { 585b411b363SPhilipp Reisner u64 md_offset; /* sector offset to 'super' block */ 586b411b363SPhilipp Reisner 587b411b363SPhilipp Reisner u64 la_size_sect; /* last agreed size, unit sectors */ 5889f2247bbSPhilipp Reisner spinlock_t uuid_lock; 589b411b363SPhilipp Reisner u64 uuid[UI_SIZE]; 590b411b363SPhilipp Reisner u64 device_uuid; 591b411b363SPhilipp Reisner u32 flags; 592b411b363SPhilipp Reisner u32 md_size_sect; 593b411b363SPhilipp Reisner 594ae8bf312SLars Ellenberg s32 al_offset; /* signed relative sector offset to activity log */ 595b411b363SPhilipp Reisner s32 bm_offset; /* signed relative sector offset to bitmap */ 5963a4d4eb3SLars Ellenberg 5973a4d4eb3SLars Ellenberg /* cached value of bdev->disk_conf->meta_dev_idx (see below) */ 5983a4d4eb3SLars Ellenberg s32 meta_dev_idx; 5993a4d4eb3SLars Ellenberg 6003a4d4eb3SLars Ellenberg /* see al_tr_number_to_on_disk_sector() */ 6013a4d4eb3SLars Ellenberg u32 al_stripes; 6023a4d4eb3SLars Ellenberg u32 al_stripe_size_4k; 6033a4d4eb3SLars Ellenberg u32 al_size_4k; /* cached product of the above */ 604b411b363SPhilipp Reisner }; 605b411b363SPhilipp Reisner 606b411b363SPhilipp Reisner struct drbd_backing_dev { 607b411b363SPhilipp Reisner struct block_device *backing_bdev; 608b411b363SPhilipp Reisner struct block_device *md_bdev; 609b411b363SPhilipp Reisner struct drbd_md md; 6100500813fSAndreas Gruenbacher struct disk_conf *disk_conf; /* RCU, for updates: resource->conf_update */ 611b411b363SPhilipp Reisner sector_t known_size; /* last known size of that backing device */ 612b411b363SPhilipp Reisner }; 613b411b363SPhilipp Reisner 614b411b363SPhilipp Reisner struct drbd_md_io { 615e37d2438SLars Ellenberg struct page *page; 616e37d2438SLars Ellenberg unsigned long start_jif; /* last call to drbd_md_get_buffer */ 617e37d2438SLars Ellenberg unsigned long submit_jif; /* last _drbd_md_sync_page_io() submit */ 618e37d2438SLars Ellenberg const char *current_use; 619e37d2438SLars Ellenberg atomic_t in_use; 6200c464425SPhilipp Reisner unsigned int done; 621b411b363SPhilipp Reisner int error; 622b411b363SPhilipp Reisner }; 623b411b363SPhilipp Reisner 624b411b363SPhilipp Reisner struct bm_io_work { 625b411b363SPhilipp Reisner struct drbd_work w; 626b411b363SPhilipp Reisner char *why; 62720ceb2b2SLars Ellenberg enum bm_flag flags; 628b30ab791SAndreas Gruenbacher int (*io_fn)(struct drbd_device *device); 629b30ab791SAndreas Gruenbacher void (*done)(struct drbd_device *device, int rv); 630b411b363SPhilipp Reisner }; 631b411b363SPhilipp Reisner 632778f271dSPhilipp Reisner struct fifo_buffer { 633778f271dSPhilipp Reisner unsigned int head_index; 634778f271dSPhilipp Reisner unsigned int size; 6359958c857SPhilipp Reisner int total; /* sum of all values */ 6369958c857SPhilipp Reisner int values[0]; 637778f271dSPhilipp Reisner }; 6389958c857SPhilipp Reisner extern struct fifo_buffer *fifo_alloc(int fifo_size); 639778f271dSPhilipp Reisner 640bde89a9eSAndreas Gruenbacher /* flag bits per connection */ 64101a311a5SPhilipp Reisner enum { 64201a311a5SPhilipp Reisner NET_CONGESTED, /* The data socket is congested */ 643427c0434SLars Ellenberg RESOLVE_CONFLICTS, /* Set on one node, cleared on the peer! */ 644668700b4SPhilipp Reisner SEND_PING, 6452a67d8b9SPhilipp Reisner GOT_PING_ACK, /* set when we receive a ping_ack packet, ping_wait gets woken */ 6464d0fc3fdSPhilipp Reisner CONN_WD_ST_CHG_REQ, /* A cluster wide state change on the connection is active */ 647fc3b10a4SPhilipp Reisner CONN_WD_ST_CHG_OKAY, 648fc3b10a4SPhilipp Reisner CONN_WD_ST_CHG_FAIL, 6498169e41bSPhilipp Reisner CONN_DRY_RUN, /* Expect disconnect after resync handshake. */ 6506936fcb4SPhilipp Reisner CREATE_BARRIER, /* next P_DATA is preceded by a P_BARRIER */ 651a1096a6eSPhilipp Reisner STATE_SENT, /* Do not change state/UUIDs while this is set */ 6526f3465edSLars Ellenberg CALLBACK_PENDING, /* Whether we have a call_usermodehelper(, UMH_WAIT_PROC) 6536f3465edSLars Ellenberg * pending, from drbd worker context. 6546f3465edSLars Ellenberg * If set, bdi_write_congested() returns true, 6556f3465edSLars Ellenberg * so shrink_page_list() would not recurse into, 6566f3465edSLars Ellenberg * and potentially deadlock on, this drbd worker. 6576f3465edSLars Ellenberg */ 658b66623e3SPhilipp Reisner DISCONNECT_SENT, 659e334f550SLars Ellenberg 660e334f550SLars Ellenberg DEVICE_WORK_PENDING, /* tell worker that some device has pending work */ 66101a311a5SPhilipp Reisner }; 66201a311a5SPhilipp Reisner 663a2972846SAndreas Gruenbacher enum which_state { NOW, OLD = NOW, NEW }; 664a2972846SAndreas Gruenbacher 66577c556f6SAndreas Gruenbacher struct drbd_resource { 66677c556f6SAndreas Gruenbacher char *name; 6674d3d5aa8SLars Ellenberg #ifdef CONFIG_DEBUG_FS 6684d3d5aa8SLars Ellenberg struct dentry *debugfs_res; 6694d3d5aa8SLars Ellenberg struct dentry *debugfs_res_volumes; 6704d3d5aa8SLars Ellenberg struct dentry *debugfs_res_connections; 6714d3d5aa8SLars Ellenberg struct dentry *debugfs_res_in_flight_summary; 6724d3d5aa8SLars Ellenberg #endif 67377c556f6SAndreas Gruenbacher struct kref kref; 674803ea134SAndreas Gruenbacher struct idr devices; /* volume number to device mapping */ 67577c556f6SAndreas Gruenbacher struct list_head connections; 67677c556f6SAndreas Gruenbacher struct list_head resources; 677eb6bea67SAndreas Gruenbacher struct res_opts res_opts; 6780500813fSAndreas Gruenbacher struct mutex conf_update; /* mutex for ready-copy-update of net_conf and disk_conf */ 6799e276872SLars Ellenberg struct mutex adm_mutex; /* mutex to serialize administrative requests */ 6800500813fSAndreas Gruenbacher spinlock_t req_lock; 6816bbf53caSAndreas Gruenbacher 6826bbf53caSAndreas Gruenbacher unsigned susp:1; /* IO suspended by user */ 6836bbf53caSAndreas Gruenbacher unsigned susp_nod:1; /* IO suspended because no data */ 6846bbf53caSAndreas Gruenbacher unsigned susp_fen:1; /* IO suspended because fence peer handler runs */ 685625a6ba2SAndreas Gruenbacher 686e9526580SPhilipp Reisner enum write_ordering_e write_ordering; 687e9526580SPhilipp Reisner 688625a6ba2SAndreas Gruenbacher cpumask_var_t cpu_mask; 68977c556f6SAndreas Gruenbacher }; 69077c556f6SAndreas Gruenbacher 691944410e9SLars Ellenberg struct drbd_thread_timing_details 692944410e9SLars Ellenberg { 693944410e9SLars Ellenberg unsigned long start_jif; 694944410e9SLars Ellenberg void *cb_addr; 695944410e9SLars Ellenberg const char *caller_fn; 696944410e9SLars Ellenberg unsigned int line; 697944410e9SLars Ellenberg unsigned int cb_nr; 698944410e9SLars Ellenberg }; 699944410e9SLars Ellenberg 70077c556f6SAndreas Gruenbacher struct drbd_connection { 70177c556f6SAndreas Gruenbacher struct list_head connections; 70277c556f6SAndreas Gruenbacher struct drbd_resource *resource; 7034d3d5aa8SLars Ellenberg #ifdef CONFIG_DEBUG_FS 7044d3d5aa8SLars Ellenberg struct dentry *debugfs_conn; 7054d3d5aa8SLars Ellenberg struct dentry *debugfs_conn_callback_history; 7064d3d5aa8SLars Ellenberg struct dentry *debugfs_conn_oldest_requests; 7074d3d5aa8SLars Ellenberg #endif 7089dc9fbb3SPhilipp Reisner struct kref kref; 709c06ece6bSAndreas Gruenbacher struct idr peer_devices; /* volume number to peer device mapping */ 710bbeb641cSPhilipp Reisner enum drbd_conns cstate; /* Only C_STANDALONE to C_WF_REPORT_PARAMS */ 7118410da8fSPhilipp Reisner struct mutex cstate_mutex; /* Protects graceful disconnects */ 71228e448bbSPhilipp Reisner unsigned int connect_cnt; /* Inc each time a connection is established */ 7132111438bSPhilipp Reisner 714062e879cSPhilipp Reisner unsigned long flags; 71544ed167dSPhilipp Reisner struct net_conf *net_conf; /* content protected by rcu */ 7162a67d8b9SPhilipp Reisner wait_queue_head_t ping_wait; /* Woken upon reception of a ping, and a state change */ 717e42325a5SPhilipp Reisner 718089c075dSAndreas Gruenbacher struct sockaddr_storage my_addr; 719089c075dSAndreas Gruenbacher int my_addr_len; 720089c075dSAndreas Gruenbacher struct sockaddr_storage peer_addr; 721089c075dSAndreas Gruenbacher int peer_addr_len; 722089c075dSAndreas Gruenbacher 723e42325a5SPhilipp Reisner struct drbd_socket data; /* data/barrier/cstate/parameter packets */ 724e42325a5SPhilipp Reisner struct drbd_socket meta; /* ping/ack (metadata) packets */ 72531890f4aSPhilipp Reisner int agreed_pro_version; /* actually used protocol version */ 72620c68fdeSLars Ellenberg u32 agreed_features; 72731890f4aSPhilipp Reisner unsigned long last_received; /* in jiffies, either socket */ 72831890f4aSPhilipp Reisner unsigned int ko_count; 729e6b3ea83SPhilipp Reisner 730b6dd1a89SLars Ellenberg struct list_head transfer_log; /* all requests not yet fully processed */ 73187eeee41SPhilipp Reisner 7329534d671SHerbert Xu struct crypto_shash *cram_hmac_tfm; 7339534d671SHerbert Xu struct crypto_ahash *integrity_tfm; /* checksums we compute, updates protected by connection->data->mutex */ 7349534d671SHerbert Xu struct crypto_ahash *peer_integrity_tfm; /* checksums we verify, only accessed from receiver thread */ 7359534d671SHerbert Xu struct crypto_ahash *csums_tfm; 7369534d671SHerbert Xu struct crypto_ahash *verify_tfm; 737a0638456SPhilipp Reisner void *int_dig_in; 738a0638456SPhilipp Reisner void *int_dig_vv; 739a0638456SPhilipp Reisner 740b6dd1a89SLars Ellenberg /* receiver side */ 74112038a3aSPhilipp Reisner struct drbd_epoch *current_epoch; 74212038a3aSPhilipp Reisner spinlock_t epoch_lock; 74312038a3aSPhilipp Reisner unsigned int epochs; 744b379c41eSLars Ellenberg atomic_t current_tle_nr; /* transfer log epoch number */ 745b6dd1a89SLars Ellenberg unsigned current_tle_writes; /* writes seen within this tl epoch */ 7464b0007c0SPhilipp Reisner 74707be15b1SLars Ellenberg unsigned long last_reconnect_jif; 748e6b3ea83SPhilipp Reisner struct drbd_thread receiver; 749e6b3ea83SPhilipp Reisner struct drbd_thread worker; 7501c03e520SPhilipp Reisner struct drbd_thread ack_receiver; 751668700b4SPhilipp Reisner struct workqueue_struct *ack_sender; 752b6dd1a89SLars Ellenberg 7537753a4c1SLars Ellenberg /* cached pointers, 7547753a4c1SLars Ellenberg * so we can look up the oldest pending requests more quickly. 7557753a4c1SLars Ellenberg * protected by resource->req_lock */ 7567753a4c1SLars Ellenberg struct drbd_request *req_next; /* DRBD 9: todo.req_next */ 7577753a4c1SLars Ellenberg struct drbd_request *req_ack_pending; 7587753a4c1SLars Ellenberg struct drbd_request *req_not_net_done; 7597753a4c1SLars Ellenberg 760b6dd1a89SLars Ellenberg /* sender side */ 761d5b27b01SLars Ellenberg struct drbd_work_queue sender_work; 762b6dd1a89SLars Ellenberg 763944410e9SLars Ellenberg #define DRBD_THREAD_DETAILS_HIST 16 764944410e9SLars Ellenberg unsigned int w_cb_nr; /* keeps counting up */ 765944410e9SLars Ellenberg unsigned int r_cb_nr; /* keeps counting up */ 766944410e9SLars Ellenberg struct drbd_thread_timing_details w_timing_details[DRBD_THREAD_DETAILS_HIST]; 767944410e9SLars Ellenberg struct drbd_thread_timing_details r_timing_details[DRBD_THREAD_DETAILS_HIST]; 768944410e9SLars Ellenberg 769b6dd1a89SLars Ellenberg struct { 77084d34f2fSLars Ellenberg unsigned long last_sent_barrier_jif; 77184d34f2fSLars Ellenberg 772b6dd1a89SLars Ellenberg /* whether this sender thread 773b6dd1a89SLars Ellenberg * has processed a single write yet. */ 774b6dd1a89SLars Ellenberg bool seen_any_write_yet; 775b6dd1a89SLars Ellenberg 776b6dd1a89SLars Ellenberg /* Which barrier number to send with the next P_BARRIER */ 777b6dd1a89SLars Ellenberg int current_epoch_nr; 778b6dd1a89SLars Ellenberg 779b6dd1a89SLars Ellenberg /* how many write requests have been sent 780b6dd1a89SLars Ellenberg * with req->epoch == current_epoch_nr. 781b6dd1a89SLars Ellenberg * If none, no P_BARRIER will be sent. */ 782b6dd1a89SLars Ellenberg unsigned current_epoch_writes; 783b6dd1a89SLars Ellenberg } send; 784b411b363SPhilipp Reisner }; 785b411b363SPhilipp Reisner 786a2972846SAndreas Gruenbacher static inline bool has_net_conf(struct drbd_connection *connection) 787a2972846SAndreas Gruenbacher { 788a2972846SAndreas Gruenbacher bool has_net_conf; 789a2972846SAndreas Gruenbacher 790a2972846SAndreas Gruenbacher rcu_read_lock(); 791a2972846SAndreas Gruenbacher has_net_conf = rcu_dereference(connection->net_conf); 792a2972846SAndreas Gruenbacher rcu_read_unlock(); 793a2972846SAndreas Gruenbacher 794a2972846SAndreas Gruenbacher return has_net_conf; 795a2972846SAndreas Gruenbacher } 796a2972846SAndreas Gruenbacher 797944410e9SLars Ellenberg void __update_timing_details( 798944410e9SLars Ellenberg struct drbd_thread_timing_details *tdp, 799944410e9SLars Ellenberg unsigned int *cb_nr, 800944410e9SLars Ellenberg void *cb, 801944410e9SLars Ellenberg const char *fn, const unsigned int line); 802944410e9SLars Ellenberg 803944410e9SLars Ellenberg #define update_worker_timing_details(c, cb) \ 804944410e9SLars Ellenberg __update_timing_details(c->w_timing_details, &c->w_cb_nr, cb, __func__ , __LINE__ ) 805944410e9SLars Ellenberg #define update_receiver_timing_details(c, cb) \ 806944410e9SLars Ellenberg __update_timing_details(c->r_timing_details, &c->r_cb_nr, cb, __func__ , __LINE__ ) 807944410e9SLars Ellenberg 808113fef9eSLars Ellenberg struct submit_worker { 809113fef9eSLars Ellenberg struct workqueue_struct *wq; 810113fef9eSLars Ellenberg struct work_struct worker; 811113fef9eSLars Ellenberg 812844a6ae7SLars Ellenberg /* protected by ..->resource->req_lock */ 813113fef9eSLars Ellenberg struct list_head writes; 814113fef9eSLars Ellenberg }; 815113fef9eSLars Ellenberg 816a6b32bc3SAndreas Gruenbacher struct drbd_peer_device { 817a6b32bc3SAndreas Gruenbacher struct list_head peer_devices; 818a6b32bc3SAndreas Gruenbacher struct drbd_device *device; 819bde89a9eSAndreas Gruenbacher struct drbd_connection *connection; 820668700b4SPhilipp Reisner struct work_struct send_acks_work; 8214d3d5aa8SLars Ellenberg #ifdef CONFIG_DEBUG_FS 8224d3d5aa8SLars Ellenberg struct dentry *debugfs_peer_dev; 8234d3d5aa8SLars Ellenberg #endif 824a6b32bc3SAndreas Gruenbacher }; 825a6b32bc3SAndreas Gruenbacher 826a6b32bc3SAndreas Gruenbacher struct drbd_device { 827d8628a86SAndreas Gruenbacher struct drbd_resource *resource; 828a6b32bc3SAndreas Gruenbacher struct list_head peer_devices; 8294ce49266SLars Ellenberg struct list_head pending_bitmap_io; 8304d3d5aa8SLars Ellenberg 8314d3d5aa8SLars Ellenberg unsigned long flush_jif; 8324d3d5aa8SLars Ellenberg #ifdef CONFIG_DEBUG_FS 8334d3d5aa8SLars Ellenberg struct dentry *debugfs_minor; 8344d3d5aa8SLars Ellenberg struct dentry *debugfs_vol; 8354d3d5aa8SLars Ellenberg struct dentry *debugfs_vol_oldest_requests; 8364d3d5aa8SLars Ellenberg struct dentry *debugfs_vol_act_log_extents; 8374d3d5aa8SLars Ellenberg struct dentry *debugfs_vol_resync_extents; 8384d3d5aa8SLars Ellenberg struct dentry *debugfs_vol_data_gen_id; 839f5ec0173SLars Ellenberg struct dentry *debugfs_vol_ed_gen_id; 8404d3d5aa8SLars Ellenberg #endif 8414d3d5aa8SLars Ellenberg 8424d3d5aa8SLars Ellenberg unsigned int vnr; /* volume number within the connection */ 8434d3d5aa8SLars Ellenberg unsigned int minor; /* device minor number */ 8444d3d5aa8SLars Ellenberg 84581fa2e67SPhilipp Reisner struct kref kref; 8462111438bSPhilipp Reisner 847b411b363SPhilipp Reisner /* things that are stored as / read from meta data on disk */ 848b411b363SPhilipp Reisner unsigned long flags; 849b411b363SPhilipp Reisner 850b411b363SPhilipp Reisner /* configured by drbdsetup */ 851b411b363SPhilipp Reisner struct drbd_backing_dev *ldev __protected_by(local); 852b411b363SPhilipp Reisner 853b411b363SPhilipp Reisner sector_t p_size; /* partner's disk size */ 854b411b363SPhilipp Reisner struct request_queue *rq_queue; 855b411b363SPhilipp Reisner struct block_device *this_bdev; 856b411b363SPhilipp Reisner struct gendisk *vdisk; 857b411b363SPhilipp Reisner 85807be15b1SLars Ellenberg unsigned long last_reattach_jif; 85984b8c06bSAndreas Gruenbacher struct drbd_work resync_work; 86084b8c06bSAndreas Gruenbacher struct drbd_work unplug_work; 861b411b363SPhilipp Reisner struct timer_list resync_timer; 862b411b363SPhilipp Reisner struct timer_list md_sync_timer; 863370a43e7SPhilipp Reisner struct timer_list start_resync_timer; 8647fde2be9SPhilipp Reisner struct timer_list request_timer; 865b411b363SPhilipp Reisner 866b411b363SPhilipp Reisner /* Used after attach while negotiating new disk state. */ 867b411b363SPhilipp Reisner union drbd_state new_state_tmp; 868b411b363SPhilipp Reisner 869da9fbc27SPhilipp Reisner union drbd_dev_state state; 870b411b363SPhilipp Reisner wait_queue_head_t misc_wait; 871b411b363SPhilipp Reisner wait_queue_head_t state_wait; /* upon each state change. */ 872b411b363SPhilipp Reisner unsigned int send_cnt; 873b411b363SPhilipp Reisner unsigned int recv_cnt; 874b411b363SPhilipp Reisner unsigned int read_cnt; 875b411b363SPhilipp Reisner unsigned int writ_cnt; 876b411b363SPhilipp Reisner unsigned int al_writ_cnt; 877b411b363SPhilipp Reisner unsigned int bm_writ_cnt; 878b411b363SPhilipp Reisner atomic_t ap_bio_cnt; /* Requests we need to complete */ 879ad3fee79SLars Ellenberg atomic_t ap_actlog_cnt; /* Requests waiting for activity log */ 880b411b363SPhilipp Reisner atomic_t ap_pending_cnt; /* AP data packets on the wire, ack expected */ 881b411b363SPhilipp Reisner atomic_t rs_pending_cnt; /* RS request/data packets on the wire */ 882d942ae44SPhilipp Reisner atomic_t unacked_cnt; /* Need to send replies for */ 883b411b363SPhilipp Reisner atomic_t local_cnt; /* Waiting for local completion */ 8847dbb4386SPhilipp Reisner atomic_t suspend_cnt; 885b2fb6dbeSPhilipp Reisner 886dac1389cSAndreas Gruenbacher /* Interval tree of pending local requests */ 887dac1389cSAndreas Gruenbacher struct rb_root read_requests; 888de696716SAndreas Gruenbacher struct rb_root write_requests; 889b411b363SPhilipp Reisner 890844a6ae7SLars Ellenberg /* for statistics and timeouts */ 891844a6ae7SLars Ellenberg /* [0] read, [1] write */ 892844a6ae7SLars Ellenberg struct list_head pending_master_completion[2]; 893844a6ae7SLars Ellenberg struct list_head pending_completion[2]; 894844a6ae7SLars Ellenberg 895aaaba345SLars Ellenberg /* use checksums for *this* resync */ 896aaaba345SLars Ellenberg bool use_csums; 8974b0715f0SLars Ellenberg /* blocks to resync in this run [unit BM_BLOCK_SIZE] */ 898b411b363SPhilipp Reisner unsigned long rs_total; 8994b0715f0SLars Ellenberg /* number of resync blocks that failed in this run */ 900b411b363SPhilipp Reisner unsigned long rs_failed; 901b411b363SPhilipp Reisner /* Syncer's start time [unit jiffies] */ 902b411b363SPhilipp Reisner unsigned long rs_start; 903b411b363SPhilipp Reisner /* cumulated time in PausedSyncX state [unit jiffies] */ 904b411b363SPhilipp Reisner unsigned long rs_paused; 9051d7734a0SLars Ellenberg /* skipped because csum was equal [unit BM_BLOCK_SIZE] */ 906b411b363SPhilipp Reisner unsigned long rs_same_csum; 9071d7734a0SLars Ellenberg #define DRBD_SYNC_MARKS 8 9081d7734a0SLars Ellenberg #define DRBD_SYNC_MARK_STEP (3*HZ) 9091d7734a0SLars Ellenberg /* block not up-to-date at mark [unit BM_BLOCK_SIZE] */ 9101d7734a0SLars Ellenberg unsigned long rs_mark_left[DRBD_SYNC_MARKS]; 9111d7734a0SLars Ellenberg /* marks's time [unit jiffies] */ 9121d7734a0SLars Ellenberg unsigned long rs_mark_time[DRBD_SYNC_MARKS]; 9131d7734a0SLars Ellenberg /* current index into rs_mark_{left,time} */ 9141d7734a0SLars Ellenberg int rs_last_mark; 915328e0f12SPhilipp Reisner unsigned long rs_last_bcast; /* [unit jiffies] */ 916b411b363SPhilipp Reisner 917b411b363SPhilipp Reisner /* where does the admin want us to start? (sector) */ 918b411b363SPhilipp Reisner sector_t ov_start_sector; 91902b91b55SLars Ellenberg sector_t ov_stop_sector; 920b411b363SPhilipp Reisner /* where are we now? (sector) */ 921b411b363SPhilipp Reisner sector_t ov_position; 922b411b363SPhilipp Reisner /* Start sector of out of sync range (to merge printk reporting). */ 923b411b363SPhilipp Reisner sector_t ov_last_oos_start; 924b411b363SPhilipp Reisner /* size of out-of-sync range in sectors. */ 925b411b363SPhilipp Reisner sector_t ov_last_oos_size; 926b411b363SPhilipp Reisner unsigned long ov_left; /* in bits */ 927b411b363SPhilipp Reisner 928b411b363SPhilipp Reisner struct drbd_bitmap *bitmap; 929b411b363SPhilipp Reisner unsigned long bm_resync_fo; /* bit offset for drbd_bm_find_next */ 930b411b363SPhilipp Reisner 931b411b363SPhilipp Reisner /* Used to track operations of resync... */ 932b411b363SPhilipp Reisner struct lru_cache *resync; 933b411b363SPhilipp Reisner /* Number of locked elements in resync LRU */ 934b411b363SPhilipp Reisner unsigned int resync_locked; 935b411b363SPhilipp Reisner /* resync extent number waiting for application requests */ 936b411b363SPhilipp Reisner unsigned int resync_wenr; 937b411b363SPhilipp Reisner 938b411b363SPhilipp Reisner int open_cnt; 939b411b363SPhilipp Reisner u64 *p_uuid; 9404b0007c0SPhilipp Reisner 94185719573SPhilipp Reisner struct list_head active_ee; /* IO in progress (P_DATA gets written to disk) */ 94285719573SPhilipp Reisner struct list_head sync_ee; /* IO in progress (P_RS_DATA_REPLY gets written to disk) */ 94318b75d75SAndreas Gruenbacher struct list_head done_ee; /* need to send P_WRITE_ACK */ 94418b75d75SAndreas Gruenbacher struct list_head read_ee; /* [RS]P_DATA_REQUEST being read */ 945b411b363SPhilipp Reisner struct list_head net_ee; /* zero-copy network send in progress */ 946b411b363SPhilipp Reisner 947b411b363SPhilipp Reisner int next_barrier_nr; 948b411b363SPhilipp Reisner struct list_head resync_reads; 949435f0740SLars Ellenberg atomic_t pp_in_use; /* allocated from page pool */ 950435f0740SLars Ellenberg atomic_t pp_in_use_by_net; /* sendpage()d, still referenced by tcp */ 951b411b363SPhilipp Reisner wait_queue_head_t ee_wait; 952cc94c650SPhilipp Reisner struct drbd_md_io md_io; 953b411b363SPhilipp Reisner spinlock_t al_lock; 954b411b363SPhilipp Reisner wait_queue_head_t al_wait; 955b411b363SPhilipp Reisner struct lru_cache *act_log; /* activity log */ 956b411b363SPhilipp Reisner unsigned int al_tr_number; 957b411b363SPhilipp Reisner int al_tr_cycle; 958b411b363SPhilipp Reisner wait_queue_head_t seq_wait; 959b411b363SPhilipp Reisner atomic_t packet_seq; 960b411b363SPhilipp Reisner unsigned int peer_seq; 961b411b363SPhilipp Reisner spinlock_t peer_seq_lock; 962b411b363SPhilipp Reisner unsigned long comm_bm_set; /* communicated number of set bits. */ 963b411b363SPhilipp Reisner struct bm_io_work bm_io_work; 964b411b363SPhilipp Reisner u64 ed_uuid; /* UUID of the exposed data */ 9658410da8fSPhilipp Reisner struct mutex own_state_mutex; 966a6b32bc3SAndreas Gruenbacher struct mutex *state_mutex; /* either own_state_mutex or first_peer_device(device)->connection->cstate_mutex */ 967b411b363SPhilipp Reisner char congestion_reason; /* Why we where congested... */ 9681d7734a0SLars Ellenberg atomic_t rs_sect_in; /* for incoming resync data rate, SyncTarget */ 9691d7734a0SLars Ellenberg atomic_t rs_sect_ev; /* for submitted resync data rate, both */ 9701d7734a0SLars Ellenberg int rs_last_sect_ev; /* counter to compare with */ 9711d7734a0SLars Ellenberg int rs_last_events; /* counter of read or write "events" (unit sectors) 9721d7734a0SLars Ellenberg * on the lower level device when we last looked. */ 9731d7734a0SLars Ellenberg int c_sync_rate; /* current resync rate after syncer throttle magic */ 974bde89a9eSAndreas Gruenbacher struct fifo_buffer *rs_plan_s; /* correction values of resync planer (RCU, connection->conn_update) */ 975778f271dSPhilipp Reisner int rs_in_flight; /* resync sectors in flight (to proxy, in proxy and from proxy) */ 976759fbdfbSPhilipp Reisner atomic_t ap_in_flight; /* App sectors in flight (waiting for ack) */ 977db141b2fSLars Ellenberg unsigned int peer_max_bio_size; 978db141b2fSLars Ellenberg unsigned int local_max_bio_size; 979113fef9eSLars Ellenberg 980113fef9eSLars Ellenberg /* any requests that would block in drbd_make_request() 981113fef9eSLars Ellenberg * are deferred to this single-threaded work queue */ 982113fef9eSLars Ellenberg struct submit_worker submit; 983b411b363SPhilipp Reisner }; 984b411b363SPhilipp Reisner 9854ce49266SLars Ellenberg struct drbd_bm_aio_ctx { 9864ce49266SLars Ellenberg struct drbd_device *device; 9874ce49266SLars Ellenberg struct list_head list; /* on device->pending_bitmap_io */; 9884ce49266SLars Ellenberg unsigned long start_jif; 9894ce49266SLars Ellenberg atomic_t in_flight; 9904ce49266SLars Ellenberg unsigned int done; 9914ce49266SLars Ellenberg unsigned flags; 9924ce49266SLars Ellenberg #define BM_AIO_COPY_PAGES 1 9934ce49266SLars Ellenberg #define BM_AIO_WRITE_HINTED 2 9944ce49266SLars Ellenberg #define BM_AIO_WRITE_ALL_PAGES 4 9954ce49266SLars Ellenberg #define BM_AIO_READ 8 9964ce49266SLars Ellenberg int error; 9974ce49266SLars Ellenberg struct kref kref; 9984ce49266SLars Ellenberg }; 9994ce49266SLars Ellenberg 1000a910b123SLars Ellenberg struct drbd_config_context { 1001a910b123SLars Ellenberg /* assigned from drbd_genlmsghdr */ 1002a910b123SLars Ellenberg unsigned int minor; 1003a910b123SLars Ellenberg /* assigned from request attributes, if present */ 1004a910b123SLars Ellenberg unsigned int volume; 1005a910b123SLars Ellenberg #define VOLUME_UNSPECIFIED (-1U) 1006a910b123SLars Ellenberg /* pointer into the request skb, 1007a910b123SLars Ellenberg * limited lifetime! */ 1008a910b123SLars Ellenberg char *resource_name; 1009a910b123SLars Ellenberg struct nlattr *my_addr; 1010a910b123SLars Ellenberg struct nlattr *peer_addr; 1011a910b123SLars Ellenberg 1012a910b123SLars Ellenberg /* reply buffer */ 1013a910b123SLars Ellenberg struct sk_buff *reply_skb; 1014a910b123SLars Ellenberg /* pointer into reply buffer */ 1015a910b123SLars Ellenberg struct drbd_genlmsghdr *reply_dh; 1016a910b123SLars Ellenberg /* resolved from attributes, if possible */ 1017a910b123SLars Ellenberg struct drbd_device *device; 1018a910b123SLars Ellenberg struct drbd_resource *resource; 1019a910b123SLars Ellenberg struct drbd_connection *connection; 1020a910b123SLars Ellenberg }; 1021a910b123SLars Ellenberg 1022b30ab791SAndreas Gruenbacher static inline struct drbd_device *minor_to_device(unsigned int minor) 1023b411b363SPhilipp Reisner { 102405a10ec7SAndreas Gruenbacher return (struct drbd_device *)idr_find(&drbd_devices, minor); 1025b411b363SPhilipp Reisner } 1026b411b363SPhilipp Reisner 1027a6b32bc3SAndreas Gruenbacher static inline struct drbd_peer_device *first_peer_device(struct drbd_device *device) 1028a6b32bc3SAndreas Gruenbacher { 1029ec4a3407SLars Ellenberg return list_first_entry_or_null(&device->peer_devices, struct drbd_peer_device, peer_devices); 1030a6b32bc3SAndreas Gruenbacher } 1031a6b32bc3SAndreas Gruenbacher 1032a2972846SAndreas Gruenbacher static inline struct drbd_peer_device * 1033a2972846SAndreas Gruenbacher conn_peer_device(struct drbd_connection *connection, int volume_number) 1034a2972846SAndreas Gruenbacher { 1035a2972846SAndreas Gruenbacher return idr_find(&connection->peer_devices, volume_number); 1036a2972846SAndreas Gruenbacher } 1037a2972846SAndreas Gruenbacher 103877c556f6SAndreas Gruenbacher #define for_each_resource(resource, _resources) \ 103977c556f6SAndreas Gruenbacher list_for_each_entry(resource, _resources, resources) 104077c556f6SAndreas Gruenbacher 104177c556f6SAndreas Gruenbacher #define for_each_resource_rcu(resource, _resources) \ 104277c556f6SAndreas Gruenbacher list_for_each_entry_rcu(resource, _resources, resources) 104377c556f6SAndreas Gruenbacher 104477c556f6SAndreas Gruenbacher #define for_each_resource_safe(resource, tmp, _resources) \ 104577c556f6SAndreas Gruenbacher list_for_each_entry_safe(resource, tmp, _resources, resources) 104677c556f6SAndreas Gruenbacher 104777c556f6SAndreas Gruenbacher #define for_each_connection(connection, resource) \ 104877c556f6SAndreas Gruenbacher list_for_each_entry(connection, &resource->connections, connections) 104977c556f6SAndreas Gruenbacher 105077c556f6SAndreas Gruenbacher #define for_each_connection_rcu(connection, resource) \ 105177c556f6SAndreas Gruenbacher list_for_each_entry_rcu(connection, &resource->connections, connections) 105277c556f6SAndreas Gruenbacher 105377c556f6SAndreas Gruenbacher #define for_each_connection_safe(connection, tmp, resource) \ 105477c556f6SAndreas Gruenbacher list_for_each_entry_safe(connection, tmp, &resource->connections, connections) 105577c556f6SAndreas Gruenbacher 1056a6b32bc3SAndreas Gruenbacher #define for_each_peer_device(peer_device, device) \ 1057a6b32bc3SAndreas Gruenbacher list_for_each_entry(peer_device, &device->peer_devices, peer_devices) 1058a6b32bc3SAndreas Gruenbacher 1059a6b32bc3SAndreas Gruenbacher #define for_each_peer_device_rcu(peer_device, device) \ 1060a6b32bc3SAndreas Gruenbacher list_for_each_entry_rcu(peer_device, &device->peer_devices, peer_devices) 1061a6b32bc3SAndreas Gruenbacher 1062a6b32bc3SAndreas Gruenbacher #define for_each_peer_device_safe(peer_device, tmp, device) \ 1063a6b32bc3SAndreas Gruenbacher list_for_each_entry_safe(peer_device, tmp, &device->peer_devices, peer_devices) 1064a6b32bc3SAndreas Gruenbacher 1065b30ab791SAndreas Gruenbacher static inline unsigned int device_to_minor(struct drbd_device *device) 1066b411b363SPhilipp Reisner { 1067b30ab791SAndreas Gruenbacher return device->minor; 1068b411b363SPhilipp Reisner } 1069b411b363SPhilipp Reisner 1070b411b363SPhilipp Reisner /* 1071b411b363SPhilipp Reisner * function declarations 1072b411b363SPhilipp Reisner *************************/ 1073b411b363SPhilipp Reisner 1074b411b363SPhilipp Reisner /* drbd_main.c */ 1075b411b363SPhilipp Reisner 1076e89b591cSPhilipp Reisner enum dds_flags { 1077e89b591cSPhilipp Reisner DDSF_FORCED = 1, 1078e89b591cSPhilipp Reisner DDSF_NO_RESYNC = 2, /* Do not run a resync for the new space */ 1079e89b591cSPhilipp Reisner }; 1080e89b591cSPhilipp Reisner 1081b30ab791SAndreas Gruenbacher extern void drbd_init_set_defaults(struct drbd_device *device); 1082b411b363SPhilipp Reisner extern int drbd_thread_start(struct drbd_thread *thi); 1083b411b363SPhilipp Reisner extern void _drbd_thread_stop(struct drbd_thread *thi, int restart, int wait); 1084b411b363SPhilipp Reisner #ifdef CONFIG_SMP 108580822284SPhilipp Reisner extern void drbd_thread_current_set_cpu(struct drbd_thread *thi); 1086b411b363SPhilipp Reisner #else 1087b411b363SPhilipp Reisner #define drbd_thread_current_set_cpu(A) ({}) 1088b411b363SPhilipp Reisner #endif 1089bde89a9eSAndreas Gruenbacher extern void tl_release(struct drbd_connection *, unsigned int barrier_nr, 1090b411b363SPhilipp Reisner unsigned int set_size); 1091bde89a9eSAndreas Gruenbacher extern void tl_clear(struct drbd_connection *); 1092bde89a9eSAndreas Gruenbacher extern void drbd_free_sock(struct drbd_connection *connection); 1093bde89a9eSAndreas Gruenbacher extern int drbd_send(struct drbd_connection *connection, struct socket *sock, 1094b411b363SPhilipp Reisner void *buf, size_t size, unsigned msg_flags); 1095bde89a9eSAndreas Gruenbacher extern int drbd_send_all(struct drbd_connection *, struct socket *, void *, size_t, 1096fb708e40SAndreas Gruenbacher unsigned); 1097fb708e40SAndreas Gruenbacher 1098bde89a9eSAndreas Gruenbacher extern int __drbd_send_protocol(struct drbd_connection *connection, enum drbd_packet cmd); 1099bde89a9eSAndreas Gruenbacher extern int drbd_send_protocol(struct drbd_connection *connection); 110069a22773SAndreas Gruenbacher extern int drbd_send_uuids(struct drbd_peer_device *); 110169a22773SAndreas Gruenbacher extern int drbd_send_uuids_skip_initial_sync(struct drbd_peer_device *); 110269a22773SAndreas Gruenbacher extern void drbd_gen_and_send_sync_uuid(struct drbd_peer_device *); 110369a22773SAndreas Gruenbacher extern int drbd_send_sizes(struct drbd_peer_device *, int trigger_reply, enum dds_flags flags); 110469a22773SAndreas Gruenbacher extern int drbd_send_state(struct drbd_peer_device *, union drbd_state s); 110569a22773SAndreas Gruenbacher extern int drbd_send_current_state(struct drbd_peer_device *); 110669a22773SAndreas Gruenbacher extern int drbd_send_sync_param(struct drbd_peer_device *); 1107bde89a9eSAndreas Gruenbacher extern void drbd_send_b_ack(struct drbd_connection *connection, u32 barrier_nr, 1108b411b363SPhilipp Reisner u32 set_size); 110969a22773SAndreas Gruenbacher extern int drbd_send_ack(struct drbd_peer_device *, enum drbd_packet, 1110f6ffca9fSAndreas Gruenbacher struct drbd_peer_request *); 111169a22773SAndreas Gruenbacher extern void drbd_send_ack_rp(struct drbd_peer_device *, enum drbd_packet, 1112b411b363SPhilipp Reisner struct p_block_req *rp); 111369a22773SAndreas Gruenbacher extern void drbd_send_ack_dp(struct drbd_peer_device *, enum drbd_packet, 11142b2bf214SLars Ellenberg struct p_data *dp, int data_size); 111569a22773SAndreas Gruenbacher extern int drbd_send_ack_ex(struct drbd_peer_device *, enum drbd_packet, 1116b411b363SPhilipp Reisner sector_t sector, int blksize, u64 block_id); 111769a22773SAndreas Gruenbacher extern int drbd_send_out_of_sync(struct drbd_peer_device *, struct drbd_request *); 111869a22773SAndreas Gruenbacher extern int drbd_send_block(struct drbd_peer_device *, enum drbd_packet, 1119f6ffca9fSAndreas Gruenbacher struct drbd_peer_request *); 112069a22773SAndreas Gruenbacher extern int drbd_send_dblock(struct drbd_peer_device *, struct drbd_request *req); 112169a22773SAndreas Gruenbacher extern int drbd_send_drequest(struct drbd_peer_device *, int cmd, 1122b411b363SPhilipp Reisner sector_t sector, int size, u64 block_id); 112369a22773SAndreas Gruenbacher extern int drbd_send_drequest_csum(struct drbd_peer_device *, sector_t sector, 1124d8763023SAndreas Gruenbacher int size, void *digest, int digest_size, 1125d8763023SAndreas Gruenbacher enum drbd_packet cmd); 112669a22773SAndreas Gruenbacher extern int drbd_send_ov_request(struct drbd_peer_device *, sector_t sector, int size); 1127b411b363SPhilipp Reisner 1128b30ab791SAndreas Gruenbacher extern int drbd_send_bitmap(struct drbd_device *device); 112969a22773SAndreas Gruenbacher extern void drbd_send_sr_reply(struct drbd_peer_device *, enum drbd_state_rv retcode); 1130bde89a9eSAndreas Gruenbacher extern void conn_send_sr_reply(struct drbd_connection *connection, enum drbd_state_rv retcode); 1131700ca8c0SPhilipp Reisner extern int drbd_send_rs_deallocated(struct drbd_peer_device *, struct drbd_peer_request *); 113263a7c8adSLars Ellenberg extern void drbd_backing_dev_free(struct drbd_device *device, struct drbd_backing_dev *ldev); 1133b30ab791SAndreas Gruenbacher extern void drbd_device_cleanup(struct drbd_device *device); 1134b30ab791SAndreas Gruenbacher void drbd_print_uuids(struct drbd_device *device, const char *text); 1135b411b363SPhilipp Reisner 1136bde89a9eSAndreas Gruenbacher extern void conn_md_sync(struct drbd_connection *connection); 1137b30ab791SAndreas Gruenbacher extern void drbd_md_write(struct drbd_device *device, void *buffer); 1138b30ab791SAndreas Gruenbacher extern void drbd_md_sync(struct drbd_device *device); 1139b30ab791SAndreas Gruenbacher extern int drbd_md_read(struct drbd_device *device, struct drbd_backing_dev *bdev); 1140b30ab791SAndreas Gruenbacher extern void drbd_uuid_set(struct drbd_device *device, int idx, u64 val) __must_hold(local); 1141b30ab791SAndreas Gruenbacher extern void _drbd_uuid_set(struct drbd_device *device, int idx, u64 val) __must_hold(local); 1142b30ab791SAndreas Gruenbacher extern void drbd_uuid_new_current(struct drbd_device *device) __must_hold(local); 1143b30ab791SAndreas Gruenbacher extern void drbd_uuid_set_bm(struct drbd_device *device, u64 val) __must_hold(local); 1144b30ab791SAndreas Gruenbacher extern void drbd_uuid_move_history(struct drbd_device *device) __must_hold(local); 1145b30ab791SAndreas Gruenbacher extern void __drbd_uuid_set(struct drbd_device *device, int idx, u64 val) __must_hold(local); 1146b30ab791SAndreas Gruenbacher extern void drbd_md_set_flag(struct drbd_device *device, int flags) __must_hold(local); 1147b30ab791SAndreas Gruenbacher extern void drbd_md_clear_flag(struct drbd_device *device, int flags)__must_hold(local); 1148b411b363SPhilipp Reisner extern int drbd_md_test_flag(struct drbd_backing_dev *, int); 1149b30ab791SAndreas Gruenbacher extern void drbd_md_mark_dirty(struct drbd_device *device); 1150b30ab791SAndreas Gruenbacher extern void drbd_queue_bitmap_io(struct drbd_device *device, 115154761697SAndreas Gruenbacher int (*io_fn)(struct drbd_device *), 115254761697SAndreas Gruenbacher void (*done)(struct drbd_device *, int), 115320ceb2b2SLars Ellenberg char *why, enum bm_flag flags); 1154b30ab791SAndreas Gruenbacher extern int drbd_bitmap_io(struct drbd_device *device, 115554761697SAndreas Gruenbacher int (*io_fn)(struct drbd_device *), 115620ceb2b2SLars Ellenberg char *why, enum bm_flag flags); 1157b30ab791SAndreas Gruenbacher extern int drbd_bitmap_io_from_worker(struct drbd_device *device, 115854761697SAndreas Gruenbacher int (*io_fn)(struct drbd_device *), 1159edc9f5ebSLars Ellenberg char *why, enum bm_flag flags); 11608fe39aacSPhilipp Reisner extern int drbd_bmio_set_n_write(struct drbd_device *device) __must_hold(local); 11618fe39aacSPhilipp Reisner extern int drbd_bmio_clear_n_write(struct drbd_device *device) __must_hold(local); 1162b411b363SPhilipp Reisner 1163b411b363SPhilipp Reisner /* Meta data layout 1164ae8bf312SLars Ellenberg * 1165ae8bf312SLars Ellenberg * We currently have two possible layouts. 1166ae8bf312SLars Ellenberg * Offsets in (512 byte) sectors. 1167ae8bf312SLars Ellenberg * external: 1168ae8bf312SLars Ellenberg * |----------- md_size_sect ------------------| 1169ae8bf312SLars Ellenberg * [ 4k superblock ][ activity log ][ Bitmap ] 1170ae8bf312SLars Ellenberg * | al_offset == 8 | 1171ae8bf312SLars Ellenberg * | bm_offset = al_offset + X | 1172ae8bf312SLars Ellenberg * ==> bitmap sectors = md_size_sect - bm_offset 1173ae8bf312SLars Ellenberg * 1174ae8bf312SLars Ellenberg * Variants: 1175ae8bf312SLars Ellenberg * old, indexed fixed size meta data: 1176ae8bf312SLars Ellenberg * 1177ae8bf312SLars Ellenberg * internal: 1178ae8bf312SLars Ellenberg * |----------- md_size_sect ------------------| 1179ae8bf312SLars Ellenberg * [data.....][ Bitmap ][ activity log ][ 4k superblock ][padding*] 1180ae8bf312SLars Ellenberg * | al_offset < 0 | 1181ae8bf312SLars Ellenberg * | bm_offset = al_offset - Y | 1182ae8bf312SLars Ellenberg * ==> bitmap sectors = Y = al_offset - bm_offset 1183ae8bf312SLars Ellenberg * 1184ae8bf312SLars Ellenberg * [padding*] are zero or up to 7 unused 512 Byte sectors to the 1185ae8bf312SLars Ellenberg * end of the device, so that the [4k superblock] will be 4k aligned. 1186ae8bf312SLars Ellenberg * 1187ae8bf312SLars Ellenberg * The activity log consists of 4k transaction blocks, 1188ae8bf312SLars Ellenberg * which are written in a ring-buffer, or striped ring-buffer like fashion, 1189ae8bf312SLars Ellenberg * which are writtensize used to be fixed 32kB, 1190ae8bf312SLars Ellenberg * but is about to become configurable. 1191ae8bf312SLars Ellenberg */ 1192b411b363SPhilipp Reisner 1193ae8bf312SLars Ellenberg /* Our old fixed size meta data layout 1194ae8bf312SLars Ellenberg * allows up to about 3.8TB, so if you want more, 11957ad651b5SLars Ellenberg * you need to use the "flexible" meta data format. */ 1196ae8bf312SLars Ellenberg #define MD_128MB_SECT (128LLU << 11) /* 128 MB, unit sectors */ 1197ae8bf312SLars Ellenberg #define MD_4kB_SECT 8 1198ae8bf312SLars Ellenberg #define MD_32kB_SECT 64 1199b411b363SPhilipp Reisner 12007ad651b5SLars Ellenberg /* One activity log extent represents 4M of storage */ 12017ad651b5SLars Ellenberg #define AL_EXTENT_SHIFT 22 1202b411b363SPhilipp Reisner #define AL_EXTENT_SIZE (1<<AL_EXTENT_SHIFT) 1203b411b363SPhilipp Reisner 12047ad651b5SLars Ellenberg /* We could make these currently hardcoded constants configurable 12057ad651b5SLars Ellenberg * variables at create-md time (or even re-configurable at runtime?). 12067ad651b5SLars Ellenberg * Which will require some more changes to the DRBD "super block" 12077ad651b5SLars Ellenberg * and attach code. 12087ad651b5SLars Ellenberg * 12097ad651b5SLars Ellenberg * updates per transaction: 12107ad651b5SLars Ellenberg * This many changes to the active set can be logged with one transaction. 12117ad651b5SLars Ellenberg * This number is arbitrary. 12127ad651b5SLars Ellenberg * context per transaction: 12137ad651b5SLars Ellenberg * This many context extent numbers are logged with each transaction. 12147ad651b5SLars Ellenberg * This number is resulting from the transaction block size (4k), the layout 12157ad651b5SLars Ellenberg * of the transaction header, and the number of updates per transaction. 12167ad651b5SLars Ellenberg * See drbd_actlog.c:struct al_transaction_on_disk 12177ad651b5SLars Ellenberg * */ 12187ad651b5SLars Ellenberg #define AL_UPDATES_PER_TRANSACTION 64 // arbitrary 12197ad651b5SLars Ellenberg #define AL_CONTEXT_PER_TRANSACTION 919 // (4096 - 36 - 6*64)/4 12207ad651b5SLars Ellenberg 1221b411b363SPhilipp Reisner #if BITS_PER_LONG == 32 1222b411b363SPhilipp Reisner #define LN2_BPL 5 1223b411b363SPhilipp Reisner #define cpu_to_lel(A) cpu_to_le32(A) 1224b411b363SPhilipp Reisner #define lel_to_cpu(A) le32_to_cpu(A) 1225b411b363SPhilipp Reisner #elif BITS_PER_LONG == 64 1226b411b363SPhilipp Reisner #define LN2_BPL 6 1227b411b363SPhilipp Reisner #define cpu_to_lel(A) cpu_to_le64(A) 1228b411b363SPhilipp Reisner #define lel_to_cpu(A) le64_to_cpu(A) 1229b411b363SPhilipp Reisner #else 1230b411b363SPhilipp Reisner #error "LN2 of BITS_PER_LONG unknown!" 1231b411b363SPhilipp Reisner #endif 1232b411b363SPhilipp Reisner 1233b411b363SPhilipp Reisner /* resync bitmap */ 1234b411b363SPhilipp Reisner /* 16MB sized 'bitmap extent' to track syncer usage */ 1235b411b363SPhilipp Reisner struct bm_extent { 1236b411b363SPhilipp Reisner int rs_left; /* number of bits set (out of sync) in this extent. */ 1237b411b363SPhilipp Reisner int rs_failed; /* number of failed resync requests in this extent. */ 1238b411b363SPhilipp Reisner unsigned long flags; 1239b411b363SPhilipp Reisner struct lc_element lce; 1240b411b363SPhilipp Reisner }; 1241b411b363SPhilipp Reisner 1242b411b363SPhilipp Reisner #define BME_NO_WRITES 0 /* bm_extent.flags: no more requests on this one! */ 1243b411b363SPhilipp Reisner #define BME_LOCKED 1 /* bm_extent.flags: syncer active on this one. */ 1244e3555d85SPhilipp Reisner #define BME_PRIORITY 2 /* finish resync IO on this extent ASAP! App IO waiting! */ 1245b411b363SPhilipp Reisner 1246b411b363SPhilipp Reisner /* drbd_bitmap.c */ 1247b411b363SPhilipp Reisner /* 1248b411b363SPhilipp Reisner * We need to store one bit for a block. 1249b411b363SPhilipp Reisner * Example: 1GB disk @ 4096 byte blocks ==> we need 32 KB bitmap. 1250b411b363SPhilipp Reisner * Bit 0 ==> local node thinks this block is binary identical on both nodes 1251b411b363SPhilipp Reisner * Bit 1 ==> local node thinks this block needs to be synced. 1252b411b363SPhilipp Reisner */ 1253b411b363SPhilipp Reisner 12548e26f9ccSPhilipp Reisner #define SLEEP_TIME (HZ/10) 12558e26f9ccSPhilipp Reisner 125645dfffebSLars Ellenberg /* We do bitmap IO in units of 4k blocks. 125745dfffebSLars Ellenberg * We also still have a hardcoded 4k per bit relation. */ 1258b411b363SPhilipp Reisner #define BM_BLOCK_SHIFT 12 /* 4k per bit */ 1259b411b363SPhilipp Reisner #define BM_BLOCK_SIZE (1<<BM_BLOCK_SHIFT) 126045dfffebSLars Ellenberg /* mostly arbitrarily set the represented size of one bitmap extent, 126145dfffebSLars Ellenberg * aka resync extent, to 16 MiB (which is also 512 Byte worth of bitmap 126245dfffebSLars Ellenberg * at 4k per bit resolution) */ 126345dfffebSLars Ellenberg #define BM_EXT_SHIFT 24 /* 16 MiB per resync extent */ 1264b411b363SPhilipp Reisner #define BM_EXT_SIZE (1<<BM_EXT_SHIFT) 1265b411b363SPhilipp Reisner 1266b411b363SPhilipp Reisner #if (BM_EXT_SHIFT != 24) || (BM_BLOCK_SHIFT != 12) 1267b411b363SPhilipp Reisner #error "HAVE YOU FIXED drbdmeta AS WELL??" 1268b411b363SPhilipp Reisner #endif 1269b411b363SPhilipp Reisner 1270b411b363SPhilipp Reisner /* thus many _storage_ sectors are described by one bit */ 1271b411b363SPhilipp Reisner #define BM_SECT_TO_BIT(x) ((x)>>(BM_BLOCK_SHIFT-9)) 1272b411b363SPhilipp Reisner #define BM_BIT_TO_SECT(x) ((sector_t)(x)<<(BM_BLOCK_SHIFT-9)) 1273b411b363SPhilipp Reisner #define BM_SECT_PER_BIT BM_BIT_TO_SECT(1) 1274b411b363SPhilipp Reisner 1275b411b363SPhilipp Reisner /* bit to represented kilo byte conversion */ 1276b411b363SPhilipp Reisner #define Bit2KB(bits) ((bits)<<(BM_BLOCK_SHIFT-10)) 1277b411b363SPhilipp Reisner 1278b411b363SPhilipp Reisner /* in which _bitmap_ extent (resp. sector) the bit for a certain 1279b411b363SPhilipp Reisner * _storage_ sector is located in */ 1280b411b363SPhilipp Reisner #define BM_SECT_TO_EXT(x) ((x)>>(BM_EXT_SHIFT-9)) 12815ab7d2c0SLars Ellenberg #define BM_BIT_TO_EXT(x) ((x) >> (BM_EXT_SHIFT - BM_BLOCK_SHIFT)) 1282b411b363SPhilipp Reisner 12835ab7d2c0SLars Ellenberg /* first storage sector a bitmap extent corresponds to */ 1284b411b363SPhilipp Reisner #define BM_EXT_TO_SECT(x) ((sector_t)(x) << (BM_EXT_SHIFT-9)) 12855ab7d2c0SLars Ellenberg /* how much _storage_ sectors we have per bitmap extent */ 1286b411b363SPhilipp Reisner #define BM_SECT_PER_EXT BM_EXT_TO_SECT(1) 12875ab7d2c0SLars Ellenberg /* how many bits are covered by one bitmap extent (resync extent) */ 12885ab7d2c0SLars Ellenberg #define BM_BITS_PER_EXT (1UL << (BM_EXT_SHIFT - BM_BLOCK_SHIFT)) 12895ab7d2c0SLars Ellenberg 12905ab7d2c0SLars Ellenberg #define BM_BLOCKS_PER_BM_EXT_MASK (BM_BITS_PER_EXT - 1) 12915ab7d2c0SLars Ellenberg 1292b411b363SPhilipp Reisner 1293b411b363SPhilipp Reisner /* in one sector of the bitmap, we have this many activity_log extents. */ 1294b411b363SPhilipp Reisner #define AL_EXT_PER_BM_SECT (1 << (BM_EXT_SHIFT - AL_EXTENT_SHIFT)) 1295b411b363SPhilipp Reisner 1296b411b363SPhilipp Reisner /* the extent in "PER_EXTENT" below is an activity log extent 1297b411b363SPhilipp Reisner * we need that many (long words/bytes) to store the bitmap 1298b411b363SPhilipp Reisner * of one AL_EXTENT_SIZE chunk of storage. 1299b411b363SPhilipp Reisner * we can store the bitmap for that many AL_EXTENTS within 1300b411b363SPhilipp Reisner * one sector of the _on_disk_ bitmap: 1301b411b363SPhilipp Reisner * bit 0 bit 37 bit 38 bit (512*8)-1 1302b411b363SPhilipp Reisner * ...|........|........|.. // ..|........| 1303b411b363SPhilipp Reisner * sect. 0 `296 `304 ^(512*8*8)-1 1304b411b363SPhilipp Reisner * 1305b411b363SPhilipp Reisner #define BM_WORDS_PER_EXT ( (AL_EXT_SIZE/BM_BLOCK_SIZE) / BITS_PER_LONG ) 1306b411b363SPhilipp Reisner #define BM_BYTES_PER_EXT ( (AL_EXT_SIZE/BM_BLOCK_SIZE) / 8 ) // 128 1307b411b363SPhilipp Reisner #define BM_EXT_PER_SECT ( 512 / BM_BYTES_PER_EXTENT ) // 4 1308b411b363SPhilipp Reisner */ 1309b411b363SPhilipp Reisner 1310b411b363SPhilipp Reisner #define DRBD_MAX_SECTORS_32 (0xffffffffLU) 1311ae8bf312SLars Ellenberg /* we have a certain meta data variant that has a fixed on-disk size of 128 1312ae8bf312SLars Ellenberg * MiB, of which 4k are our "superblock", and 32k are the fixed size activity 1313ae8bf312SLars Ellenberg * log, leaving this many sectors for the bitmap. 1314ae8bf312SLars Ellenberg */ 1315ae8bf312SLars Ellenberg 1316ae8bf312SLars Ellenberg #define DRBD_MAX_SECTORS_FIXED_BM \ 1317ae8bf312SLars Ellenberg ((MD_128MB_SECT - MD_32kB_SECT - MD_4kB_SECT) * (1LL<<(BM_EXT_SHIFT-9))) 1318ae8bf312SLars Ellenberg #if !defined(CONFIG_LBDAF) && BITS_PER_LONG == 32 1319b411b363SPhilipp Reisner #define DRBD_MAX_SECTORS DRBD_MAX_SECTORS_32 1320b411b363SPhilipp Reisner #define DRBD_MAX_SECTORS_FLEX DRBD_MAX_SECTORS_32 1321b411b363SPhilipp Reisner #else 1322ae8bf312SLars Ellenberg #define DRBD_MAX_SECTORS DRBD_MAX_SECTORS_FIXED_BM 1323b411b363SPhilipp Reisner /* 16 TB in units of sectors */ 1324b411b363SPhilipp Reisner #if BITS_PER_LONG == 32 1325b411b363SPhilipp Reisner /* adjust by one page worth of bitmap, 1326b411b363SPhilipp Reisner * so we won't wrap around in drbd_bm_find_next_bit. 1327b411b363SPhilipp Reisner * you should use 64bit OS for that much storage, anyways. */ 1328b411b363SPhilipp Reisner #define DRBD_MAX_SECTORS_FLEX BM_BIT_TO_SECT(0xffff7fff) 1329b411b363SPhilipp Reisner #else 13304b0715f0SLars Ellenberg /* we allow up to 1 PiB now on 64bit architecture with "flexible" meta data */ 13314b0715f0SLars Ellenberg #define DRBD_MAX_SECTORS_FLEX (1UL << 51) 13324b0715f0SLars Ellenberg /* corresponds to (1UL << 38) bits right now. */ 1333b411b363SPhilipp Reisner #endif 1334b411b363SPhilipp Reisner #endif 1335b411b363SPhilipp Reisner 13368bf223c2SMing Lei /* Estimate max bio size as 256 * PAGE_SIZE, 1337ea1754a0SKirill A. Shutemov * so for typical PAGE_SIZE of 4k, that is (1<<20) Byte. 133823361cf3SLars Ellenberg * Since we may live in a mixed-platform cluster, 133923361cf3SLars Ellenberg * we limit us to a platform agnostic constant here for now. 134023361cf3SLars Ellenberg * A followup commit may allow even bigger BIO sizes, 134123361cf3SLars Ellenberg * once we thought that through. */ 134298683650SPhilipp Reisner #define DRBD_MAX_BIO_SIZE (1U << 20) 13438bf223c2SMing Lei #if DRBD_MAX_BIO_SIZE > (BIO_MAX_PAGES << PAGE_SHIFT) 134423361cf3SLars Ellenberg #error Architecture not supported: DRBD_MAX_BIO_SIZE > BIO_MAX_SIZE 134523361cf3SLars Ellenberg #endif 1346db141b2fSLars Ellenberg #define DRBD_MAX_BIO_SIZE_SAFE (1U << 12) /* Works always = 4k */ 1347b411b363SPhilipp Reisner 134898683650SPhilipp Reisner #define DRBD_MAX_SIZE_H80_PACKET (1U << 15) /* Header 80 only allows packets up to 32KiB data */ 134998683650SPhilipp Reisner #define DRBD_MAX_BIO_SIZE_P95 (1U << 17) /* Protocol 95 to 99 allows bios up to 128KiB */ 1350b411b363SPhilipp Reisner 1351505675f9SLars Ellenberg /* For now, don't allow more than half of what we can "activate" in one 1352505675f9SLars Ellenberg * activity log transaction to be discarded in one go. We may need to rework 1353505675f9SLars Ellenberg * drbd_al_begin_io() to allow for even larger discard ranges */ 13549104d31aSLars Ellenberg #define DRBD_MAX_BATCH_BIO_SIZE (AL_UPDATES_PER_TRANSACTION/2*AL_EXTENT_SIZE) 13559104d31aSLars Ellenberg #define DRBD_MAX_BBIO_SECTORS (DRBD_MAX_BATCH_BIO_SIZE >> 9) 1356a0fb3c47SLars Ellenberg 1357b30ab791SAndreas Gruenbacher extern int drbd_bm_init(struct drbd_device *device); 1358b30ab791SAndreas Gruenbacher extern int drbd_bm_resize(struct drbd_device *device, sector_t sectors, int set_new_bits); 1359b30ab791SAndreas Gruenbacher extern void drbd_bm_cleanup(struct drbd_device *device); 1360b30ab791SAndreas Gruenbacher extern void drbd_bm_set_all(struct drbd_device *device); 1361b30ab791SAndreas Gruenbacher extern void drbd_bm_clear_all(struct drbd_device *device); 13624b0715f0SLars Ellenberg /* set/clear/test only a few bits at a time */ 1363b411b363SPhilipp Reisner extern int drbd_bm_set_bits( 1364b30ab791SAndreas Gruenbacher struct drbd_device *device, unsigned long s, unsigned long e); 1365b411b363SPhilipp Reisner extern int drbd_bm_clear_bits( 1366b30ab791SAndreas Gruenbacher struct drbd_device *device, unsigned long s, unsigned long e); 13674b0715f0SLars Ellenberg extern int drbd_bm_count_bits( 1368b30ab791SAndreas Gruenbacher struct drbd_device *device, const unsigned long s, const unsigned long e); 13694b0715f0SLars Ellenberg /* bm_set_bits variant for use while holding drbd_bm_lock, 13704b0715f0SLars Ellenberg * may process the whole bitmap in one go */ 1371b30ab791SAndreas Gruenbacher extern void _drbd_bm_set_bits(struct drbd_device *device, 1372b411b363SPhilipp Reisner const unsigned long s, const unsigned long e); 1373b30ab791SAndreas Gruenbacher extern int drbd_bm_test_bit(struct drbd_device *device, unsigned long bitnr); 1374b30ab791SAndreas Gruenbacher extern int drbd_bm_e_weight(struct drbd_device *device, unsigned long enr); 1375b30ab791SAndreas Gruenbacher extern int drbd_bm_read(struct drbd_device *device) __must_hold(local); 1376b30ab791SAndreas Gruenbacher extern void drbd_bm_mark_for_writeout(struct drbd_device *device, int page_nr); 1377b30ab791SAndreas Gruenbacher extern int drbd_bm_write(struct drbd_device *device) __must_hold(local); 137827ea1d87SLars Ellenberg extern void drbd_bm_reset_al_hints(struct drbd_device *device) __must_hold(local); 1379b30ab791SAndreas Gruenbacher extern int drbd_bm_write_hinted(struct drbd_device *device) __must_hold(local); 1380c7a58db4SLars Ellenberg extern int drbd_bm_write_lazy(struct drbd_device *device, unsigned upper_idx) __must_hold(local); 1381b30ab791SAndreas Gruenbacher extern int drbd_bm_write_all(struct drbd_device *device) __must_hold(local); 1382b30ab791SAndreas Gruenbacher extern int drbd_bm_write_copy_pages(struct drbd_device *device) __must_hold(local); 1383b30ab791SAndreas Gruenbacher extern size_t drbd_bm_words(struct drbd_device *device); 1384b30ab791SAndreas Gruenbacher extern unsigned long drbd_bm_bits(struct drbd_device *device); 1385b30ab791SAndreas Gruenbacher extern sector_t drbd_bm_capacity(struct drbd_device *device); 13864b0715f0SLars Ellenberg 13874b0715f0SLars Ellenberg #define DRBD_END_OF_BITMAP (~(unsigned long)0) 1388b30ab791SAndreas Gruenbacher extern unsigned long drbd_bm_find_next(struct drbd_device *device, unsigned long bm_fo); 1389b411b363SPhilipp Reisner /* bm_find_next variants for use while you hold drbd_bm_lock() */ 1390b30ab791SAndreas Gruenbacher extern unsigned long _drbd_bm_find_next(struct drbd_device *device, unsigned long bm_fo); 1391b30ab791SAndreas Gruenbacher extern unsigned long _drbd_bm_find_next_zero(struct drbd_device *device, unsigned long bm_fo); 1392b30ab791SAndreas Gruenbacher extern unsigned long _drbd_bm_total_weight(struct drbd_device *device); 1393b30ab791SAndreas Gruenbacher extern unsigned long drbd_bm_total_weight(struct drbd_device *device); 1394b411b363SPhilipp Reisner /* for receive_bitmap */ 1395b30ab791SAndreas Gruenbacher extern void drbd_bm_merge_lel(struct drbd_device *device, size_t offset, 1396b411b363SPhilipp Reisner size_t number, unsigned long *buffer); 139719f843aaSLars Ellenberg /* for _drbd_send_bitmap */ 1398b30ab791SAndreas Gruenbacher extern void drbd_bm_get_lel(struct drbd_device *device, size_t offset, 1399b411b363SPhilipp Reisner size_t number, unsigned long *buffer); 1400b411b363SPhilipp Reisner 1401b30ab791SAndreas Gruenbacher extern void drbd_bm_lock(struct drbd_device *device, char *why, enum bm_flag flags); 1402b30ab791SAndreas Gruenbacher extern void drbd_bm_unlock(struct drbd_device *device); 1403b411b363SPhilipp Reisner /* drbd_main.c */ 1404b411b363SPhilipp Reisner 1405b411b363SPhilipp Reisner extern struct kmem_cache *drbd_request_cache; 14066c852becSAndreas Gruenbacher extern struct kmem_cache *drbd_ee_cache; /* peer requests */ 1407b411b363SPhilipp Reisner extern struct kmem_cache *drbd_bm_ext_cache; /* bitmap extents */ 1408b411b363SPhilipp Reisner extern struct kmem_cache *drbd_al_ext_cache; /* activity log extents */ 1409b411b363SPhilipp Reisner extern mempool_t *drbd_request_mempool; 1410b411b363SPhilipp Reisner extern mempool_t *drbd_ee_mempool; 1411b411b363SPhilipp Reisner 14124281808fSLars Ellenberg /* drbd's page pool, used to buffer data received from the peer, 14134281808fSLars Ellenberg * or data requested by the peer. 14144281808fSLars Ellenberg * 14154281808fSLars Ellenberg * This does not have an emergency reserve. 14164281808fSLars Ellenberg * 14174281808fSLars Ellenberg * When allocating from this pool, it first takes pages from the pool. 14184281808fSLars Ellenberg * Only if the pool is depleted will try to allocate from the system. 14194281808fSLars Ellenberg * 14204281808fSLars Ellenberg * The assumption is that pages taken from this pool will be processed, 14214281808fSLars Ellenberg * and given back, "quickly", and then can be recycled, so we can avoid 14224281808fSLars Ellenberg * frequent calls to alloc_page(), and still will be able to make progress even 14234281808fSLars Ellenberg * under memory pressure. 14244281808fSLars Ellenberg */ 14254281808fSLars Ellenberg extern struct page *drbd_pp_pool; 1426b411b363SPhilipp Reisner extern spinlock_t drbd_pp_lock; 1427b411b363SPhilipp Reisner extern int drbd_pp_vacant; 1428b411b363SPhilipp Reisner extern wait_queue_head_t drbd_pp_wait; 1429b411b363SPhilipp Reisner 14304281808fSLars Ellenberg /* We also need a standard (emergency-reserve backed) page pool 14314281808fSLars Ellenberg * for meta data IO (activity log, bitmap). 14324281808fSLars Ellenberg * We can keep it global, as long as it is used as "N pages at a time". 14334281808fSLars Ellenberg * 128 should be plenty, currently we probably can get away with as few as 1. 14344281808fSLars Ellenberg */ 14354281808fSLars Ellenberg #define DRBD_MIN_POOL_PAGES 128 14364281808fSLars Ellenberg extern mempool_t *drbd_md_io_page_pool; 14374281808fSLars Ellenberg 14389476f39dSLars Ellenberg /* We also need to make sure we get a bio 14399476f39dSLars Ellenberg * when we need it for housekeeping purposes */ 14409476f39dSLars Ellenberg extern struct bio_set *drbd_md_io_bio_set; 14419476f39dSLars Ellenberg /* to allocate from that set */ 14429476f39dSLars Ellenberg extern struct bio *bio_alloc_drbd(gfp_t gfp_mask); 14439476f39dSLars Ellenberg 144428bc3b8cSAndreas Gruenbacher extern struct mutex resources_mutex; 1445b411b363SPhilipp Reisner 1446bde89a9eSAndreas Gruenbacher extern int conn_lowest_minor(struct drbd_connection *connection); 1447a910b123SLars Ellenberg extern enum drbd_ret_code drbd_create_device(struct drbd_config_context *adm_ctx, unsigned int minor); 144805a10ec7SAndreas Gruenbacher extern void drbd_destroy_device(struct kref *kref); 1449a910b123SLars Ellenberg extern void drbd_delete_device(struct drbd_device *device); 1450b411b363SPhilipp Reisner 145177c556f6SAndreas Gruenbacher extern struct drbd_resource *drbd_create_resource(const char *name); 145277c556f6SAndreas Gruenbacher extern void drbd_free_resource(struct drbd_resource *resource); 145377c556f6SAndreas Gruenbacher 1454eb6bea67SAndreas Gruenbacher extern int set_resource_options(struct drbd_resource *resource, struct res_opts *res_opts); 1455bde89a9eSAndreas Gruenbacher extern struct drbd_connection *conn_create(const char *name, struct res_opts *res_opts); 145605a10ec7SAndreas Gruenbacher extern void drbd_destroy_connection(struct kref *kref); 1457bde89a9eSAndreas Gruenbacher extern struct drbd_connection *conn_get_by_addrs(void *my_addr, int my_addr_len, 1458089c075dSAndreas Gruenbacher void *peer_addr, int peer_addr_len); 14594bc76048SAndreas Gruenbacher extern struct drbd_resource *drbd_find_resource(const char *name); 146077c556f6SAndreas Gruenbacher extern void drbd_destroy_resource(struct kref *kref); 1461bde89a9eSAndreas Gruenbacher extern void conn_free_crypto(struct drbd_connection *connection); 1462b411b363SPhilipp Reisner 1463b411b363SPhilipp Reisner extern int proc_details; 1464b411b363SPhilipp Reisner 1465b411b363SPhilipp Reisner /* drbd_req */ 1466113fef9eSLars Ellenberg extern void do_submit(struct work_struct *ws); 146754761697SAndreas Gruenbacher extern void __drbd_make_request(struct drbd_device *, struct bio *, unsigned long); 1468dece1635SJens Axboe extern blk_qc_t drbd_make_request(struct request_queue *q, struct bio *bio); 1469b30ab791SAndreas Gruenbacher extern int drbd_read_remote(struct drbd_device *device, struct drbd_request *req); 1470b411b363SPhilipp Reisner extern int is_valid_ar_handle(struct drbd_request *, sector_t); 1471b411b363SPhilipp Reisner 1472b411b363SPhilipp Reisner 1473b411b363SPhilipp Reisner /* drbd_nl.c */ 1474a2972846SAndreas Gruenbacher 1475a2972846SAndreas Gruenbacher extern struct mutex notification_mutex; 1476a2972846SAndreas Gruenbacher 1477b30ab791SAndreas Gruenbacher extern void drbd_suspend_io(struct drbd_device *device); 1478b30ab791SAndreas Gruenbacher extern void drbd_resume_io(struct drbd_device *device); 1479b411b363SPhilipp Reisner extern char *ppsize(char *buf, unsigned long long size); 148054761697SAndreas Gruenbacher extern sector_t drbd_new_dev_size(struct drbd_device *, struct drbd_backing_dev *, sector_t, int); 1481e96c9633SPhilipp Reisner enum determine_dev_size { 1482d752b269SPhilipp Reisner DS_ERROR_SHRINK = -3, 1483d752b269SPhilipp Reisner DS_ERROR_SPACE_MD = -2, 1484e96c9633SPhilipp Reisner DS_ERROR = -1, 1485e96c9633SPhilipp Reisner DS_UNCHANGED = 0, 1486e96c9633SPhilipp Reisner DS_SHRUNK = 1, 148757737adcSPhilipp Reisner DS_GREW = 2, 148857737adcSPhilipp Reisner DS_GREW_FROM_ZERO = 3, 1489e96c9633SPhilipp Reisner }; 1490d752b269SPhilipp Reisner extern enum determine_dev_size 149154761697SAndreas Gruenbacher drbd_determine_dev_size(struct drbd_device *, enum dds_flags, struct resize_parms *) __must_hold(local); 149254761697SAndreas Gruenbacher extern void resync_after_online_grow(struct drbd_device *); 14939104d31aSLars Ellenberg extern void drbd_reconsider_queue_parameters(struct drbd_device *device, 14949104d31aSLars Ellenberg struct drbd_backing_dev *bdev, struct o_qlim *o); 1495b30ab791SAndreas Gruenbacher extern enum drbd_state_rv drbd_set_role(struct drbd_device *device, 1496bf885f8aSAndreas Gruenbacher enum drbd_role new_role, 1497b411b363SPhilipp Reisner int force); 1498bde89a9eSAndreas Gruenbacher extern bool conn_try_outdate_peer(struct drbd_connection *connection); 1499bde89a9eSAndreas Gruenbacher extern void conn_try_outdate_peer_async(struct drbd_connection *connection); 15007e5fec31SFabian Frederick extern enum drbd_peer_state conn_khelper(struct drbd_connection *connection, char *cmd); 1501b30ab791SAndreas Gruenbacher extern int drbd_khelper(struct drbd_device *device, char *cmd); 1502b411b363SPhilipp Reisner 1503b411b363SPhilipp Reisner /* drbd_worker.c */ 1504d40e5671SPhilipp Reisner /* bi_end_io handlers */ 15054246a0b6SChristoph Hellwig extern void drbd_md_endio(struct bio *bio); 15064246a0b6SChristoph Hellwig extern void drbd_peer_request_endio(struct bio *bio); 15074246a0b6SChristoph Hellwig extern void drbd_request_endio(struct bio *bio); 1508b411b363SPhilipp Reisner extern int drbd_worker(struct drbd_thread *thi); 1509b30ab791SAndreas Gruenbacher enum drbd_ret_code drbd_resync_after_valid(struct drbd_device *device, int o_minor); 1510b30ab791SAndreas Gruenbacher void drbd_resync_after_changed(struct drbd_device *device); 1511b30ab791SAndreas Gruenbacher extern void drbd_start_resync(struct drbd_device *device, enum drbd_conns side); 1512b30ab791SAndreas Gruenbacher extern void resume_next_sg(struct drbd_device *device); 1513b30ab791SAndreas Gruenbacher extern void suspend_other_sg(struct drbd_device *device); 1514b30ab791SAndreas Gruenbacher extern int drbd_resync_finished(struct drbd_device *device); 1515b411b363SPhilipp Reisner /* maybe rather drbd_main.c ? */ 1516e37d2438SLars Ellenberg extern void *drbd_md_get_buffer(struct drbd_device *device, const char *intent); 1517b30ab791SAndreas Gruenbacher extern void drbd_md_put_buffer(struct drbd_device *device); 1518b30ab791SAndreas Gruenbacher extern int drbd_md_sync_page_io(struct drbd_device *device, 1519bb3cc85eSMike Christie struct drbd_backing_dev *bdev, sector_t sector, int op); 152054761697SAndreas Gruenbacher extern void drbd_ov_out_of_sync_found(struct drbd_device *, sector_t, int); 1521b30ab791SAndreas Gruenbacher extern void wait_until_done_or_force_detached(struct drbd_device *device, 152244edfb0dSLars Ellenberg struct drbd_backing_dev *bdev, unsigned int *done); 1523b30ab791SAndreas Gruenbacher extern void drbd_rs_controller_reset(struct drbd_device *device); 1524b411b363SPhilipp Reisner 1525b30ab791SAndreas Gruenbacher static inline void ov_out_of_sync_print(struct drbd_device *device) 1526b411b363SPhilipp Reisner { 1527b30ab791SAndreas Gruenbacher if (device->ov_last_oos_size) { 1528d0180171SAndreas Gruenbacher drbd_err(device, "Out of sync: start=%llu, size=%lu (sectors)\n", 1529b30ab791SAndreas Gruenbacher (unsigned long long)device->ov_last_oos_start, 1530b30ab791SAndreas Gruenbacher (unsigned long)device->ov_last_oos_size); 1531b411b363SPhilipp Reisner } 1532b30ab791SAndreas Gruenbacher device->ov_last_oos_size = 0; 1533b411b363SPhilipp Reisner } 1534b411b363SPhilipp Reisner 1535b411b363SPhilipp Reisner 15369534d671SHerbert Xu extern void drbd_csum_bio(struct crypto_ahash *, struct bio *, void *); 15379534d671SHerbert Xu extern void drbd_csum_ee(struct crypto_ahash *, struct drbd_peer_request *, void *); 1538b411b363SPhilipp Reisner /* worker callbacks */ 153999920dc5SAndreas Gruenbacher extern int w_e_end_data_req(struct drbd_work *, int); 154099920dc5SAndreas Gruenbacher extern int w_e_end_rsdata_req(struct drbd_work *, int); 154199920dc5SAndreas Gruenbacher extern int w_e_end_csum_rs_req(struct drbd_work *, int); 154299920dc5SAndreas Gruenbacher extern int w_e_end_ov_reply(struct drbd_work *, int); 154399920dc5SAndreas Gruenbacher extern int w_e_end_ov_req(struct drbd_work *, int); 154499920dc5SAndreas Gruenbacher extern int w_ov_finished(struct drbd_work *, int); 154599920dc5SAndreas Gruenbacher extern int w_resync_timer(struct drbd_work *, int); 154699920dc5SAndreas Gruenbacher extern int w_send_write_hint(struct drbd_work *, int); 154799920dc5SAndreas Gruenbacher extern int w_send_dblock(struct drbd_work *, int); 154899920dc5SAndreas Gruenbacher extern int w_send_read_req(struct drbd_work *, int); 154999920dc5SAndreas Gruenbacher extern int w_e_reissue(struct drbd_work *, int); 155099920dc5SAndreas Gruenbacher extern int w_restart_disk_io(struct drbd_work *, int); 15518f7bed77SAndreas Gruenbacher extern int w_send_out_of_sync(struct drbd_work *, int); 155299920dc5SAndreas Gruenbacher extern int w_start_resync(struct drbd_work *, int); 1553b411b363SPhilipp Reisner 1554b411b363SPhilipp Reisner extern void resync_timer_fn(unsigned long data); 1555370a43e7SPhilipp Reisner extern void start_resync_timer_fn(unsigned long data); 1556b411b363SPhilipp Reisner 1557a0fb3c47SLars Ellenberg extern void drbd_endio_write_sec_final(struct drbd_peer_request *peer_req); 1558a0fb3c47SLars Ellenberg 1559b411b363SPhilipp Reisner /* drbd_receiver.c */ 1560753c6191SAndreas Gruenbacher extern int drbd_receiver(struct drbd_thread *thi); 15611c03e520SPhilipp Reisner extern int drbd_ack_receiver(struct drbd_thread *thi); 1562668700b4SPhilipp Reisner extern void drbd_send_ping_wf(struct work_struct *ws); 1563668700b4SPhilipp Reisner extern void drbd_send_acks_wf(struct work_struct *ws); 1564e8299874SLars Ellenberg extern bool drbd_rs_c_min_rate_throttle(struct drbd_device *device); 1565ad3fee79SLars Ellenberg extern bool drbd_rs_should_slow_down(struct drbd_device *device, sector_t sector, 1566ad3fee79SLars Ellenberg bool throttle_if_app_is_waiting); 156754761697SAndreas Gruenbacher extern int drbd_submit_peer_request(struct drbd_device *, 1568fbe29decSAndreas Gruenbacher struct drbd_peer_request *, const unsigned, 1569bb3cc85eSMike Christie const unsigned, const int); 157054761697SAndreas Gruenbacher extern int drbd_free_peer_reqs(struct drbd_device *, struct list_head *); 157169a22773SAndreas Gruenbacher extern struct drbd_peer_request *drbd_alloc_peer_req(struct drbd_peer_device *, u64, 15720db55363SAndreas Gruenbacher sector_t, unsigned int, 15739104d31aSLars Ellenberg unsigned int, 1574f6ffca9fSAndreas Gruenbacher gfp_t) __must_hold(local); 157554761697SAndreas Gruenbacher extern void __drbd_free_peer_req(struct drbd_device *, struct drbd_peer_request *, 1576f6ffca9fSAndreas Gruenbacher int); 15773967deb1SAndreas Gruenbacher #define drbd_free_peer_req(m,e) __drbd_free_peer_req(m, e, 0) 15783967deb1SAndreas Gruenbacher #define drbd_free_net_peer_req(m,e) __drbd_free_peer_req(m, e, 1) 157969a22773SAndreas Gruenbacher extern struct page *drbd_alloc_pages(struct drbd_peer_device *, unsigned int, bool); 1580b30ab791SAndreas Gruenbacher extern void drbd_set_recv_tcq(struct drbd_device *device, int tcq_enabled); 1581b30ab791SAndreas Gruenbacher extern void _drbd_clear_done_ee(struct drbd_device *device, struct list_head *to_be_freed); 158269a22773SAndreas Gruenbacher extern int drbd_connected(struct drbd_peer_device *); 1583b411b363SPhilipp Reisner 1584b411b363SPhilipp Reisner static inline void drbd_tcp_cork(struct socket *sock) 1585b411b363SPhilipp Reisner { 1586ed439848SLars Ellenberg int val = 1; 1587e805b983SPhilipp Reisner (void) kernel_setsockopt(sock, SOL_TCP, TCP_CORK, 1588ed439848SLars Ellenberg (char*)&val, sizeof(val)); 1589b411b363SPhilipp Reisner } 1590b411b363SPhilipp Reisner 1591b411b363SPhilipp Reisner static inline void drbd_tcp_uncork(struct socket *sock) 1592b411b363SPhilipp Reisner { 1593ed439848SLars Ellenberg int val = 0; 1594e805b983SPhilipp Reisner (void) kernel_setsockopt(sock, SOL_TCP, TCP_CORK, 1595ed439848SLars Ellenberg (char*)&val, sizeof(val)); 1596b411b363SPhilipp Reisner } 1597b411b363SPhilipp Reisner 1598b411b363SPhilipp Reisner static inline void drbd_tcp_nodelay(struct socket *sock) 1599b411b363SPhilipp Reisner { 1600ed439848SLars Ellenberg int val = 1; 1601e805b983SPhilipp Reisner (void) kernel_setsockopt(sock, SOL_TCP, TCP_NODELAY, 1602ed439848SLars Ellenberg (char*)&val, sizeof(val)); 1603b411b363SPhilipp Reisner } 1604b411b363SPhilipp Reisner 1605b411b363SPhilipp Reisner static inline void drbd_tcp_quickack(struct socket *sock) 1606b411b363SPhilipp Reisner { 1607ed439848SLars Ellenberg int val = 2; 1608e805b983SPhilipp Reisner (void) kernel_setsockopt(sock, SOL_TCP, TCP_QUICKACK, 1609ed439848SLars Ellenberg (char*)&val, sizeof(val)); 1610b411b363SPhilipp Reisner } 1611b411b363SPhilipp Reisner 1612d40e5671SPhilipp Reisner /* sets the number of 512 byte sectors of our virtual device */ 1613d40e5671SPhilipp Reisner static inline void drbd_set_my_capacity(struct drbd_device *device, 1614d40e5671SPhilipp Reisner sector_t size) 1615d40e5671SPhilipp Reisner { 1616d40e5671SPhilipp Reisner /* set_capacity(device->this_bdev->bd_disk, size); */ 1617d40e5671SPhilipp Reisner set_capacity(device->vdisk, size); 1618d40e5671SPhilipp Reisner device->this_bdev->bd_inode->i_size = (loff_t)size << 9; 1619d40e5671SPhilipp Reisner } 1620d40e5671SPhilipp Reisner 1621d40e5671SPhilipp Reisner /* 1622d40e5671SPhilipp Reisner * used to submit our private bio 1623d40e5671SPhilipp Reisner */ 1624d40e5671SPhilipp Reisner static inline void drbd_generic_make_request(struct drbd_device *device, 1625d40e5671SPhilipp Reisner int fault_type, struct bio *bio) 1626d40e5671SPhilipp Reisner { 1627d40e5671SPhilipp Reisner __release(local); 1628d40e5671SPhilipp Reisner if (!bio->bi_bdev) { 1629f88c5d90SLars Ellenberg drbd_err(device, "drbd_generic_make_request: bio->bi_bdev == NULL\n"); 1630*4e4cbee9SChristoph Hellwig bio->bi_status = BLK_STS_IOERR; 16314246a0b6SChristoph Hellwig bio_endio(bio); 1632d40e5671SPhilipp Reisner return; 1633d40e5671SPhilipp Reisner } 1634d40e5671SPhilipp Reisner 1635d40e5671SPhilipp Reisner if (drbd_insert_fault(device, fault_type)) 16364246a0b6SChristoph Hellwig bio_io_error(bio); 1637d40e5671SPhilipp Reisner else 1638d40e5671SPhilipp Reisner generic_make_request(bio); 1639d40e5671SPhilipp Reisner } 1640d40e5671SPhilipp Reisner 16418fe39aacSPhilipp Reisner void drbd_bump_write_ordering(struct drbd_resource *resource, struct drbd_backing_dev *bdev, 16428fe39aacSPhilipp Reisner enum write_ordering_e wo); 1643b411b363SPhilipp Reisner 1644b411b363SPhilipp Reisner /* drbd_proc.c */ 1645b411b363SPhilipp Reisner extern struct proc_dir_entry *drbd_proc; 16467d4e9d09SEmese Revfy extern const struct file_operations drbd_proc_fops; 1647b411b363SPhilipp Reisner 1648b411b363SPhilipp Reisner /* drbd_actlog.c */ 1649e4d7d6f4SLars Ellenberg extern bool drbd_al_begin_io_prepare(struct drbd_device *device, struct drbd_interval *i); 1650b30ab791SAndreas Gruenbacher extern int drbd_al_begin_io_nonblock(struct drbd_device *device, struct drbd_interval *i); 16514dd726f0SLars Ellenberg extern void drbd_al_begin_io_commit(struct drbd_device *device); 1652b30ab791SAndreas Gruenbacher extern bool drbd_al_begin_io_fastpath(struct drbd_device *device, struct drbd_interval *i); 16534dd726f0SLars Ellenberg extern void drbd_al_begin_io(struct drbd_device *device, struct drbd_interval *i); 1654b30ab791SAndreas Gruenbacher extern void drbd_al_complete_io(struct drbd_device *device, struct drbd_interval *i); 1655b30ab791SAndreas Gruenbacher extern void drbd_rs_complete_io(struct drbd_device *device, sector_t sector); 1656b30ab791SAndreas Gruenbacher extern int drbd_rs_begin_io(struct drbd_device *device, sector_t sector); 1657b30ab791SAndreas Gruenbacher extern int drbd_try_rs_begin_io(struct drbd_device *device, sector_t sector); 1658b30ab791SAndreas Gruenbacher extern void drbd_rs_cancel_all(struct drbd_device *device); 1659b30ab791SAndreas Gruenbacher extern int drbd_rs_del_all(struct drbd_device *device); 1660b30ab791SAndreas Gruenbacher extern void drbd_rs_failed_io(struct drbd_device *device, 1661b411b363SPhilipp Reisner sector_t sector, int size); 1662b30ab791SAndreas Gruenbacher extern void drbd_advance_rs_marks(struct drbd_device *device, unsigned long still_to_go); 16635ab7d2c0SLars Ellenberg 16645ab7d2c0SLars Ellenberg enum update_sync_bits_mode { RECORD_RS_FAILED, SET_OUT_OF_SYNC, SET_IN_SYNC }; 16655ab7d2c0SLars Ellenberg extern int __drbd_change_sync(struct drbd_device *device, sector_t sector, int size, 1666179e20b8SAndreas Gruenbacher enum update_sync_bits_mode mode); 1667b30ab791SAndreas Gruenbacher #define drbd_set_in_sync(device, sector, size) \ 1668179e20b8SAndreas Gruenbacher __drbd_change_sync(device, sector, size, SET_IN_SYNC) 1669b30ab791SAndreas Gruenbacher #define drbd_set_out_of_sync(device, sector, size) \ 1670179e20b8SAndreas Gruenbacher __drbd_change_sync(device, sector, size, SET_OUT_OF_SYNC) 16715ab7d2c0SLars Ellenberg #define drbd_rs_failed_io(device, sector, size) \ 1672179e20b8SAndreas Gruenbacher __drbd_change_sync(device, sector, size, RECORD_RS_FAILED) 1673b30ab791SAndreas Gruenbacher extern void drbd_al_shrink(struct drbd_device *device); 16745f7c0124SLars Ellenberg extern int drbd_al_initialize(struct drbd_device *, void *); 1675b411b363SPhilipp Reisner 1676b411b363SPhilipp Reisner /* drbd_nl.c */ 16773b98c0c2SLars Ellenberg /* state info broadcast */ 16783b98c0c2SLars Ellenberg struct sib_info { 16793b98c0c2SLars Ellenberg enum drbd_state_info_bcast_reason sib_reason; 16803b98c0c2SLars Ellenberg union { 16813b98c0c2SLars Ellenberg struct { 16823b98c0c2SLars Ellenberg char *helper_name; 16833b98c0c2SLars Ellenberg unsigned helper_exit_code; 16843b98c0c2SLars Ellenberg }; 16853b98c0c2SLars Ellenberg struct { 16863b98c0c2SLars Ellenberg union drbd_state os; 16873b98c0c2SLars Ellenberg union drbd_state ns; 16883b98c0c2SLars Ellenberg }; 16893b98c0c2SLars Ellenberg }; 16903b98c0c2SLars Ellenberg }; 1691b30ab791SAndreas Gruenbacher void drbd_bcast_event(struct drbd_device *device, const struct sib_info *sib); 1692b411b363SPhilipp Reisner 1693a2972846SAndreas Gruenbacher extern void notify_resource_state(struct sk_buff *, 1694a2972846SAndreas Gruenbacher unsigned int, 1695a2972846SAndreas Gruenbacher struct drbd_resource *, 1696a2972846SAndreas Gruenbacher struct resource_info *, 1697a2972846SAndreas Gruenbacher enum drbd_notification_type); 1698a2972846SAndreas Gruenbacher extern void notify_device_state(struct sk_buff *, 1699a2972846SAndreas Gruenbacher unsigned int, 1700a2972846SAndreas Gruenbacher struct drbd_device *, 1701a2972846SAndreas Gruenbacher struct device_info *, 1702a2972846SAndreas Gruenbacher enum drbd_notification_type); 1703a2972846SAndreas Gruenbacher extern void notify_connection_state(struct sk_buff *, 1704a2972846SAndreas Gruenbacher unsigned int, 1705a2972846SAndreas Gruenbacher struct drbd_connection *, 1706a2972846SAndreas Gruenbacher struct connection_info *, 1707a2972846SAndreas Gruenbacher enum drbd_notification_type); 1708a2972846SAndreas Gruenbacher extern void notify_peer_device_state(struct sk_buff *, 1709a2972846SAndreas Gruenbacher unsigned int, 1710a2972846SAndreas Gruenbacher struct drbd_peer_device *, 1711a2972846SAndreas Gruenbacher struct peer_device_info *, 1712a2972846SAndreas Gruenbacher enum drbd_notification_type); 1713a2972846SAndreas Gruenbacher extern void notify_helper(enum drbd_notification_type, struct drbd_device *, 1714a2972846SAndreas Gruenbacher struct drbd_connection *, const char *, int); 1715a2972846SAndreas Gruenbacher 1716b411b363SPhilipp Reisner /* 1717b411b363SPhilipp Reisner * inline helper functions 1718b411b363SPhilipp Reisner *************************/ 1719b411b363SPhilipp Reisner 172045bb912bSLars Ellenberg /* see also page_chain_add and friends in drbd_receiver.c */ 172145bb912bSLars Ellenberg static inline struct page *page_chain_next(struct page *page) 172245bb912bSLars Ellenberg { 172345bb912bSLars Ellenberg return (struct page *)page_private(page); 172445bb912bSLars Ellenberg } 172545bb912bSLars Ellenberg #define page_chain_for_each(page) \ 172645bb912bSLars Ellenberg for (; page && ({ prefetch(page_chain_next(page)); 1; }); \ 172745bb912bSLars Ellenberg page = page_chain_next(page)) 172845bb912bSLars Ellenberg #define page_chain_for_each_safe(page, n) \ 172945bb912bSLars Ellenberg for (; page && ({ n = page_chain_next(page); 1; }); page = n) 173045bb912bSLars Ellenberg 173145bb912bSLars Ellenberg 1732045417f7SAndreas Gruenbacher static inline int drbd_peer_req_has_active_page(struct drbd_peer_request *peer_req) 173345bb912bSLars Ellenberg { 1734db830c46SAndreas Gruenbacher struct page *page = peer_req->pages; 173545bb912bSLars Ellenberg page_chain_for_each(page) { 173645bb912bSLars Ellenberg if (page_count(page) > 1) 173745bb912bSLars Ellenberg return 1; 173845bb912bSLars Ellenberg } 173945bb912bSLars Ellenberg return 0; 174045bb912bSLars Ellenberg } 174145bb912bSLars Ellenberg 1742b30ab791SAndreas Gruenbacher static inline union drbd_state drbd_read_state(struct drbd_device *device) 1743b411b363SPhilipp Reisner { 17446bbf53caSAndreas Gruenbacher struct drbd_resource *resource = device->resource; 174578bae59bSPhilipp Reisner union drbd_state rv; 174678bae59bSPhilipp Reisner 1747b30ab791SAndreas Gruenbacher rv.i = device->state.i; 17486bbf53caSAndreas Gruenbacher rv.susp = resource->susp; 17496bbf53caSAndreas Gruenbacher rv.susp_nod = resource->susp_nod; 17506bbf53caSAndreas Gruenbacher rv.susp_fen = resource->susp_fen; 175178bae59bSPhilipp Reisner 175278bae59bSPhilipp Reisner return rv; 1753b411b363SPhilipp Reisner } 1754b411b363SPhilipp Reisner 1755383606e0SLars Ellenberg enum drbd_force_detach_flags { 1756a2a3c74fSLars Ellenberg DRBD_READ_ERROR, 1757a2a3c74fSLars Ellenberg DRBD_WRITE_ERROR, 1758383606e0SLars Ellenberg DRBD_META_IO_ERROR, 1759383606e0SLars Ellenberg DRBD_FORCE_DETACH, 1760383606e0SLars Ellenberg }; 1761383606e0SLars Ellenberg 1762b411b363SPhilipp Reisner #define __drbd_chk_io_error(m,f) __drbd_chk_io_error_(m,f, __func__) 1763b30ab791SAndreas Gruenbacher static inline void __drbd_chk_io_error_(struct drbd_device *device, 1764a2a3c74fSLars Ellenberg enum drbd_force_detach_flags df, 1765383606e0SLars Ellenberg const char *where) 1766b411b363SPhilipp Reisner { 1767daeda1ccSPhilipp Reisner enum drbd_io_error_p ep; 1768daeda1ccSPhilipp Reisner 1769daeda1ccSPhilipp Reisner rcu_read_lock(); 1770b30ab791SAndreas Gruenbacher ep = rcu_dereference(device->ldev->disk_conf)->on_io_error; 1771daeda1ccSPhilipp Reisner rcu_read_unlock(); 1772daeda1ccSPhilipp Reisner switch (ep) { 1773daeda1ccSPhilipp Reisner case EP_PASS_ON: /* FIXME would this be better named "Ignore"? */ 1774a2a3c74fSLars Ellenberg if (df == DRBD_READ_ERROR || df == DRBD_WRITE_ERROR) { 17757383506cSLars Ellenberg if (__ratelimit(&drbd_ratelimit_state)) 1776d0180171SAndreas Gruenbacher drbd_err(device, "Local IO failed in %s.\n", where); 1777b30ab791SAndreas Gruenbacher if (device->state.disk > D_INCONSISTENT) 1778b30ab791SAndreas Gruenbacher _drbd_set_state(_NS(device, disk, D_INCONSISTENT), CS_HARD, NULL); 1779b411b363SPhilipp Reisner break; 1780b411b363SPhilipp Reisner } 1781a2a3c74fSLars Ellenberg /* NOTE fall through for DRBD_META_IO_ERROR or DRBD_FORCE_DETACH */ 1782b411b363SPhilipp Reisner case EP_DETACH: 1783b411b363SPhilipp Reisner case EP_CALL_HELPER: 1784a2a3c74fSLars Ellenberg /* Remember whether we saw a READ or WRITE error. 1785a2a3c74fSLars Ellenberg * 1786a2a3c74fSLars Ellenberg * Recovery of the affected area for WRITE failure is covered 1787a2a3c74fSLars Ellenberg * by the activity log. 1788a2a3c74fSLars Ellenberg * READ errors may fall outside that area though. Certain READ 1789a2a3c74fSLars Ellenberg * errors can be "healed" by writing good data to the affected 1790a2a3c74fSLars Ellenberg * blocks, which triggers block re-allocation in lower layers. 1791a2a3c74fSLars Ellenberg * 1792a2a3c74fSLars Ellenberg * If we can not write the bitmap after a READ error, 1793a2a3c74fSLars Ellenberg * we may need to trigger a full sync (see w_go_diskless()). 1794a2a3c74fSLars Ellenberg * 1795a2a3c74fSLars Ellenberg * Force-detach is not really an IO error, but rather a 1796a2a3c74fSLars Ellenberg * desperate measure to try to deal with a completely 1797a2a3c74fSLars Ellenberg * unresponsive lower level IO stack. 1798a2a3c74fSLars Ellenberg * Still it should be treated as a WRITE error. 1799a2a3c74fSLars Ellenberg * 1800a2a3c74fSLars Ellenberg * Meta IO error is always WRITE error: 1801a2a3c74fSLars Ellenberg * we read meta data only once during attach, 1802a2a3c74fSLars Ellenberg * which will fail in case of errors. 1803a2a3c74fSLars Ellenberg */ 1804b30ab791SAndreas Gruenbacher set_bit(WAS_IO_ERROR, &device->flags); 1805a2a3c74fSLars Ellenberg if (df == DRBD_READ_ERROR) 1806b30ab791SAndreas Gruenbacher set_bit(WAS_READ_ERROR, &device->flags); 1807a2a3c74fSLars Ellenberg if (df == DRBD_FORCE_DETACH) 1808b30ab791SAndreas Gruenbacher set_bit(FORCE_DETACH, &device->flags); 1809b30ab791SAndreas Gruenbacher if (device->state.disk > D_FAILED) { 1810b30ab791SAndreas Gruenbacher _drbd_set_state(_NS(device, disk, D_FAILED), CS_HARD, NULL); 1811d0180171SAndreas Gruenbacher drbd_err(device, 181282f59cc6SLars Ellenberg "Local IO failed in %s. Detaching...\n", where); 1813b411b363SPhilipp Reisner } 1814b411b363SPhilipp Reisner break; 1815b411b363SPhilipp Reisner } 1816b411b363SPhilipp Reisner } 1817b411b363SPhilipp Reisner 1818b411b363SPhilipp Reisner /** 1819b411b363SPhilipp Reisner * drbd_chk_io_error: Handle the on_io_error setting, should be called from all io completion handlers 1820b30ab791SAndreas Gruenbacher * @device: DRBD device. 1821b411b363SPhilipp Reisner * @error: Error code passed to the IO completion callback 1822b411b363SPhilipp Reisner * @forcedetach: Force detach. I.e. the error happened while accessing the meta data 1823b411b363SPhilipp Reisner * 1824b411b363SPhilipp Reisner * See also drbd_main.c:after_state_ch() if (os.disk > D_FAILED && ns.disk == D_FAILED) 1825b411b363SPhilipp Reisner */ 1826b411b363SPhilipp Reisner #define drbd_chk_io_error(m,e,f) drbd_chk_io_error_(m,e,f, __func__) 1827b30ab791SAndreas Gruenbacher static inline void drbd_chk_io_error_(struct drbd_device *device, 1828383606e0SLars Ellenberg int error, enum drbd_force_detach_flags forcedetach, const char *where) 1829b411b363SPhilipp Reisner { 1830b411b363SPhilipp Reisner if (error) { 1831b411b363SPhilipp Reisner unsigned long flags; 18320500813fSAndreas Gruenbacher spin_lock_irqsave(&device->resource->req_lock, flags); 1833b30ab791SAndreas Gruenbacher __drbd_chk_io_error_(device, forcedetach, where); 18340500813fSAndreas Gruenbacher spin_unlock_irqrestore(&device->resource->req_lock, flags); 1835b411b363SPhilipp Reisner } 1836b411b363SPhilipp Reisner } 1837b411b363SPhilipp Reisner 1838b411b363SPhilipp Reisner 1839b411b363SPhilipp Reisner /** 1840b411b363SPhilipp Reisner * drbd_md_first_sector() - Returns the first sector number of the meta data area 1841b411b363SPhilipp Reisner * @bdev: Meta data block device. 1842b411b363SPhilipp Reisner * 1843b411b363SPhilipp Reisner * BTW, for internal meta data, this happens to be the maximum capacity 1844b411b363SPhilipp Reisner * we could agree upon with our peer node. 1845b411b363SPhilipp Reisner */ 184668e41a43SLars Ellenberg static inline sector_t drbd_md_first_sector(struct drbd_backing_dev *bdev) 1847b411b363SPhilipp Reisner { 184868e41a43SLars Ellenberg switch (bdev->md.meta_dev_idx) { 1849b411b363SPhilipp Reisner case DRBD_MD_INDEX_INTERNAL: 1850b411b363SPhilipp Reisner case DRBD_MD_INDEX_FLEX_INT: 1851b411b363SPhilipp Reisner return bdev->md.md_offset + bdev->md.bm_offset; 1852b411b363SPhilipp Reisner case DRBD_MD_INDEX_FLEX_EXT: 1853b411b363SPhilipp Reisner default: 1854b411b363SPhilipp Reisner return bdev->md.md_offset; 1855b411b363SPhilipp Reisner } 1856b411b363SPhilipp Reisner } 1857b411b363SPhilipp Reisner 1858b411b363SPhilipp Reisner /** 1859b411b363SPhilipp Reisner * drbd_md_last_sector() - Return the last sector number of the meta data area 1860b411b363SPhilipp Reisner * @bdev: Meta data block device. 1861b411b363SPhilipp Reisner */ 1862b411b363SPhilipp Reisner static inline sector_t drbd_md_last_sector(struct drbd_backing_dev *bdev) 1863b411b363SPhilipp Reisner { 186468e41a43SLars Ellenberg switch (bdev->md.meta_dev_idx) { 1865b411b363SPhilipp Reisner case DRBD_MD_INDEX_INTERNAL: 1866b411b363SPhilipp Reisner case DRBD_MD_INDEX_FLEX_INT: 1867ae8bf312SLars Ellenberg return bdev->md.md_offset + MD_4kB_SECT -1; 1868b411b363SPhilipp Reisner case DRBD_MD_INDEX_FLEX_EXT: 1869b411b363SPhilipp Reisner default: 1870ae8bf312SLars Ellenberg return bdev->md.md_offset + bdev->md.md_size_sect -1; 1871b411b363SPhilipp Reisner } 1872b411b363SPhilipp Reisner } 1873b411b363SPhilipp Reisner 1874b411b363SPhilipp Reisner /* Returns the number of 512 byte sectors of the device */ 1875b411b363SPhilipp Reisner static inline sector_t drbd_get_capacity(struct block_device *bdev) 1876b411b363SPhilipp Reisner { 1877b411b363SPhilipp Reisner /* return bdev ? get_capacity(bdev->bd_disk) : 0; */ 187877304d2aSMike Snitzer return bdev ? i_size_read(bdev->bd_inode) >> 9 : 0; 1879b411b363SPhilipp Reisner } 1880b411b363SPhilipp Reisner 1881b411b363SPhilipp Reisner /** 1882b411b363SPhilipp Reisner * drbd_get_max_capacity() - Returns the capacity we announce to out peer 1883b411b363SPhilipp Reisner * @bdev: Meta data block device. 1884b411b363SPhilipp Reisner * 1885b411b363SPhilipp Reisner * returns the capacity we announce to out peer. we clip ourselves at the 1886b411b363SPhilipp Reisner * various MAX_SECTORS, because if we don't, current implementation will 1887b411b363SPhilipp Reisner * oops sooner or later 1888b411b363SPhilipp Reisner */ 1889b411b363SPhilipp Reisner static inline sector_t drbd_get_max_capacity(struct drbd_backing_dev *bdev) 1890b411b363SPhilipp Reisner { 1891b411b363SPhilipp Reisner sector_t s; 1892daeda1ccSPhilipp Reisner 189368e41a43SLars Ellenberg switch (bdev->md.meta_dev_idx) { 1894b411b363SPhilipp Reisner case DRBD_MD_INDEX_INTERNAL: 1895b411b363SPhilipp Reisner case DRBD_MD_INDEX_FLEX_INT: 1896b411b363SPhilipp Reisner s = drbd_get_capacity(bdev->backing_bdev) 1897b411b363SPhilipp Reisner ? min_t(sector_t, DRBD_MAX_SECTORS_FLEX, 189868e41a43SLars Ellenberg drbd_md_first_sector(bdev)) 1899b411b363SPhilipp Reisner : 0; 1900b411b363SPhilipp Reisner break; 1901b411b363SPhilipp Reisner case DRBD_MD_INDEX_FLEX_EXT: 1902b411b363SPhilipp Reisner s = min_t(sector_t, DRBD_MAX_SECTORS_FLEX, 1903b411b363SPhilipp Reisner drbd_get_capacity(bdev->backing_bdev)); 1904b411b363SPhilipp Reisner /* clip at maximum size the meta device can support */ 1905b411b363SPhilipp Reisner s = min_t(sector_t, s, 1906b411b363SPhilipp Reisner BM_EXT_TO_SECT(bdev->md.md_size_sect 1907b411b363SPhilipp Reisner - bdev->md.bm_offset)); 1908b411b363SPhilipp Reisner break; 1909b411b363SPhilipp Reisner default: 1910b411b363SPhilipp Reisner s = min_t(sector_t, DRBD_MAX_SECTORS, 1911b411b363SPhilipp Reisner drbd_get_capacity(bdev->backing_bdev)); 1912b411b363SPhilipp Reisner } 1913b411b363SPhilipp Reisner return s; 1914b411b363SPhilipp Reisner } 1915b411b363SPhilipp Reisner 1916b411b363SPhilipp Reisner /** 19173a4d4eb3SLars Ellenberg * drbd_md_ss() - Return the sector number of our meta data super block 1918b411b363SPhilipp Reisner * @bdev: Meta data block device. 1919b411b363SPhilipp Reisner */ 19203a4d4eb3SLars Ellenberg static inline sector_t drbd_md_ss(struct drbd_backing_dev *bdev) 1921b411b363SPhilipp Reisner { 19223a4d4eb3SLars Ellenberg const int meta_dev_idx = bdev->md.meta_dev_idx; 1923daeda1ccSPhilipp Reisner 19243a4d4eb3SLars Ellenberg if (meta_dev_idx == DRBD_MD_INDEX_FLEX_EXT) 1925b411b363SPhilipp Reisner return 0; 19263a4d4eb3SLars Ellenberg 19273a4d4eb3SLars Ellenberg /* Since drbd08, internal meta data is always "flexible". 1928ae8bf312SLars Ellenberg * position: last 4k aligned block of 4k size */ 19293a4d4eb3SLars Ellenberg if (meta_dev_idx == DRBD_MD_INDEX_INTERNAL || 19303a4d4eb3SLars Ellenberg meta_dev_idx == DRBD_MD_INDEX_FLEX_INT) 1931ae8bf312SLars Ellenberg return (drbd_get_capacity(bdev->backing_bdev) & ~7ULL) - 8; 19323a4d4eb3SLars Ellenberg 19333a4d4eb3SLars Ellenberg /* external, some index; this is the old fixed size layout */ 19343a4d4eb3SLars Ellenberg return MD_128MB_SECT * bdev->md.meta_dev_idx; 1935b411b363SPhilipp Reisner } 1936b411b363SPhilipp Reisner 1937b411b363SPhilipp Reisner static inline void 1938b411b363SPhilipp Reisner drbd_queue_work(struct drbd_work_queue *q, struct drbd_work *w) 1939b411b363SPhilipp Reisner { 1940b411b363SPhilipp Reisner unsigned long flags; 1941b411b363SPhilipp Reisner spin_lock_irqsave(&q->q_lock, flags); 1942b411b363SPhilipp Reisner list_add_tail(&w->list, &q->q); 1943b411b363SPhilipp Reisner spin_unlock_irqrestore(&q->q_lock, flags); 19448c0785a5SLars Ellenberg wake_up(&q->q_wait); 1945b411b363SPhilipp Reisner } 1946b411b363SPhilipp Reisner 1947e334f550SLars Ellenberg static inline void 194815e26f6aSLars Ellenberg drbd_queue_work_if_unqueued(struct drbd_work_queue *q, struct drbd_work *w) 194915e26f6aSLars Ellenberg { 195015e26f6aSLars Ellenberg unsigned long flags; 195115e26f6aSLars Ellenberg spin_lock_irqsave(&q->q_lock, flags); 195215e26f6aSLars Ellenberg if (list_empty_careful(&w->list)) 195315e26f6aSLars Ellenberg list_add_tail(&w->list, &q->q); 195415e26f6aSLars Ellenberg spin_unlock_irqrestore(&q->q_lock, flags); 195515e26f6aSLars Ellenberg wake_up(&q->q_wait); 195615e26f6aSLars Ellenberg } 195715e26f6aSLars Ellenberg 195815e26f6aSLars Ellenberg static inline void 1959e334f550SLars Ellenberg drbd_device_post_work(struct drbd_device *device, int work_bit) 1960e334f550SLars Ellenberg { 1961e334f550SLars Ellenberg if (!test_and_set_bit(work_bit, &device->flags)) { 1962e334f550SLars Ellenberg struct drbd_connection *connection = 1963e334f550SLars Ellenberg first_peer_device(device)->connection; 1964e334f550SLars Ellenberg struct drbd_work_queue *q = &connection->sender_work; 1965e334f550SLars Ellenberg if (!test_and_set_bit(DEVICE_WORK_PENDING, &connection->flags)) 1966e334f550SLars Ellenberg wake_up(&q->q_wait); 1967e334f550SLars Ellenberg } 1968e334f550SLars Ellenberg } 1969e334f550SLars Ellenberg 1970b5043c5eSAndreas Gruenbacher extern void drbd_flush_workqueue(struct drbd_work_queue *work_queue); 1971b5043c5eSAndreas Gruenbacher 1972668700b4SPhilipp Reisner /* To get the ack_receiver out of the blocking network stack, 1973668700b4SPhilipp Reisner * so it can change its sk_rcvtimeo from idle- to ping-timeout, 1974668700b4SPhilipp Reisner * and send a ping, we need to send a signal. 1975668700b4SPhilipp Reisner * Which signal we send is irrelevant. */ 1976668700b4SPhilipp Reisner static inline void wake_ack_receiver(struct drbd_connection *connection) 1977b411b363SPhilipp Reisner { 1978668700b4SPhilipp Reisner struct task_struct *task = connection->ack_receiver.task; 1979668700b4SPhilipp Reisner if (task && get_t_state(&connection->ack_receiver) == RUNNING) 1980668700b4SPhilipp Reisner force_sig(SIGXCPU, task); 1981b411b363SPhilipp Reisner } 1982b411b363SPhilipp Reisner 1983bde89a9eSAndreas Gruenbacher static inline void request_ping(struct drbd_connection *connection) 1984b411b363SPhilipp Reisner { 1985bde89a9eSAndreas Gruenbacher set_bit(SEND_PING, &connection->flags); 1986668700b4SPhilipp Reisner wake_ack_receiver(connection); 1987b411b363SPhilipp Reisner } 1988b411b363SPhilipp Reisner 1989bde89a9eSAndreas Gruenbacher extern void *conn_prepare_command(struct drbd_connection *, struct drbd_socket *); 199069a22773SAndreas Gruenbacher extern void *drbd_prepare_command(struct drbd_peer_device *, struct drbd_socket *); 1991bde89a9eSAndreas Gruenbacher extern int conn_send_command(struct drbd_connection *, struct drbd_socket *, 1992dba58587SAndreas Gruenbacher enum drbd_packet, unsigned int, void *, 1993dba58587SAndreas Gruenbacher unsigned int); 199469a22773SAndreas Gruenbacher extern int drbd_send_command(struct drbd_peer_device *, struct drbd_socket *, 1995dba58587SAndreas Gruenbacher enum drbd_packet, unsigned int, void *, 1996dba58587SAndreas Gruenbacher unsigned int); 1997b411b363SPhilipp Reisner 1998bde89a9eSAndreas Gruenbacher extern int drbd_send_ping(struct drbd_connection *connection); 1999bde89a9eSAndreas Gruenbacher extern int drbd_send_ping_ack(struct drbd_connection *connection); 200069a22773SAndreas Gruenbacher extern int drbd_send_state_req(struct drbd_peer_device *, union drbd_state, union drbd_state); 2001bde89a9eSAndreas Gruenbacher extern int conn_send_state_req(struct drbd_connection *, union drbd_state, union drbd_state); 2002b411b363SPhilipp Reisner 2003b411b363SPhilipp Reisner static inline void drbd_thread_stop(struct drbd_thread *thi) 2004b411b363SPhilipp Reisner { 200581e84650SAndreas Gruenbacher _drbd_thread_stop(thi, false, true); 2006b411b363SPhilipp Reisner } 2007b411b363SPhilipp Reisner 2008b411b363SPhilipp Reisner static inline void drbd_thread_stop_nowait(struct drbd_thread *thi) 2009b411b363SPhilipp Reisner { 201081e84650SAndreas Gruenbacher _drbd_thread_stop(thi, false, false); 2011b411b363SPhilipp Reisner } 2012b411b363SPhilipp Reisner 2013b411b363SPhilipp Reisner static inline void drbd_thread_restart_nowait(struct drbd_thread *thi) 2014b411b363SPhilipp Reisner { 201581e84650SAndreas Gruenbacher _drbd_thread_stop(thi, true, false); 2016b411b363SPhilipp Reisner } 2017b411b363SPhilipp Reisner 2018b411b363SPhilipp Reisner /* counts how many answer packets packets we expect from our peer, 2019b411b363SPhilipp Reisner * for either explicit application requests, 2020b411b363SPhilipp Reisner * or implicit barrier packets as necessary. 2021b411b363SPhilipp Reisner * increased: 2022b411b363SPhilipp Reisner * w_send_barrier 20238554df1cSAndreas Gruenbacher * _req_mod(req, QUEUE_FOR_NET_WRITE or QUEUE_FOR_NET_READ); 2024b411b363SPhilipp Reisner * it is much easier and equally valid to count what we queue for the 2025b411b363SPhilipp Reisner * worker, even before it actually was queued or send. 2026b411b363SPhilipp Reisner * (drbd_make_request_common; recovery path on read io-error) 2027b411b363SPhilipp Reisner * decreased: 2028b411b363SPhilipp Reisner * got_BarrierAck (respective tl_clear, tl_clear_barrier) 20298554df1cSAndreas Gruenbacher * _req_mod(req, DATA_RECEIVED) 2030b411b363SPhilipp Reisner * [from receive_DataReply] 20318554df1cSAndreas Gruenbacher * _req_mod(req, WRITE_ACKED_BY_PEER or RECV_ACKED_BY_PEER or NEG_ACKED) 2032b411b363SPhilipp Reisner * [from got_BlockAck (P_WRITE_ACK, P_RECV_ACK)] 2033b411b363SPhilipp Reisner * for some reason it is NOT decreased in got_NegAck, 2034b411b363SPhilipp Reisner * but in the resulting cleanup code from report_params. 2035b411b363SPhilipp Reisner * we should try to remember the reason for that... 20368554df1cSAndreas Gruenbacher * _req_mod(req, SEND_FAILED or SEND_CANCELED) 20378554df1cSAndreas Gruenbacher * _req_mod(req, CONNECTION_LOST_WHILE_PENDING) 2038b411b363SPhilipp Reisner * [from tl_clear_barrier] 2039b411b363SPhilipp Reisner */ 2040b30ab791SAndreas Gruenbacher static inline void inc_ap_pending(struct drbd_device *device) 2041b411b363SPhilipp Reisner { 2042b30ab791SAndreas Gruenbacher atomic_inc(&device->ap_pending_cnt); 2043b411b363SPhilipp Reisner } 2044b411b363SPhilipp Reisner 204549559d87SPhilipp Reisner #define ERR_IF_CNT_IS_NEGATIVE(which, func, line) \ 2046b30ab791SAndreas Gruenbacher if (atomic_read(&device->which) < 0) \ 2047d0180171SAndreas Gruenbacher drbd_err(device, "in %s:%d: " #which " = %d < 0 !\n", \ 204849559d87SPhilipp Reisner func, line, \ 2049b30ab791SAndreas Gruenbacher atomic_read(&device->which)) 2050b411b363SPhilipp Reisner 2051659b2e3bSJoe Perches #define dec_ap_pending(device) _dec_ap_pending(device, __func__, __LINE__) 2052b30ab791SAndreas Gruenbacher static inline void _dec_ap_pending(struct drbd_device *device, const char *func, int line) 205349559d87SPhilipp Reisner { 2054b30ab791SAndreas Gruenbacher if (atomic_dec_and_test(&device->ap_pending_cnt)) 2055b30ab791SAndreas Gruenbacher wake_up(&device->misc_wait); 205649559d87SPhilipp Reisner ERR_IF_CNT_IS_NEGATIVE(ap_pending_cnt, func, line); 205749559d87SPhilipp Reisner } 2058b411b363SPhilipp Reisner 2059b411b363SPhilipp Reisner /* counts how many resync-related answers we still expect from the peer 2060b411b363SPhilipp Reisner * increase decrease 2061b411b363SPhilipp Reisner * C_SYNC_TARGET sends P_RS_DATA_REQUEST (and expects P_RS_DATA_REPLY) 206225985edcSLucas De Marchi * C_SYNC_SOURCE sends P_RS_DATA_REPLY (and expects P_WRITE_ACK with ID_SYNCER) 2063b411b363SPhilipp Reisner * (or P_NEG_ACK with ID_SYNCER) 2064b411b363SPhilipp Reisner */ 2065b30ab791SAndreas Gruenbacher static inline void inc_rs_pending(struct drbd_device *device) 2066b411b363SPhilipp Reisner { 2067b30ab791SAndreas Gruenbacher atomic_inc(&device->rs_pending_cnt); 2068b411b363SPhilipp Reisner } 2069b411b363SPhilipp Reisner 2070659b2e3bSJoe Perches #define dec_rs_pending(device) _dec_rs_pending(device, __func__, __LINE__) 2071b30ab791SAndreas Gruenbacher static inline void _dec_rs_pending(struct drbd_device *device, const char *func, int line) 207249559d87SPhilipp Reisner { 2073b30ab791SAndreas Gruenbacher atomic_dec(&device->rs_pending_cnt); 207449559d87SPhilipp Reisner ERR_IF_CNT_IS_NEGATIVE(rs_pending_cnt, func, line); 207549559d87SPhilipp Reisner } 2076b411b363SPhilipp Reisner 2077b411b363SPhilipp Reisner /* counts how many answers we still need to send to the peer. 2078b411b363SPhilipp Reisner * increased on 2079b411b363SPhilipp Reisner * receive_Data unless protocol A; 2080b411b363SPhilipp Reisner * we need to send a P_RECV_ACK (proto B) 2081b411b363SPhilipp Reisner * or P_WRITE_ACK (proto C) 2082b411b363SPhilipp Reisner * receive_RSDataReply (recv_resync_read) we need to send a P_WRITE_ACK 2083b411b363SPhilipp Reisner * receive_DataRequest (receive_RSDataRequest) we need to send back P_DATA 2084b411b363SPhilipp Reisner * receive_Barrier_* we need to send a P_BARRIER_ACK 2085b411b363SPhilipp Reisner */ 2086b30ab791SAndreas Gruenbacher static inline void inc_unacked(struct drbd_device *device) 2087b411b363SPhilipp Reisner { 2088b30ab791SAndreas Gruenbacher atomic_inc(&device->unacked_cnt); 2089b411b363SPhilipp Reisner } 2090b411b363SPhilipp Reisner 2091659b2e3bSJoe Perches #define dec_unacked(device) _dec_unacked(device, __func__, __LINE__) 2092b30ab791SAndreas Gruenbacher static inline void _dec_unacked(struct drbd_device *device, const char *func, int line) 2093b411b363SPhilipp Reisner { 2094b30ab791SAndreas Gruenbacher atomic_dec(&device->unacked_cnt); 209549559d87SPhilipp Reisner ERR_IF_CNT_IS_NEGATIVE(unacked_cnt, func, line); 2096b411b363SPhilipp Reisner } 2097b411b363SPhilipp Reisner 2098659b2e3bSJoe Perches #define sub_unacked(device, n) _sub_unacked(device, n, __func__, __LINE__) 2099b30ab791SAndreas Gruenbacher static inline void _sub_unacked(struct drbd_device *device, int n, const char *func, int line) 2100b411b363SPhilipp Reisner { 2101b30ab791SAndreas Gruenbacher atomic_sub(n, &device->unacked_cnt); 210249559d87SPhilipp Reisner ERR_IF_CNT_IS_NEGATIVE(unacked_cnt, func, line); 2103b411b363SPhilipp Reisner } 2104b411b363SPhilipp Reisner 21055052fee2SLars Ellenberg static inline bool is_sync_target_state(enum drbd_conns connection_state) 21065052fee2SLars Ellenberg { 21075052fee2SLars Ellenberg return connection_state == C_SYNC_TARGET || 21085052fee2SLars Ellenberg connection_state == C_PAUSED_SYNC_T; 21095052fee2SLars Ellenberg } 21105052fee2SLars Ellenberg 21115052fee2SLars Ellenberg static inline bool is_sync_source_state(enum drbd_conns connection_state) 21125052fee2SLars Ellenberg { 21135052fee2SLars Ellenberg return connection_state == C_SYNC_SOURCE || 21145052fee2SLars Ellenberg connection_state == C_PAUSED_SYNC_S; 21155052fee2SLars Ellenberg } 21165052fee2SLars Ellenberg 21175ab7d2c0SLars Ellenberg static inline bool is_sync_state(enum drbd_conns connection_state) 21185ab7d2c0SLars Ellenberg { 21195052fee2SLars Ellenberg return is_sync_source_state(connection_state) || 21205052fee2SLars Ellenberg is_sync_target_state(connection_state); 21215ab7d2c0SLars Ellenberg } 21225ab7d2c0SLars Ellenberg 2123b411b363SPhilipp Reisner /** 2124b30ab791SAndreas Gruenbacher * get_ldev() - Increase the ref count on device->ldev. Returns 0 if there is no ldev 2125d1b80853SAndreas Gruenbacher * @_device: DRBD device. 2126d1b80853SAndreas Gruenbacher * @_min_state: Minimum device state required for success. 2127b411b363SPhilipp Reisner * 2128b30ab791SAndreas Gruenbacher * You have to call put_ldev() when finished working with device->ldev. 2129b411b363SPhilipp Reisner */ 2130d1b80853SAndreas Gruenbacher #define get_ldev_if_state(_device, _min_state) \ 2131d1b80853SAndreas Gruenbacher (_get_ldev_if_state((_device), (_min_state)) ? \ 2132d1b80853SAndreas Gruenbacher ({ __acquire(x); true; }) : false) 2133d1b80853SAndreas Gruenbacher #define get_ldev(_device) get_ldev_if_state(_device, D_INCONSISTENT) 2134b411b363SPhilipp Reisner 2135b30ab791SAndreas Gruenbacher static inline void put_ldev(struct drbd_device *device) 2136b411b363SPhilipp Reisner { 213711f8b2b6SAndreas Gruenbacher enum drbd_disk_state disk_state = device->state.disk; 2138ba3c6fb8SLars Ellenberg /* We must check the state *before* the atomic_dec becomes visible, 2139ba3c6fb8SLars Ellenberg * or we have a theoretical race where someone hitting zero, 2140ba3c6fb8SLars Ellenberg * while state still D_FAILED, will then see D_DISKLESS in the 2141ba3c6fb8SLars Ellenberg * condition below and calling into destroy, where he must not, yet. */ 2142b30ab791SAndreas Gruenbacher int i = atomic_dec_return(&device->local_cnt); 21439a0d9d03SLars Ellenberg 21449a0d9d03SLars Ellenberg /* This may be called from some endio handler, 21459a0d9d03SLars Ellenberg * so we must not sleep here. */ 21469a0d9d03SLars Ellenberg 2147b411b363SPhilipp Reisner __release(local); 21480b0ba1efSAndreas Gruenbacher D_ASSERT(device, i >= 0); 2149e9e6f3ecSLars Ellenberg if (i == 0) { 215011f8b2b6SAndreas Gruenbacher if (disk_state == D_DISKLESS) 215182f59cc6SLars Ellenberg /* even internal references gone, safe to destroy */ 2152e334f550SLars Ellenberg drbd_device_post_work(device, DESTROY_DISK); 215311f8b2b6SAndreas Gruenbacher if (disk_state == D_FAILED) 215482f59cc6SLars Ellenberg /* all application IO references gone. */ 2155e334f550SLars Ellenberg if (!test_and_set_bit(GOING_DISKLESS, &device->flags)) 2156e334f550SLars Ellenberg drbd_device_post_work(device, GO_DISKLESS); 2157b30ab791SAndreas Gruenbacher wake_up(&device->misc_wait); 2158b411b363SPhilipp Reisner } 2159e9e6f3ecSLars Ellenberg } 2160b411b363SPhilipp Reisner 2161b411b363SPhilipp Reisner #ifndef __CHECKER__ 2162b30ab791SAndreas Gruenbacher static inline int _get_ldev_if_state(struct drbd_device *device, enum drbd_disk_state mins) 2163b411b363SPhilipp Reisner { 2164b411b363SPhilipp Reisner int io_allowed; 2165b411b363SPhilipp Reisner 216682f59cc6SLars Ellenberg /* never get a reference while D_DISKLESS */ 2167b30ab791SAndreas Gruenbacher if (device->state.disk == D_DISKLESS) 216882f59cc6SLars Ellenberg return 0; 216982f59cc6SLars Ellenberg 2170b30ab791SAndreas Gruenbacher atomic_inc(&device->local_cnt); 2171b30ab791SAndreas Gruenbacher io_allowed = (device->state.disk >= mins); 2172b411b363SPhilipp Reisner if (!io_allowed) 2173b30ab791SAndreas Gruenbacher put_ldev(device); 2174b411b363SPhilipp Reisner return io_allowed; 2175b411b363SPhilipp Reisner } 2176b411b363SPhilipp Reisner #else 2177b30ab791SAndreas Gruenbacher extern int _get_ldev_if_state(struct drbd_device *device, enum drbd_disk_state mins); 2178b411b363SPhilipp Reisner #endif 2179b411b363SPhilipp Reisner 2180b411b363SPhilipp Reisner /* this throttles on-the-fly application requests 2181b411b363SPhilipp Reisner * according to max_buffers settings; 2182b411b363SPhilipp Reisner * maybe re-implement using semaphores? */ 2183b30ab791SAndreas Gruenbacher static inline int drbd_get_max_buffers(struct drbd_device *device) 2184b411b363SPhilipp Reisner { 218544ed167dSPhilipp Reisner struct net_conf *nc; 218644ed167dSPhilipp Reisner int mxb; 218744ed167dSPhilipp Reisner 218844ed167dSPhilipp Reisner rcu_read_lock(); 2189a6b32bc3SAndreas Gruenbacher nc = rcu_dereference(first_peer_device(device)->connection->net_conf); 219044ed167dSPhilipp Reisner mxb = nc ? nc->max_buffers : 1000000; /* arbitrary limit on open requests */ 219144ed167dSPhilipp Reisner rcu_read_unlock(); 219244ed167dSPhilipp Reisner 2193b411b363SPhilipp Reisner return mxb; 2194b411b363SPhilipp Reisner } 2195b411b363SPhilipp Reisner 2196b30ab791SAndreas Gruenbacher static inline int drbd_state_is_stable(struct drbd_device *device) 2197b411b363SPhilipp Reisner { 2198b30ab791SAndreas Gruenbacher union drbd_dev_state s = device->state; 2199b411b363SPhilipp Reisner 2200b411b363SPhilipp Reisner /* DO NOT add a default clause, we want the compiler to warn us 2201b411b363SPhilipp Reisner * for any newly introduced state we may have forgotten to add here */ 2202b411b363SPhilipp Reisner 2203b411b363SPhilipp Reisner switch ((enum drbd_conns)s.conn) { 2204b411b363SPhilipp Reisner /* new io only accepted when there is no connection, ... */ 2205b411b363SPhilipp Reisner case C_STANDALONE: 2206b411b363SPhilipp Reisner case C_WF_CONNECTION: 2207b411b363SPhilipp Reisner /* ... or there is a well established connection. */ 2208b411b363SPhilipp Reisner case C_CONNECTED: 2209b411b363SPhilipp Reisner case C_SYNC_SOURCE: 2210b411b363SPhilipp Reisner case C_SYNC_TARGET: 2211b411b363SPhilipp Reisner case C_VERIFY_S: 2212b411b363SPhilipp Reisner case C_VERIFY_T: 2213b411b363SPhilipp Reisner case C_PAUSED_SYNC_S: 2214b411b363SPhilipp Reisner case C_PAUSED_SYNC_T: 221567531718SPhilipp Reisner case C_AHEAD: 221667531718SPhilipp Reisner case C_BEHIND: 22173719094eSPhilipp Reisner /* transitional states, IO allowed */ 2218b411b363SPhilipp Reisner case C_DISCONNECTING: 2219b411b363SPhilipp Reisner case C_UNCONNECTED: 2220b411b363SPhilipp Reisner case C_TIMEOUT: 2221b411b363SPhilipp Reisner case C_BROKEN_PIPE: 2222b411b363SPhilipp Reisner case C_NETWORK_FAILURE: 2223b411b363SPhilipp Reisner case C_PROTOCOL_ERROR: 2224b411b363SPhilipp Reisner case C_TEAR_DOWN: 2225b411b363SPhilipp Reisner case C_WF_REPORT_PARAMS: 2226b411b363SPhilipp Reisner case C_STARTING_SYNC_S: 2227b411b363SPhilipp Reisner case C_STARTING_SYNC_T: 22283719094eSPhilipp Reisner break; 22293719094eSPhilipp Reisner 22303719094eSPhilipp Reisner /* Allow IO in BM exchange states with new protocols */ 2231b411b363SPhilipp Reisner case C_WF_BITMAP_S: 2232a6b32bc3SAndreas Gruenbacher if (first_peer_device(device)->connection->agreed_pro_version < 96) 22333719094eSPhilipp Reisner return 0; 22343719094eSPhilipp Reisner break; 22353719094eSPhilipp Reisner 22363719094eSPhilipp Reisner /* no new io accepted in these states */ 2237b411b363SPhilipp Reisner case C_WF_BITMAP_T: 2238b411b363SPhilipp Reisner case C_WF_SYNC_UUID: 2239b411b363SPhilipp Reisner case C_MASK: 2240b411b363SPhilipp Reisner /* not "stable" */ 2241b411b363SPhilipp Reisner return 0; 2242b411b363SPhilipp Reisner } 2243b411b363SPhilipp Reisner 2244b411b363SPhilipp Reisner switch ((enum drbd_disk_state)s.disk) { 2245b411b363SPhilipp Reisner case D_DISKLESS: 2246b411b363SPhilipp Reisner case D_INCONSISTENT: 2247b411b363SPhilipp Reisner case D_OUTDATED: 2248b411b363SPhilipp Reisner case D_CONSISTENT: 2249b411b363SPhilipp Reisner case D_UP_TO_DATE: 22505ca1de03SPhilipp Reisner case D_FAILED: 2251b411b363SPhilipp Reisner /* disk state is stable as well. */ 2252b411b363SPhilipp Reisner break; 2253b411b363SPhilipp Reisner 2254d942ae44SPhilipp Reisner /* no new io accepted during transitional states */ 2255b411b363SPhilipp Reisner case D_ATTACHING: 2256b411b363SPhilipp Reisner case D_NEGOTIATING: 2257b411b363SPhilipp Reisner case D_UNKNOWN: 2258b411b363SPhilipp Reisner case D_MASK: 2259b411b363SPhilipp Reisner /* not "stable" */ 2260b411b363SPhilipp Reisner return 0; 2261b411b363SPhilipp Reisner } 2262b411b363SPhilipp Reisner 2263b411b363SPhilipp Reisner return 1; 2264b411b363SPhilipp Reisner } 2265b411b363SPhilipp Reisner 2266b30ab791SAndreas Gruenbacher static inline int drbd_suspended(struct drbd_device *device) 2267fb22c402SPhilipp Reisner { 22686bbf53caSAndreas Gruenbacher struct drbd_resource *resource = device->resource; 22698e0af25fSPhilipp Reisner 22706bbf53caSAndreas Gruenbacher return resource->susp || resource->susp_fen || resource->susp_nod; 2271fb22c402SPhilipp Reisner } 2272fb22c402SPhilipp Reisner 2273b30ab791SAndreas Gruenbacher static inline bool may_inc_ap_bio(struct drbd_device *device) 2274b411b363SPhilipp Reisner { 2275b30ab791SAndreas Gruenbacher int mxb = drbd_get_max_buffers(device); 2276b411b363SPhilipp Reisner 2277b30ab791SAndreas Gruenbacher if (drbd_suspended(device)) 22781b881ef7SAndreas Gruenbacher return false; 22797dbb4386SPhilipp Reisner if (atomic_read(&device->suspend_cnt)) 22801b881ef7SAndreas Gruenbacher return false; 2281b411b363SPhilipp Reisner 2282b411b363SPhilipp Reisner /* to avoid potential deadlock or bitmap corruption, 2283b411b363SPhilipp Reisner * in various places, we only allow new application io 2284b411b363SPhilipp Reisner * to start during "stable" states. */ 2285b411b363SPhilipp Reisner 2286b411b363SPhilipp Reisner /* no new io accepted when attaching or detaching the disk */ 2287b30ab791SAndreas Gruenbacher if (!drbd_state_is_stable(device)) 22881b881ef7SAndreas Gruenbacher return false; 2289b411b363SPhilipp Reisner 2290b411b363SPhilipp Reisner /* since some older kernels don't have atomic_add_unless, 2291b411b363SPhilipp Reisner * and we are within the spinlock anyways, we have this workaround. */ 2292b30ab791SAndreas Gruenbacher if (atomic_read(&device->ap_bio_cnt) > mxb) 22931b881ef7SAndreas Gruenbacher return false; 2294b30ab791SAndreas Gruenbacher if (test_bit(BITMAP_IO, &device->flags)) 22951b881ef7SAndreas Gruenbacher return false; 22961b881ef7SAndreas Gruenbacher return true; 2297b411b363SPhilipp Reisner } 2298b411b363SPhilipp Reisner 2299b30ab791SAndreas Gruenbacher static inline bool inc_ap_bio_cond(struct drbd_device *device) 23008869d683SPhilipp Reisner { 23011b881ef7SAndreas Gruenbacher bool rv = false; 23028869d683SPhilipp Reisner 23030500813fSAndreas Gruenbacher spin_lock_irq(&device->resource->req_lock); 2304b30ab791SAndreas Gruenbacher rv = may_inc_ap_bio(device); 23058869d683SPhilipp Reisner if (rv) 2306b30ab791SAndreas Gruenbacher atomic_inc(&device->ap_bio_cnt); 23070500813fSAndreas Gruenbacher spin_unlock_irq(&device->resource->req_lock); 23088869d683SPhilipp Reisner 23098869d683SPhilipp Reisner return rv; 23108869d683SPhilipp Reisner } 23118869d683SPhilipp Reisner 2312b30ab791SAndreas Gruenbacher static inline void inc_ap_bio(struct drbd_device *device) 2313b411b363SPhilipp Reisner { 2314b411b363SPhilipp Reisner /* we wait here 2315b411b363SPhilipp Reisner * as long as the device is suspended 2316b411b363SPhilipp Reisner * until the bitmap is no longer on the fly during connection 2317d942ae44SPhilipp Reisner * handshake as long as we would exceed the max_buffer limit. 2318b411b363SPhilipp Reisner * 2319b411b363SPhilipp Reisner * to avoid races with the reconnect code, 2320b411b363SPhilipp Reisner * we need to atomic_inc within the spinlock. */ 2321b411b363SPhilipp Reisner 2322b30ab791SAndreas Gruenbacher wait_event(device->misc_wait, inc_ap_bio_cond(device)); 2323b411b363SPhilipp Reisner } 2324b411b363SPhilipp Reisner 2325b30ab791SAndreas Gruenbacher static inline void dec_ap_bio(struct drbd_device *device) 2326b411b363SPhilipp Reisner { 2327b30ab791SAndreas Gruenbacher int mxb = drbd_get_max_buffers(device); 2328b30ab791SAndreas Gruenbacher int ap_bio = atomic_dec_return(&device->ap_bio_cnt); 2329b411b363SPhilipp Reisner 23300b0ba1efSAndreas Gruenbacher D_ASSERT(device, ap_bio >= 0); 23317ee1fb93SLars Ellenberg 2332b30ab791SAndreas Gruenbacher if (ap_bio == 0 && test_bit(BITMAP_IO, &device->flags)) { 2333b30ab791SAndreas Gruenbacher if (!test_and_set_bit(BITMAP_IO_QUEUED, &device->flags)) 233484b8c06bSAndreas Gruenbacher drbd_queue_work(&first_peer_device(device)-> 233584b8c06bSAndreas Gruenbacher connection->sender_work, 233684b8c06bSAndreas Gruenbacher &device->bm_io_work.w); 23377ee1fb93SLars Ellenberg } 23387ee1fb93SLars Ellenberg 2339b411b363SPhilipp Reisner /* this currently does wake_up for every dec_ap_bio! 2340b411b363SPhilipp Reisner * maybe rather introduce some type of hysteresis? 2341b411b363SPhilipp Reisner * e.g. (ap_bio == mxb/2 || ap_bio == 0) ? */ 2342b411b363SPhilipp Reisner if (ap_bio < mxb) 2343b30ab791SAndreas Gruenbacher wake_up(&device->misc_wait); 2344b411b363SPhilipp Reisner } 2345b411b363SPhilipp Reisner 2346b30ab791SAndreas Gruenbacher static inline bool verify_can_do_stop_sector(struct drbd_device *device) 234758ffa580SLars Ellenberg { 2348a6b32bc3SAndreas Gruenbacher return first_peer_device(device)->connection->agreed_pro_version >= 97 && 2349a6b32bc3SAndreas Gruenbacher first_peer_device(device)->connection->agreed_pro_version != 100; 235058ffa580SLars Ellenberg } 235158ffa580SLars Ellenberg 2352b30ab791SAndreas Gruenbacher static inline int drbd_set_ed_uuid(struct drbd_device *device, u64 val) 2353b411b363SPhilipp Reisner { 2354b30ab791SAndreas Gruenbacher int changed = device->ed_uuid != val; 2355b30ab791SAndreas Gruenbacher device->ed_uuid = val; 235662b0da3aSLars Ellenberg return changed; 2357b411b363SPhilipp Reisner } 2358b411b363SPhilipp Reisner 2359b30ab791SAndreas Gruenbacher static inline int drbd_queue_order_type(struct drbd_device *device) 2360b411b363SPhilipp Reisner { 2361b411b363SPhilipp Reisner /* sorry, we currently have no working implementation 2362b411b363SPhilipp Reisner * of distributed TCQ stuff */ 2363b411b363SPhilipp Reisner #ifndef QUEUE_ORDERED_NONE 2364b411b363SPhilipp Reisner #define QUEUE_ORDERED_NONE 0 2365b411b363SPhilipp Reisner #endif 2366b411b363SPhilipp Reisner return QUEUE_ORDERED_NONE; 2367b411b363SPhilipp Reisner } 2368b411b363SPhilipp Reisner 236977c556f6SAndreas Gruenbacher static inline struct drbd_connection *first_connection(struct drbd_resource *resource) 237077c556f6SAndreas Gruenbacher { 2371ec4a3407SLars Ellenberg return list_first_entry_or_null(&resource->connections, 237277c556f6SAndreas Gruenbacher struct drbd_connection, connections); 237377c556f6SAndreas Gruenbacher } 237477c556f6SAndreas Gruenbacher 2375b411b363SPhilipp Reisner #endif 2376