1 /* 2 * CDDL HEADER START 3 * 4 * The contents of this file are subject to the terms of the 5 * Common Development and Distribution License (the "License"). 6 * You may not use this file except in compliance with the License. 7 * 8 * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE 9 * or http://www.opensolaris.org/os/licensing. 10 * See the License for the specific language governing permissions 11 * and limitations under the License. 12 * 13 * When distributing Covered Code, include this CDDL HEADER in each 14 * file and include the License file at usr/src/OPENSOLARIS.LICENSE. 15 * If applicable, add the following below this CDDL HEADER, with the 16 * fields enclosed by brackets "[]" replaced with your own identifying 17 * information: Portions Copyright [yyyy] [name of copyright owner] 18 * 19 * CDDL HEADER END 20 */ 21 /* 22 * Copyright 2006 Sun Microsystems, Inc. All rights reserved. 23 * Use is subject to license terms. 24 */ 25 26 #ifndef _SYS_MD_RAID_H 27 #define _SYS_MD_RAID_H 28 29 #pragma ident "%Z%%M% %I% %E% SMI" 30 31 #include <sys/lvm/mdvar.h> 32 #include <sys/lvm/md_rename.h> 33 34 #ifdef __cplusplus 35 extern "C" { 36 #endif 37 38 39 /* 40 * following bits are used in status word in the common section 41 * of unit structure: un_status 42 */ 43 #define RAID_UNMAGIC 0xBADBABE0 44 #define RAID_PSMAGIC 0xBADBABE1 45 #define RAID_CSMAGIC 0xBADBABE2 46 #define RAID_PWMAGIC 0xBADBABE3 47 #define RAID_BUFMAGIC 0xBADBABE4 48 /* 49 * These are the major constants for the definition of a raid device 50 */ 51 #define PWCNT_MIN 10 /* mininum # prewrites */ 52 #define PWCNT_MAX 100 /* maximum # prewrites */ 53 #define RAID_MIN_INTERLACE (DEV_BSIZE * 2) 54 55 #define UNIT_STATE(un) ((un)->un_state) 56 #define COLUMN_STATE(un, column) ((un)->un_column[(column)].un_devstate) 57 58 #define COLUMN_STATE_ONLY(un, column) (\ 59 ((un)->un_column[(column)].un_devstate == RCS_INIT) || \ 60 ((un)->un_column[(column)].un_devstate == RCS_OKAY) || \ 61 ((un)->un_column[(column)].un_devstate == RCS_ERRED) || \ 62 ((un)->un_column[(column)].un_devstate == RCS_RESYNC) || \ 63 ((un)->un_column[(column)].un_devstate == RCS_LAST_ERRED) || \ 64 ((un)->un_column[(column)].un_devstate == RCS_REGEN))) 65 66 #define COLUMN_ISUP(un, column) (\ 67 ((un)->un_column[(column)].un_devstate == RCS_OKAY) || \ 68 ((un)->un_column[(column)].un_devstate == RCS_RESYNC) || \ 69 ((un)->un_column[(column)].un_devstate == RCS_LAST_ERRED)) 70 71 #define COLUMN_ISOKAY(un, column) (\ 72 ((un)->un_column[(column)].un_devstate == RCS_OKAY)) 73 74 #define COLUMN_ISLASTERR(un, column) (\ 75 ((un)->un_column[(column)].un_devstate == RCS_LAST_ERRED)) 76 77 #define WRITE_ALT(un, column) ( \ 78 ((un)->un_column[(column)].un_alt_dev != NODEV64) && \ 79 (((un)->un_column[(column)].un_devflags & MD_RAID_WRITE_ALT))) 80 81 #define HOTSPARED(un, column) ( \ 82 ((un)->un_column[(column)].un_hs_id != 0)) 83 84 #define OVERLAPED(blk1, lblk1, blk2, lblk2) ( \ 85 (((blk1 > lblk2) ? 1 : 0) || \ 86 ((lblk1 < blk2) ? 1 : 0))) 87 88 89 /* 90 * Note: magic is needed only to set rpw_magic, not rpw_magic_ext! 91 */ 92 #define RAID_FILLIN_RPW(buf, un, sum, colnum, \ 93 blkno, blkcnt, id, \ 94 colcount, col, magic) { \ 95 if ((un)->c.un_revision & MD_64BIT_META_DEV) { \ 96 raid_pwhdr_t *rpw64 = (raid_pwhdr_t *)(void *)(buf);\ 97 rpw64->rpw_magic = magic; \ 98 rpw64->rpw_sum = sum; \ 99 rpw64->rpw_columnnum = colnum; \ 100 rpw64->rpw_blkno = (diskaddr_t)blkno; \ 101 rpw64->rpw_blkcnt = blkcnt; \ 102 rpw64->rpw_id = id; \ 103 rpw64->rpw_colcount = colcount; \ 104 rpw64->rpw_column = col; \ 105 rpw64->rpw_unit = MD_SID(un); \ 106 rpw64->rpw_magic_ext = RAID_PWMAGIC; \ 107 rpw64->rpw_origcolumncnt = (un)->un_origcolumncnt; \ 108 rpw64->rpw_totalcolumncnt = (un)->un_totalcolumncnt; \ 109 rpw64->rpw_segsize = (un)->un_segsize; \ 110 rpw64->rpw_segsincolumn = (diskaddr_t)((un)->un_segsincolumn);\ 111 rpw64->rpw_pwcnt = (un)->un_pwcnt; \ 112 rpw64->rpw_pwsize = (un)->un_pwsize; \ 113 rpw64->rpw_devstart = \ 114 (diskaddr_t)((un)->un_column[col].un_orig_devstart);\ 115 rpw64->rpw_pwstart = \ 116 (diskaddr_t)((un)->un_column[col].un_orig_pwstart);\ 117 } else { \ 118 raid_pwhdr32_od_t *rpw32 = \ 119 (raid_pwhdr32_od_t *)(void *)(buf); \ 120 rpw32->rpw_magic = magic; \ 121 rpw32->rpw_sum = sum; \ 122 rpw32->rpw_columnnum = colnum; \ 123 rpw32->rpw_blkno = (daddr_t)blkno; \ 124 rpw32->rpw_blkcnt = blkcnt; \ 125 rpw32->rpw_id = id; \ 126 rpw32->rpw_colcount = colcount; \ 127 rpw32->rpw_column = col; \ 128 rpw32->rpw_unit = MD_SID(un); \ 129 rpw32->rpw_magic_ext = RAID_PWMAGIC; \ 130 rpw32->rpw_origcolumncnt = (un)->un_origcolumncnt; \ 131 rpw32->rpw_totalcolumncnt = (un)->un_totalcolumncnt; \ 132 rpw32->rpw_segsize = (daddr_t)((un)->un_segsize); \ 133 rpw32->rpw_segsincolumn = (daddr_t)((un)->un_segsincolumn);\ 134 rpw32->rpw_pwcnt = (un)->un_pwcnt; \ 135 rpw32->rpw_pwsize = (un)->un_pwsize; \ 136 rpw32->rpw_devstart = \ 137 (daddr_t)((un)->un_column[col].un_orig_devstart);\ 138 rpw32->rpw_pwstart = \ 139 (daddr_t)((un)->un_column[col].un_orig_pwstart);\ 140 } \ 141 } 142 143 #define RAID_CONVERT_RPW(rpw32, rpw64) { \ 144 (rpw64)->rpw_magic = (rpw32)->rpw_magic; \ 145 (rpw64)->rpw_sum = (rpw32)->rpw_sum; \ 146 (rpw64)->rpw_columnnum = (rpw32)->rpw_columnnum; \ 147 (rpw64)->rpw_blkno = (rpw32)->rpw_blkno; \ 148 (rpw64)->rpw_blkcnt = (rpw32)->rpw_blkcnt; \ 149 (rpw64)->rpw_id = (rpw32)->rpw_id; \ 150 (rpw64)->rpw_colcount = (rpw32)->rpw_colcount; \ 151 (rpw64)->rpw_column = (rpw32)->rpw_column; \ 152 (rpw64)->rpw_unit = (rpw32)->rpw_unit; \ 153 (rpw64)->rpw_magic_ext = (rpw32)->rpw_magic_ext; \ 154 (rpw64)->rpw_origcolumncnt = (rpw32)->rpw_origcolumncnt; \ 155 (rpw64)->rpw_totalcolumncnt = (rpw32)->rpw_totalcolumncnt; \ 156 (rpw64)->rpw_segsize = (rpw32)->rpw_segsize; \ 157 (rpw64)->rpw_segsincolumn = (rpw32)->rpw_segsincolumn; \ 158 (rpw64)->rpw_pwcnt = (rpw32)->rpw_pwcnt; \ 159 (rpw64)->rpw_pwsize = (rpw32)->rpw_pwsize; \ 160 (rpw64)->rpw_devstart = (rpw32)->rpw_devstart; \ 161 (rpw64)->rpw_pwstart = (rpw32)->rpw_pwstart; \ 162 } 163 164 typedef struct mr_scoreboard { 165 int sb_column; 166 int sb_flags; 167 diskaddr_t sb_start_blk; 168 diskaddr_t sb_last_blk; 169 void *sb_cs; 170 } mr_scoreboard_t; 171 172 #define SB_AVAIL (0x00000001) /* useable and valid blocks */ 173 #define SB_INUSE (0x00000002) /* being used */ 174 #define SB_UNUSED (0x00000004) /* useable and no valid blocks */ 175 #define SB_INVAL_PEND (0x00000008) /* being invalidated */ 176 177 typedef struct mr_pw_reserve { 178 uint_t pw_magic; 179 int pw_column; 180 int pw_free; 181 mr_scoreboard_t pw_sb[1]; 182 } mr_pw_reserve_t; 183 184 185 #if _LONG_LONG_ALIGNMENT == 8 && _LONG_LONG_ALIGNMENT_32 == 4 186 #pragma pack(4) 187 #endif 188 typedef struct mr_column { 189 rcs_state_t un_devstate; 190 rcs_flags_t un_devflags; 191 md_timeval32_t un_devtimestamp; /* time of last state change, 32 bit */ 192 193 mddb_recid_t un_hs_id; 194 diskaddr_t un_hs_pwstart; 195 diskaddr_t un_hs_devstart; 196 mdkey_t un_hs_key; 197 198 199 md_dev64_t un_orig_dev; /* original device, 64 bit */ 200 mdkey_t un_orig_key; 201 diskaddr_t un_orig_pwstart; 202 diskaddr_t un_orig_devstart; 203 204 md_dev64_t un_dev; /* current read/write dev */ 205 diskaddr_t un_pwstart; 206 diskaddr_t un_devstart; 207 208 md_dev64_t un_alt_dev; /* write to if resync */ 209 diskaddr_t un_alt_pwstart; 210 diskaddr_t un_alt_devstart; 211 } mr_column_t; 212 213 /* 214 * mr_column32_od is for old 32 bit format only 215 */ 216 typedef struct mr_column32_od { 217 rcs_state_t un_devstate; 218 rcs_flags_t un_devflags; 219 struct timeval32 un_devtimestamp; /* time of last state change */ 220 caddr32_t xx_un_pw_reserve; 221 222 mddb_recid_t un_hs_id; 223 daddr32_t un_hs_pwstart; 224 daddr32_t un_hs_devstart; 225 mdkey_t un_hs_key; 226 227 dev32_t un_orig_dev; /* original device */ 228 mdkey_t un_orig_key; 229 daddr32_t un_orig_pwstart; 230 daddr32_t un_orig_devstart; 231 232 dev32_t un_dev; /* current read/write dev */ 233 daddr32_t un_pwstart; 234 daddr32_t un_devstart; 235 236 dev32_t un_alt_dev; /* write to if resync */ 237 daddr32_t un_alt_pwstart; 238 daddr32_t un_alt_devstart; 239 } mr_column32_od_t; 240 241 242 /* 243 * Incore only elements structures 244 */ 245 typedef struct mr_column_ic { 246 mr_pw_reserve_t *un_pw_reserve; 247 } mr_column_ic_t; 248 249 typedef struct mr_unit_ic { 250 caddr_t _t_un_pbuffer; 251 caddr_t _t_un_dbuffer; 252 struct md_raidcs *_t_un_linlck_chn; 253 kmutex_t _t_un_linlck_mx; 254 kcondvar_t _t_un_linlck_cv; 255 kmutex_t _t_un_mx; 256 kcondvar_t _t_un_cv; 257 mr_column_ic_t *_t_un_column_ic; 258 } mr_unit_ic_t; 259 260 typedef struct mr_unit { 261 mdc_unit_t c; 262 int un_raid_res; 263 uint_t un_magic; 264 rus_state_t un_state; 265 md_timeval32_t un_timestamp; /* 32 bit fixed size */ 266 uint_t un_origcolumncnt; 267 uint_t un_totalcolumncnt; 268 uint_t un_rflags; 269 uint_t un_segsize; 270 diskaddr_t un_segsincolumn; 271 uint_t un_maxio; /* in blks */ 272 uint_t un_iosize; /* in blks */ 273 uint_t un_linlck_flg; 274 uint_t un_pwcnt; 275 uint_t un_pwsize; 276 long long un_pwid; 277 uint_t un_percent_done; 278 uint_t un_resync_copysize; /* in blks */ 279 hsp_t un_hsp_id; 280 /* 281 * This union has to begin at an 8 byte aligned address. 282 * If not, this structure has different sizes in 32 / 64 bit 283 * environments, since in a 64 bit environment the compiler 284 * adds paddings before a long long, if it doesn't start at an 8byte 285 * aligned address. 286 * Be careful if you add or remove structure elements before it! 287 */ 288 289 union { 290 struct { 291 diskaddr_t _t_un_resync_line_index; 292 uint_t _t_un_resync_segment; 293 int _t_un_resync_index; 294 } _resync; 295 struct { 296 diskaddr_t _t_un_grow_tb; 297 uint_t _t_un_init_colcnt; 298 u_longlong_t _t_un_init_iocnt; 299 } _init; 300 } _t_un; 301 302 /* 303 * This union has to begin at an 8 byte aligned address. 304 * Be careful if you add or remove structure elements before it! 305 */ 306 union { 307 mr_unit_ic_t *_mr_ic; 308 uint_t _mr_ic_pad[2]; 309 } un_mr_ic; 310 311 mr_column_t un_column[1]; 312 } mr_unit_t; 313 314 #define mr_ic un_mr_ic._mr_ic 315 #define un_pbuffer mr_ic->_t_un_pbuffer 316 #define un_dbuffer mr_ic->_t_un_dbuffer 317 #define un_linlck_chn mr_ic->_t_un_linlck_chn 318 #define un_linlck_mx mr_ic->_t_un_linlck_mx 319 #define un_linlck_cv mr_ic->_t_un_linlck_cv 320 #define un_mx mr_ic->_t_un_mx 321 #define un_cv mr_ic->_t_un_cv 322 #define un_column_ic mr_ic->_t_un_column_ic 323 324 /* 325 * For old 32 bit format use only 326 */ 327 typedef struct mr_unit32_od { 328 mdc_unit32_od_t c; 329 caddr32_t xx_un_raid_res; 330 uint_t un_magic; 331 rus_state_t un_state; 332 struct timeval32 un_timestamp; 333 uint_t un_origcolumncnt; 334 uint_t un_totalcolumncnt; 335 uint_t un_rflags; 336 uint_t un_segsize; 337 uint_t un_segsincolumn; 338 uint_t un_maxio; 339 uint_t un_iosize; 340 caddr32_t xx_un_pbuffer; 341 caddr32_t xx_un_dbuffer; 342 uint_t un_linlck_flg; 343 caddr32_t xx_un_linlck_chn; 344 uint_t un_pwcnt; 345 uint_t un_pwsize; 346 long long un_pwid; 347 uint_t un_rebuild_size; 348 uint_t un_percent_done; 349 union { 350 struct { 351 uint_t _t_un_resync_segment; 352 int _t_un_resync_index; 353 uint_t _t_un_resync_line_index; 354 } _resync; 355 struct { 356 daddr32_t _t_un_grow_tb; 357 uint_t _t_un_init_colcnt; 358 uint_t _t_un_init_iocnt; 359 } _init; 360 } _t_un; 361 uint_t un_resync_copysize; 362 363 /* 364 * This spot is 8 byte aligned!!! 365 * Don't change this arrangement. 366 */ 367 union { 368 struct { 369 mr_unit_ic_t *_t_mr_ic; 370 } _mric; 371 struct { 372 uint_t xx_un_linlck_mx[2]; 373 } _lckmx; 374 } _unic; 375 376 short xx_un_linlck_cv; 377 int xx_un_mx[2]; 378 short xx_un_cv; 379 hsp_t un_hsp_id; 380 mr_column32_od_t un_column[1]; 381 } mr_unit32_od_t; 382 383 typedef struct raid_pwhdr { 384 uint_t rpw_magic; 385 uint_t rpw_sum; 386 int rpw_columnnum; 387 diskaddr_t rpw_blkno; 388 uint_t rpw_blkcnt; 389 long long rpw_id; 390 uint_t rpw_colcount; 391 uint_t rpw_column; 392 uint_t rpw_unit; 393 uint_t rpw_magic_ext; 394 uint_t rpw_origcolumncnt; 395 uint_t rpw_totalcolumncnt; 396 uint_t rpw_segsize; 397 diskaddr_t rpw_segsincolumn; 398 uint_t rpw_pwcnt; 399 uint_t rpw_pwsize; 400 diskaddr_t rpw_devstart; 401 diskaddr_t rpw_pwstart; 402 char rpw_filler[12]; 403 } raid_pwhdr_t; 404 405 /* 406 * For old 32 bit pre-write area 407 */ 408 typedef struct raid_pwhdr32_od { 409 uint_t rpw_magic; 410 uint_t rpw_sum; 411 int rpw_columnnum; 412 daddr32_t rpw_blkno; 413 daddr32_t rpw_blkcnt; 414 long long rpw_id; 415 uint_t rpw_colcount; 416 uint_t rpw_column; 417 uint_t rpw_unit; 418 uint_t rpw_magic_ext; 419 uint_t rpw_origcolumncnt; 420 uint_t rpw_totalcolumncnt; 421 uint_t rpw_segsize; 422 uint_t rpw_segsincolumn; 423 uint_t rpw_pwcnt; 424 uint_t rpw_pwsize; 425 uint_t rpw_devstart; 426 uint_t rpw_pwstart; 427 rus_state_t rpw_unit_state; 428 rcs_state_t rpw_next_column_state; 429 rcs_state_t rpw_prev_column_state; 430 } raid_pwhdr32_od_t; 431 #if _LONG_LONG_ALIGNMENT == 8 && _LONG_LONG_ALIGNMENT_32 == 4 432 #pragma pack() 433 #endif 434 435 #ifdef _KERNEL 436 437 /* 438 * the buffer header is only bp_mapin if it is needed. It is needed on 439 * all writes and on some reads. ps_mapin is non zero if the buffer is 440 * maped in. ps_mapin_mx protect ps_mapin. The protocol for usage is 441 * 442 * 1) check for non-zero and continue if non-zero 443 * 2) aquire the ps_mapin_mx 444 * 3) recheck for non-zero and continue if non-zero 445 * 4) bp_mapin 446 * 5) set ps_mapin to non-zero 447 * 6) drop ps_mapin_mx 448 * 449 * the reason for this is to avoid the mutex when possible. 450 */ 451 typedef struct md_raidps { /* raid parent save */ 452 DAEMON_QUEUE 453 uint_t ps_magic; 454 mr_unit_t *ps_un; 455 mdi_unit_t *ps_ui; 456 buf_t *ps_bp; 457 caddr_t ps_addr; 458 int ps_flags; 459 int ps_error; 460 int ps_frags; 461 int ps_pwfrags; 462 int ps_mapin; /* buffer maped in if non zero */ 463 kmutex_t ps_mx; 464 kmutex_t ps_mapin_mx; /* protects ps_mapin */ 465 } md_raidps_t; 466 467 /* flags for parent save area */ 468 469 #define MD_RPS_ERROR 0x0001 470 #define MD_RPS_READ 0x0020 471 #define MD_RPS_WRITE 0x0040 472 #define MD_RPS_DONE 0x0080 473 #define MD_RPS_INUSE 0x0100 474 #define MD_RPS_IODONE 0x0200 475 #define MD_RPS_HSREQ 0x0400 476 477 /* 478 * used in cs_state to describe the type of io operation in progress 479 */ 480 enum raid_io_stage { 481 RAID_NONE = 0x0, 482 RAID_READ_DONE = 0x1, 483 RAID_WRITE_DONE = 0x2, 484 RAID_PREWRITE_DONE = 0x4, 485 RAID_WRITE_PONLY_DONE = 0x8, 486 RAID_WRITE_DONLY_DONE = 0x10, 487 RAID_LINE_PWDONE = 0x20 488 }; 489 490 typedef struct md_raidcbuf { 491 DAEMON_QUEUE 492 uint_t cbuf_magic; 493 struct md_raidcbuf *cbuf_next; /* 0x10 */ 494 mr_unit_t *cbuf_un; 495 md_raidps_t *cbuf_ps; 496 int cbuf_column; 497 size_t cbuf_bcount; /* 0x20 */ 498 caddr_t cbuf_buffer; 499 int cbuf_sum; 500 int cbuf_pwslot; 501 int cbuf_pwcnt; /* 0x30 */ 502 int cbuf_flags; 503 buf_t cbuf_bp; 504 uint_t cbuf_pad[4]; 505 } md_raidcbuf_t; 506 #define CBUF_PW_INVALIDATE (0x00000001) 507 #define CBUF_WRITE (0x00000002) 508 509 typedef struct md_raidcs { 510 DAEMON_QUEUE 511 uint_t cs_magic; 512 minor_t cs_mdunit; 513 mr_unit_t *cs_un; 514 int cs_flags; 515 md_raidps_t *cs_ps; 516 diskaddr_t cs_line; 517 void (*cs_call)(); 518 void (*cs_error_call)(); 519 void (*cs_retry_call)(); 520 struct md_raidcs *cs_linlck_next; 521 struct md_raidcs *cs_linlck_prev; 522 long long cs_pwid; 523 int cs_dcolumn; 524 int cs_dpwslot; 525 uint_t cs_dflags; 526 int cs_pcolumn; 527 int cs_ppwslot; 528 uint_t cs_pflags; 529 size_t cs_bcount; 530 uint_t cs_blkcnt; 531 diskaddr_t cs_blkno; 532 diskaddr_t cs_lastblk; 533 int cs_loop; 534 caddr_t cs_addr; /* base address of io */ 535 off_t cs_offset; /* offset into the base */ 536 caddr_t cs_dbuffer; 537 caddr_t cs_pbuffer; 538 int cs_frags; 539 int cs_strategy_flag; 540 void *cs_strategy_private; 541 md_raidcbuf_t *cs_buflist; 542 int cs_error; 543 int cs_resync_check; 544 int cs_rstate; 545 enum raid_io_stage cs_stage; /* current io stage */ 546 md_raidcbuf_t *cs_pw_inval_list; 547 548 kmutex_t cs_mx; 549 550 buf_t cs_pbuf; 551 uint_t cs_pad1; 552 buf_t cs_hbuf; 553 uint_t cs_pad2; 554 /* Add new structure members HERE!! */ 555 buf_t cs_dbuf; 556 /* DO NOT add struture members here; cs_dbuf is dynamically sized */ 557 } md_raidcs_t; 558 559 /* value definitions for cs_resync_check */ 560 #define RCL_OKAY 0x01 /* write to both orig and alt */ 561 #define RCL_ERRED 0x08 /* treat column as rcs_ERRED */ 562 563 #define RCL_DATA_MASK 0x000000ff 564 #define RCL_PARITY_MASK 0x0000ff00 565 #define RCL_PARITY_OFFSET 8 /* insure masks match offset */ 566 567 #define RCL_PARITY(value) (((value) & RCL_PARITY_MASK) >> \ 568 RCL_PARITY_OFFSET) 569 570 #define RCL_DATA(value) ((value) & RCL_DATA_MASK) 571 572 /* value definitions for cs_flags */ 573 #define MD_RCS_ISCALL 0x000001 /* call cs_call in interrupt */ 574 #define MD_RCS_UNDBUF 0x000002 /* holding unit data buffer */ 575 #define MD_RCS_UNPBUF 0x000004 /* holding unit parity buffer */ 576 #define MD_RCS_MPBUF 0x000008 577 #define MD_RCS_HAVE_PW_SLOTS 0x000010 /* pw slots gotten */ 578 #define MD_RCS_PWDONE 0x000040 /* pwfrags are decremented */ 579 #define MD_RCS_READER 0x000100 /* reader line lock needed */ 580 #define MD_RCS_WRITER 0x000200 /* writer line lock needed */ 581 #define MD_RCS_LLOCKD 0x000400 /* line lock held */ 582 #define MD_RCS_WAITING 0x000800 /* line lock waiting */ 583 #define MD_RCS_LINE 0x001000 /* full line write */ 584 #define MD_RCS_ERROR 0x010000 /* I/O error on this child */ 585 #define MD_RCS_RECOVERY 0x020000 586 587 /* value definitions for cs_pflags or cs_dflags */ 588 #define MD_RCS_ISUP 0x0002 589 590 /* value definitions for gcs_flags */ 591 #define MD_RGCS_ALLOCBUF 0x0001 592 /* returned value from raid_replay() */ 593 #define RAID_RPLY_SUCCESS 0x0000 594 #define RAID_RPLY_ALLOCFAIL 0x0001 595 #define RAID_RPLY_COMPREPLAY 0x0002 596 #define RAID_RPLY_READONLY 0x0004 597 #define RAID_RPLY_EIO 0x0008 598 599 typedef struct raid_rplybuf { 600 caddr_t rpl_data; 601 buf_t *rpl_buf; 602 } raid_rplybuf_t; 603 604 typedef struct raid_rplylst { 605 struct raid_rplylst *rpl_next; 606 uint_t rpl_colcnt; 607 long long rpl_id; 608 int rpl_column1; 609 uint_t rpl_slot1; 610 raid_pwhdr_t rpl_pwhdr1; 611 int rpl_column2; 612 uint_t rpl_slot2; 613 raid_pwhdr_t rpl_pwhdr2; 614 } raid_rplylst_t; 615 616 /* Externals from raid.c */ 617 extern int raid_build_incore(void *, int); 618 extern void reset_raid(mr_unit_t *, minor_t, int); 619 620 /* Externals from raid_ioctl.c */ 621 extern int md_raid_ioctl(dev_t dev, int cmd, void *data, 622 int mode, IOLOCK *lockp); 623 624 /* rename named service functions */ 625 md_ren_svc_t raid_rename_check; 626 md_ren_svc_t raid_rename_lock; 627 md_ren_void_svc_t raid_rename_unlock; 628 629 630 /* redefinitions of the union shared by resync and init */ 631 #define un_resync_segment _t_un._resync._t_un_resync_segment 632 #define un_resync_index _t_un._resync._t_un_resync_index 633 #define un_resync_line_index _t_un._resync._t_un_resync_line_index 634 635 #define un_grow_tb _t_un._init._t_un_grow_tb 636 #define un_init_colcnt _t_un._init._t_un_init_colcnt 637 #define un_init_iocnt _t_un._init._t_un_init_iocnt 638 639 #define MD_RFLAG_NEEDBUF (0x0001) 640 #define MD_RFLAG_CLEAR (0x0002) 641 #define MD_RFLAG_KEEP (0x0004) 642 #define MD_RFLAG_NEEDPW (0x0008) 643 644 645 extern void raid_set_state(mr_unit_t *un, int col, 646 rcs_state_t new_state, int force); 647 extern int raid_replay(mr_unit_t *un); 648 extern void raid_commit(mr_unit_t *un, mddb_recid_t *extras); 649 extern char *raid_unit_state(rus_state_t state); 650 extern intptr_t raid_hotspares(); 651 extern void raid_hs_release(hs_cmds_t cmd, mr_unit_t *un, 652 mddb_recid_t *recids, int hs_index); 653 extern int raid_internal_open(minor_t mnum, int flag, int otyp, 654 int oflags); 655 extern int raid_internal_close(minor_t mnum, int otyp, 656 int init_pw, int cflags); 657 extern int raid_build_pwslot(mr_unit_t *unit, int column_index); 658 extern void raid_free_pwslot(mr_unit_t *unit, int column_index); 659 extern void release_resync_request(minor_t mnum); 660 extern int resync_request(minor_t mnum, int column_index, 661 size_t copysize, md_error_t *ep); 662 extern int raid_resync_unit(minor_t mnum, md_error_t *ep); 663 extern void raid_line_reader_lock(md_raidcs_t *cs, 664 int resync_thread); 665 extern void raid_line_exit(md_raidcs_t *cs); 666 extern int raid_state_cnt(mr_unit_t *un, rcs_state_t state); 667 extern int raid_build_pw_reservation(mr_unit_t *un, 668 int colindex); 669 extern int init_pw_area(mr_unit_t *un, md_dev64_t dev_to_write, 670 diskaddr_t pwstart, uint_t col); 671 extern void init_buf(buf_t *bp, int flags, size_t size); 672 extern void destroy_buf(buf_t *bp); 673 extern void reset_buf(buf_t *bp, int flags, size_t size); 674 extern void md_raid_strategy(buf_t *pb, int flag, void *private); 675 extern void raid_free_pw_reservation(mr_unit_t *un, 676 int colindex); 677 extern void raid_fillin_rpw(mr_unit_t *un, 678 raid_pwhdr_t *pwhdrp, int col); 679 #endif /* _KERNEL */ 680 681 #ifdef __cplusplus 682 } 683 #endif 684 685 #endif /* _SYS_MD_RAID_H */ 686